BIRD uses its own abstraction of IP address in order to share the same code for both IPv4 and IPv6. IP addresses are represented as entities of type ip_addr which are never to be treated as numbers and instead they must be manipulated using the following functions and macros.
char * ip_scope_text (uint scope) -- get textual representation of address scope
scope (SCOPE_xxx)
Returns a pointer to a textual name of the scope given.
int ipa_equal (ip_addr x, ip_addr y) -- compare two IP addresses for equality
IP address
IP address
ipa_equal() returns 1 if x and y represent the same IP address, else 0.
int ipa_nonzero (ip_addr x) -- test if an IP address is defined
IP address
ipa_nonzero returns 1 if x is a defined IP address (not all bits are zero), else 0.
The undefined all-zero address is reachable as a IPA_NONE
macro.
ip_addr ipa_and (ip_addr x, ip_addr y) -- compute bitwise and of two IP addresses
IP address
IP address
This function returns a bitwise and of x and y. It's primarily used for network masking.
ip_addr ipa_or (ip_addr x, ip_addr y) -- compute bitwise or of two IP addresses
IP address
IP address
This function returns a bitwise or of x and y.
ip_addr ipa_xor (ip_addr x, ip_addr y) -- compute bitwise xor of two IP addresses
IP address
IP address
This function returns a bitwise xor of x and y.
ip_addr ipa_not (ip_addr x) -- compute bitwise negation of two IP addresses
IP address
This function returns a bitwise negation of x.
ip_addr ipa_mkmask (int x) -- create a netmask
prefix length
This function returns an ip_addr corresponding of a netmask of an address prefix of size x.
int ipa_masklen (ip_addr x) -- calculate netmask length
IP address
This function checks whether x represents a valid netmask and returns the size of the associate network prefix or -1 for invalid mask.
int ipa_hash (ip_addr x) -- hash IP addresses
IP address
ipa_hash() returns a 16-bit hash value of the IP address x.
void ipa_hton (ip_addr x) -- convert IP address to network order
IP address
Converts the IP address x to the network byte order.
Beware, this is a macro and it alters the argument!
void ipa_ntoh (ip_addr x) -- convert IP address to host order
IP address
Converts the IP address x from the network byte order.
Beware, this is a macro and it alters the argument!
int ipa_classify (ip_addr x) -- classify an IP address
IP address
ipa_classify() returns an address class of x, that is a bitwise or of address type (IADDR_INVALID, IADDR_HOST, IADDR_BROADCAST, IADDR_MULTICAST) with address scope (SCOPE_HOST to SCOPE_UNIVERSE) or -1 (IADDR_INVALID) for an invalid address.
ip4_addr ip4_class_mask (ip4_addr x) -- guess netmask according to address class
IPv4 address
This function (available in IPv4 version only) returns a network mask according to the address class of x. Although classful addressing is nowadays obsolete, there still live routing protocols transferring no prefix lengths nor netmasks and this function could be useful to them.
u32 ipa_from_u32 (ip_addr x) -- convert IPv4 address to an integer
IP address
This function takes an IPv4 address and returns its numeric representation.
ip_addr ipa_to_u32 (u32 x) -- convert integer to IPv4 address
a 32-bit integer
ipa_to_u32() takes a numeric representation of an IPv4 address and converts it to the corresponding ip_addr.
int ipa_compare (ip_addr x, ip_addr y) -- compare two IP addresses for order
IP address
IP address
The ipa_compare() function takes two IP addresses and returns -1 if x is less than y in canonical ordering (lexicographical order of the bit strings), 1 if x is greater than y and 0 if they are the same.
ip_addr ipa_build6 (u32 a1, u32 a2, u32 a3, u32 a4) -- build an IPv6 address from parts
part #1
part #2
part #3
part #4
ipa_build() takes a1 to a4 and assembles them to a single IPv6 address. It's used for example when a protocol wants to bind its socket to a hard-wired multicast address.
char * ip_ntop (ip_addr a, char * buf) -- convert IP address to textual representation
IP address
buffer of size at least STD_ADDRESS_P_LENGTH
This function takes an IP address and creates its textual representation for presenting to the user.
char * ip_ntox (ip_addr a, char * buf) -- convert IP address to hexadecimal representation
IP address
buffer of size at least STD_ADDRESS_P_LENGTH
This function takes an IP address and creates its hexadecimal textual representation. Primary use: debugging dumps.
int ip_pton (char * a, ip_addr * o) -- parse textual representation of IP address
textual representation
where to put the resulting address
This function parses a textual IP address representation and stores the decoded address to a variable pointed to by o. Returns 0 if a parse error has occurred, else 0.
The BIRD library provides a set of functions for operating on linked lists. The lists are internally represented as standard doubly linked lists with synthetic head and tail which makes all the basic operations run in constant time and contain no extra end-of-list checks. Each list is described by a list structure, nodes can have any format as long as they start with a node structure. If you want your nodes to belong to multiple lists at once, you can embed multiple node structures in them and use the SKIP_BACK() macro to calculate a pointer to the start of the structure from a node pointer, but beware of obscurity.
There also exist safe linked lists (slist, snode and all functions
being prefixed with s_
) which support asynchronous walking very
similar to that used in the fib structure.
LIST_INLINE void add_tail (list * l, node * n) -- append a node to a list
linked list
list node
add_tail() takes a node n and appends it at the end of the list l.
LIST_INLINE void add_head (list * l, node * n) -- prepend a node to a list
linked list
list node
add_head() takes a node n and prepends it at the start of the list l.
LIST_INLINE void insert_node (node * n, node * after) -- insert a node to a list
a new list node
a node of a list
Inserts a node n to a linked list after an already inserted node after.
LIST_INLINE void rem_node (node * n) -- remove a node from a list
node to be removed
Removes a node n from the list it's linked in. Afterwards, node n is cleared.
LIST_INLINE void replace_node (node * old, node * new) -- replace a node in a list with another one
node to be removed
node to be inserted
Replaces node old in the list it's linked in with node new. Node old may be a copy of the original node, which is not accessed through the list. The function could be called with old == new, which just fixes neighbors' pointers in the case that the node was reallocated.
LIST_INLINE void init_list (list * l) -- create an empty list
list
init_list() takes a list structure and initializes its fields, so that it represents an empty list.
LIST_INLINE void add_tail_list (list * to, list * l) -- concatenate two lists
destination list
source list
This function appends all elements of the list l to the list to in constant time.
int ipsum_verify (void * frag, uint len, ... ...) -- verify an IP checksum
first packet fragment
length in bytes
variable arguments
This function verifies whether a given fragmented packet has correct one's complement checksum as used by the IP protocol.
It uses all the clever tricks described in RFC 1071 to speed up checksum calculation as much as possible.
1 if the checksum is correct, 0 else.
u16 ipsum_calculate (void * frag, uint len, ... ...) -- compute an IP checksum
first packet fragment
length in bytes
variable arguments
This function calculates a one's complement checksum of a given fragmented packet.
It uses all the clever tricks described in RFC 1071 to speed up checksum calculation as much as possible.
u32 u32_mkmask (uint n) -- create a bit mask
number of bits
u32_mkmask() returns an unsigned 32-bit integer which binary representation consists of n ones followed by zeroes.
int u32_masklen (u32 x) -- calculate length of a bit mask
bit mask
This function checks whether the given integer x represents a valid bit mask (binary representation contains first ones, then zeroes) and returns the number of ones or -1 if the mask is invalid.
u32 u32_log2 (u32 v) -- compute a binary logarithm.
number
This function computes a integral part of binary logarithm of given integer v and returns it. The computed value is also an index of the most significant non-zero bit position.
int patmatch (byte * p, byte * s) -- match shell-like patterns
pattern
string
patmatch() returns whether given string s matches the given shell-like pattern p. The patterns consist of characters (which are matched literally), question marks which match any single character, asterisks which match any (possibly empty) string of characters and backslashes which are used to escape any special characters and force them to be treated literally.
The matching process is not optimized with respect to time, so please avoid using this function for complex patterns.
int bvsnprintf (char * buf, int size, const char * fmt, va_list args) -- BIRD's vsnprintf()
destination buffer
size of the buffer
format string
a list of arguments to be formatted
This functions acts like ordinary sprintf() except that it checks available space to avoid buffer overflows and it allows some more
I
for formatting of IP addresses (any non-zero
width is automatically replaced by standard IP address width which
depends on whether we use IPv4 or IPv6; %#I
gives hexadecimal format),
R
for Router / Network ID (u32 value printed as IPv4 address)
lR
for 64bit Router / Network ID (u64 value printed as eight :-separated octets)
and m
resp. M
for error messages (uses strerror() to translate errno code to
message text). On the other hand, it doesn't support floating
point numbers.
number of characters of the output string or -1 if the buffer space was insufficient.
int bvsprintf (char * buf, const char * fmt, va_list args) -- BIRD's vsprintf()
buffer
format string
a list of arguments to be formatted
This function is equivalent to bvsnprintf() with an infinite buffer size. Please use carefully only when you are absolutely sure the buffer won't overflow.
int bsprintf (char * buf, const char * fmt, ... ...) -- BIRD's sprintf()
buffer
format string
variable arguments
This function is equivalent to bvsnprintf() with an infinite buffer size and variable arguments instead of a va_list. Please use carefully only when you are absolutely sure the buffer won't overflow.
int bsnprintf (char * buf, int size, const char * fmt, ... ...) -- BIRD's snprintf()
buffer
buffer size
format string
variable arguments
This function is equivalent to bsnprintf() with variable arguments instead of a va_list.
void * xmalloc (uint size) -- malloc with checking
block size
This function is equivalent to malloc() except that in case of failure it calls die() to quit the program instead of returning a NULL pointer.
Wherever possible, please use the memory resources instead.
void * xrealloc (void * ptr, uint size) -- realloc with checking
original memory block
block size
This function is equivalent to realloc() except that in case of failure it calls die() to quit the program instead of returning a NULL pointer.
Wherever possible, please use the memory resources instead.
MAC algorithms are simple cryptographic tools for message authentication. They use shared a secret key a and message text to generate authentication code, which is then passed with the message to the other side, where the code is verified. There are multiple families of MAC algorithms based on different cryptographic primitives, BIRD implements two MAC families which use hash functions.
The first family is simply a cryptographic hash camouflaged as MAC algorithm. Originally supposed to be (m|k)-hash (message is concatenated with key, and that is hashed), but later it turned out that a raw hash is more practical. This is used for cryptographic authentication in OSPFv2, RIP and BFD.
The second family is the standard HMAC (RFC 2104), using inner and outer hash to process key and message. HMAC (with SHA) is used in advanced OSPF and RIP authentication (RFC 5709, RFC 4822).
void mac_init (struct mac_context * ctx, uint id, const byte * key, uint keylen) -- initialize MAC algorithm
context to initialize
MAC algorithm ID
MAC key
MAC key length
Initialize MAC context ctx for algorithm id (e.g., ALG_HMAC_SHA1), with key key of length keylen. After that, message data could be added using mac_update() function.
void mac_update (struct mac_context * ctx, const byte * data, uint datalen) -- add more data to MAC algorithm
MAC context
data to add
length of data
Push another datalen bytes of data pointed to by data into the MAC algorithm currently in ctx. Can be called multiple times for the same MAC context. It has the same effect as concatenating all the data together and passing them at once.
byte * mac_final (struct mac_context * ctx) -- finalize MAC algorithm
MAC context
Finish MAC computation and return a pointer to the result. No more mac_update() calls could be done, but the context may be reinitialized later.
Note that the returned pointer points into data in the ctx context. If it ceases to exist, the pointer becomes invalid.
void mac_cleanup (struct mac_context * ctx) -- cleanup MAC context
MAC context
Cleanup MAC context after computation (by filling with zeros). Not strictly necessary, just to erase sensitive data from stack. This also invalidates the pointer returned by mac_final().
void mac_fill (uint id, const byte * key, uint keylen, const byte * data, uint datalen, byte * mac) -- compute and fill MAC
MAC algorithm ID
secret key
key length
message data
message length
place to fill MAC
Compute MAC for specified key key and message data using algorithm id and copy it to buffer mac. mac_fill() is a shortcut function doing all usual steps for transmitted messages.
int mac_verify (uint id, const byte * key, uint keylen, const byte * data, uint datalen, const byte * mac) -- compute and verify MAC
MAC algorithm ID
secret key
key length
message data
message length
received MAC
Compute MAC for specified key key and message data using algorithm id and compare it with received mac, return whether they are the same. mac_verify() is a shortcut function doing all usual steps for received messages.