diff options
author | Thomas Graf <tgr@lsx.localdomain> | 2008-05-22 22:02:02 (GMT) |
---|---|---|
committer | Thomas Graf <tgr@lsx.localdomain> | 2008-05-22 22:02:02 (GMT) |
commit | 10cf5a586c149fdb7e2639000dbfae5e6f8522a5 (patch) | |
tree | 399a15d767fd15b85c92be2e70b748645eeb983e | |
parent | 337fbd24cad1f5cf9c8b4287a75f2c69f088adce (diff) | |
download | libnl-10cf5a586c149fdb7e2639000dbfae5e6f8522a5.zip libnl-10cf5a586c149fdb7e2639000dbfae5e6f8522a5.tar.gz libnl-10cf5a586c149fdb7e2639000dbfae5e6f8522a5.tar.bz2 |
New set of libnl tools
Converts all tools to the API changes and improves the useability by
introducing regular options and long options.
62 files changed, 2143 insertions, 1788 deletions
diff --git a/src/.gitignore b/src/.gitignore index 8d71209..60233c8 100644 --- a/src/.gitignore +++ b/src/.gitignore @@ -1,13 +1,12 @@ -genl-ctrl-dump -genl-ctrl-get -nf-ct-dump +genl-ctrl-list +nf-ct-list nf-log nf-monitor nl-addr-add nl-addr-delete -nl-addr-dump +nl-addr-list nl-fib-lookup -nl-link-dump +nl-link-list nl-link-ifindex2name nl-link-name2ifindex nl-link-set @@ -17,15 +16,16 @@ nl-list-sockets nl-monitor nl-neigh-add nl-neigh-delete -nl-neigh-dump -nl-neightbl-dump +nl-neigh-list +nl-neightbl-list nl-qdisc-add nl-qdisc-delete -nl-qdisc-dump +nl-qdisc-list nl-route-add nl-route-delete nl-route-list nl-route-get -nl-rule-dump -nl-tctree-dump +nl-rule-list +nl-tctree-list nl-util-addr +nf-queue diff --git a/src/Makefile b/src/Makefile index 5dad9e6..55ee339 100644 --- a/src/Makefile +++ b/src/Makefile @@ -20,19 +20,35 @@ TOOLS := $(CIN:%.c=%) all: $(TOOLS) $(TOOLS): utils.o -nl-route-add nl-route-delete nl-route-list: route-utils.o -nl-addr-add nl-addr-delete nl-addr-list: addr-utils.o +nl-route-add nl-route-delete nl-route-list: route-utils.o rtnl-utils.o +nl-route-get: rtnl-utils.o +nl-addr-add nl-addr-delete nl-addr-list: addr-utils.o rtnl-utils.o +nl-link-list nl-link-set nl-link-stats: link-utils.o rtnl-utils.o +nl-link-ifindex2name nl-link-name2ifindex: rtnl-utils.o +nl-neigh-add nl-neigh-delete nl-neigh-list: neigh-utils.o rtnl-utils.o +nl-qdisc-delete nl-qdisc-list: qdisc-utils.o rtnl-utils.o +nl-rule-list: rule-utils.o rtnl-utils.o +nl-neightbl-list: rtnl-utils.o +nl-monitor: rtnl-utils.o +nl-tctree-list: rtnl-utils.o + +genl-ctrl-list: ctrl-utils.o + +nf-ct-list: ct-utils.o +nf-log: log-utils.o rtnl-utils.o +nf-queue: queue-utils.o rtnl-utils.o nl-%: nl-%.c + @echo " LD $@"; \ $(CC) $(CFLAGS) -o $@ $^ $(LDFLAGS) -lnl-route genl-%: genl-%.c @echo " LD $@"; \ - $(CC) $(CFLAGS) -o $@ $^ $(LDFLAGS) + $(CC) $(CFLAGS) -o $@ $^ $(LDFLAGS) -lnl-genl nf-%: nf-%.c @echo " LD $@"; \ - $(CC) $(CFLAGS) -o $@ $^ $(LDFLAGS) + $(CC) $(CFLAGS) -o $@ $^ $(LDFLAGS) -lnl-nf clean: @echo " CLEAN src"; \ diff --git a/src/addr-utils.c b/src/addr-utils.c index 3c8ee4d..900be14 100644 --- a/src/addr-utils.c +++ b/src/addr-utils.c @@ -11,6 +11,17 @@ #include "addr-utils.h" +struct rtnl_addr *nlt_alloc_addr(void) +{ + struct rtnl_addr *addr; + + addr = rtnl_addr_alloc(); + if (!addr) + fatal(ENOMEM, "Unable to allocate address object"); + + return addr; +} + void parse_family(struct rtnl_addr *addr, char *arg) { int family; diff --git a/src/addr-utils.h b/src/addr-utils.h index 0a4db23..45a9709 100644 --- a/src/addr-utils.h +++ b/src/addr-utils.h @@ -14,6 +14,7 @@ #include "utils.h" +extern struct rtnl_addr *nlt_alloc_addr(void); extern void parse_family(struct rtnl_addr *, char *); extern void parse_local(struct rtnl_addr *, char *); extern void parse_dev(struct rtnl_addr *, struct nl_cache *, char *); diff --git a/src/ct-utils.c b/src/ct-utils.c new file mode 100644 index 0000000..7d116fa --- /dev/null +++ b/src/ct-utils.c @@ -0,0 +1,148 @@ +/* + * src/ct-utils.c Conntrack Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "ct-utils.h" + +struct nfnl_ct *nlt_alloc_ct(void) +{ + struct nfnl_ct *ct; + + ct = nfnl_ct_alloc(); + if (!ct) + fatal(ENOMEM, "Unable to allocate conntrack object"); + + return ct; +} + +struct nl_cache *nlt_alloc_ct_cache(struct nl_sock *sk) +{ + return alloc_cache(sk, "conntrack", nfnl_ct_alloc_cache); +} + +void parse_family(struct nfnl_ct *ct, char *arg) +{ + int family; + + if ((family = nl_str2af(arg)) == AF_UNSPEC) + fatal(EINVAL, "Unable to parse family \"%s\": %s", + arg, nl_geterror(NLE_INVAL)); + + nfnl_ct_set_family(ct, family); +} + +void parse_protocol(struct nfnl_ct *ct, char *arg) +{ + int proto; + + if ((proto = nl_str2ip_proto(arg)) < 0) + fatal(proto, "Unable to parse protocol \"%s\": %s", + arg, nl_geterror(proto)); + + nfnl_ct_set_proto(ct, proto); +} + +void parse_mark(struct nfnl_ct *ct, char *arg) +{ + uint32_t mark = parse_u32(arg); + nfnl_ct_set_mark(ct, mark); +} + +void parse_timeout(struct nfnl_ct *ct, char *arg) +{ + uint32_t timeout = parse_u32(arg); + nfnl_ct_set_timeout(ct, timeout); +} + +void parse_id(struct nfnl_ct *ct, char *arg) +{ + uint32_t id = parse_u32(arg); + nfnl_ct_set_id(ct, id); +} + +void parse_use(struct nfnl_ct *ct, char *arg) +{ + uint32_t use = parse_u32(arg); + nfnl_ct_set_use(ct, use); +} + +void parse_src(struct nfnl_ct *ct, int reply, char *arg) +{ + int err; + struct nl_addr *a = nlt_addr_parse(arg, nfnl_ct_get_family(ct)); + if ((err = nfnl_ct_set_src(ct, reply, a)) < 0) + fatal(err, "Unable to set source address: %s", + nl_geterror(err)); +} + +void parse_dst(struct nfnl_ct *ct, int reply, char *arg) +{ + int err; + struct nl_addr *a = nlt_addr_parse(arg, nfnl_ct_get_family(ct)); + if ((err = nfnl_ct_set_dst(ct, reply, a)) < 0) + fatal(err, "Unable to set destination address: %s", + nl_geterror(err)); +} + +void parse_src_port(struct nfnl_ct *ct, int reply, char *arg) +{ + uint32_t port = parse_u32(arg); + nfnl_ct_set_src_port(ct, reply, port); +} + +void parse_dst_port(struct nfnl_ct *ct, int reply, char *arg) +{ + uint32_t port = parse_u32(arg); + nfnl_ct_set_dst_port(ct, reply, port); +} + +void parse_tcp_state(struct nfnl_ct *ct, char *arg) +{ + int state; + + if ((state = nfnl_ct_str2tcp_state(arg)) < 0) + fatal(state, "Unable to parse tcp state \"%s\": %s", + arg, nl_geterror(state)); + + nfnl_ct_set_tcp_state(ct, state); +} + +void parse_status(struct nfnl_ct *ct, char *arg) +{ + int status; + + if ((status = nfnl_ct_str2status(arg)) < 0) + fatal(status, "Unable to parse flags \"%s\": %s", + arg, nl_geterror(status)); + + nfnl_ct_set_status(ct, status); +} + +#if 0 + } else if (arg_match("origicmpid")) { + if (argc > ++idx) + nfnl_ct_set_icmp_id(ct, 0, strtoul(argv[idx++], NULL, 0)); + } else if (arg_match("origicmptype")) { + if (argc > ++idx) + nfnl_ct_set_icmp_type(ct, 0, strtoul(argv[idx++], NULL, 0)); + } else if (arg_match("origicmpcode")) { + if (argc > ++idx) + nfnl_ct_set_icmp_code(ct, 0, strtoul(argv[idx++], NULL, 0)); + } else if (arg_match("replyicmpid")) { + if (argc > ++idx) + nfnl_ct_set_icmp_id(ct, 1, strtoul(argv[idx++], NULL, 0)); + } else if (arg_match("replyicmptype")) { + if (argc > ++idx) + nfnl_ct_set_icmp_type(ct, 1, strtoul(argv[idx++], NULL, 0)); + } else if (arg_match("replyicmpcode")) { + if (argc > ++idx) + nfnl_ct_set_icmp_code(ct, 1, strtoul(argv[idx++], NULL, 0)); + } +#endif diff --git a/src/ct-utils.h b/src/ct-utils.h new file mode 100644 index 0000000..fc20e49 --- /dev/null +++ b/src/ct-utils.h @@ -0,0 +1,34 @@ +/* + * src/ct-utils.h Conntrack Helper + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __CT_UTILS_H_ +#define __CT_UTILS_H_ + +#include "utils.h" +#include <netlink/netfilter/ct.h> +#include <linux/netfilter/nf_conntrack_common.h> + +extern struct nfnl_ct *nlt_alloc_ct(void); +extern struct nl_cache *nlt_alloc_ct_cache(struct nl_sock *); +extern void parse_family(struct nfnl_ct *, char *); +extern void parse_protocol(struct nfnl_ct *, char *); +extern void parse_mark(struct nfnl_ct *, char *); +extern void parse_timeout(struct nfnl_ct *, char *); +extern void parse_id(struct nfnl_ct *, char *); +extern void parse_use(struct nfnl_ct *, char *); +extern void parse_src(struct nfnl_ct *, int, char *); +extern void parse_dst(struct nfnl_ct *, int, char *); +extern void parse_src_port(struct nfnl_ct *, int, char *); +extern void parse_dst_port(struct nfnl_ct *, int, char *); +extern void parse_tcp_state(struct nfnl_ct *, char *); +extern void parse_status(struct nfnl_ct *, char *); + +#endif diff --git a/src/ctrl-utils.c b/src/ctrl-utils.c new file mode 100644 index 0000000..5309c23 --- /dev/null +++ b/src/ctrl-utils.c @@ -0,0 +1,18 @@ +/* + * src/ctrl-utils.c Generic Ctrl Netlink Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "ctrl-utils.h" + +struct nl_cache *nlt_alloc_genl_family_cache(struct nl_sock *sk) +{ + return alloc_cache(sk, "generic netlink family", + genl_ctrl_alloc_cache); +} diff --git a/src/ctrl-utils.h b/src/ctrl-utils.h new file mode 100644 index 0000000..59e3cdc --- /dev/null +++ b/src/ctrl-utils.h @@ -0,0 +1,19 @@ +/* + * src/ctrl-utils.h Generic Netlink Ctrl Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __SRC_CTRL_UTILS_H_ +#define __SRC_CTRL_UTILS_H_ + +#include "utils.h" + +extern struct nl_cache *nlt_alloc_genl_family_cache(struct nl_sock *); + +#endif diff --git a/src/nl-qdisc-add.c b/src/disabled-nl-qdisc-add.c index be19f9b..be19f9b 100644 --- a/src/nl-qdisc-add.c +++ b/src/disabled-nl-qdisc-add.c diff --git a/src/f_ct.c b/src/f_ct.c deleted file mode 100644 index fbb04fc..0000000 --- a/src/f_ct.c +++ /dev/null @@ -1,170 +0,0 @@ -/* - * src/f_ct.c Conntrack Filter - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - * Copyright (c) 2007 Philip Craig <philipc@snapgear.com> - * Copyright (c) 2007 Secure Computing Corporation - */ - -static void get_filter(struct nfnl_ct *ct, int argc, char **argv, int idx) -{ - struct nl_addr *a; - - while (argc > idx) { - if (arg_match("family")) { - if (argc > ++idx) { - int family = nl_str2af(argv[idx++]); - if (family == AF_UNSPEC) - goto err_invaf; - nfnl_ct_set_family(ct, family); - } - } else if (arg_match("proto")) { - if (argc > ++idx) { - int proto = nl_str2ip_proto(argv[idx++]); - if (proto < 0) - goto err_invproto; - nfnl_ct_set_proto(ct, proto); - } - } else if (arg_match("tcpstate")) { - if (argc > ++idx) { - int state = nfnl_ct_str2tcp_state(argv[idx++]); - if (state < 0) - goto err_invtcpstate; - nfnl_ct_set_tcp_state(ct, state); - } - } else if (arg_match("status")) { - if (argc > ++idx) { - int status = strtoul(argv[idx++], NULL, 0); - nfnl_ct_set_status(ct, status); - nfnl_ct_unset_status(ct, ~status); - } - } else if (arg_match("timeout")) { - if (argc > ++idx) - nfnl_ct_set_timeout(ct, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("mark")) { - if (argc > ++idx) - nfnl_ct_set_mark(ct, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("use")) { - if (argc > ++idx) - nfnl_ct_set_use(ct, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("id")) { - if (argc > ++idx) - nfnl_ct_set_id(ct, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("origsrc")) { - if (argc > ++idx) { - a = nl_addr_parse(argv[idx++], - nfnl_ct_get_family(ct)); - if (!a) - goto err_invaddr; - nfnl_ct_set_src(ct, 0, a); - nl_addr_put(a); - } - } else if (arg_match("origdst")) { - if (argc > ++idx) { - a = nl_addr_parse(argv[idx++], - nfnl_ct_get_family(ct)); - if (!a) - goto err_invaddr; - nfnl_ct_set_dst(ct, 0, a); - nl_addr_put(a); - } - } else if (arg_match("origsrcport")) { - if (argc > ++idx) - nfnl_ct_set_src_port(ct, 0, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("origdstport")) { - if (argc > ++idx) - nfnl_ct_set_dst_port(ct, 0, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("origicmpid")) { - if (argc > ++idx) - nfnl_ct_set_icmp_id(ct, 0, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("origicmptype")) { - if (argc > ++idx) - nfnl_ct_set_icmp_type(ct, 0, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("origicmpcode")) { - if (argc > ++idx) - nfnl_ct_set_icmp_code(ct, 0, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("origpackets")) { - if (argc > ++idx) - nfnl_ct_set_packets(ct, 0, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("origbytes")) { - if (argc > ++idx) - nfnl_ct_set_bytes(ct, 0, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("replysrc")) { - if (argc > ++idx) { - a = nl_addr_parse(argv[idx++], - nfnl_ct_get_family(ct)); - if (!a) - goto err_invaddr; - nfnl_ct_set_src(ct, 1, a); - nl_addr_put(a); - } - } else if (arg_match("replydst")) { - if (argc > ++idx) { - a = nl_addr_parse(argv[idx++], - nfnl_ct_get_family(ct)); - if (!a) - goto err_invaddr; - nfnl_ct_set_dst(ct, 1, a); - nl_addr_put(a); - } - } else if (arg_match("replysrcport")) { - if (argc > ++idx) - nfnl_ct_set_src_port(ct, 1, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("replydstport")) { - if (argc > ++idx) - nfnl_ct_set_dst_port(ct, 1, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("replyicmpid")) { - if (argc > ++idx) - nfnl_ct_set_icmp_id(ct, 1, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("replyicmptype")) { - if (argc > ++idx) - nfnl_ct_set_icmp_type(ct, 1, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("replyicmpcode")) { - if (argc > ++idx) - nfnl_ct_set_icmp_code(ct, 1, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("replypackets")) { - if (argc > ++idx) - nfnl_ct_set_packets(ct, 1, strtoul(argv[idx++], NULL, 0)); - } else if (arg_match("replybytes")) { - if (argc > ++idx) - nfnl_ct_set_bytes(ct, 1, strtoul(argv[idx++], NULL, 0)); - } -#define MSTATUS(STR, STATUS) \ - else if (!strcasecmp(argv[idx], STR)) { \ - nfnl_ct_set_status(ct, STATUS); idx++; } -#define MNOSTATUS(STR, STATUS) \ - else if (!strcasecmp(argv[idx], STR)) { \ - nfnl_ct_unset_status(ct, STATUS); idx++; } - - MSTATUS("replied", IPS_SEEN_REPLY) - MNOSTATUS("unreplied", IPS_SEEN_REPLY) - MSTATUS("assured", IPS_ASSURED) - MNOSTATUS("unassured", IPS_ASSURED) -#undef MSTATUS -#undef MNOSTATUS - else { - fprintf(stderr, "What is '%s'?\n", argv[idx]); - exit(1); - } - } - - return; - -err_invproto: - fprintf(stderr, "Invalid IP protocol \"%s\".\n", argv[idx-1]); - exit(1); -err_invtcpstate: - fprintf(stderr, "Invalid TCP state \"%s\".\n", argv[idx-1]); - exit(1); -err_invaf: - fprintf(stderr, "Invalid address family \"%s\"\n", argv[idx-1]); - exit(1); -err_invaddr: - fprintf(stderr, "Invalid address \"%s\": %s\n", argv[idx-1], nl_geterror()); - exit(1); -} diff --git a/src/f_link.c b/src/f_link.c deleted file mode 100644 index 3c1cb93..0000000 --- a/src/f_link.c +++ /dev/null @@ -1,106 +0,0 @@ -/* - * src/f_link.c Link Filter - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - */ - -#include <linux/if.h> - -static void get_filter(struct rtnl_link *l, int ac, char **av, int idx, - struct nl_cache *cache) -{ - while (ac > idx) { - if (!strcasecmp(av[idx], "dev")) { - if (ac > ++idx) { - int ifindex = rtnl_link_name2i(cache, av[idx++]); - if (ifindex == RTNL_LINK_NOT_FOUND) - goto err_notfound; - rtnl_link_set_ifindex(l, ifindex); - } - } else if (!strcasecmp(av[idx], "mtu")) { - if (ac > ++idx) - rtnl_link_set_mtu(l, strtoul(av[idx++], NULL, 0)); - } else if (!strcasecmp(av[idx], "txqlen")) { - if (ac > ++idx) - rtnl_link_set_txqlen(l, strtoul(av[idx++], NULL, 0)); - } else if (!strcasecmp(av[idx], "weight")) { - if (ac > ++idx) - rtnl_link_set_weight(l, strtoul(av[idx++], NULL, 0)); - } else if (!strcasecmp(av[idx], "link")) { - if (ac > ++idx) { - int ifindex = rtnl_link_name2i(cache, av[idx++]); - if (ifindex == RTNL_LINK_NOT_FOUND) - goto err_notfound; - rtnl_link_set_link(l, ifindex); - } - } else if (!strcasecmp(av[idx], "master")) { - if (ac > ++idx) { - int ifindex = rtnl_link_name2i(cache, av[idx++]); - if (ifindex == RTNL_LINK_NOT_FOUND) - goto err_notfound; - rtnl_link_set_master(l, ifindex); - } - } else if (!strcasecmp(av[idx], "qdisc")) { - if (ac > ++idx) - rtnl_link_set_qdisc(l, av[idx++]); - } else if (!strcasecmp(av[idx], "name")) { - if (ac > ++idx) - rtnl_link_set_name(l, av[idx++]); - } else if (!strcasecmp(av[idx], "addr")) { - if (ac > ++idx) { - struct nl_addr *a = nl_addr_parse(av[idx++], AF_UNSPEC); - if (a == NULL) - goto err; - rtnl_link_set_addr(l, a); - nl_addr_put(a); - } - } else if (!strcasecmp(av[idx], "broadcast")) { - if (ac > ++idx) { - struct nl_addr *a = nl_addr_parse(av[idx++], AF_UNSPEC); - if (a == NULL) - goto err; - rtnl_link_set_broadcast(l, a); - nl_addr_put(a); - } - } -#define MFLAG(STR, FLAG) \ - else if (!strcasecmp(av[idx], STR)) { \ - rtnl_link_set_flags(l, FLAG); idx++; } -#define MNOFLAG(STR, FLAG) \ - else if (!strcasecmp(av[idx], STR)) { \ - rtnl_link_unset_flags(l, FLAG); idx++; } - - MFLAG("up", IFF_UP) - MNOFLAG("down", IFF_UP) - MFLAG("noarp", IFF_NOARP) - MNOFLAG("arp", IFF_NOARP) - MFLAG("promisc", IFF_PROMISC) - MNOFLAG("nopromisc", IFF_PROMISC) - MFLAG("dynamic", IFF_DYNAMIC) - MNOFLAG("nodynamic", IFF_DYNAMIC) - MFLAG("multicast", IFF_MULTICAST) - MNOFLAG("nomulticast", IFF_MULTICAST) - MFLAG("allmulticast", IFF_ALLMULTI) - MNOFLAG("noallmulticast", IFF_ALLMULTI) -#undef MFLAG -#undef MNOFLAG - else { - fprintf(stderr, "What is '%s'?\n", av[idx]); - exit(1); - } - } - - return; - -err_notfound: - fprintf(stderr, "Unknown link %s\n", av[idx-1]); - exit(1); -err: - fprintf(stderr, "%s\n", nl_geterror()); - exit(1); -} diff --git a/src/f_neigh.c b/src/f_neigh.c deleted file mode 100644 index ac9355c..0000000 --- a/src/f_neigh.c +++ /dev/null @@ -1,51 +0,0 @@ -/* - * src/f_neigh.c Neighbour Filter - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - */ - -static void get_filter(struct rtnl_neigh *n, int ac, char **av, int idx, - struct nl_cache *cache) -{ - struct nl_cache *lc = nl_cache_mngt_require("route/link"); - - while (ac > idx) { - if (!strcasecmp(av[idx], "dev")) { - if (ac > ++idx) { - int ifindex = rtnl_link_name2i(lc, av[idx++]); - if (ifindex == RTNL_LINK_NOT_FOUND) - goto err_notfound; - rtnl_neigh_set_ifindex(n, ifindex); - } - } else if (!strcasecmp(av[idx], "dst")) { - if (ac > ++idx) { - struct nl_addr *a = nl_addr_parse(av[idx++], AF_UNSPEC); - if (a == NULL) - goto err; - rtnl_neigh_set_dst(n, a); - nl_addr_put(a); - } - } else if (!strcasecmp(av[idx], "lladdr")) { - if (ac > ++idx) { - struct nl_addr *a = nl_addr_parse(av[idx++], AF_UNSPEC); - if (a == NULL) - goto err; - rtnl_neigh_set_lladdr(n, a); - nl_addr_put(a); - } - } - } - - return; -err_notfound: - fprintf(stderr, "Unable to find interface %s\n", av[idx-1]); - exit(1); -err: - fprintf(stderr, "%s\n", nl_geterror()); - exit(1); -} diff --git a/src/genl-ctrl-dump.c b/src/genl-ctrl-dump.c deleted file mode 100644 index 98a26a1..0000000 --- a/src/genl-ctrl-dump.c +++ /dev/null @@ -1,65 +0,0 @@ -/* - * src/genl-ctrl-dump.c Dump Generic Netlink Controller - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - */ - -#include "utils.h" - -static void print_usage(void) -{ - printf( - "Usage: genl-ctrl-dump <mode> [<filter>]\n" - " mode := { brief | detailed | stats }\n" - " filter := \n"); - exit(1); -} - -int main(int argc, char *argv[]) -{ - struct nl_handle *nlh; - struct nl_cache *family_cache; - struct nl_dump_params params = { - .dp_fd = stdout, - .dp_type = NL_DUMP_BRIEF - }; - int err = 1; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) - print_usage(); - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - if (genl_connect(nlh) < 0) { - fprintf(stderr, "Unable to connect generic netlink socket%s\n", - nl_geterror()); - goto errout; - } - - family_cache = nltool_alloc_genl_family_cache(nlh); - if (!family_cache) - goto errout; - - params.dp_type = nltool_parse_dumptype(argv[1]); - if (params.dp_type < 0) - goto errout; - - //get_filter(link, argc, argv, 2, link_cache); - nl_cache_dump(family_cache, ¶ms); - nl_cache_free(family_cache); - err = 0; -errout: - nl_close(nlh); - nl_handle_destroy(nlh); - return err; -} diff --git a/src/genl-ctrl-list.c b/src/genl-ctrl-list.c new file mode 100644 index 0000000..335c62b --- /dev/null +++ b/src/genl-ctrl-list.c @@ -0,0 +1,63 @@ +/* + * src/genl-ctrl-list.c List Generic Netlink Controller + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "ctrl-utils.h" + +static void print_usage(void) +{ + printf( + "Usage: genl-ctrl-list [OPTION]...\n" + "\n" + "Options\n" + " -f, --format=TYPE Output format { brief | details | stats }\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + ); + exit(0); +} + +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct nl_cache *family_cache; + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_GENERIC); + family_cache = nlt_alloc_genl_family_cache(sock); + + for (;;) { + int c, optidx = 0; + static struct option long_opts[] = { + { "format", 1, 0, 'f' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "f:hv", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + } + } + + nl_cache_dump(family_cache, ¶ms); + + return 0; +} diff --git a/src/link-utils.c b/src/link-utils.c new file mode 100644 index 0000000..93bb4c0 --- /dev/null +++ b/src/link-utils.c @@ -0,0 +1,62 @@ +/* + * src/link-utils.c Link Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "link-utils.h" + +struct rtnl_link *nlt_alloc_link(void) +{ + struct rtnl_link *link; + + link = rtnl_link_alloc(); + if (!link) + fatal(ENOMEM, "Unable to allocate link object"); + + return link; +} + +void parse_family(struct rtnl_link *link, char *arg) +{ + int family; + + if ((family = nl_str2af(arg)) == AF_UNSPEC) + fatal(EINVAL, "Unable to translate address family \"%s\"", arg); + + rtnl_link_set_family(link, family); +} + +void parse_name(struct rtnl_link *link, char *arg) +{ + rtnl_link_set_name(link, arg); +} + +void parse_mtu(struct rtnl_link *link, char *arg) +{ + uint32_t mtu = parse_u32(arg); + rtnl_link_set_mtu(link, mtu); +} + +void parse_ifindex(struct rtnl_link *link, char *arg) +{ + uint32_t index = parse_u32(arg); + rtnl_link_set_ifindex(link, index); +} + +void parse_txqlen(struct rtnl_link *link, char *arg) +{ + uint32_t qlen = parse_u32(arg); + rtnl_link_set_txqlen(link, qlen); +} + +void parse_weight(struct rtnl_link *link, char *arg) +{ + uint32_t weight = parse_u32(arg); + rtnl_link_set_weight(link, weight); +} diff --git a/src/link-utils.h b/src/link-utils.h new file mode 100644 index 0000000..1d5c6c0 --- /dev/null +++ b/src/link-utils.h @@ -0,0 +1,25 @@ +/* + * src/link-utils.h Link Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __LINK_UTILS_H_ +#define __LINK_UTILS_H_ + +#include "utils.h" + +extern struct rtnl_link *nlt_alloc_link(void); +extern void parse_family(struct rtnl_link *, char *); +extern void parse_name(struct rtnl_link *, char *); +extern void parse_mtu(struct rtnl_link *, char *); +extern void parse_ifindex(struct rtnl_link *, char *); +extern void parse_txqlen(struct rtnl_link *, char *); +extern void parse_weight(struct rtnl_link *, char *); + +#endif diff --git a/src/log-utils.c b/src/log-utils.c new file mode 100644 index 0000000..e3cfe44 --- /dev/null +++ b/src/log-utils.c @@ -0,0 +1,23 @@ +/* + * src/ct-utils.c Conntrack Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "log-utils.h" + +struct nfnl_log *nlt_alloc_log(void) +{ + struct nfnl_log *log; + + log = nfnl_log_alloc(); + if (!log) + fatal(ENOMEM, "Unable to allocate log object"); + + return log; +} diff --git a/src/log-utils.h b/src/log-utils.h new file mode 100644 index 0000000..fb5bf2a --- /dev/null +++ b/src/log-utils.h @@ -0,0 +1,22 @@ +/* + * src/log-utils.h Log Helper + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __LOG_UTILS_H_ +#define __LOG_UTILS_H_ + +#include "utils.h" +#include <linux/netfilter/nfnetlink_log.h> +#include <netlink/netfilter/nfnl.h> +#include <netlink/netfilter/log.h> + +extern struct nfnl_log *nlt_alloc_log(void); + +#endif diff --git a/src/neigh-utils.c b/src/neigh-utils.c new file mode 100644 index 0000000..3e2d699 --- /dev/null +++ b/src/neigh-utils.c @@ -0,0 +1,76 @@ +/* + * src/neigh-utils.c Neighbour Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "neigh-utils.h" + +struct rtnl_neigh *nlt_alloc_neigh(void) +{ + struct rtnl_neigh *neigh; + + neigh = rtnl_neigh_alloc(); + if (!neigh) + fatal(ENOMEM, "Unable to allocate neighbout object"); + + return neigh; +} + +void parse_dst(struct rtnl_neigh *neigh, char *arg) +{ + struct nl_addr *a; + int err; + + a = nlt_addr_parse(arg, rtnl_neigh_get_family(neigh)); + if ((err = rtnl_neigh_set_dst(neigh, a)) < 0) + fatal(err, "Unable to set local address: %s", + nl_geterror(err)); + + nl_addr_put(a); +} + +void parse_lladdr(struct rtnl_neigh *neigh, char *arg) +{ + struct nl_addr *a; + + a = nlt_addr_parse(arg, AF_UNSPEC); + rtnl_neigh_set_lladdr(neigh, a); + nl_addr_put(a); +} + +void parse_dev(struct rtnl_neigh *neigh, struct nl_cache *link_cache, char *arg) +{ + int ival; + + if (!(ival = rtnl_link_name2i(link_cache, arg))) + fatal(ENOENT, "Link \"%s\" does not exist", arg); + + rtnl_neigh_set_ifindex(neigh, ival); +} + +void parse_family(struct rtnl_neigh *neigh, char *arg) +{ + int family; + + if ((family = nl_str2af(arg)) == AF_UNSPEC) + fatal(EINVAL, "Unable to translate address family \"%s\"", arg); + + rtnl_neigh_set_family(neigh, family); +} + +void parse_state(struct rtnl_neigh *neigh, char *arg) +{ + int state; + + if ((state = rtnl_neigh_str2state(arg)) < 0) + fatal(state, "Unable to translate state \"%s\": %s", + arg, state); + + rtnl_neigh_set_state(neigh, state); +} diff --git a/src/neigh-utils.h b/src/neigh-utils.h new file mode 100644 index 0000000..3662546 --- /dev/null +++ b/src/neigh-utils.h @@ -0,0 +1,24 @@ +/* + * src/neigh-utils.h Neighbour Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __NEIGH_UTILS_H_ +#define __NEIGH_UTILS_H_ + +#include "utils.h" + +extern struct rtnl_neigh *nlt_alloc_neigh(void); +extern void parse_dst(struct rtnl_neigh *, char *); +extern void parse_lladdr(struct rtnl_neigh *, char *); +extern void parse_dev(struct rtnl_neigh *, struct nl_cache *, char *); +extern void parse_family(struct rtnl_neigh *, char *); +extern void parse_state(struct rtnl_neigh *, char *); + +#endif diff --git a/src/nf-ct-dump.c b/src/nf-ct-dump.c deleted file mode 100644 index 54ee4c7..0000000 --- a/src/nf-ct-dump.c +++ /dev/null @@ -1,91 +0,0 @@ -/* - * src/nf-ct-dump.c Dump conntrack attributes - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - * Copyright (c) 2007 Philip Craig <philipc@snapgear.com> - * Copyright (c) 2007 Secure Computing Corporation - */ - -#include "utils.h" -#include <netlink/netfilter/ct.h> -#include <linux/netfilter/nf_conntrack_common.h> - -#include "f_ct.c" - -static void print_usage(void) -{ - printf( - "Usage: nf-ct-dump <mode> [<filter>]\n" - " mode := { brief | detailed | stats | xml }\n" - " filter := [family FAMILY] [proto PROTO] [tcpstate TCPSTATE]\n" - " [status STATUS] [timeout TIMEOUT] [mark MARK] [use USE] [id ID]\n" - " [origsrc ADDR] [origdst ADDR] [origsrcport PORT] [origdstport PORT]\n" - " [origicmpid ID] [origicmptype TYPE] [origicmpcode CODE]\n" - " [origpackets PACKETS] [origbytes BYTES]\n" - " [replysrc ADDR] [replydst ADDR] [replysrcport PORT] [replydstport PORT]\n" - " [replyicmpid ID] [replyicmptype TYPE] [replyicmpcode CODE]\n" - " [replypackets PACKETS] [replybytes BYTES]\n" - " [{ replied | unreplied }] [{ assured | unassured }]\n" - ); - exit(1); -} - -int main(int argc, char *argv[]) -{ - struct nl_handle *nlh; - struct nl_cache *ct_cache; - struct nfnl_ct *ct; - struct nl_dump_params params = { - .dp_fd = stdout, - .dp_type = NL_DUMP_BRIEF - }; - int err = 1; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) - print_usage(); - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - ct = nfnl_ct_alloc(); - if (!ct) - goto errout; - - if (nltool_connect(nlh, NETLINK_NETFILTER) < 0) - goto errout_free; - - ct_cache = nfnl_ct_alloc_cache(nlh); - if (!ct_cache) { - fprintf(stderr, "Unable to retrieve ct cache: %s\n", - nl_geterror()); - goto errout_close; - } - nl_cache_mngt_provide(ct_cache); - - params.dp_type = nltool_parse_dumptype(argv[1]); - if (params.dp_type < 0) - goto errout_ct_cache; - - get_filter(ct, argc, argv, 2); - nl_cache_dump_filter(ct_cache, ¶ms, (struct nl_object *) ct); - - err = 0; - -errout_ct_cache: - nl_cache_free(ct_cache); -errout_close: - nl_close(nlh); -errout_free: - nfnl_ct_put(ct); -errout: - return err; -} diff --git a/src/nf-ct-list.c b/src/nf-ct-list.c new file mode 100644 index 0000000..2f4c4fc --- /dev/null +++ b/src/nf-ct-list.c @@ -0,0 +1,135 @@ +/* + * src/nf-ct-list.c List Conntrack Entries + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2007 Philip Craig <philipc@snapgear.com> + * Copyright (c) 2007 Secure Computing Corporation + */ + +#include "ct-utils.h" + +static void print_usage(void) +{ + printf( + "Usage: nf-ct-list [OPTION]... [CONNTRACK ENTRY]\n" + "\n" + "Options\n" + " -f, --format=TYPE Output format { brief | details | stats }\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "Conntrack Selection\n" + " -i, --id=NUM Identifier\n" + " -p, --proto=PROTOCOL Protocol\n" + " --tcp-state=STATE TCP connection state\n" + " --orig-src=ADDR Original source address\n" + " --orig-sport=PORT Original source port\n" + " --orig-dst=ADDR Original destination address\n" + " --orig-dport=PORT Original destination port\n" + " --reply-src=ADDR Reply source address\n" + " --reply-sport=PORT Reply source port\n" + " --reply-dst=ADDR Reply destination address\n" + " --reply-dport=PORT Reply destination port\n" + " -F, --family=FAMILY Address family\n" + " --mark=NUM Mark value\n" + " --timeout=NUM Timeout value\n" + " --refcnt=NUM Use counter value\n" + " --flags Flags\n" + ); + exit(0); +} + +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct nl_cache *ct_cache; + struct nfnl_ct *ct; + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + + ct = nlt_alloc_ct(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_MARK = 257, + ARG_TCP_STATE = 258, + ARG_ORIG_SRC, + ARG_ORIG_SPORT, + ARG_ORIG_DST, + ARG_ORIG_DPORT, + ARG_REPLY_SRC, + ARG_REPLY_SPORT, + ARG_REPLY_DST, + ARG_REPLY_DPORT, + ARG_TIMEOUT, + ARG_REFCNT, + ARG_FLAGS, + }; + static struct option long_opts[] = { + { "format", 1, 0, 'f' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "id", 1, 0, 'i' }, + { "proto", 1, 0, 'p' }, + { "tcp-state", 1, 0, ARG_TCP_STATE }, + { "orig-src", 1, 0, ARG_ORIG_SRC }, + { "orig-sport", 1, 0, ARG_ORIG_SPORT }, + { "orig-dst", 1, 0, ARG_ORIG_DST }, + { "orig-dport", 1, 0, ARG_ORIG_DPORT }, + { "reply-src", 1, 0, ARG_REPLY_SRC }, + { "reply-sport", 1, 0, ARG_REPLY_SPORT }, + { "reply-dst", 1, 0, ARG_REPLY_DST }, + { "reply-dport", 1, 0, ARG_REPLY_DPORT }, + { "family", 1, 0, 'F' }, + { "mark", 1, 0, ARG_MARK }, + { "timeout", 1, 0, ARG_TIMEOUT }, + { "refcnt", 1, 0, ARG_REFCNT }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "46f:hvi:p:F:", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case '?': exit(NLE_INVAL); + case '4': nfnl_ct_set_family(ct, AF_INET); break; + case '6': nfnl_ct_set_family(ct, AF_INET6); break; + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'i': parse_id(ct, optarg); break; + case 'p': parse_protocol(ct, optarg); break; + case ARG_TCP_STATE: parse_tcp_state(ct, optarg); break; + case ARG_ORIG_SRC: parse_src(ct, 0, optarg); break; + case ARG_ORIG_SPORT: parse_src_port(ct, 0, optarg); break; + case ARG_ORIG_DST: parse_dst(ct, 0, optarg); break; + case ARG_ORIG_DPORT: parse_dst_port(ct, 0, optarg); break; + case ARG_REPLY_SRC: parse_src(ct, 1, optarg); break; + case ARG_REPLY_SPORT: parse_src_port(ct, 1, optarg); break; + case ARG_REPLY_DST: parse_dst(ct, 1, optarg); break; + case ARG_REPLY_DPORT: parse_dst_port(ct, 1, optarg); break; + case 'F': parse_family(ct, optarg); break; + case ARG_MARK: parse_mark(ct, optarg); break; + case ARG_TIMEOUT: parse_timeout(ct, optarg); break; + case ARG_REFCNT: parse_use(ct, optarg); break; + case ARG_FLAGS: parse_status(ct, optarg); break; + } + } + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_NETFILTER); + ct_cache = nlt_alloc_ct_cache(sock); + + nl_cache_dump_filter(ct_cache, ¶ms, OBJ_CAST(ct)); + + return 0; +} diff --git a/src/nf-log.c b/src/nf-log.c index d1f0ed6..d855efc 100644 --- a/src/nf-log.c +++ b/src/nf-log.c @@ -6,17 +6,12 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> * Copyright (c) 2007 Philip Craig <philipc@snapgear.com> * Copyright (c) 2007 Secure Computing Corporation */ -#include <sys/types.h> -#include <linux/netfilter/nfnetlink_log.h> - -#include "utils.h" -#include <netlink/netfilter/nfnl.h> -#include <netlink/netfilter/log.h> +#include "log-utils.h" static void obj_input(struct nl_object *obj, void *arg) { @@ -40,25 +35,18 @@ static int event_input(struct nl_msg *msg, void *arg) int main(int argc, char *argv[]) { - struct nl_handle *nfnlh; - struct nl_handle *rtnlh; + struct nl_sock *nf_sock; + struct nl_sock *rt_sock; struct nl_cache *link_cache; struct nfnl_log *log; enum nfnl_log_copy_mode copy_mode; uint32_t copy_range; - int err = 1; + int err; int family; - if (nltool_init(argc, argv) < 0) - return -1; - - nfnlh = nltool_alloc_handle(); - if (nfnlh == NULL) - return -1; - - nl_disable_sequence_check(nfnlh); - - nl_socket_modify_cb(nfnlh, NL_CB_VALID, NL_CB_CUSTOM, event_input, NULL); + nf_sock = nlt_alloc_socket(); + nl_disable_sequence_check(nf_sock); + nl_socket_modify_cb(nf_sock, NL_CB_VALID, NL_CB_CUSTOM, event_input, NULL); if ((argc > 1 && !strcasecmp(argv[1], "-h")) || argc < 3) { printf("Usage: nf-log family group [ copy_mode ] " @@ -66,38 +54,26 @@ int main(int argc, char *argv[]) return 2; } - if (nfnl_connect(nfnlh) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + nlt_connect(nf_sock, NETLINK_NETFILTER); family = nl_str2af(argv[1]); - if (family == AF_UNSPEC) { - fprintf(stderr, "Unknown family: %s\n", argv[1]); - goto errout; - } + if (family == AF_UNSPEC) + fatal(NLE_INVAL, "Unknown family \"%s\": %s", + argv[1], nl_geterror(family)); - nfnl_log_pf_unbind(nfnlh, family); - if (nfnl_log_pf_bind(nfnlh, family) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } - - log = nfnl_log_alloc(); - if (log == NULL) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + nfnl_log_pf_unbind(nf_sock, family); + if ((err = nfnl_log_pf_bind(nf_sock, family)) < 0) + fatal(err, "Unable to bind logger: %s", nl_geterror(err)); + log = nlt_alloc_log(); nfnl_log_set_group(log, atoi(argv[2])); copy_mode = NFNL_LOG_COPY_META; if (argc > 3) { copy_mode = nfnl_log_str2copy_mode(argv[3]); - if (copy_mode < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + if (copy_mode < 0) + fatal(copy_mode, "Unable to parse copy mode \"%s\": %s", + argv[3], nl_geterror(copy_mode)); } nfnl_log_set_copy_mode(log, copy_mode); @@ -106,10 +82,8 @@ int main(int argc, char *argv[]) copy_mode = atoi(argv[4]); nfnl_log_set_copy_range(log, copy_range); - if (nfnl_log_create(nfnlh, log) <0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + if ((err = nfnl_log_create(nf_sock, log)) < 0) + fatal(err, "Unable to bind instance: %s", nl_geterror(err)); { struct nl_dump_params dp = { @@ -122,22 +96,9 @@ int main(int argc, char *argv[]) nl_object_dump((struct nl_object *) log, &dp); } - rtnlh = nltool_alloc_handle(); - if (rtnlh == NULL) { - goto errout_close; - } - - if (nl_connect(rtnlh, NETLINK_ROUTE) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } - - if ((link_cache = rtnl_link_alloc_cache(rtnlh)) == NULL) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_close; - } - - nl_cache_mngt_provide(link_cache); + rt_sock = nlt_alloc_socket(); + nlt_connect(rt_sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(rt_sock); while (1) { fd_set rfds; @@ -145,35 +106,24 @@ int main(int argc, char *argv[]) FD_ZERO(&rfds); - maxfd = nffd = nl_socket_get_fd(nfnlh); + maxfd = nffd = nl_socket_get_fd(nf_sock); FD_SET(nffd, &rfds); - rtfd = nl_socket_get_fd(rtnlh); + rtfd = nl_socket_get_fd(rt_sock); FD_SET(rtfd, &rfds); if (maxfd < rtfd) maxfd = rtfd; - /* wait for an incoming message on the netlink socket */ + /* wait for an incoming message on the netlink nf_socket */ retval = select(maxfd+1, &rfds, NULL, NULL, NULL); if (retval) { if (FD_ISSET(nffd, &rfds)) - nl_recvmsgs_default(nfnlh); + nl_recvmsgs_default(nf_sock); if (FD_ISSET(rtfd, &rfds)) - nl_recvmsgs_default(rtnlh); + nl_recvmsgs_default(rt_sock); } } - nl_cache_mngt_unprovide(link_cache); - nl_cache_free(link_cache); - - nfnl_log_put(log); - - nl_close(rtnlh); - nl_handle_destroy(rtnlh); -errout_close: - nl_close(nfnlh); - nl_handle_destroy(nfnlh); -errout: - return err; + return 0; } diff --git a/src/nf-monitor.c b/src/nf-monitor.c index 2bc58c9..0113931 100644 --- a/src/nf-monitor.c +++ b/src/nf-monitor.c @@ -6,7 +6,7 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> * Copyright (c) 2007 Philip Craig <philipc@snapgear.com> * Copyright (c) 2007 Secure Computing Corporation */ @@ -36,67 +36,58 @@ static int event_input(struct nl_msg *msg, void *arg) int main(int argc, char *argv[]) { - struct nl_handle *nlh; - int err = 1; + struct nl_sock *sock; + int err; int i, idx; static const struct { enum nfnetlink_groups gr_id; const char* gr_name; - } known_groups[] = { + } groups[] = { { NFNLGRP_CONNTRACK_NEW, "ct-new" }, { NFNLGRP_CONNTRACK_UPDATE, "ct-update" }, { NFNLGRP_CONNTRACK_DESTROY, "ct-destroy" }, { NFNLGRP_NONE, NULL } }; - if (nltool_init(argc, argv) < 0) - return -1; - - nlh = nltool_alloc_handle(); - if (nlh == NULL) - return -1; - - nl_disable_sequence_check(nlh); - - nl_socket_modify_cb(nlh, NL_CB_VALID, NL_CB_CUSTOM, event_input, NULL); + sock = nlt_alloc_socket(); + nl_disable_sequence_check(sock); + nl_socket_modify_cb(sock, NL_CB_VALID, NL_CB_CUSTOM, event_input, NULL); if (argc > 1 && !strcasecmp(argv[1], "-h")) { printf("Usage: nf-monitor [<groups>]\n"); printf("Known groups:"); - for (i = 0; known_groups[i].gr_id != NFNLGRP_NONE; i++) - printf(" %s", known_groups[i].gr_name); + for (i = 0; groups[i].gr_id != NFNLGRP_NONE; i++) + printf(" %s", groups[i].gr_name); printf("\n"); return 2; } - if (nfnl_connect(nlh) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + nlt_connect(sock, NETLINK_NETFILTER); for (idx = 1; argc > idx; idx++) { - for (i = 0; known_groups[i].gr_id != NFNLGRP_NONE; i++) { - if (!strcmp(argv[idx], known_groups[i].gr_name)) { - - if (nl_socket_add_membership(nlh, known_groups[i].gr_id) < 0) { - fprintf(stderr, "%s: %s\n", argv[idx], nl_geterror()); - goto errout; - } - - break; - } + for (i = 0; groups[i].gr_id != NFNLGRP_NONE; i++) { + if (strcmp(argv[idx], groups[i].gr_name)) + continue; + + err = nl_socket_add_membership(sock, groups[i].gr_id); + if (err < 0) + fatal(err, "Unable to add membership: %s", + nl_geterror(err)); + break; } - if (known_groups[i].gr_id == NFNLGRP_NONE) - fprintf(stderr, "Warning: Unknown group: %s\n", argv[idx]); + + if (groups[i].gr_id == NFNLGRP_NONE) + fatal(NLE_OBJ_NOTFOUND, "Unknown group: \"%s\"", + argv[idx]); } while (1) { fd_set rfds; int fd, retval; - fd = nl_socket_get_fd(nlh); + fd = nl_socket_get_fd(sock); FD_ZERO(&rfds); FD_SET(fd, &rfds); @@ -105,11 +96,9 @@ int main(int argc, char *argv[]) if (retval) { /* FD_ISSET(fd, &rfds) will be true */ - nl_recvmsgs_default(nlh); + nl_recvmsgs_default(sock); } } - nl_close(nlh); -errout: - return err; + return 0; } diff --git a/src/nf-queue.c b/src/nf-queue.c index 1420273..4e17f70 100644 --- a/src/nf-queue.c +++ b/src/nf-queue.c @@ -9,16 +9,10 @@ * Copyright (c) 2007, 2008 Patrick McHardy <kaber@trash.net> */ -#include <sys/types.h> -#include <linux/netfilter.h> -#include <linux/netfilter/nfnetlink_queue.h> -#include "utils.h" -#include <netlink/netfilter/nfnl.h> -#include <netlink/netfilter/queue.h> -#include <netlink/netfilter/queue_msg.h> +#include "queue-utils.h" -static struct nl_handle *nfnlh; +static struct nl_sock *nf_sock; static void obj_input(struct nl_object *obj, void *arg) { @@ -31,7 +25,7 @@ static void obj_input(struct nl_object *obj, void *arg) nfnl_queue_msg_set_verdict(msg, NF_ACCEPT); nl_object_dump(obj, &dp); - nfnl_queue_msg_send_verdict(nfnlh, msg); + nfnl_queue_msg_send_verdict(nf_sock, msg); } static int event_input(struct nl_msg *msg, void *arg) @@ -45,7 +39,7 @@ static int event_input(struct nl_msg *msg, void *arg) int main(int argc, char *argv[]) { - struct nl_handle *rtnlh; + struct nl_sock *rt_sock; struct nl_cache *link_cache; struct nfnl_queue *queue; enum nfnl_queue_copy_mode copy_mode; @@ -53,16 +47,9 @@ int main(int argc, char *argv[]) int err = 1; int family; - if (nltool_init(argc, argv) < 0) - return -1; - - nfnlh = nltool_alloc_handle(); - if (nfnlh == NULL) - return -1; - - nl_disable_sequence_check(nfnlh); - - nl_socket_modify_cb(nfnlh, NL_CB_VALID, NL_CB_CUSTOM, event_input, NULL); + nf_sock = nlt_alloc_socket(); + nl_disable_sequence_check(nf_sock); + nl_socket_modify_cb(nf_sock, NL_CB_VALID, NL_CB_CUSTOM, event_input, NULL); if ((argc > 1 && !strcasecmp(argv[1], "-h")) || argc < 3) { printf("Usage: nf-queue family group [ copy_mode ] " @@ -70,38 +57,24 @@ int main(int argc, char *argv[]) return 2; } - if (nfnl_connect(nfnlh) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + nlt_connect(nf_sock, NETLINK_NETFILTER); - family = nl_str2af(argv[1]); - if (family == AF_UNSPEC) { - fprintf(stderr, "Unknown family: %s\n", argv[1]); - goto errout; - } + if ((family = nl_str2af(argv[1])) == AF_UNSPEC) + fatal(NLE_INVAL, "Unknown family \"%s\"", argv[1]); - nfnl_queue_pf_unbind(nfnlh, family); - if (nfnl_queue_pf_bind(nfnlh, family) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } - - queue = nfnl_queue_alloc(); - if (queue == NULL) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + nfnl_queue_pf_unbind(nf_sock, family); + if ((err = nfnl_queue_pf_bind(nf_sock, family)) < 0) + fatal(err, "Unable to bind logger: %s", nl_geterror(err)); + queue = nlt_alloc_queue(); nfnl_queue_set_group(queue, atoi(argv[2])); copy_mode = NFNL_QUEUE_COPY_PACKET; if (argc > 3) { copy_mode = nfnl_queue_str2copy_mode(argv[3]); - if (copy_mode < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + if (copy_mode < 0) + fatal(copy_mode, "Unable to parse copy mode \"%s\": %s", + argv[3], nl_geterror(copy_mode)); } nfnl_queue_set_copy_mode(queue, copy_mode); @@ -110,27 +83,12 @@ int main(int argc, char *argv[]) copy_range = atoi(argv[4]); nfnl_queue_set_copy_range(queue, copy_range); - if (nfnl_queue_create(nfnlh, queue) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + if ((err = nfnl_queue_create(nf_sock, queue)) < 0) + fatal(err, "Unable to bind queue: %s", nl_geterror(err)); - rtnlh = nltool_alloc_handle(); - if (rtnlh == NULL) { - goto errout_close; - } - - if (nl_connect(rtnlh, NETLINK_ROUTE) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } - - if ((link_cache = rtnl_link_alloc_cache(rtnlh)) == NULL) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_close; - } - - nl_cache_mngt_provide(link_cache); + rt_sock = nlt_alloc_socket(); + nlt_connect(rt_sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(rt_sock); while (1) { fd_set rfds; @@ -138,10 +96,10 @@ int main(int argc, char *argv[]) FD_ZERO(&rfds); - maxfd = nffd = nl_socket_get_fd(nfnlh); + maxfd = nffd = nl_socket_get_fd(nf_sock); FD_SET(nffd, &rfds); - rtfd = nl_socket_get_fd(rtnlh); + rtfd = nl_socket_get_fd(rt_sock); FD_SET(rtfd, &rfds); if (maxfd < rtfd) maxfd = rtfd; @@ -151,22 +109,11 @@ int main(int argc, char *argv[]) if (retval) { if (FD_ISSET(nffd, &rfds)) - nl_recvmsgs_default(nfnlh); + nl_recvmsgs_default(nf_sock); if (FD_ISSET(rtfd, &rfds)) - nl_recvmsgs_default(rtnlh); + nl_recvmsgs_default(rt_sock); } } - nl_cache_mngt_unprovide(link_cache); - nl_cache_free(link_cache); - - nfnl_queue_put(queue); - - nl_close(rtnlh); - nl_handle_destroy(rtnlh); -errout_close: - nl_close(nfnlh); - nl_handle_destroy(nfnlh); -errout: - return err; + return 0; } diff --git a/src/nl-fib-lookup.c b/src/nl-fib-lookup.c index 5bbf91e..2507be8 100644 --- a/src/nl-fib-lookup.c +++ b/src/nl-fib-lookup.c @@ -37,9 +37,6 @@ int main(int argc, char *argv[]) int tos = 0, err = 1; uint64_t fwmark = 0; - if (nltool_init(argc, argv) < 0) - return -1; - while (1) { static struct option long_opts[] = { {"table", 1, 0, 't'}, @@ -76,24 +73,19 @@ int main(int argc, char *argv[]) if (optind >= argc) print_usage(); - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; + nlh = nlt_alloc_socket(); - addr = nl_addr_parse(argv[optind], AF_INET); - if (!addr) { - fprintf(stderr, "Unable to parse address \"%s\": %s\n", - argv[optind], nl_geterror()); - goto errout; - } + if ((err = nl_addr_parse(argv[optind], AF_INET, &addr)) < 0) + fatal(err, "Unable to parse address \"%s\": %s\n", + argv[optind], nl_geterror(err)); result = flnl_result_alloc_cache(); if (!result) - goto errout_addr; + fatal(ENOMEM, "Unable to allocate cache"); request = flnl_request_alloc(); if (!request) - goto errout_result; + fatal(ENOMEM, "Unable to allocate request"); flnl_request_set_table(request, table); flnl_request_set_fwmark(request, fwmark); @@ -103,28 +95,15 @@ int main(int argc, char *argv[]) err = flnl_request_set_addr(request, addr); nl_addr_put(addr); if (err < 0) - goto errout_put; + fatal(err, "Unable to send request: %s", nl_geterror(err)); - if (nltool_connect(nlh, NETLINK_FIB_LOOKUP) < 0) - goto errout_put; + nlt_connect(nlh, NETLINK_FIB_LOOKUP); err = flnl_lookup(nlh, request, result); - if (err < 0) { - fprintf(stderr, "Unable to lookup: %s\n", nl_geterror()); - goto errout_put; - } + if (err < 0) + fatal(err, "Unable to lookup: %s\n", nl_geterror(err)); nl_cache_dump(result, ¶ms); - err = 0; -errout_put: - nl_object_put(OBJ_CAST(request)); -errout_result: - nl_cache_free(result); -errout_addr: - nl_addr_put(addr); -errout: - nl_close(nlh); - nl_handle_destroy(nlh); - return err; + return 0; } diff --git a/src/nl-link-dump.c b/src/nl-link-dump.c deleted file mode 100644 index 0214025..0000000 --- a/src/nl-link-dump.c +++ /dev/null @@ -1,75 +0,0 @@ -/* - * src/nl-link-dump.c Dump link attributes - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - */ - -#include "utils.h" - -static void print_usage(void) -{ - printf( - "Usage: nl-link-dump <mode> [<filter>]\n" - " mode := { brief | detailed | stats | xml }\n" - " filter := [dev DEV] [mtu MTU] [txqlen TXQLEN] [weight WEIGHT] [link LINK]\n" - " [master MASTER] [qdisc QDISC] [addr ADDR] [broadcast BRD]\n" - " [{ up | down }] [{ arp | noarp }] [{ promisc | nopromisc }]\n" - " [{ dynamic | nodynamic }] [{ multicast | nomulticast }]\n" - " [{ trailers | notrailers }] [{ allmulticast | noallmulticast }]\n"); - exit(1); -} - -#include "f_link.c" - -int main(int argc, char *argv[]) -{ - struct nl_handle *nlh; - struct nl_cache *link_cache; - struct rtnl_link *link; - struct nl_dump_params params = { - .dp_fd = stdout, - .dp_type = NL_DUMP_BRIEF - }; - int err = 1; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) - print_usage(); - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - link = rtnl_link_alloc(); - if (!link) - goto errout; - - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout_put; - - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout_put; - - params.dp_type = nltool_parse_dumptype(argv[1]); - if (params.dp_type < 0) - goto errout_put; - - get_filter(link, argc, argv, 2, link_cache); - nl_cache_dump_filter(link_cache, ¶ms, (struct nl_object *) link); - nl_cache_free(link_cache); - err = 0; -errout_put: - rtnl_link_put(link); -errout: - nl_close(nlh); - nl_handle_destroy(nlh); - return err; -} diff --git a/src/nl-link-ifindex2name.c b/src/nl-link-ifindex2name.c index e1043fb..109ec46 100644 --- a/src/nl-link-ifindex2name.c +++ b/src/nl-link-ifindex2name.c @@ -6,50 +6,37 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ #include "utils.h" -int main(int argc, char **argv) +static void print_usage(void) { - struct nl_handle *nlh; - struct nl_cache *link_cache; - int err = -1, ifindex; - char dst[32] = {0}; - const char *name; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) { - fprintf(stderr, "Usage: nl-link-ifindex2name <ifindex>\n"); - return -1; - } + printf("Usage: nl-link-ifindex2name <ifindex>\n"); + exit(0); +} - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct nl_cache *link_cache; + char name[IFNAMSIZ]; + uint32_t ifindex; - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout; + if (argc < 2) + print_usage(); - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout; + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); - ifindex = strtoul(argv[1], NULL, 0); + ifindex = parse_u32(argv[1]); - if (!(name = rtnl_link_i2name(link_cache, ifindex, dst, sizeof(dst)))) - fprintf(stderr, "Interface index %d does not exist\n", ifindex); - else - printf("%s\n", name); + if (!rtnl_link_i2name(link_cache, ifindex, name, sizeof(name))) + fatal(ENOENT, "Interface index %d does not exist", ifindex); - nl_cache_free(link_cache); - err = 0; -errout: - nl_close(nlh); - nl_handle_destroy(nlh); + printf("%s\n", name); - return err; + return 0; } diff --git a/src/nl-link-list.c b/src/nl-link-list.c new file mode 100644 index 0000000..3afa5ed --- /dev/null +++ b/src/nl-link-list.c @@ -0,0 +1,105 @@ +/* + * src/nl-link-dump.c Dump link attributes + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> + */ + +#if 0 +static void print_usage(void) +{ + printf( + "Usage: nl-link-dump <mode> [<filter>]\n" + " mode := { brief | detailed | stats | xml }\n" + " filter := [dev DEV] [mtu MTU] [txqlen TXQLEN] [weight WEIGHT] [link LINK]\n" + " [master MASTER] [qdisc QDISC] [addr ADDR] [broadcast BRD]\n" + " [{ up | down }] [{ arp | noarp }] [{ promisc | nopromisc }]\n" + " [{ dynamic | nodynamic }] [{ multicast | nomulticast }]\n" + " [{ trailers | notrailers }] [{ allmulticast | noallmulticast }]\n"); + exit(1); +} +#endif + +#include "link-utils.h" + +static void print_usage(void) +{ + printf( + "Usage: nl-link-list [OPTION]... [Link]\n" + "\n" + "Options\n" + " -f, --format=TYPE Output format { brief | details | stats }\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "Link Options\n" + " -n, --name=NAME link name\n" + " -i, --index interface index\n" + " --mtu=NUM MTU value\n" + " --txqlen=NUM TX queue length\n" + " --weight=NUM weight\n" + ); + exit(0); +} + +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct nl_cache *link_cache; + struct rtnl_link *link; + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + link = nlt_alloc_link(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_FAMILY = 257, + ARG_MTU = 258, + ARG_TXQLEN, + ARG_WEIGHT, + }; + static struct option long_opts[] = { + { "format", 1, 0, 'f' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "name", 1, 0, 'n' }, + { "index", 1, 0, 'i' }, + { "family", 1, 0, ARG_FAMILY }, + { "mtu", 1, 0, ARG_MTU }, + { "txqlen", 1, 0, ARG_TXQLEN }, + { "weight", 1, 0, ARG_WEIGHT }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "f:hvn:i:", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'n': parse_name(link, optarg); break; + case 'i': parse_ifindex(link, optarg); break; + case ARG_FAMILY: parse_family(link, optarg); break; + case ARG_MTU: parse_mtu(link, optarg); break; + case ARG_TXQLEN: parse_txqlen(link, optarg); break; + case ARG_WEIGHT: parse_weight(link, optarg); break; + } + } + + nl_cache_dump_filter(link_cache, ¶ms, OBJ_CAST(link)); + + return 0; +} diff --git a/src/nl-link-name2ifindex.c b/src/nl-link-name2ifindex.c index 993397d..12a61c6 100644 --- a/src/nl-link-name2ifindex.c +++ b/src/nl-link-name2ifindex.c @@ -6,46 +6,34 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ #include "utils.h" +static void print_usage(void) +{ + printf("Usage: nl-link-ifindex2name <ifindex>\n"); + exit(0); +} + int main(int argc, char *argv[]) { - struct nl_handle *nlh; + struct nl_sock *sock; struct nl_cache *link_cache; - int err = -1, ifindex; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) { - printf("Usage: nl-link-name2ifindex <name>\n"); - return -1; - } - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; + uint32_t ifindex; - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout; + if (argc < 2) + print_usage(); - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout; + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); - if ((ifindex = rtnl_link_name2i(link_cache, argv[1])) == RTNL_LINK_NOT_FOUND) - fprintf(stderr, "Interface %s does not exist\n", argv[1]); - else - printf("%d\n", ifindex); + if (!(ifindex = rtnl_link_name2i(link_cache, argv[1]))) + fatal(ENOENT, "Interface \"%s\" does not exist", argv[1]); - nl_cache_free(link_cache); - err = 0; -errout: - nl_close(nlh); - nl_handle_destroy(nlh); + printf("%u\n", ifindex); - return err; + return 0; } diff --git a/src/nl-link-set.c b/src/nl-link-set.c index 1872301..02c35d6 100644 --- a/src/nl-link-set.c +++ b/src/nl-link-set.c @@ -6,78 +6,117 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ -#include "utils.h" +#include "link-utils.h" -static void print_usage(void) -{ - printf( - "Usage: nl-link-set <ifindex> <changes>\n" - " changes := [dev DEV] [mtu MTU] [txqlen TXQLEN] [weight WEIGHT] [link LINK]\n" +static struct nl_sock *sock; +static int quiet = 0; + +#if 0 + " changes := [link LINK]\n" " [master MASTER] [qdisc QDISC] [addr ADDR] [broadcast BRD]\n" " [{ up | down }] [{ arp | noarp }] [{ promisc | nopromisc }]\n" " [{ dynamic | nodynamic }] [{ multicast | nomulticast }]\n" " [{ trailers | notrailers }] [{ allmulticast | noallmulticast }]\n"); - exit(1); +#endif + +static void print_usage(void) +{ + printf( + "Usage: nl-link-set [OPTION]... [LINK]\n" + "\n" + "Options\n" + " -q, --quiet Do not print informal notifications\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "Selecting the Link\n" + " -n, --name=NAME link name\n" + " -i, --index interface index\n" + "Change Options\n" + " --rename=NAME rename interface\n" + " --mtu=NUM MTU value\n" + " --txqlen=NUM TX queue length\n" + " --weight=NUM weight\n" + ); + exit(0); } -#include "f_link.c" +static void set_cb(struct nl_object *obj, void *arg) +{ + struct rtnl_link *link = nl_object_priv(obj); + struct rtnl_link *change = arg; + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + int err; + + if ((err = rtnl_link_change(sock, link, change, 0) < 0)) + fatal(err, "Unable to change link: %s", nl_geterror(err)); + + if (!quiet) { + printf("Changed "); + nl_object_dump(OBJ_CAST(link), ¶ms); + } +} int main(int argc, char *argv[]) { - struct nl_handle *nlh; struct nl_cache *link_cache; - struct rtnl_link *link, *orig; - int err = 1, ifindex; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) - print_usage(); - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - link = rtnl_link_alloc(); - if (!link) - goto errout; - - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout_free; - - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout_close; - - ifindex = strtoul(argv[1], NULL, 0); - - if (!(orig = rtnl_link_get(link_cache, ifindex))) { - fprintf(stderr, "Interface index %d does not exist\n", ifindex); - goto errout_cache; + struct rtnl_link *link, *change; + int ok = 0; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + link = nlt_alloc_link(); + change = nlt_alloc_link(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_RENAME = 257, + ARG_MTU = 258, + ARG_TXQLEN, + ARG_WEIGHT, + }; + static struct option long_opts[] = { + { "quiet", 0, 0, 'q' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "name", 1, 0, 'n' }, + { "index", 1, 0, 'i' }, + { "rename", 1, 0, ARG_RENAME }, + { "mtu", 1, 0, ARG_MTU }, + { "txqlen", 1, 0, ARG_TXQLEN }, + { "weight", 1, 0, ARG_WEIGHT }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "qhvn:i:", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'q': quiet = 1; break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'n': ok++; parse_name(link, optarg); break; + case 'i': ok++; parse_ifindex(link, optarg); break; + case ARG_RENAME: parse_name(change, optarg); break; + case ARG_MTU: parse_mtu(link, optarg); break; + case ARG_TXQLEN: parse_txqlen(link, optarg); break; + case ARG_WEIGHT: parse_weight(link, optarg); break; + } } - get_filter(link, argc, argv, 2, link_cache); - - if (rtnl_link_change(nlh, orig, link, 0) < 0) { - fprintf(stderr, "Unable to change link: %s\n", nl_geterror()); - goto errout_put; - } + if (!ok) + print_usage(); - err = 0; + nl_cache_foreach_filter(link_cache, OBJ_CAST(link), set_cb, change); -errout_put: - rtnl_link_put(orig); -errout_cache: - nl_cache_free(link_cache); -errout_close: - nl_close(nlh); -errout_free: - rtnl_link_put(link); -errout: - nl_handle_destroy(nlh); - return err; + return 0; } diff --git a/src/nl-link-stats.c b/src/nl-link-stats.c index 8a9200e..9203e08 100644 --- a/src/nl-link-stats.c +++ b/src/nl-link-stats.c @@ -6,31 +6,45 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ -#include "utils.h" +#include "link-utils.h" static void print_usage(void) { printf( -"Usage: nl-link-stats <ifindex> [<statistic> ...]\n" -" ifindex := { all | number }\n" -" statistic := { (rx|tx)_packets | (rx|tx)_bytes | (rx|tx)_errors |\n" -" (rx|tx)_dropped | (rx|tx)_compressed | (rx|tx)_fifo_err |\n" \ -" rx_len_err | rx_over_err | rx_crc_err | rx_frame_err |\n" -" rx_missed_err | tx_abort_err | tx_carrier_err |\n" -" tx_hbeat_err | tx_win_err | tx_collision | multicast }\n"); - exit(1); + "Usage: nl-link-stats [OPTION]... [LINK] [ListOfStats]\n" + "\n" + "Options\n" + " -l, --list List available statistic names\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "Link Options\n" + " -n, --name=NAME link name\n" + " -i, --index=NUM interface index\n" + ); + exit(0); +} + +static void list_stat_names(void) +{ + char buf[64]; + int i; + + for (i = 0; i < RTNL_LINK_STATS_MAX; i++) + printf("%s\n", rtnl_link_stat2str(i, buf, sizeof(buf))); + + exit(0); } -static char **gargv; static int gargc; static void dump_stat(struct rtnl_link *link, int id) { uint64_t st = rtnl_link_get_stat(link, id); - char buf[62]; + char buf[64]; printf("%s.%s %" PRIu64 "\n", rtnl_link_get_name(link), rtnl_link_stat2str(id, buf, sizeof(buf)), st); @@ -38,72 +52,67 @@ static void dump_stat(struct rtnl_link *link, int id) static void dump_stats(struct nl_object *obj, void *arg) { - int i; struct rtnl_link *link = (struct rtnl_link *) obj; + char **argv = arg; + + if (optind >= gargc) { + int i; - if (!strcasecmp(gargv[0], "all")) { for (i = 0; i < RTNL_LINK_STATS_MAX; i++) dump_stat(link, i); } else { - for (i = 0; i < gargc; i++) { - int id = rtnl_link_str2stat(gargv[i]); + while (optind < gargc) { + int id = rtnl_link_str2stat(argv[optind]); if (id < 0) fprintf(stderr, "Warning: Unknown statistic " - "\"%s\"\n", gargv[i]); + "\"%s\"\n", argv[optind]); else dump_stat(link, id); + + optind++; } } } int main(int argc, char *argv[]) { - struct nl_handle *nlh; + struct nl_sock *sock; struct nl_cache *link_cache; - int err = 1; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 3 || !strcmp(argv[1], "-h")) - print_usage(); - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout; - - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout_close; - - gargv = &argv[2]; - gargc = argc - 2; - - if (!strcasecmp(argv[1], "all")) - nl_cache_foreach(link_cache, dump_stats, NULL); - else { - int ifindex = strtoul(argv[1], NULL, 0); - struct rtnl_link *link = rtnl_link_get(link_cache, ifindex); - - if (!link) { - fprintf(stderr, "Could not find ifindex %d\n", ifindex); - goto errout_link_cache; + struct rtnl_link *link; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + link = nlt_alloc_link(); + + for (;;) { + int c, optidx = 0; + static struct option long_opts[] = { + { "list", 0, 0, 'l' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "name", 1, 0, 'n' }, + { "index", 1, 0, 'i' }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "lhvn:i:", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'l': list_stat_names(); break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'n': parse_name(link, optarg); break; + case 'i': parse_ifindex(link, optarg); break; } - - dump_stats((struct nl_object *) link, NULL); - rtnl_link_put(link); } - err = 0; -errout_link_cache: - nl_cache_free(link_cache); -errout_close: - nl_close(nlh); -errout: - nl_handle_destroy(nlh); - return err; + gargc = argc; + nl_cache_foreach_filter(link_cache, OBJ_CAST(link), dump_stats, argv); + + return 0; } + diff --git a/src/nl-monitor.c b/src/nl-monitor.c index 9f21dbb..520ac37 100644 --- a/src/nl-monitor.c +++ b/src/nl-monitor.c @@ -6,7 +6,7 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ #include "utils.h" @@ -35,7 +35,7 @@ static int event_input(struct nl_msg *msg, void *arg) int main(int argc, char *argv[]) { - struct nl_handle *nlh; + struct nl_sock *sock; struct nl_cache *link_cache; int err = 1; int i, idx; @@ -61,16 +61,9 @@ int main(int argc, char *argv[]) { RTNLGRP_NONE, NULL } }; - if (nltool_init(argc, argv) < 0) - return -1; - - nlh = nltool_alloc_handle(); - if (nlh == NULL) - return -1; - - nl_disable_sequence_check(nlh); - - nl_socket_modify_cb(nlh, NL_CB_VALID, NL_CB_CUSTOM, event_input, NULL); + sock = nlt_alloc_socket(); + nl_disable_sequence_check(sock); + nl_socket_modify_cb(sock, NL_CB_VALID, NL_CB_CUSTOM, event_input, NULL); if (argc > 1 && !strcasecmp(argv[1], "-h")) { printf("Usage: nl-monitor [<groups>]\n"); @@ -82,18 +75,14 @@ int main(int argc, char *argv[]) return 2; } - if (nl_connect(nlh, NETLINK_ROUTE) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout; - } + nlt_connect(sock, NETLINK_ROUTE); for (idx = 1; argc > idx; idx++) { for (i = 0; known_groups[i].gr_id != RTNLGRP_NONE; i++) { if (!strcmp(argv[idx], known_groups[i].gr_name)) { - if (nl_socket_add_membership(nlh, known_groups[i].gr_id) < 0) { - fprintf(stderr, "%s: %s\n", argv[idx], nl_geterror()); - goto errout; + if ((err = nl_socket_add_membership(sock, known_groups[i].gr_id)) < 0) { + fatal(err, "%s: %s\n", argv[idx], nl_geterror(err)); } break; @@ -103,18 +92,13 @@ int main(int argc, char *argv[]) fprintf(stderr, "Warning: Unknown group: %s\n", argv[idx]); } - if ((link_cache = rtnl_link_alloc_cache(nlh)) == NULL) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_close; - } - - nl_cache_mngt_provide(link_cache); + link_cache = nlt_alloc_link_cache(sock); while (1) { fd_set rfds; int fd, retval; - fd = nl_socket_get_fd(nlh); + fd = nl_socket_get_fd(sock); FD_ZERO(&rfds); FD_SET(fd, &rfds); @@ -123,13 +107,9 @@ int main(int argc, char *argv[]) if (retval) { /* FD_ISSET(fd, &rfds) will be true */ - nl_recvmsgs_default(nlh); + nl_recvmsgs_default(sock); } } - nl_cache_free(link_cache); -errout_close: - nl_close(nlh); -errout: - return err; + return 0; } diff --git a/src/nl-neigh-add.c b/src/nl-neigh-add.c index 14b99de..b222c7a 100644 --- a/src/nl-neigh-add.c +++ b/src/nl-neigh-add.c @@ -6,74 +6,102 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ -#include "utils.h" +#include "neigh-utils.h" -int main(int argc, char *argv[]) -{ - struct nl_handle *nlh; - struct rtnl_neigh *neigh; - struct nl_addr *addr; - int err = 1; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 4 || !strcmp(argv[1], "-h")) { - printf("Usage: nl-neigh-add <addr> <lladdr> " - "<ifindex> [<state>]\n"); - return 1; - } - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - neigh = rtnl_neigh_alloc(); - if (!neigh) - goto errout; +static int quiet = 0; - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout_free; - - addr = nltool_addr_parse(argv[1]); - if (!addr) - goto errout_close; - rtnl_neigh_set_dst(neigh, addr); - nl_addr_put(addr); +static void print_usage(void) +{ + printf( + "Usage: nl-neigh-add [OPTION]... NEIGHBOUR\n" + "\n" + "Options\n" + " --update-only Do not create neighbour, updates exclusively\n" + " --create-only Do not update neighbour if it exists already.\n" + " -q, --quiet Do not print informal notifications\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "Neighbour Options\n" + " -a, --addr=ADDR Destination address of neighbour\n" + " -l, --lladdr=ADDR Link layer address of neighbour\n" + " -d, --dev=DEV Device the neighbour is connected to\n" + " --state=STATE Neighbour state, (default = permanent)\n" + "\n" + "Example\n" + " nl-neigh-add --create-only --addr=10.0.0.1 --dev=eth0 \\\n" + " --lladdr=AA:BB:CC:DD:EE:FF\n" + ); - addr = nltool_addr_parse(argv[2]); - if (!addr) - goto errout_close; - rtnl_neigh_set_lladdr(neigh, addr); - nl_addr_put(addr); + exit(0); +} - rtnl_neigh_set_ifindex(neigh, strtoul(argv[3], NULL, 0)); +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct rtnl_neigh *neigh; + struct nl_cache *link_cache; + struct nl_dump_params dp = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + int err, ok = 0, nlflags = NLM_F_REPLACE | NLM_F_CREATE; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + neigh = nlt_alloc_neigh(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_UPDATE_ONLY = 257, + ARG_CREATE_ONLY = 258, + ARG_STATE, + }; + static struct option long_opts[] = { + { "update-only", 0, 0, ARG_UPDATE_ONLY }, + { "create-only", 0, 0, ARG_CREATE_ONLY }, + { "quiet", 0, 0, 'q' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "addr", 1, 0, 'a' }, + { "lladdr", 1, 0, 'l' }, + { "dev", 1, 0, 'd' }, + { "state", 1, 0, ARG_STATE }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "qhva:l:d:", long_opts, &optidx); + if (c == -1) + break; - if (argc > 4) { - int state = rtnl_neigh_str2state(argv[4]); - if (state < 0) { - fprintf(stderr, "Unknown state \"%s\"\n", argv[4]); - goto errout_close; + switch (c) { + case ARG_UPDATE_ONLY: nlflags &= ~NLM_F_CREATE; break; + case ARG_CREATE_ONLY: nlflags |= NLM_F_EXCL; break; + case 'q': quiet = 1; break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'a': ok++; parse_dst(neigh, optarg); break; + case 'l': parse_lladdr(neigh, optarg); break; + case 'd': parse_dev(neigh, link_cache, optarg); break; + case ARG_STATE: parse_state(neigh, optarg); break; } - rtnl_neigh_set_state(neigh, state); - } else - rtnl_neigh_set_state(neigh, NUD_PERMANENT); + } + + if (!ok) + print_usage(); - if (rtnl_neigh_add(nlh, neigh, 0) < 0) { - fprintf(stderr, "Unable to add address: %s\n", nl_geterror()); - goto errout_close; - } + if ((err = rtnl_neigh_add(sock, neigh, nlflags)) < 0) + fatal(err, "Unable to add neighbour: %s", nl_geterror(err)); - err = 0; + if (!quiet) { + printf("Added "); + nl_object_dump(OBJ_CAST(neigh), &dp); + } -errout_close: - nl_close(nlh); -errout_free: - rtnl_neigh_put(neigh); -errout: - nl_handle_destroy(nlh); - return err; + return 0; } diff --git a/src/nl-neigh-delete.c b/src/nl-neigh-delete.c index 7829d34..c9facb9 100644 --- a/src/nl-neigh-delete.c +++ b/src/nl-neigh-delete.c @@ -6,61 +6,114 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ -#include "utils.h" +#include "neigh-utils.h" -int main(int argc, char *argv[]) +static int quiet = 0, default_yes = 0, deleted = 0, interactive = 0; +struct nl_sock *sock; + +static void print_usage(void) { - struct nl_handle *nlh; - struct rtnl_neigh *neigh; - struct nl_addr *addr; - int err = 1; + printf( + "Usage: nl-neigh-delete [OPTION]... [NEIGHBOUR]\n" + "\n" + "Options\n" + " -i, --interactive Run interactively\n" + " --yes Set default answer to yes\n" + " -q, --quiet Do not print informal notifications\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "Neighbour Options\n" + " -a, --addr=ADDR Destination address of neighbour\n" + " -l, --lladdr=ADDR Link layer address of neighbour\n" + " -d, --dev=DEV Device the neighbour is connected to\n" + " --family=FAMILY Destination address family\n" + " --state=STATE Neighbour state, (default = permanent)\n" + ); - if (nltool_init(argc, argv) < 0) - return -1; + exit(0); +} - if (argc < 3 || !strcmp(argv[1], "-h")) { - printf("Usage: nl-neigh-delete <addr> <ifindex>\n"); - return 2; - } +static void delete_cb(struct nl_object *obj, void *arg) +{ + struct rtnl_neigh *neigh = nl_object_priv(obj); + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + int err; - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; + if (interactive && !nlt_confirm(obj, ¶ms, default_yes)) + return; - neigh = rtnl_neigh_alloc(); - if (neigh == NULL) - goto errout; + if ((err = rtnl_neigh_delete(sock, neigh, 0)) < 0) + fatal(err, "Unable to delete neighbour: %s\n", nl_geterror(err)); - if (nl_connect(nlh, NETLINK_ROUTE) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_free; + if (!quiet) { + printf("Deleted "); + nl_object_dump(obj, ¶ms); } - addr = nl_addr_parse(argv[1], AF_UNSPEC); - if (addr == NULL) { - fprintf(stderr, "Invalid address \"%s\"\n", argv[1]); - goto errout_close; - } - rtnl_neigh_set_dst(neigh, addr); - nl_addr_put(addr); + deleted++; +} + +int main(int argc, char *argv[]) +{ + struct rtnl_neigh *neigh; + struct nl_cache *link_cache, *neigh_cache; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + neigh_cache = nlt_alloc_neigh_cache(sock); + neigh = nlt_alloc_neigh(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_FAMILY = 257, + ARG_STATE = 258, + ARG_YES, + }; + static struct option long_opts[] = { + { "interactive", 0, 0, 'i' }, + { "yes", 0, 0, ARG_YES }, + { "quiet", 0, 0, 'q' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "addr", 1, 0, 'a' }, + { "lladdr", 1, 0, 'l' }, + { "dev", 1, 0, 'd' }, + { "family", 1, 0, ARG_FAMILY }, + { "state", 1, 0, ARG_STATE }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "qhva:l:d:", long_opts, &optidx); + if (c == -1) + break; - rtnl_neigh_set_ifindex(neigh, strtoul(argv[2], NULL, 0)); + switch (c) { + case 'i': interactive = 1; break; + case ARG_YES: default_yes = 1; break; + case 'q': quiet = 1; break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'a': parse_dst(neigh, optarg); break; + case 'l': parse_lladdr(neigh, optarg); break; + case 'd': parse_dev(neigh, link_cache, optarg); break; + case ARG_FAMILY: parse_family(neigh, optarg); break; + case ARG_STATE: parse_state(neigh, optarg); break; + } + } - if (rtnl_neigh_delete(nlh, neigh, 0) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_close; - } + nl_cache_foreach_filter(neigh_cache, OBJ_CAST(neigh), delete_cb, NULL); - err = 0; + if (!quiet) + printf("Deleted %d neighbours\n", deleted); -errout_close: - nl_close(nlh); -errout_free: - rtnl_neigh_put(neigh); -errout: - nl_handle_destroy(nlh); - return err; + return 0; } diff --git a/src/nl-neigh-dump.c b/src/nl-neigh-dump.c deleted file mode 100644 index 4553f2e..0000000 --- a/src/nl-neigh-dump.c +++ /dev/null @@ -1,82 +0,0 @@ -/* - * src/nl-neigh-dump.c Dump neighbour attributes - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - */ - -#include "utils.h" - -static void print_usage(void) -{ - printf( - "Usage: nl-neigh-dump <mode> [<filter>]\n" - " mode := { brief | detailed | stats | xml }\n" - " filter := [dev DEV] [dst ADDR] [lladdr ADDR]\n"); - exit(1); -} - -#include "f_neigh.c" - -int main(int argc, char *argv[]) -{ - struct nl_handle *nlh; - struct nl_cache *link_cache, *neigh_cache; - struct rtnl_neigh *neigh; - struct nl_dump_params params = { - .dp_fd = stdout, - .dp_type = NL_DUMP_BRIEF - }; - int err = 1; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) - print_usage(); - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - neigh = rtnl_neigh_alloc(); - if (neigh == NULL) - goto errout; - - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout_free; - - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout_close; - - neigh_cache = nltool_alloc_neigh_cache(nlh); - if (!neigh_cache) - goto errout_link_cache; - - params.dp_type = nltool_parse_dumptype(argv[1]); - if (params.dp_type < 0) - goto errout_neigh_cache; - - get_filter(neigh, argc, argv, 2, neigh_cache); - - nl_cache_dump_filter(neigh_cache, ¶ms, (struct nl_object *) neigh); - - err = 0; - -errout_neigh_cache: - nl_cache_free(neigh_cache); -errout_link_cache: - nl_cache_free(link_cache); -errout_close: - nl_close(nlh); -errout_free: - rtnl_neigh_put(neigh); -errout: - nl_handle_destroy(nlh); - return err; -} diff --git a/src/nl-neigh-list.c b/src/nl-neigh-list.c new file mode 100644 index 0000000..aa766d5 --- /dev/null +++ b/src/nl-neigh-list.c @@ -0,0 +1,87 @@ +/* + * src/nl-neigh-list.c List Neighbours + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "neigh-utils.h" + +static void print_usage(void) +{ + printf( + "Usage: nl-neigh-list [OPTION]... [NEIGHBOUR]\n" + "\n" + "Options\n" + " -f, --format=TYPE Output format { brief | details | stats }\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "Neighbour Options\n" + " -a, --addr=ADDR Destination address of neighbour\n" + " -l, --lladdr=ADDR Link layer address of neighbour\n" + " -d, --dev=DEV Device the neighbour is connected to\n" + " --family=FAMILY Destination address family\n" + " --state=STATE Neighbour state, (default = permanent)\n" + ); + exit(0); +} + +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct rtnl_neigh *neigh; + struct nl_cache *link_cache, *neigh_cache; + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + neigh_cache = nlt_alloc_neigh_cache(sock); + neigh = nlt_alloc_neigh(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_FAMILY = 257, + ARG_STATE = 258, + }; + static struct option long_opts[] = { + { "format", 1, 0, 'f' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "addr", 1, 0, 'a' }, + { "lladdr", 1, 0, 'l' }, + { "dev", 1, 0, 'd' }, + { "family", 1, 0, ARG_FAMILY }, + { "state", 1, 0, ARG_STATE }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "f:hva:l:d:", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'a': parse_dst(neigh, optarg); break; + case 'l': parse_lladdr(neigh, optarg); break; + case 'd': parse_dev(neigh, link_cache, optarg); break; + case ARG_FAMILY: parse_family(neigh, optarg); break; + case ARG_STATE: parse_state(neigh, optarg); break; + } + } + + nl_cache_dump_filter(neigh_cache, ¶ms, OBJ_CAST(neigh)); + + return 0; +} diff --git a/src/nl-neightbl-dump.c b/src/nl-neightbl-dump.c deleted file mode 100644 index 0d79711..0000000 --- a/src/nl-neightbl-dump.c +++ /dev/null @@ -1,70 +0,0 @@ -/* - * src/nl-neightbl-dump.c Dump neighbour tables - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - */ - -#include "utils.h" - -static void print_usage(void) -{ - printf( - "Usage: nl-neightbl-dump <mode> [<filter>]\n" - " mode := { brief | detailed | stats | xml }\n" - " filter :=\n"); - exit(1); -} - -int main(int argc, char *argv[]) -{ - int err = -1; - struct nl_handle *nlh; - struct nl_cache *ntc, *lc; - struct nl_dump_params params = { - .dp_fd = stdout, - .dp_type = NL_DUMP_BRIEF, - }; - - if (argc < 2) - print_usage(); - - if (nltool_init(argc, argv) < 0) - return -1; - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout; - - ntc = nltool_alloc_neightbl_cache(nlh); - if (!ntc) - goto errout_close; - - lc = nltool_alloc_link_cache(nlh); - if (!lc) - goto errout_ntbl_cache; - - params.dp_type = nltool_parse_dumptype(argv[1]); - if (params.dp_type < 0) - goto errout_link_cache; - - nl_cache_dump(ntc, ¶ms); - err = 0; - -errout_link_cache: - nl_cache_free(lc); -errout_ntbl_cache: - nl_cache_free(ntc); -errout_close: - nl_close(nlh); -errout: - nl_handle_destroy(nlh); - return err; -} diff --git a/src/nl-neightbl-list.c b/src/nl-neightbl-list.c new file mode 100644 index 0000000..4e5acc6 --- /dev/null +++ b/src/nl-neightbl-list.c @@ -0,0 +1,64 @@ +/* + * src/nl-neightbl-list.c Dump neighbour tables + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "utils.h" + +static void print_usage(void) +{ + printf( + "Usage: nl-neightbl-list [OPTION]...\n" + "\n" + "Options\n" + " -f, --format=TYPE Output format { brief | details | stats }\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + ); + exit(0); +} + +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct nl_cache *link_cache, *neightbl_cache; + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + neightbl_cache = nlt_alloc_neightbl_cache(sock); + + for (;;) { + int c, optidx = 0; + static struct option long_opts[] = { + { "format", 1, 0, 'f' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "f:hv", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + } + } + + nl_cache_dump(neightbl_cache, ¶ms); + + return 0; +} diff --git a/src/nl-qdisc-delete.c b/src/nl-qdisc-delete.c index b8a17ca..32523b7 100644 --- a/src/nl-qdisc-delete.c +++ b/src/nl-qdisc-delete.c @@ -1,76 +1,114 @@ /* - * src/nl-qdisc-delete.c Delete Qdiscs + * src/nl-qdisc-delete.c Delete Queuing Disciplines * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ -#include "utils.h" +#include "qdisc-utils.h" + +static int quiet = 0, default_yes = 0, deleted = 0, interactive = 0; +struct nl_sock *sock; static void print_usage(void) { - printf("Usage: nl-qdisc-delete <ifindex> <parent> <handle>\n"); - exit(1); + printf( + "Usage: nl-qdisc-delete [OPTION]... [QDISC]\n" + "\n" + "Options\n" + " -i, --interactive Run interactively\n" + " --yes Set default answer to yes\n" + " -q, --quiet Do not print informal notifications\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "QDisc Options\n" + " -d, --dev=DEV Device the qdisc is attached to\n" + " -p, --parent=HANDLE Identifier of parent qdisc\n" + " -H, --handle=HANDLE Identifier\n" + " -k, --kind=NAME Kind of qdisc (e.g. pfifo_fast)\n" + ); + + exit(0); } -int main(int argc, char *argv[]) +static void delete_cb(struct nl_object *obj, void *arg) { - struct nl_handle *nlh; - struct rtnl_qdisc *qdisc; - uint32_t handle, parent; - int err = 1; + struct rtnl_qdisc *qdisc = nl_object_priv(obj); + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + int err; - if (nltool_init(argc, argv) < 0) - return -1; + if (interactive && !nlt_confirm(obj, ¶ms, default_yes)) + return; - if (argc < 3 || !strcmp(argv[1], "-h")) - print_usage(); + if ((err = rtnl_qdisc_delete(sock, qdisc)) < 0) + fatal(err, "Unable to delete qdisc: %s\n", nl_geterror(err)); - nlh = nltool_alloc_handle(); - if (!nlh) - goto errout; - - qdisc = rtnl_qdisc_alloc(); - if (!qdisc) - goto errout_free_handle; - - rtnl_qdisc_set_ifindex(qdisc, strtoul(argv[1], NULL, 0)); - - if (rtnl_tc_str2handle(argv[2], &parent) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_free_qdisc; + if (!quiet) { + printf("Deleted "); + nl_object_dump(obj, ¶ms); } - if (argc > 3) { - if (rtnl_tc_str2handle(argv[3], &handle) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_free_qdisc; - } + deleted++; +} - rtnl_qdisc_set_handle(qdisc, handle); - } +int main(int argc, char *argv[]) +{ + struct rtnl_qdisc *qdisc; + struct nl_cache *link_cache, *qdisc_cache; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + qdisc_cache = nlt_alloc_qdisc_cache(sock); + qdisc = nlt_alloc_qdisc(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_YES = 257, + }; + static struct option long_opts[] = { + { "interactive", 0, 0, 'i' }, + { "yes", 0, 0, ARG_YES }, + { "quiet", 0, 0, 'q' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "dev", 1, 0, 'd' }, + { "parent", 1, 0, 'p' }, + { "handle", 1, 0, 'H' }, + { "kind", 1, 0, 'k' }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "iqhvd:p:H:k:", long_opts, &optidx); + if (c == -1) + break; - rtnl_qdisc_set_parent(qdisc, parent); + switch (c) { + case 'i': interactive = 1; break; + case ARG_YES: default_yes = 1; break; + case 'q': quiet = 1; break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'd': parse_dev(qdisc, link_cache, optarg); break; + case 'p': parse_parent(qdisc, optarg); break; + case 'H': parse_handle(qdisc, optarg); break; + case 'k': parse_kind(qdisc, optarg); break; + } + } - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout_free_qdisc; + nl_cache_foreach_filter(qdisc_cache, OBJ_CAST(qdisc), delete_cb, NULL); - if (rtnl_qdisc_delete(nlh, qdisc) < 0) { - fprintf(stderr, "Unable to delete Qdisc: %s\n", nl_geterror()); - goto errout_close; - } + if (!quiet) + printf("Deleted %d qdiscs\n", deleted); - err = 0; -errout_close: - nl_close(nlh); -errout_free_qdisc: - rtnl_qdisc_put(qdisc); -errout_free_handle: - nl_handle_destroy(nlh); -errout: - return err; + return 0; } diff --git a/src/nl-qdisc-dump.c b/src/nl-qdisc-dump.c deleted file mode 100644 index 167dc7f..0000000 --- a/src/nl-qdisc-dump.c +++ /dev/null @@ -1,74 +0,0 @@ -/* - * src/nl-qdisc-dump.c Dump qdisc attributes - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - */ - -#include "utils.h" - -static void print_usage(void) -{ - printf( -"Usage: nl-qdisc-dump <mode>\n" -" mode := { brief | detailed | stats | xml }\n"); - exit(1); -} - -int main(int argc, char *argv[]) -{ - struct nl_handle *nlh; - struct nl_cache *link_cache, *qdisc_cache; - struct rtnl_qdisc *qdisc; - struct nl_dump_params params = { - .dp_fd = stdout, - .dp_type = NL_DUMP_BRIEF - }; - int err = 1; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) - print_usage(); - - params.dp_type = nltool_parse_dumptype(argv[1]); - if (params.dp_type < 0) - return -1; - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - qdisc = rtnl_qdisc_alloc(); - if (!qdisc) - goto errout_no_put; - - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout; - - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout; - - qdisc_cache = nltool_alloc_qdisc_cache(nlh); - if (!qdisc_cache) - goto errout_link_cache; - - nl_cache_dump_filter(qdisc_cache, ¶ms, (struct nl_object *) qdisc); - nl_cache_free(qdisc_cache); - err = 0; - -errout_link_cache: - nl_cache_free(link_cache); -errout: - rtnl_qdisc_put(qdisc); -errout_no_put: - nl_close(nlh); - nl_handle_destroy(nlh); - return err; -} diff --git a/src/nl-qdisc-list.c b/src/nl-qdisc-list.c new file mode 100644 index 0000000..bad3817 --- /dev/null +++ b/src/nl-qdisc-list.c @@ -0,0 +1,88 @@ +/* + * src/nl-qdisc-list.c List Qdiscs + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "qdisc-utils.h" + +static int quiet = 0; + +static void print_usage(void) +{ + printf( + "Usage: nl-qdisc-list [OPTION]... [QDISC]\n" + "\n" + "Options\n" + " -f, --format=TYPE Output format { brief | details | stats }\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "QDisc Options\n" + " -d, --dev=DEV Device the qdisc is attached to\n" + " -p, --parent=HANDLE Identifier of parent qdisc\n" + " -H, --handle=HANDLE Identifier\n" + " -k, --kind=NAME Kind of qdisc (e.g. pfifo_fast)\n" + ); + exit(0); +} + +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct rtnl_qdisc *qdisc; + struct nl_cache *link_cache, *qdisc_cache; + struct nl_dump_params params = { + .dp_type = NL_DUMP_ONELINE, + .dp_fd = stdout, + }; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + qdisc_cache = nlt_alloc_qdisc_cache(sock); + qdisc = nlt_alloc_qdisc(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_YES = 257, + }; + static struct option long_opts[] = { + { "format", 1, 0, 'f' }, + { "quiet", 0, 0, 'q' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "dev", 1, 0, 'd' }, + { "parent", 1, 0, 'p' }, + { "handle", 1, 0, 'H' }, + { "kind", 1, 0, 'k' }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "f:qhvd:p:H:k:", + long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; + case 'q': quiet = 1; break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case 'd': parse_dev(qdisc, link_cache, optarg); break; + case 'p': parse_parent(qdisc, optarg); break; + case 'H': parse_handle(qdisc, optarg); break; + case 'k': parse_kind(qdisc, optarg); break; + } + } + + nl_cache_dump_filter(qdisc_cache, ¶ms, OBJ_CAST(qdisc)); + + return 0; +} diff --git a/src/nl-route-add.c b/src/nl-route-add.c index f411b30..9c3c36a 100644 --- a/src/nl-route-add.c +++ b/src/nl-route-add.c @@ -14,12 +14,6 @@ static int quiet = 0; static struct nl_cache *link_cache, *route_cache; -static void print_version(void) -{ - fprintf(stderr, "%s\n", LIBNL_STRING); - exit(0); -} - static void print_usage(void) { printf( @@ -55,7 +49,7 @@ static void print_usage(void) int main(int argc, char *argv[]) { - struct nl_handle *nlh; + struct nl_handle *sock; struct rtnl_route *route; struct nl_dump_params dp = { .dp_type = NL_DUMP_ONELINE, @@ -63,14 +57,11 @@ int main(int argc, char *argv[]) }; int err = 1; - nlh = nltool_alloc_handle(); - nltool_connect(nlh, NETLINK_ROUTE); - link_cache = nltool_alloc_link_cache(nlh); - route_cache = nltool_alloc_route_cache(nlh, 0); - - route = rtnl_route_alloc(); - if (!route) - goto errout; + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + route_cache = nlt_alloc_route_cache(sock, 0); + route = nlt_alloc_route(); for (;;) { int c, optidx = 0; @@ -111,7 +102,7 @@ int main(int argc, char *argv[]) switch (c) { case 'q': quiet = 1; break; case 'h': print_usage(); break; - case 'v': print_version(); break; + case 'v': nlt_print_version(); break; case 'd': parse_dst(route, optarg); break; case 'n': parse_nexthop(route, optarg, link_cache); break; case 't': parse_table(route, optarg); break; @@ -127,24 +118,13 @@ int main(int argc, char *argv[]) } } - if (rtnl_route_add(nlh, route, 0) < 0) { - fprintf(stderr, "rtnl_route_add failed: %s\n", nl_geterror()); - goto errout_free; - } + if ((err = rtnl_route_add(sock, route, 0)) < 0) + fatal(err, "Unable to add route: %s", nl_geterror(err)); if (!quiet) { printf("Added "); nl_object_dump(OBJ_CAST(route), &dp); } - err = 0; -errout_free: - rtnl_route_put(route); -errout: - nl_cache_free(route_cache); - nl_cache_free(link_cache); - nl_close(nlh); - nl_handle_destroy(nlh); - - return err; + return 0; } diff --git a/src/nl-route-delete.c b/src/nl-route-delete.c index 78403f6..5a442b5 100644 --- a/src/nl-route-delete.c +++ b/src/nl-route-delete.c @@ -13,7 +13,7 @@ static int interactive = 0, default_yes = 0, quiet = 0; static int deleted = 0; -static struct nl_handle *nlh; +static struct nl_handle *sock; static void print_version(void) { @@ -59,36 +59,21 @@ static void print_usage(void) static void delete_cb(struct nl_object *obj, void *arg) { struct rtnl_route *route = (struct rtnl_route *) obj; - struct nl_dump_params dp = { + struct nl_dump_params params = { .dp_type = NL_DUMP_ONELINE, .dp_fd = stdout, }; int err; - if (interactive) { - int answer; + if (interactive && !nlt_confirm(obj, ¶ms, default_yes)) + return; - nl_object_dump(obj, &dp); - printf("Delete? (%c/%c) ", - default_yes ? 'Y' : 'y', - default_yes ? 'n' : 'N'); - - do { - answer = tolower(getchar()); - if (answer == '\n') - answer = default_yes ? 'y' : 'n'; - } while (answer != 'y' && answer != 'n'); - - if (answer == 'n') - return; - } - - if ((err = rtnl_route_delete(nlh, route, 0)) < 0) - fatal(err, "rtnl_route_del failed: %s\n", nl_geterror()); + if ((err = rtnl_route_delete(sock, route, 0)) < 0) + fatal(err, "Unable to delete route: %s", nl_geterror(err)); if (!quiet) { printf("Deleted "); - nl_object_dump(obj, &dp); + nl_object_dump(obj, ¶ms); } deleted++; @@ -98,16 +83,13 @@ int main(int argc, char *argv[]) { struct nl_cache *link_cache, *route_cache; struct rtnl_route *route; - int err = 1, nf = 0; + int nf = 0; - nlh = nltool_alloc_handle(); - nltool_connect(nlh, NETLINK_ROUTE); - link_cache = nltool_alloc_link_cache(nlh); - route_cache = nltool_alloc_route_cache(nlh, 0); - - route = rtnl_route_alloc(); - if (!route) - goto errout; + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + route_cache = nlt_alloc_route_cache(sock, 0); + route = nlt_alloc_route(); for (;;) { int c, optidx = 0; @@ -180,14 +162,5 @@ int main(int argc, char *argv[]) if (!quiet) printf("Deleted %d routes\n", deleted); - err = 0; - - rtnl_route_put(route); -errout: - nl_cache_free(route_cache); - nl_cache_free(link_cache); - nl_close(nlh); - nl_handle_destroy(nlh); - - return err; + return 0; } diff --git a/src/nl-route-get.c b/src/nl-route-get.c index dbd8648..ce267ec 100644 --- a/src/nl-route-get.c +++ b/src/nl-route-get.c @@ -6,7 +6,7 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ #include "utils.h" @@ -17,48 +17,43 @@ static void print_usage(void) exit(1); } +static void parse_cb(struct nl_object *obj, void *arg) +{ + //struct rtnl_route *route = (struct rtnl_route *) obj; + struct nl_dump_params params = { + .dp_fd = stdout, + .dp_type = NL_DUMP_DETAILS, + }; + + nl_object_dump(obj, ¶ms); +} + static int cb(struct nl_msg *msg, void *arg) { - nl_cache_parse_and_add(arg, msg); + int err; + + if ((err = nl_msg_parse(msg, &parse_cb, NULL)) < 0) + fatal(err, "Unable to parse object: %s", nl_geterror(err)); return 0; } int main(int argc, char *argv[]) { - struct nl_handle *nlh; + struct nl_sock *sock; struct nl_cache *link_cache, *route_cache; struct nl_addr *dst; - struct nl_dump_params params = { - .dp_fd = stdout, - .dp_type = NL_DUMP_BRIEF - }; int err = 1; if (argc < 2 || !strcmp(argv[1], "-h")) print_usage(); - if (nltool_init(argc, argv) < 0) - goto errout; - - nlh = nltool_alloc_handle(); - if (!nlh) - goto errout; - - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout_free_handle; - - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout_close; + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + route_cache = nlt_alloc_route_cache(sock, 0); - dst = nltool_addr_parse(argv[1]); - if (!dst) - goto errout_link_cache; - - route_cache = nltool_alloc_route_cache(nlh, 0); - if (!route_cache) - goto errout_addr_put; + dst = nlt_addr_parse(argv[1], AF_INET); { struct nl_msg *m; @@ -71,36 +66,18 @@ int main(int argc, char *argv[]) nlmsg_append(m, &rmsg, sizeof(rmsg), NLMSG_ALIGNTO); nla_put_addr(m, RTA_DST, dst); - if ((err = nl_send_auto_complete(nlh, m)) < 0) { - nlmsg_free(m); - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_route_cache; - } - + err = nl_send_auto_complete(sock, m); nlmsg_free(m); + if (err < 0) + fatal(err, "%s", nl_geterror(err)); - nl_socket_modify_cb(nlh, NL_CB_VALID, NL_CB_CUSTOM, cb, - route_cache); + nl_socket_modify_cb(sock, NL_CB_VALID, NL_CB_CUSTOM, cb, NULL); - if (nl_recvmsgs_default(nlh) < 0) { - fprintf(stderr, "%s\n", nl_geterror()); - goto errout_route_cache; - } + if (nl_recvmsgs_default(sock) < 0) + fatal(err, "%s", nl_geterror(err)); } - nl_cache_dump(route_cache, ¶ms); - - err = 0; -errout_route_cache: - nl_cache_free(route_cache); -errout_addr_put: - nl_addr_put(dst); -errout_link_cache: - nl_cache_free(link_cache); -errout_close: - nl_close(nlh); -errout_free_handle: - nl_handle_destroy(nlh); -errout: - return err; + //nl_cache_dump(route_cache, ¶ms); + + return 0; } diff --git a/src/nl-route-list.c b/src/nl-route-list.c index 9999a02..02b4851 100644 --- a/src/nl-route-list.c +++ b/src/nl-route-list.c @@ -11,12 +11,6 @@ #include "route-utils.h" -static void print_version(void) -{ - fprintf(stderr, "%s\n", LIBNL_STRING); - exit(0); -} - static void print_usage(void) { printf( @@ -53,22 +47,19 @@ static void print_usage(void) int main(int argc, char *argv[]) { - struct nl_handle *nlh; + struct nl_sock *sock; struct nl_cache *link_cache, *route_cache; struct rtnl_route *route; struct nl_dump_params params = { .dp_fd = stdout, .dp_type = NL_DUMP_BRIEF }; - int err = 1, print_cache = 0; + int print_cache = 0; - nlh = nltool_alloc_handle(); - nltool_connect(nlh, NETLINK_ROUTE); - link_cache = nltool_alloc_link_cache(nlh); - - route = rtnl_route_alloc(); - if (!route) - goto errout; + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + route = nlt_alloc_route(); for (;;) { int c, optidx = 0; @@ -109,9 +100,9 @@ int main(int argc, char *argv[]) switch (c) { case 'c': print_cache = 1; break; - case 'f': params.dp_type = nltool_parse_dumptype(optarg); break; + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; case 'h': print_usage(); break; - case 'v': print_version(); break; + case 'v': nlt_print_version(); break; case 'd': parse_dst(route, optarg); break; case 'n': parse_nexthop(route, optarg, link_cache); break; case 't': parse_table(route, optarg); break; @@ -127,19 +118,10 @@ int main(int argc, char *argv[]) } } - route_cache = nltool_alloc_route_cache(nlh, + route_cache = nlt_alloc_route_cache(sock, print_cache ? ROUTE_CACHE_CONTENT : 0); nl_cache_dump_filter(route_cache, ¶ms, OBJ_CAST(route)); - err = 0; - - rtnl_route_put(route); - nl_cache_free(route_cache); -errout: - nl_cache_free(link_cache); - nl_close(nlh); - nl_handle_destroy(nlh); - - return err; + return 0; } diff --git a/src/nl-rule-dump.c b/src/nl-rule-dump.c deleted file mode 100644 index f9e483a..0000000 --- a/src/nl-rule-dump.c +++ /dev/null @@ -1,78 +0,0 @@ -/* - * src/nl-rule-dump.c Dump rule attributes - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation version 2.1 - * of the License. - * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> - */ - -#include "utils.h" - -static void print_usage(void) -{ - printf( - "Usage: nl-rule-dump <mode> [<filter>]\n" - " mode := { brief | detailed | stats | xml }\n"); - exit(1); -} - -int main(int argc, char *argv[]) -{ - struct nl_handle *nlh; - struct nl_cache *link_cache, *rule_cache; - struct rtnl_rule *rule; - struct nl_dump_params params = { - .dp_fd = stdout, - .dp_type = NL_DUMP_BRIEF - }; - int err = 1; - - if (nltool_init(argc, argv) < 0) - return -1; - - if (argc < 2 || !strcmp(argv[1], "-h")) - print_usage(); - - nlh = nltool_alloc_handle(); - if (!nlh) - return -1; - - rule = rtnl_rule_alloc(); - if (!rule) - goto errout; - - if (nltool_connect(nlh, NETLINK_ROUTE) < 0) - goto errout_free; - - link_cache = nltool_alloc_link_cache(nlh); - if (!link_cache) - goto errout_close; - - rule_cache = nltool_alloc_rule_cache(nlh); - if (!rule_cache) - goto errout_link_cache; - - params.dp_type = nltool_parse_dumptype(argv[1]); - if (params.dp_type < 0) - goto errout_rule_cache; - - //get_filter(route, argc, argv, 2, route_cache); - - nl_cache_dump_filter(rule_cache, ¶ms, (struct nl_object *) rule); - - err = 0; - -errout_rule_cache: - nl_cache_free(rule_cache); -errout_link_cache: - nl_cache_free(link_cache); -errout_close: - nl_close(nlh); -errout_free: - nl_object_put((struct nl_object *) rule); -errout: - return err; -} diff --git a/src/nl-rule-list.c b/src/nl-rule-list.c new file mode 100644 index 0000000..7541d0a --- /dev/null +++ b/src/nl-rule-list.c @@ -0,0 +1,75 @@ +/* + * src/nl-rule-dump.c Dump rule attributes + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "rule-utils.h" + +static void print_usage(void) +{ + printf( + "Usage: nl-rule-list [OPTION]... [ROUTE]\n" + "\n" + "Options\n" + " -c, --cache List the contents of the route cache\n" + " -f, --format=TYPE Output format { brief | details | stats }\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + "\n" + "Rule Options\n" + " --family Address family\n" + ); + exit(0); +} + +int main(int argc, char *argv[]) +{ + struct nl_sock *sock; + struct rtnl_rule *rule; + struct nl_cache *link_cache, *rule_cache; + struct nl_dump_params params = { + .dp_fd = stdout, + .dp_type = NL_DUMP_BRIEF + }; + + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + rule_cache = nlt_alloc_rule_cache(sock); + rule = nlt_alloc_rule(); + + for (;;) { + int c, optidx = 0; + enum { + ARG_FAMILY = 257, + }; + static struct option long_opts[] = { + { "format", 1, 0, 'f' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { "family", 1, 0, ARG_FAMILY }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "f:hv", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + case ARG_FAMILY: parse_family(rule, optarg); break; + } + } + + nl_cache_dump_filter(rule_cache, ¶ms, OBJ_CAST(rule)); + + return 0; +} diff --git a/src/nl-tctree-dump.c b/src/nl-tctree-list.c index 8b45e7b..6f6bf56 100644 --- a/src/nl-tctree-dump.c +++ b/src/nl-tctree-list.c @@ -1,26 +1,39 @@ /* - * src/nl-tctree-dump.c Dump Traffic Control Tree + * src/nl-tctree-list.c List Traffic Control Tree * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ #include "utils.h" #include <linux/pkt_sched.h> -static struct nl_handle *nl_handle; +static struct nl_sock *sock; static struct nl_cache *qdisc_cache, *class_cache; -static struct nl_dump_params dump_params = { - .dp_type = NL_DUMP_FULL, +static struct nl_dump_params params = { + .dp_type = NL_DUMP_DETAILS, }; static int ifindex; static void print_qdisc(struct nl_object *, void *); +static void print_usage(void) +{ + printf( + "Usage: nl-tctree-list [OPTION]...\n" + "\n" + "Options\n" + " -f, --format=TYPE Output format { brief | details | stats }\n" + " -h, --help Show this help\n" + " -v, --version Show versioning information\n" + ); + exit(0); +} + static void print_class(struct nl_object *obj, void *arg) { struct rtnl_qdisc *leaf; @@ -28,8 +41,8 @@ static void print_class(struct nl_object *obj, void *arg) struct nl_cache *cls_cache; uint32_t parent = rtnl_class_get_handle(class); - dump_params.dp_prefix = (int)(long) arg; - nl_object_dump(obj, &dump_params); + params.dp_prefix = (int)(long) arg; + nl_object_dump(obj, ¶ms); leaf = rtnl_class_leaf_qdisc(class, qdisc_cache); if (leaf) @@ -37,12 +50,11 @@ static void print_class(struct nl_object *obj, void *arg) rtnl_class_foreach_child(class, class_cache, &print_class, arg + 2); - cls_cache = rtnl_cls_alloc_cache(nl_handle, ifindex, parent); - if (!cls_cache) + if (rtnl_cls_alloc_cache(sock, ifindex, parent, &cls_cache) < 0) return; - dump_params.dp_prefix = (int)(long) arg + 2; - nl_cache_dump(cls_cache, &dump_params); + params.dp_prefix = (int)(long) arg + 2; + nl_cache_dump(cls_cache, ¶ms); nl_cache_free(cls_cache); } @@ -52,17 +64,16 @@ static void print_qdisc(struct nl_object *obj, void *arg) struct nl_cache *cls_cache; uint32_t parent = rtnl_qdisc_get_handle(qdisc); - dump_params.dp_prefix = (int)(long) arg; - nl_object_dump(obj, &dump_params); + params.dp_prefix = (int)(long) arg; + nl_object_dump(obj, ¶ms); rtnl_qdisc_foreach_child(qdisc, class_cache, &print_class, arg + 2); - cls_cache = rtnl_cls_alloc_cache(nl_handle, ifindex, parent); - if (!cls_cache) + if (rtnl_cls_alloc_cache(sock, ifindex, parent, &cls_cache) < 0) return; - dump_params.dp_prefix = (int)(long) arg + 2; - nl_cache_dump(cls_cache, &dump_params); + params.dp_prefix = (int)(long) arg + 2; + nl_cache_dump(cls_cache, ¶ms); nl_cache_free(cls_cache); } @@ -72,11 +83,10 @@ static void print_link(struct nl_object *obj, void *arg) struct rtnl_qdisc *qdisc; ifindex = rtnl_link_get_ifindex(link); - dump_params.dp_prefix = 0; - nl_object_dump(obj, &dump_params); + params.dp_prefix = 0; + nl_object_dump(obj, ¶ms); - class_cache = rtnl_class_alloc_cache(nl_handle, ifindex); - if (!class_cache) + if (rtnl_class_alloc_cache(sock, ifindex, &class_cache) < 0) return; qdisc = rtnl_qdisc_get_by_parent(qdisc_cache, ifindex, TC_H_ROOT); @@ -104,41 +114,34 @@ int main(int argc, char *argv[]) { struct nl_cache *link_cache; - if (nltool_init(argc, argv) < 0) - return -1; - - dump_params.dp_fd = stdout; - - if (argc > 1) { - if (!strcasecmp(argv[1], "brief")) - dump_params.dp_type = NL_DUMP_BRIEF; - else if (!strcasecmp(argv[1], "full")) - dump_params.dp_type = NL_DUMP_FULL; - else if (!strcasecmp(argv[1], "stats")) - dump_params.dp_type = NL_DUMP_STATS; + sock = nlt_alloc_socket(); + nlt_connect(sock, NETLINK_ROUTE); + link_cache = nlt_alloc_link_cache(sock); + qdisc_cache = nlt_alloc_qdisc_cache(sock); + + params.dp_fd = stdout; + + for (;;) { + int c, optidx = 0; + static struct option long_opts[] = { + { "format", 1, 0, 'f' }, + { "help", 0, 0, 'h' }, + { "version", 0, 0, 'v' }, + { 0, 0, 0, 0 } + }; + + c = getopt_long(argc, argv, "f:hv", long_opts, &optidx); + if (c == -1) + break; + + switch (c) { + case 'f': params.dp_type = nlt_parse_dumptype(optarg); break; + case 'h': print_usage(); break; + case 'v': nlt_print_version(); break; + } } - nl_handle = nltool_alloc_handle(); - if (!nl_handle) - return 1; - - if (nltool_connect(nl_handle, NETLINK_ROUTE) < 0) - return 1; - - link_cache = nltool_alloc_link_cache(nl_handle); - if (!link_cache) - return 1; - - qdisc_cache = nltool_alloc_qdisc_cache(nl_handle); - if (!qdisc_cache) - return 1; - nl_cache_foreach(link_cache, &print_link, NULL); - nl_cache_free(qdisc_cache); - nl_cache_free(link_cache); - - nl_close(nl_handle); - nl_handle_destroy(nl_handle); return 0; } diff --git a/src/nl-util-addr.c b/src/nl-util-addr.c index 9f12795..93779ea 100644 --- a/src/nl-util-addr.c +++ b/src/nl-util-addr.c @@ -6,7 +6,7 @@ * License as published by the Free Software Foundation version 2.1 * of the License. * - * Copyright (c) 2003-2006 Thomas Graf <tgraf@suug.ch> + * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch> */ #include "utils.h" @@ -21,19 +21,12 @@ int main(int argc, char *argv[]) fprintf(stderr, "Usage: nl-util-addr <address>\n"); return -1; } - - a = nl_addr_parse(argv[1], AF_UNSPEC); - if (a == NULL) { - fprintf(stderr, "Cannot parse address \"%s\"\n", argv[1]); - return -1; - } + a = nlt_addr_parse(argv[1], AF_UNSPEC); err = nl_addr_resolve(a, host, sizeof(host)); - if (err != 0) { - fprintf(stderr, "Cannot resolve address \"%s\": %d\n", - argv[1], err); - return -1; - } + if (err != 0) + fatal(err, "Unable to resolve address \"%s\": %s", + argv[1], nl_geterror(err)); printf("%s\n", host); diff --git a/src/qdisc-utils.c b/src/qdisc-utils.c new file mode 100644 index 0000000..57b5066 --- /dev/null +++ b/src/qdisc-utils.c @@ -0,0 +1,62 @@ +/* + * src/qdisc-utils.c QDisc Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "qdisc-utils.h" + +struct rtnl_qdisc *nlt_alloc_qdisc(void) +{ + struct rtnl_qdisc *qdisc; + + qdisc = rtnl_qdisc_alloc(); + if (!qdisc) + fatal(ENOMEM, "Unable to allocate qdisc object"); + + return qdisc; +} + +void parse_dev(struct rtnl_qdisc *qdisc, struct nl_cache *link_cache, char *arg) +{ + int ival; + + if (!(ival = rtnl_link_name2i(link_cache, arg))) + fatal(ENOENT, "Link \"%s\" does not exist", arg); + + rtnl_qdisc_set_ifindex(qdisc, ival); +} + +void parse_parent(struct rtnl_qdisc *qdisc, char *arg) +{ + uint32_t parent; + int err; + + if ((err = rtnl_tc_str2handle(arg, &parent)) < 0) + fatal(err, "Unable to parse handle \"%s\": %s", + arg, nl_geterror(err)); + + rtnl_qdisc_set_parent(qdisc, parent); +} + +void parse_handle(struct rtnl_qdisc *qdisc, char *arg) +{ + uint32_t handle; + int err; + + if ((err = rtnl_tc_str2handle(arg, &handle)) < 0) + fatal(err, "Unable to parse handle \"%s\": %s", + arg, nl_geterror(err)); + + rtnl_qdisc_set_handle(qdisc, handle); +} + +void parse_kind(struct rtnl_qdisc *qdisc, char *arg) +{ + rtnl_qdisc_set_kind(qdisc, arg); +} diff --git a/src/qdisc-utils.h b/src/qdisc-utils.h new file mode 100644 index 0000000..f6ce3ef --- /dev/null +++ b/src/qdisc-utils.h @@ -0,0 +1,23 @@ +/* + * src/qdisc-utils.h QDisc Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __QDISC_UTILS_H_ +#define __QDISC_UTILS_H_ + +#include "utils.h" + +extern struct rtnl_qdisc *nlt_alloc_qdisc(void); +extern void parse_dev(struct rtnl_qdisc *, struct nl_cache *, char *); +extern void parse_parent(struct rtnl_qdisc *, char *); +extern void parse_handle(struct rtnl_qdisc *, char *); +extern void parse_kind(struct rtnl_qdisc *, char *); + +#endif diff --git a/src/queue-utils.c b/src/queue-utils.c new file mode 100644 index 0000000..77038aa --- /dev/null +++ b/src/queue-utils.c @@ -0,0 +1,24 @@ +/* + * src/queue-utils.c Queue Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "queue-utils.h" + +struct nfnl_queue *nlt_alloc_queue(void) +{ + struct nfnl_queue *queue; + + queue = nfnl_queue_alloc(); + if (!queue) + fatal(ENOMEM, "Unable to allocate queue object"); + + return queue; +} + diff --git a/src/queue-utils.h b/src/queue-utils.h new file mode 100644 index 0000000..5a628fe --- /dev/null +++ b/src/queue-utils.h @@ -0,0 +1,24 @@ +/* + * src/queue-utils.h Queue Helper + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __QUEUE_UTILS_H_ +#define __QUEUE_UTILS_H_ + +#include "utils.h" +#include <linux/netfilter.h> +#include <linux/netfilter/nfnetlink_queue.h> +#include <netlink/netfilter/nfnl.h> +#include <netlink/netfilter/queue.h> +#include <netlink/netfilter/queue_msg.h> + +extern struct nfnl_queue *nlt_alloc_queue(void); + +#endif diff --git a/src/route-utils.c b/src/route-utils.c index 7f73a41..549e6ff 100644 --- a/src/route-utils.c +++ b/src/route-utils.c @@ -11,6 +11,17 @@ #include "route-utils.h" +struct rtnl_route *nlt_alloc_route(void) +{ + struct rtnl_route *route; + + route = rtnl_route_alloc(); + if (!route) + fatal(ENOMEM, "Unable to allocate route object"); + + return route; +} + void parse_family(struct rtnl_route *route, char *arg) { int family; @@ -24,12 +35,10 @@ void parse_dst(struct rtnl_route *route, char *arg) struct nl_addr *addr; int err; - addr = nl_addr_parse(arg, rtnl_route_get_family(route)); - if (addr == NULL) - fatal(nl_get_errno(), nl_geterror()); - + addr = nlt_addr_parse(arg, rtnl_route_get_family(route)); if ((err = rtnl_route_set_dst(route, addr)) < 0) - fatal(err, nl_geterror()); + fatal(err, "Unable to set destination address: %s", + nl_geterror(err)); nl_addr_put(addr); } @@ -39,12 +48,10 @@ void parse_src(struct rtnl_route *route, char *arg) struct nl_addr *addr; int err; - addr = nl_addr_parse(arg, rtnl_route_get_family(route)); - if (addr == NULL) - fatal(nl_get_errno(), nl_geterror()); - + addr = nlt_addr_parse(arg, rtnl_route_get_family(route)); if ((err = rtnl_route_set_src(route, addr)) < 0) - fatal(err, nl_geterror()); + fatal(err, "Unable to set source address: %s", + nl_geterror(err)); nl_addr_put(addr); } @@ -54,12 +61,10 @@ void parse_pref_src(struct rtnl_route *route, char *arg) struct nl_addr *addr; int err; - addr = nl_addr_parse(arg, rtnl_route_get_family(route)); - if (addr == NULL) - fatal(nl_get_errno(), nl_geterror()); - + addr = nlt_addr_parse(arg, rtnl_route_get_family(route)); if ((err = rtnl_route_set_pref_src(route, addr)) < 0) - fatal(err, nl_geterror()); + fatal(err, "Unable to set preferred source address: %s", + nl_geterror(err)); nl_addr_put(addr); } @@ -102,7 +107,8 @@ void parse_metric(struct rtnl_route *route, char *subopts) fatal(EINVAL, "Metric \"%s\", value not numeric", tokens[ret]); if ((ret = rtnl_route_set_metric(route, ret, lval)) < 0) - fatal(ret, nl_geterror()); + fatal(ret, "Unable to set metric: %s", + nl_geterror(ret)); } } @@ -140,18 +146,14 @@ void parse_nexthop(struct rtnl_route *route, char *subopts, switch (ret) { case NH_DEV: - ival = rtnl_link_name2i(link_cache, arg); - if (ival == RTNL_LINK_NOT_FOUND) - fatal(ENOENT, "Link \"%s\" does not exist", arg); + if (!(ival = rtnl_link_name2i(link_cache, arg))) + fatal(ENOENT,"Link \"%s\" does not exist", arg); rtnl_route_nh_set_ifindex(nh, ival); break; case NH_VIA: - addr = nl_addr_parse(arg, rtnl_route_get_family(route)); - if (addr == NULL) - fatal(nl_get_errno(), nl_geterror()); - + addr = nlt_addr_parse(arg,rtnl_route_get_family(route)); rtnl_route_nh_set_gateway(nh, addr); nl_addr_put(addr); break; @@ -226,15 +228,15 @@ void parse_type(struct rtnl_route *route, char *arg) fatal(EINVAL, "Unknown routing type \"%s\"", arg); if ((ival = rtnl_route_set_type(route, ival)) < 0) - fatal(ival, nl_geterror()); + fatal(ival, "Unable to set routing type: %s", + nl_geterror(ival)); } void parse_iif(struct rtnl_route *route, char *arg, struct nl_cache *link_cache) { int ival; - ival = rtnl_link_name2i(link_cache, arg); - if (ival == RTNL_LINK_NOT_FOUND) + if (!(ival = rtnl_link_name2i(link_cache, arg))) fatal(ENOENT, "Link \"%s\" does not exist", arg); rtnl_route_set_iif(route, ival); diff --git a/src/route-utils.h b/src/route-utils.h index 873835c..b410557 100644 --- a/src/route-utils.h +++ b/src/route-utils.h @@ -14,6 +14,7 @@ #include "utils.h" +extern struct rtnl_route *nlt_alloc_route(void); extern void parse_family(struct rtnl_route *, char *); extern void parse_dst(struct rtnl_route *, char *); extern void parse_src(struct rtnl_route *, char *); diff --git a/src/rtnl-utils.c b/src/rtnl-utils.c new file mode 100644 index 0000000..5c4228b --- /dev/null +++ b/src/rtnl-utils.c @@ -0,0 +1,66 @@ +/* + * src/rtnl-utils.c rtnetlink helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "rtnl-utils.h" + +struct nl_cache *nlt_alloc_link_cache(struct nl_sock *sk) +{ + return alloc_cache(sk, "link", rtnl_link_alloc_cache); +} + +struct nl_cache *nlt_alloc_addr_cache(struct nl_sock *sk) +{ + return alloc_cache(sk, "address", rtnl_addr_alloc_cache); +} + +struct nl_cache *nlt_alloc_neigh_cache(struct nl_sock *sk) +{ + return alloc_cache(sk, "neighbour", rtnl_neigh_alloc_cache); +} + +struct nl_cache *nlt_alloc_neightbl_cache(struct nl_sock *sk) +{ + return alloc_cache(sk, "neighbour table", rtnl_neightbl_alloc_cache); +} + +struct nl_cache *nlt_alloc_route_cache(struct nl_sock *sk, int flags) +{ + struct nl_cache *cache; + int err; + + if ((err = rtnl_route_alloc_cache(sk, AF_UNSPEC, flags, &cache)) < 0) + fatal(err, "Unable to allocate route cache: %s\n", + nl_geterror(err)); + + nl_cache_mngt_provide(cache); + + return cache; +} + +struct nl_cache *nlt_alloc_rule_cache(struct nl_sock *sk) +{ + struct nl_cache *cache; + int err; + + if ((err = rtnl_rule_alloc_cache(sk, AF_UNSPEC, &cache)) < 0) + fatal(err, "Unable to allocate routing rule cache: %s\n", + nl_geterror(err)); + + nl_cache_mngt_provide(cache); + + return cache; +} + +struct nl_cache *nlt_alloc_qdisc_cache(struct nl_sock *sk) +{ + return alloc_cache(sk, "queueing disciplines", rtnl_qdisc_alloc_cache); +} + diff --git a/src/rtnl-utils.h b/src/rtnl-utils.h new file mode 100644 index 0000000..5f2bbe3 --- /dev/null +++ b/src/rtnl-utils.h @@ -0,0 +1,25 @@ +/* + * src/rtnl-utils.h rtnetlink helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __SRC_RTNL_UTILS_H_ +#define __SRC_RTNL_UTILS_H_ + +#include "utils.h" + +extern struct nl_cache *nlt_alloc_link_cache(struct nl_sock *); +extern struct nl_cache *nlt_alloc_addr_cache(struct nl_sock *); +extern struct nl_cache *nlt_alloc_neigh_cache(struct nl_sock *); +extern struct nl_cache *nlt_alloc_neightbl_cache(struct nl_sock *); +extern struct nl_cache *nlt_alloc_qdisc_cache(struct nl_sock *); +extern struct nl_cache *nlt_alloc_route_cache(struct nl_sock *, int); +extern struct nl_cache *nlt_alloc_rule_cache(struct nl_sock *); + +#endif diff --git a/src/rule-utils.c b/src/rule-utils.c new file mode 100644 index 0000000..e8f3ba7 --- /dev/null +++ b/src/rule-utils.c @@ -0,0 +1,31 @@ +/* + * src/rule-utils.c Routing Rule Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#include "rule-utils.h" + +struct rtnl_rule *nlt_alloc_rule(void) +{ + struct rtnl_rule *rule; + + rule = rtnl_rule_alloc(); + if (!rule) + fatal(ENOMEM, "Unable to allocate rule object"); + + return rule; +} + +void parse_family(struct rtnl_rule *rule, char *arg) +{ + int family; + + if ((family = nl_str2af(arg)) != AF_UNSPEC) + rtnl_rule_set_family(rule, family); +} diff --git a/src/rule-utils.h b/src/rule-utils.h new file mode 100644 index 0000000..fcbf9a7 --- /dev/null +++ b/src/rule-utils.h @@ -0,0 +1,20 @@ +/* + * src/rule-utils.h Routing Rule Helpers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation version 2.1 + * of the License. + * + * Copyright (c) 2008 Thomas Graf <tgraf@suug.ch> + */ + +#ifndef __RULE_UTILS_H_ +#define __RULE_UTILS_H_ + +#include "utils.h" + +extern struct rtnl_rule *nlt_alloc_rule(void); +extern void parse_family(struct rtnl_rule *, char *); + +#endif diff --git a/src/utils.c b/src/utils.c index f7fd648..95c9329 100644 --- a/src/utils.c +++ b/src/utils.c @@ -13,6 +13,18 @@ #include <stdlib.h> +uint32_t parse_u32(const char *arg) +{ + unsigned long lval; + char *endptr; + + lval = strtoul(arg, &endptr, 0); + if (endptr == arg || lval == ULONG_MAX) + fatal(EINVAL, "Unable to parse \"%s\", not a number.", arg); + + return (uint32_t) lval; +} + void nlt_print_version(void) { printf("libnl tools version %s\n", LIBNL_VERSION); @@ -112,8 +124,8 @@ int nlt_confirm(struct nl_object *obj, struct nl_dump_params *params, return answer == 'y'; } -static struct nl_cache *alloc_cache(struct nl_sock *sock, const char *name, - int (*ac)(struct nl_sock *, struct nl_cache **)) +struct nl_cache *alloc_cache(struct nl_sock *sock, const char *name, + int (*ac)(struct nl_sock *, struct nl_cache **)) { struct nl_cache *cache; int err; @@ -127,67 +139,3 @@ static struct nl_cache *alloc_cache(struct nl_sock *sock, const char *name, return cache; } -struct nl_cache *nlt_alloc_link_cache(struct nl_sock *sk) -{ - return alloc_cache(sk, "link", rtnl_link_alloc_cache); -} - -struct nl_cache *nlt_alloc_addr_cache(struct nl_sock *sk) -{ - return alloc_cache(sk, "address", rtnl_addr_alloc_cache); -} - -struct rtnl_addr *nlt_alloc_addr(void) -{ - struct rtnl_addr *addr; - - addr = rtnl_addr_alloc(); - if (!addr) - fatal(ENOMEM, "Unable to allocate address object"); - - return addr; -} - -struct nl_cache *nltool_alloc_neigh_cache(struct nl_sock *sk) -{ - return alloc_cache(sk, "neighbour", rtnl_neigh_alloc_cache); -} - -struct nl_cache *nltool_alloc_neightbl_cache(struct nl_sock *sk) -{ - return alloc_cache(sk, "neighbour table", rtnl_neightbl_alloc_cache); -} - -struct nl_cache *nltool_alloc_route_cache(struct nl_sock *sk, int flags) -{ - struct nl_cache *cache; - int err; - - if ((err = rtnl_route_alloc_cache(sk, AF_UNSPEC, flags, &cache)) < 0) - fatal(err, "Unable to allocate route cache: %s\n", - nl_geterror(err)); - - nl_cache_mngt_provide(cache); - - return cache; -} - -struct nl_cache *nltool_alloc_rule_cache(struct nl_sock *sk) -{ - struct nl_cache *cache; - int err; - - if ((err = rtnl_rule_alloc_cache(sk, AF_UNSPEC, &cache)) < 0) - fatal(err, "Unable to allocate routing rule cache: %s\n", - nl_geterror(err)); - - nl_cache_mngt_provide(cache); - - return cache; -} - -struct nl_cache *nltool_alloc_qdisc_cache(struct nl_sock *sk) -{ - return alloc_cache(sk, "queueing disciplines", rtnl_qdisc_alloc_cache); -} - diff --git a/src/utils.h b/src/utils.h index b22dfbf..12f7c52 100644 --- a/src/utils.h +++ b/src/utils.h @@ -44,6 +44,8 @@ #include <netlink/genl/mngt.h> #include <netlink/netfilter/ct.h> +extern uint32_t parse_u32(const char *); + extern void nlt_print_version(void); extern void fatal(int err, const char *fmt, ...); extern struct nl_addr * nlt_addr_parse(const char *, int); @@ -55,15 +57,13 @@ extern int nlt_parse_dumptype(const char *str); extern int nlt_confirm(struct nl_object *, struct nl_dump_params *, int); extern struct nl_cache *nlt_alloc_link_cache(struct nl_sock *); - extern struct nl_cache *nlt_alloc_addr_cache(struct nl_sock *); -extern struct rtnl_addr *nlt_alloc_addr(void); - -extern struct nl_cache *nltool_alloc_neigh_cache(struct nl_sock *nlh); -extern struct nl_cache *nltool_alloc_neightbl_cache(struct nl_sock *nlh); -extern struct nl_cache *nltool_alloc_route_cache(struct nl_sock *nlh, int); -extern struct nl_cache *nltool_alloc_rule_cache(struct nl_sock *nlh); -extern struct nl_cache *nltool_alloc_qdisc_cache(struct nl_sock *nlh); -extern struct nl_cache *nltool_alloc_genl_family_cache(struct nl_sock *nlh); +extern struct nl_cache *nlt_alloc_neigh_cache(struct nl_sock *); +extern struct nl_cache *nlt_alloc_neightbl_cache(struct nl_sock *); +extern struct nl_cache *nlt_alloc_qdisc_cache(struct nl_sock *); +extern struct nl_cache *nlt_alloc_route_cache(struct nl_sock *, int); +extern struct nl_cache *nlt_alloc_rule_cache(struct nl_sock *); +extern struct nl_cache *alloc_cache(struct nl_sock *, const char *, + int (*ac)(struct nl_sock *, struct nl_cache **)); #endif |