The accessrules library interface

The following functions and structures are declared in the s6/accessrules.h header,
and implemented in the libs6.a or libs6.so library.

General information

accessrules is an access control library. It looks up
a key in a user-specified database, then returns a code depending on
whether the database allows access (in which case additional information
can also be returned), denies access, or does not contain the key.

accessrules has been designed to be easily extensible to any
database format and any key format.

Check the s6/accessrules.h header for the exact definitions.

Data structures

A s6_accessrules_result_t is a scalar that
can have the following values: S6_ACCESSRULES_ERROR,
S6_ACCESSRULES_DENY, S6_ACCESSRULES_ALLOW or S6_ACCESSRULES_NOTFOUND.

A s6_accessrules_params_t is a structure containing two
strallocs,
.env and .exec, used to return data contained in the
database when a key has been allowed. The interpretation of this data is
application-defined.

Function types

Backend lookups

A s6_accessrules_backend_func_t is the type of a function
that takes a single key, looks it up in a database, and returns the result.
Namely:

f looks up key key of length keylen in the database
represented by handle in an implementation-defined way. It returns a
number that says the key has been allowed, denied or not found, or an error
occurred. If the key has been allowed, f stores additional information
from the database into *params.

Two s6_accessrules_backend_func_t functions are natively implemented:

s6_accessrules_backend_fs takes a char const *handle and interprets it as a base directory to look up key
under, in the format understood by
s6-accessrules-cdb-from-fs.

s6_accessrules_backend_cdb takes a struct cdb *handle and looks up key in the
CDB it points to. handle must
already be mapped to a CDB file. Such a file can be built with the
s6-accessrules-cdb-from-fs
utility.

Frontend key checking

A s6_accessrules_keycheck_func_t is the type of a function that
takes a user-level key, makes a list of corresponding backend-level keys and
calls a s6_accessrules_backend_func_t function until it finds
a match. Namely:

f derives a list of low-level keys to check from key.
Then, for each key k of length klen in this list, it calls
(*backend)(k, klen, handle, params), returning *backend's result if it
is not S6_ACCESSRULES_NOTFOUND. If no match can be found in the whole list,
f finally returns S6_ACCESSRULES_NOTFOUND.

Five s6_accessrules_keycheck_func_t functions are natively implemented:

s6_accessrules_keycheck_uidgid interprets key as a
pointer to a structure containing an uid u and a gid g.
The function first looks
for a uid/u match; if it cannot find one, it looks for a
gid/g match. If it cannot find one either, it checks
uid/default and returns the result.

s6_accessrules_keycheck_reversedns interprets key
as a string containing a FQDN. Then for each suffix k of key,
starting with key itself and ending with key's TLD,
it looks up reversedns/k. The final dot is excluded from
k. If no match can be found, the function checks reversedns/@
and returns the result. For instance, if key is "foo.bar.com",
the following strings are looked up, in that order:

reversedns/foo.bar.com

reversedns/bar.com

reversedns/com

reversedns/@

s6_accessrules_keycheck_ip4 interprets key as
4 network-byte-order characters containing an IPv4 address. Then for each
netmask mask from 32 to 0, it constructs the IPv4 network
prefix addr corresponding to that address, and looks up
ip4/addr_mask. For instance, if key
is "\300\250\001\007", representing the 192.168.1.7 address, the following
strings are looked up, in that order:

ip4/192.168.1.7_32

ip4/192.168.1.6_31

ip4/192.168.1.4_30

ip4/192.168.1.0_29

ip4/192.168.0.0_28

ip4/192.168.0.0_27

and so on, down to:

ip4/192.0.0.0_3

ip4/192.0.0.0_2

ip4/128.0.0.0_1

ip4/0.0.0.0_0

Note that the ip4/0.0.0.0_0 string is a catch-all key that
matches everything.

