diff options
author | Carlos Falgueras García <carlosfg@riseup.net> | 2016-03-22 20:46:24 +0100 |
---|---|---|
committer | Pablo Neira Ayuso <pablo@netfilter.org> | 2016-04-14 02:23:26 +0200 |
commit | 5c3bc232dc9d1dd01d589fab096f67d944621fc2 (patch) | |
tree | 51d84afbca7fe6adc6b7c0b941ae3dba4f9117bc /include | |
parent | 2d5f3998fa478a4555b0d0599e015b763f03576c (diff) |
udata: add TLV user data infrastructure
These functions allow to create a buffer (struct nftnl_udata_buf) of
user data attributes in TLV format (struct nftnl_udata). It is inspired
by libmnl/src/attr.c. It can be used to store several TLVs sequentially
into an object.
Example:
struct nftnl_udata_buf *buf;
struct nftnl_udata *attr;
const char *str = "Hello World!";
buf = nftnl_udata_buf_alloc(UDATA_SIZE);
if (!buf) {
perror("OOM");
exit(EXIT_FAILURE);
}
if (!nftnl_udata_put_strz(buf, MY_TYPE, str)) {
perror("Can't put attribute \"%s\"", str);
exit(EXIT_FAILURE);
}
nftnl_udata_for_each(buf, attr)
printf("%s\n", (char *)nftnl_udata_attr_value(attr));
nftnl_udata_buf_free(buf);
Signed-off-by: Carlos Falgueras García <carlosfg@riseup.net>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
Diffstat (limited to 'include')
-rw-r--r-- | include/Makefile.am | 1 | ||||
-rw-r--r-- | include/libnftnl/Makefile.am | 1 | ||||
-rw-r--r-- | include/libnftnl/udata.h | 52 | ||||
-rw-r--r-- | include/udata.h | 40 |
4 files changed, 94 insertions, 0 deletions
diff --git a/include/Makefile.am b/include/Makefile.am index be9eb9b..9f55737 100644 --- a/include/Makefile.am +++ b/include/Makefile.am @@ -12,4 +12,5 @@ noinst_HEADERS = internal.h \ expr.h \ json.h \ set_elem.h \ + udata.h \ utils.h diff --git a/include/libnftnl/Makefile.am b/include/libnftnl/Makefile.am index 84f01b6..457ec95 100644 --- a/include/libnftnl/Makefile.am +++ b/include/libnftnl/Makefile.am @@ -7,4 +7,5 @@ pkginclude_HEADERS = batch.h \ set.h \ ruleset.h \ common.h \ + udata.h \ gen.h diff --git a/include/libnftnl/udata.h b/include/libnftnl/udata.h new file mode 100644 index 0000000..312ce26 --- /dev/null +++ b/include/libnftnl/udata.h @@ -0,0 +1,52 @@ +#ifndef _LIBNFTNL_UDATA_H_ +#define _LIBNFTNL_UDATA_H_ + +#include <stdio.h> +#include <stdint.h> +#include <stdbool.h> + +/* + * nftnl user data attributes API + */ +struct nftnl_udata; +struct nftnl_udata_buf; + +/* nftnl_udata_buf */ +struct nftnl_udata_buf *nftnl_udata_buf_alloc(uint32_t data_size); +void nftnl_udata_buf_free(struct nftnl_udata_buf *buf); +uint32_t nftnl_udata_buf_len(const struct nftnl_udata_buf *buf); +void *nftnl_udata_buf_data(const struct nftnl_udata_buf *buf); +void nftnl_udata_buf_put(struct nftnl_udata_buf *buf, const void *data, + uint32_t len); +struct nftnl_udata *nftnl_udata_start(const struct nftnl_udata_buf *buf); +struct nftnl_udata *nftnl_udata_end(const struct nftnl_udata_buf *buf); + +/* putters */ +bool nftnl_udata_put(struct nftnl_udata_buf *buf, uint8_t type, uint32_t len, + const void *value); +bool nftnl_udata_put_strz(struct nftnl_udata_buf *buf, uint8_t type, + const char *strz); + +/* nftnl_udata_attr */ +uint8_t nftnl_udata_type(const struct nftnl_udata *attr); +uint8_t nftnl_udata_len(const struct nftnl_udata *attr); +void *nftnl_udata_get(const struct nftnl_udata *attr); + +/* iterator */ +struct nftnl_udata *nftnl_udata_next(const struct nftnl_udata *attr); + +#define nftnl_udata_for_each(buf, attr) \ + for ((attr) = nftnl_udata_start(buf); \ + (char *)(nftnl_udata_end(buf)) > (char *)(attr); \ + (attr) = nftnl_udata_next(attr)) + +#define nftnl_udata_for_each_data(data, data_len, attr) \ + for ((attr) = (struct nftnl_udata *)(data); \ + (char *)(data + data_len) > (char *)(attr); \ + (attr) = nftnl_udata_next(attr)) + +typedef int (*nftnl_udata_cb_t)(const struct nftnl_udata *attr, void *data); +int nftnl_udata_parse(const void *data, uint32_t data_len, nftnl_udata_cb_t cb, + void *cb_data); + +#endif /* _LIBNFTNL_UDATA_H_ */ diff --git a/include/udata.h b/include/udata.h new file mode 100644 index 0000000..407a3b9 --- /dev/null +++ b/include/udata.h @@ -0,0 +1,40 @@ +#ifndef _LIBNFTNL_UDATA_INTERNAL_H_ +#define _LIBNFTNL_UDATA_INTERNAL_H_ + +#include <stdint.h> +#include <stddef.h> + +/* + * TLV structures: + * nftnl_udata + * <-------- HEADER --------> <------ PAYLOAD ------> + * +------------+-------------+- - - - - - - - - - - -+ + * | type | len | value | + * | (1 byte) | (1 byte) | | + * +--------------------------+- - - - - - - - - - - -+ + * <-- sizeof(nftnl_udata) -> <-- nftnl_udata->len --> + */ +struct nftnl_udata { + uint8_t type; + uint8_t len; + unsigned char value[]; +} __attribute__((__packed__)); + +/* + * +---------------------------------++ + * | data[] || + * | || || + * | \/ \/ + * +-------+-------+-------+-------+ ... +-------+- - - - - - -+ + * | size | end | TLV | TLV | | TLV | Empty | + * +-------+-------+-------+-------+ ... +-------+- - - - - - -+ + * |<---- nftnl_udata_len() ---->| + * |<----------- nftnl_udata_size() ---------->| + */ +struct nftnl_udata_buf { + uint32_t size; + char *end; + char data[]; +}; + +#endif /* _LIBNFTNL_UDATA_INTERNAL_H_ */ |