--- a/src/nfacct.c +++ b/src/nfacct.c @@ -211,19 +211,61 @@ return 0; } +static const char *fmt_options[FMT_MAX + 1] = { + "def","3pl","iec","kib", + "mib","gib","tib","pib","eib", + "si","kb","mb", "gb", "tb", + "pb","eb","" + }; + +static uint32_t nfacct_parse_format_options(const char *argv) { + char *ptr; + char *tmp = strdup(argv); + int i, j; + enum nfacct_format fmt[2] = { FMT_MAX, FMT_MAX }; + + for (i = 0; i <= 2 && tmp != NULL; i++) { + ptr = strsep(&tmp, ","); + + if (ptr != NULL && strlen(ptr) == 0) { + fmt[i] = FMT_DEFAULT; + } else { + for (j = 0; j <= FMT_MAX && + strncmp(ptr, fmt_options[j], 3) != 0; j++) { ; } + + if (j >= FMT_MAX) + break; + + fmt[i] = j; + } + } + + if (i > 2 || j >= FMT_MAX) + return -1; + + if (fmt[0] == FMT_MAX) + fmt[0] = fmt[1]; + + if (fmt[1] == FMT_MAX) + fmt[1] = fmt[0]; + + return (fmt[0] << 4) | fmt[1]; +} + static int nfacct_cmd_add(int argc, char *argv[]) { struct mnl_socket *nl; char buf[MNL_SOCKET_BUFFER_SIZE]; struct nlmsghdr *nlh; uint32_t portid, seq; + uint32_t fmt; struct nfacct *nfacct; int ret; if (argc < 3) { nfacct_perror("missing object name"); return -1; - } else if (argc > 3) { + } else if (argc > 4) { nfacct_perror("too many arguments"); return -1; } @@ -236,6 +278,15 @@ nfacct_attr_set(nfacct, NFACCT_ATTR_NAME, argv[2]); + if (argc == 4 && argv[3] != NULL) { + fmt = nfacct_parse_format_options(argv[3]); + if (fmt == -1) { + nfacct_perror("packets/bytes format wrong"); + return -1; + } + nfacct_attr_set(nfacct, NFACCT_ATTR_FMT, &fmt); + } + seq = time(NULL); nlh = nfacct_nlmsg_build_hdr(buf, NFNL_MSG_ACCT_NEW, NLM_F_CREATE | NLM_F_ACK, seq);