s6_accessrules_keycheck_ip6 interprets key as
16 network-byte-order characters containing an IPv6 address. Then for each
netmask mask from 128 to 0, it constructs the IPv6 network
prefix addr corresponding to that address,
in canonical form,
and looks up
ip6/addr_mask. For instance, if key
is "*\0\024P@\002\b\003\0\0\0\0\0\0\020\006", representing the
2a00:1450:4002:803::1006 address, the following
strings are looked up, in that order:

ip6/2a00:1450:4002:803::1006_128

ip6/2a00:1450:4002:803::1006_127

ip6/2a00:1450:4002:803::1004_126

ip6/2a00:1450:4002:803::1000_125

ip6/2a00:1450:4002:803::1000_124

ip6/2a00:1450:4002:803::1000_123

ip6/2a00:1450:4002:803::1000_122

ip6/2a00:1450:4002:803::1000_121

ip6/2a00:1450:4002:803::1000_120

ip6/2a00:1450:4002:803::1000_119

ip6/2a00:1450:4002:803::1000_118

ip6/2a00:1450:4002:803::1000_117

ip6/2a00:1450:4002:803::1000_116

ip6/2a00:1450:4002:803::1000_115

ip6/2a00:1450:4002:803::1000_114

ip6/2a00:1450:4002:803::1000_113

ip6/2a00:1450:4002:803::_112

ip6/2a00:1450:4002:803::_111

and so on, down to:

ip6/2a00::_11

ip6/2800::_10

ip6/2800::_9

ip6/2000::_8

ip6/2000::_7

ip6/2000::_6

ip6/2000::_5

ip6/2000::_4

ip6/2000::_3

ip6/::_2

ip6/::_1

ip6/::_0

Note that the ip6/::_0 string is a catch-all key that
matches everything.

s6_accessrules_keycheck_ip46 interprets key as a pointer to an
ip46_t, and
behaves either as s6_accessrules_keycheck_ip6 or s6_accessrules_keycheck_ip4,
depending on the type of address *key contains.

Ready-to-use functions

Those functions are mostly macros; they're built by associating a frontend
function with a backend function.

s6_accessrules_result_t s6_accessrules_uidgid_cdb
(uid_t u, gid_t g, struct cdb *c,
s6_accessrules_params_t *params)
Checks the *c CDB database for an authorization for uid u
and gid g. If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_uidgid_fs
(uid_t u, gid_t g, char const *dir,
s6_accessrules_params_t *params)
Checks the dir base directory for an authorization for uid u
and gid g. If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_reversedns_cdb
(char const *name, struct cdb *c,
s6_accessrules_params_t *params)
Checks the *c CDB database for an authorization for the
name FQDN. If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_reversedns_fs
(char const *name, char const *dir,
s6_accessrules_params_t *params)
Checks the dir base directory for an authorization for the
name FQDN. If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_ip4_cdb
(char const *ip4, struct cdb *c,
s6_accessrules_params_t *params)
Checks the *c CDB database for an authorization for the
ip4 IPv4 address (4 network byte order characters).
If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_ip4_fs
(char const *ip4, char const *dir,
s6_accessrules_params_t *params)
Checks the dir base directory for an authorization for the
ip4 IPv4 address (4 network byte order characters).
If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_ip6_cdb
(char const *ip6, struct cdb *c,
s6_accessrules_params_t *params)
Checks the *c CDB database for an authorization for the
ip6 IPv6 address (16 network byte order characters).
If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_ip6_fs
(char const *ip6, char const *dir,
s6_accessrules_params_t *params)
Checks the dir base directory for an authorization for the
ip6 IPv6 address (16 network byte order characters).
If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_ip46_cdb
(ip46_t *ip, struct cdb *c,
s6_accessrules_params_t *params)
Checks the *c CDB database for an authorization for the
ip IP address.
If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.

s6_accessrules_result_t s6_accessrules_ip46_fs
(ip46_t const *ip, char const *dir,
s6_accessrules_params_t *params)
Checks the dir base directory for an authorization for the
ip IP address.
If the result is S6_ACCESSRULES_ALLOW, additional
information may be stored into params.