static int ipnetns_have_nsid(void) { struct { struct nlmsghdr n; struct rtgenmsg g; char buf[1024]; } req; int fd; if (have_rtnl_getnsid < 0) { memset(&req, 0, sizeof(req)); req.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct rtgenmsg)); req.n.nlmsg_flags = NLM_F_REQUEST; req.n.nlmsg_type = RTM_GETNSID; req.g.rtgen_family = AF_UNSPEC; fd = open("/proc/self/ns/net", O_RDONLY); if (fd < 0) { perror("open(\"/proc/self/ns/net\")"); exit(1); } addattr32(&req.n, 1024, NETNSA_FD, fd); if (rtnl_send(&rth, &req.n, req.n.nlmsg_len) < 0) { perror("request send failed"); exit(1); } rtnl_listen(&rth, ipnetns_accept_msg, NULL); close(fd); } return have_rtnl_getnsid; }
static int do_show(int argc, char **argv) { struct { struct nlmsghdr n; struct netconfmsg ncm; char buf[1024]; } req; ipnetconf_reset_filter(0); filter.family = preferred_family; if (filter.family == AF_UNSPEC) filter.family = AF_INET; while (argc > 0) { if (strcmp(*argv, "dev") == 0) { NEXT_ARG(); filter.ifindex = ll_name_to_index(*argv); if (filter.ifindex <= 0) { fprintf(stderr, "Device \"%s\" does not exist.\n", *argv); return -1; } } argv++; argc--; } ll_init_map(&rth); if (filter.ifindex) { memset(&req, 0, sizeof(req)); req.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct netconfmsg)); req.n.nlmsg_flags = NLM_F_REQUEST|NLM_F_ACK; req.n.nlmsg_type = RTM_GETNETCONF; req.ncm.ncm_family = filter.family; if (filter.ifindex) addattr_l(&req.n, sizeof(req), NETCONFA_IFINDEX, &filter.ifindex, sizeof(filter.ifindex)); if (rtnl_send(&rth, &req.n, req.n.nlmsg_len) < 0) { perror("Can not send request"); exit(1); } rtnl_listen(&rth, print_netconf, stdout); } else { dump: if (rtnl_wilddump_request(&rth, filter.family, RTM_GETNETCONF) < 0) { perror("Cannot send dump request"); exit(1); } if (rtnl_dump_filter(&rth, print_netconf2, stdout) < 0) { fprintf(stderr, "Dump terminated\n"); exit(1); } if (preferred_family == AF_UNSPEC) { preferred_family = AF_INET6; filter.family = AF_INET6; goto dump; } } return 0; }
static int iplink_have_newlink(void) { struct iplink_req req; struct softgred_config *cfg = softgred_config_ref(); if (have_rtnl_newlink < 0) { memset(&req, 0, sizeof(req)); req.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct ifinfomsg)); req.n.nlmsg_flags = NLM_F_REQUEST|NLM_F_ACK; req.n.nlmsg_type = RTM_NEWLINK; req.i.ifi_family = AF_UNSPEC; if (rtnl_send(&cfg->rth, &req.n, req.n.nlmsg_len) < 0) { perror("request send failed"); exit(1); } rtnl_listen(&cfg->rth, accept_msg, NULL); } return have_rtnl_newlink; }
static inline void br_ev_handler(uint32_t events, struct epoll_event_handler *h) { if(rtnl_listen(&rth, dump_msg, stdout) < 0) { fprintf(stderr, "Error on bridge monitoring socket\n"); exit(-1); } }
int do_monitor(int argc, char **argv) { char *file = NULL; unsigned groups = ~RTMGRP_TC; int llink=0; int lneigh=0; rtnl_close(&rth); while (argc > 0) { if (matches(*argv, "file") == 0) { NEXT_ARG(); file = *argv; } else if (matches(*argv, "link") == 0) { llink=1; groups = 0; } else if (matches(*argv, "fdb") == 0) { lneigh = 1; groups = 0; } else if (strcmp(*argv, "all") == 0) { groups = ~RTMGRP_TC; prefix_banner=1; } else if (matches(*argv, "help") == 0) { usage(); } else { fprintf(stderr, "Argument \"%s\" is unknown, try \"bridge monitor help\".\n", *argv); exit(-1); } argc--; argv++; } if (llink) groups |= nl_mgrp(RTNLGRP_LINK); if (lneigh) { groups |= nl_mgrp(RTNLGRP_NEIGH); } if (file) { FILE *fp; fp = fopen(file, "r"); if (fp == NULL) { perror("Cannot fopen"); exit(-1); } return rtnl_from_file(fp, accept_msg, stdout); } if (rtnl_open(&rth, groups) < 0) exit(1); ll_init_map(&rth); if (rtnl_listen(&rth, accept_msg, stdout) < 0) exit(2); return 0; }
int test_look_interface_changes(){ struct rtnl_handle rth; if (rtnl_open(&rth, RTNLGRP_LINK) < 0){ printf("cannot open rtnetlink\n"); return -1; } int status = rtnl_listen(&rth,test_handle,0); rtnl_close(&rth); return status; }
int look_interface_changes(){ if (rtnl_open(&rtnl_interface, RTNLGRP_LINK) < 0){ printf("cannot open rtnetlink\n"); return -1; } int status = rtnl_listen(&rtnl_interface,handle,0); rtnl_close(&rtnl_interface); printf("RTNL OFF\n"); return status; }
static int ctrl_listen(int argc, char **argv) { struct rtnl_handle rth; if (rtnl_open_byproto(&rth, nl_mgrp(GENL_ID_CTRL), NETLINK_GENERIC) < 0) { fprintf(stderr, "Canot open generic netlink socket\n"); return -1; } if (rtnl_listen(&rth, print_ctrl, (void *) stdout) < 0) return -1; return 0; }
int do_xfrm_monitor(int argc, char **argv) { struct rtnl_handle rth; char *file = NULL; unsigned groups = ~((unsigned)0); /* XXX */ int lacquire=0; int lexpire=0; while (argc > 0) { if (matches(*argv, "file") == 0) { NEXT_ARG(); file = *argv; } else if (matches(*argv, "acquire") == 0) { lacquire=1; groups = 0; } else if (matches(*argv, "expire") == 0) { lexpire=1; groups = 0; } else if (matches(*argv, "help") == 0) { usage(); } else { fprintf(stderr, "Argument \"%s\" is unknown, try \"ip xfrm monitor help\".\n", *argv); exit(-1); } argc--; argv++; } if (lacquire) groups |= XFRMGRP_ACQUIRE; if (lexpire) groups |= XFRMGRP_EXPIRE; if (file) { FILE *fp; fp = fopen(file, "r"); if (fp == NULL) { perror("Cannot fopen"); exit(-1); } return rtnl_from_file(fp, xfrm_accept_msg, (void*)stdout); } //ll_init_map(&rth); if (rtnl_listen(&rth, xfrm_accept_msg, (void*)stdout) < 0) exit(2); return 0; }
int do_tcmonitor(int argc, char **argv) { struct rtnl_handle rth; char *file = NULL; unsigned groups = nl_mgrp(RTNLGRP_TC); while (argc > 0) { if (matches(*argv, "file") == 0) { NEXT_ARG(); file = *argv; } else { if (matches(*argv, "help") == 0) { usage(); } else { fprintf(stderr, "Argument \"%s\" is unknown, try \"tc monitor help\".\n", *argv); exit(-1); } } argc--; argv++; } if (file) { FILE *fp; fp = fopen(file, "r"); if (fp == NULL) { perror("Cannot fopen"); exit(-1); } return rtnl_from_file(fp, accept_tcmsg, (void*)stdout); } if (rtnl_open(&rth, groups) < 0) exit(1); ll_init_map(&rth); if (rtnl_listen(&rth, accept_tcmsg, (void*)stdout) < 0) { rtnl_close(&rth); exit(2); } rtnl_close(&rth); exit(0); }
static int iplink_have_newlink(void) { struct { struct nlmsghdr n; struct ifinfomsg i; char buf[1024]; } req = { .n.nlmsg_len = NLMSG_LENGTH(sizeof(struct ifinfomsg)), .n.nlmsg_flags = NLM_F_REQUEST | NLM_F_ACK, .n.nlmsg_type = RTM_NEWLINK, .i.ifi_family = AF_UNSPEC, }; if (have_rtnl_newlink < 0) { if (rtnl_send(&rth, &req.n, req.n.nlmsg_len) < 0) { perror("request send failed"); exit(1); } rtnl_listen(&rth, accept_msg, NULL); } return have_rtnl_newlink; } #else /* IPLINK_IOCTL_COMPAT */ static int iplink_have_newlink(void) { return 1; } #endif /* ! IPLINK_IOCTL_COMPAT */ static int nl_get_ll_addr_len(unsigned int dev_index) { int len; struct iplink_req req = { .n = { .nlmsg_len = NLMSG_LENGTH(sizeof(struct ifinfomsg)), .nlmsg_type = RTM_GETLINK, .nlmsg_flags = NLM_F_REQUEST }, .i = { .ifi_family = preferred_family, .ifi_index = dev_index, } };
static int iplink_have_newlink(void) { struct { struct nlmsghdr n; struct ifinfomsg i; char buf[1024]; } req; if (have_rtnl_newlink < 0) { memset(&req, 0, sizeof(req)); req.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct ifinfomsg)); req.n.nlmsg_flags = NLM_F_REQUEST|NLM_F_ACK; req.n.nlmsg_type = RTM_NEWLINK; req.i.ifi_family = AF_UNSPEC; rtnl_send(&rth, &req.n, req.n.nlmsg_len); rtnl_listen(&rth, accept_msg, NULL); } return have_rtnl_newlink; }
int do_xfrm_monitor(int argc, char **argv) { char *file = NULL; unsigned int groups = ~((unsigned)0); /* XXX */ int lacquire = 0; int lexpire = 0; int laevent = 0; int lpolicy = 0; int lsa = 0; int lreport = 0; rtnl_close(&rth); while (argc > 0) { if (matches(*argv, "file") == 0) { NEXT_ARG(); file = *argv; } else if (matches(*argv, "all-nsid") == 0) { listen_all_nsid = 1; } else if (matches(*argv, "acquire") == 0) { lacquire = 1; groups = 0; } else if (matches(*argv, "expire") == 0) { lexpire = 1; groups = 0; } else if (matches(*argv, "SA") == 0) { lsa = 1; groups = 0; } else if (matches(*argv, "aevent") == 0) { laevent = 1; groups = 0; } else if (matches(*argv, "policy") == 0) { lpolicy = 1; groups = 0; } else if (matches(*argv, "report") == 0) { lreport = 1; groups = 0; } else if (matches(*argv, "help") == 0) { usage(); } else if (strcmp(*argv, "all")) { fprintf(stderr, "Argument \"%s\" is unknown, try \"ip xfrm monitor help\".\n", *argv); exit(-1); } argc--; argv++; } if (lacquire) groups |= nl_mgrp(XFRMNLGRP_ACQUIRE); if (lexpire) groups |= nl_mgrp(XFRMNLGRP_EXPIRE); if (lsa) groups |= nl_mgrp(XFRMNLGRP_SA); if (lpolicy) groups |= nl_mgrp(XFRMNLGRP_POLICY); if (laevent) groups |= nl_mgrp(XFRMNLGRP_AEVENTS); if (lreport) groups |= nl_mgrp(XFRMNLGRP_REPORT); if (file) { FILE *fp; int err; fp = fopen(file, "r"); if (fp == NULL) { perror("Cannot fopen"); exit(-1); } err = rtnl_from_file(fp, xfrm_accept_msg, stdout); fclose(fp); return err; } if (rtnl_open_byproto(&rth, groups, NETLINK_XFRM) < 0) exit(1); if (listen_all_nsid && rtnl_listen_all_nsid(&rth) < 0) exit(1); if (rtnl_listen(&rth, xfrm_accept_msg, (void *)stdout) < 0) exit(2); return 0; }
int main(int argc, char **argv) { FILE *fp; struct rtnl_handle rth; int family = AF_UNSPEC; unsigned groups = ~0U; int llink = 0; int laddr = 0; int lroute = 0; char *file = NULL; while (argc > 1) { if (matches(argv[1], "-family") == 0) { argc--; argv++; if (argc <= 1) usage(); if (strcmp(argv[1], "inet") == 0) family = AF_INET; else if (strcmp(argv[1], "inet6") == 0) family = AF_INET6; else if (strcmp(argv[1], "link") == 0) family = AF_INET6; else if (strcmp(argv[1], "help") == 0) usage(); else { fprintf(stderr, "Protocol ID \"%s\" is unknown, try \"rtmon help\".\n", argv[1]); exit(-1); } } else if (strcmp(argv[1], "-4") == 0) { family = AF_INET; } else if (strcmp(argv[1], "-6") == 0) { family = AF_INET6; } else if (strcmp(argv[1], "-0") == 0) { family = AF_PACKET; } else if (matches(argv[1], "-Version") == 0) { printf("rtmon utility, iproute2-ss%s\n", SNAPSHOT); exit(0); } else if (matches(argv[1], "file") == 0) { argc--; argv++; if (argc <= 1) usage(); file = argv[1]; } else if (matches(argv[1], "link") == 0) { llink=1; groups = 0; } else if (matches(argv[1], "address") == 0) { laddr=1; groups = 0; } else if (matches(argv[1], "route") == 0) { lroute=1; groups = 0; } else if (strcmp(argv[1], "all") == 0) { groups = ~0U; } else if (matches(argv[1], "help") == 0) { usage(); } else { fprintf(stderr, "Argument \"%s\" is unknown, try \"rtmon help\".\n", argv[1]); exit(-1); } argc--; argv++; } if (file == NULL) { fprintf(stderr, "Not enough information: argument \"file\" is required\n"); exit(-1); } if (llink) groups |= nl_mgrp(RTNLGRP_LINK); if (laddr) { if (!family || family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_IFADDR); if (!family || family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_IFADDR); } if (lroute) { if (!family || family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_ROUTE); if (!family || family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_ROUTE); } fp = fopen(file, "w"); if (fp == NULL) { perror("Cannot fopen"); exit(-1); } if (rtnl_open(&rth, groups) < 0) exit(1); if (rtnl_wilddump_request(&rth, AF_UNSPEC, RTM_GETLINK) < 0) { perror("Cannot send dump request"); exit(1); } write_stamp(fp); if (rtnl_dump_filter(&rth, dump_msg, fp, NULL, NULL) < 0) { fprintf(stderr, "Dump terminated\n"); return 1; } init_phase = 0; if (rtnl_listen(&rth, dump_msg, (void*)fp) < 0) exit(2); exit(0); }
static int do_show(int argc, char **argv) { struct { struct nlmsghdr n; struct netconfmsg ncm; char buf[1024]; } req = { .n.nlmsg_len = NLMSG_LENGTH(sizeof(struct netconfmsg)), .n.nlmsg_flags = NLM_F_REQUEST | NLM_F_ACK, .n.nlmsg_type = RTM_GETNETCONF, }; ipnetconf_reset_filter(0); filter.family = preferred_family; while (argc > 0) { if (strcmp(*argv, "dev") == 0) { NEXT_ARG(); filter.ifindex = ll_name_to_index(*argv); if (filter.ifindex <= 0) { fprintf(stderr, "Device \"%s\" does not exist.\n", *argv); return -1; } } argv++; argc--; } ll_init_map(&rth); if (filter.ifindex && filter.family != AF_UNSPEC) { req.ncm.ncm_family = filter.family; addattr_l(&req.n, sizeof(req), NETCONFA_IFINDEX, &filter.ifindex, sizeof(filter.ifindex)); if (rtnl_send(&rth, &req.n, req.n.nlmsg_len) < 0) { perror("Can not send request"); exit(1); } rtnl_listen(&rth, print_netconf, stdout); } else { rth.flags = RTNL_HANDLE_F_SUPPRESS_NLERR; dump: if (rtnl_wilddump_request(&rth, filter.family, RTM_GETNETCONF) < 0) { perror("Cannot send dump request"); exit(1); } if (rtnl_dump_filter(&rth, print_netconf2, stdout) < 0) { /* kernel does not support netconf dump on AF_UNSPEC; * fall back to requesting by family */ if (errno == EOPNOTSUPP && filter.family == AF_UNSPEC) { filter.family = AF_INET; goto dump; } perror("RTNETLINK answers"); fprintf(stderr, "Dump terminated\n"); exit(1); } if (preferred_family == AF_UNSPEC && filter.family == AF_INET) { preferred_family = AF_INET6; filter.family = AF_INET6; goto dump; } } return 0; } int do_ipnetconf(int argc, char **argv) { if (argc > 0) { if (matches(*argv, "show") == 0 || matches(*argv, "lst") == 0 || matches(*argv, "list") == 0) return do_show(argc-1, argv+1); if (matches(*argv, "help") == 0) usage(); } else return do_show(0, NULL); fprintf(stderr, "Command \"%s\" is unknown, try \"ip netconf help\".\n", *argv); exit(-1); }
int do_ipmonitor(int argc, char **argv) { struct rtnl_handle rth; char *file = NULL; unsigned groups = ~RTMGRP_TC; int llink=0; int laddr=0; int lroute=0; ipaddr_reset_filter(1); iproute_reset_filter(); ipneigh_reset_filter(); while (argc > 0) { if (matches(*argv, "file") == 0) { NEXT_ARG(); file = *argv; } else if (matches(*argv, "link") == 0) { llink=1; groups = 0; } else if (matches(*argv, "address") == 0) { laddr=1; groups = 0; } else if (matches(*argv, "route") == 0) { lroute=1; groups = 0; } else if (strcmp(*argv, "all") == 0) { groups = ~RTMGRP_TC; } else if (matches(*argv, "help") == 0) { usage(); } else { fprintf(stderr, "Argument \"%s\" is unknown, try \"ip monitor help\".\n", *argv); exit(-1); } argc--; argv++; } if (llink) groups |= RTMGRP_LINK; if (laddr) { if (!preferred_family || preferred_family == AF_INET) groups |= RTMGRP_IPV4_IFADDR; if (!preferred_family || preferred_family == AF_INET6) groups |= RTMGRP_IPV6_IFADDR; } if (lroute) { if (!preferred_family || preferred_family == AF_INET) groups |= RTMGRP_IPV4_ROUTE; if (!preferred_family || preferred_family == AF_INET6) groups |= RTMGRP_IPV6_ROUTE; } if (file) { FILE *fp; fp = fopen(file, "r"); if (fp == NULL) { perror("Cannot fopen"); exit(-1); } return rtnl_from_file(fp, accept_msg, (void*)stdout); } if (rtnl_open(&rth, groups) < 0) exit(1); ll_init_map(&rth); if (rtnl_listen(&rth, accept_msg, (void*)stdout) < 0) exit(2); exit(0); }
static int ctrl_list(int cmd, int argc, char **argv) { struct rtnl_handle rth; int ret = -1; char d[GENL_NAMSIZ]; struct { struct nlmsghdr n; struct genlmsghdr g; char buf[4096]; } req = { .n.nlmsg_len = NLMSG_LENGTH(GENL_HDRLEN), .n.nlmsg_flags = NLM_F_REQUEST | NLM_F_ACK, .n.nlmsg_type = GENL_ID_CTRL, .g.cmd = CTRL_CMD_GETFAMILY, }; struct nlmsghdr *nlh = &req.n; if (rtnl_open_byproto(&rth, 0, NETLINK_GENERIC) < 0) { fprintf(stderr, "Cannot open generic netlink socket\n"); exit(1); } if (cmd == CTRL_CMD_GETFAMILY) { if (argc != 2) { fprintf(stderr, "Wrong number of params\n"); return -1; } if (matches(*argv, "name") == 0) { NEXT_ARG(); strncpy(d, *argv, sizeof (d) - 1); addattr_l(nlh, 128, CTRL_ATTR_FAMILY_NAME, d, strlen(d) + 1); } else if (matches(*argv, "id") == 0) { __u16 id; NEXT_ARG(); if (get_u16(&id, *argv, 0)) { fprintf(stderr, "Illegal \"id\"\n"); goto ctrl_done; } addattr_l(nlh, 128, CTRL_ATTR_FAMILY_ID, &id, 2); } else { fprintf(stderr, "Wrong params\n"); goto ctrl_done; } if (rtnl_talk(&rth, nlh, nlh, sizeof(req)) < 0) { fprintf(stderr, "Error talking to the kernel\n"); goto ctrl_done; } if (print_ctrl2(NULL, nlh, (void *) stdout) < 0) { fprintf(stderr, "Dump terminated\n"); goto ctrl_done; } } if (cmd == CTRL_CMD_UNSPEC) { nlh->nlmsg_flags = NLM_F_ROOT|NLM_F_MATCH|NLM_F_REQUEST; nlh->nlmsg_seq = rth.dump = ++rth.seq; if (rtnl_send(&rth, nlh, nlh->nlmsg_len) < 0) { perror("Failed to send dump request\n"); goto ctrl_done; } rtnl_dump_filter(&rth, print_ctrl2, stdout); } ret = 0; ctrl_done: rtnl_close(&rth); return ret; } static int ctrl_listen(int argc, char **argv) { struct rtnl_handle rth; if (rtnl_open_byproto(&rth, nl_mgrp(GENL_ID_CTRL), NETLINK_GENERIC) < 0) { fprintf(stderr, "Canot open generic netlink socket\n"); return -1; } if (rtnl_listen(&rth, print_ctrl, (void *) stdout) < 0) return -1; return 0; } static int parse_ctrl(struct genl_util *a, int argc, char **argv) { argv++; if (--argc <= 0) { fprintf(stderr, "wrong controller params\n"); return -1; } if (matches(*argv, "monitor") == 0) return ctrl_listen(argc-1, argv+1); if (matches(*argv, "get") == 0) return ctrl_list(CTRL_CMD_GETFAMILY, argc-1, argv+1); if (matches(*argv, "list") == 0 || matches(*argv, "show") == 0 || matches(*argv, "lst") == 0) return ctrl_list(CTRL_CMD_UNSPEC, argc-1, argv+1); if (matches(*argv, "help") == 0) return usage(); fprintf(stderr, "ctrl command \"%s\" is unknown, try \"ctrl help\".\n", *argv); return -1; }
int do_ipmonitor(int argc, char **argv) { char *file = NULL; unsigned groups = ~RTMGRP_TC; int llink=0; int laddr=0; int lroute=0; int lprefix=0; int lneigh=0; rtnl_close(&rth); ipaddr_reset_filter(1); iproute_reset_filter(); ipneigh_reset_filter(); while (argc > 0) { if (matches(*argv, "file") == 0) { NEXT_ARG(); file = *argv; } else if (matches(*argv, "link") == 0) { llink=1; groups = 0; } else if (matches(*argv, "address") == 0) { laddr=1; groups = 0; } else if (matches(*argv, "route") == 0) { lroute=1; groups = 0; } else if (matches(*argv, "prefix") == 0) { lprefix=1; groups = 0; } else if (matches(*argv, "neigh") == 0) { lneigh = 1; groups = 0; } else if (strcmp(*argv, "all") == 0) { groups = ~RTMGRP_TC; prefix_banner=1; } else if (matches(*argv, "help") == 0) { usage(); } else { fprintf(stderr, "Argument \"%s\" is unknown, try \"ip monitor help\".\n", *argv); exit(-1); } argc--; argv++; } if (llink) groups |= nl_mgrp(RTNLGRP_LINK); if (laddr) { if (!preferred_family || preferred_family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_IFADDR); if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_IFADDR); } if (lroute) { if (!preferred_family || preferred_family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_ROUTE); if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_ROUTE); } if (lprefix) { if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_PREFIX); } if (lneigh) { groups |= nl_mgrp(RTNLGRP_NEIGH); } if (file) { FILE *fp; fp = fopen(file, "r"); if (fp == NULL) { perror("Cannot fopen"); exit(-1); } return rtnl_from_file(fp, accept_msg, stdout); } if (rtnl_open(&rth, groups) < 0) exit(1); ll_init_map(&rth); if (rtnl_listen(&rth, accept_msg, stdout) < 0) exit(2); return 0; }
int do_ipmonitor(int argc, char **argv) { char *file = NULL; unsigned int groups = 0; int llink = 0; int laddr = 0; int lroute = 0; int lmroute = 0; int lprefix = 0; int lneigh = 0; int lnetconf = 0; int lrule = 0; int lnsid = 0; int ifindex = 0; groups |= nl_mgrp(RTNLGRP_LINK); groups |= nl_mgrp(RTNLGRP_IPV4_IFADDR); groups |= nl_mgrp(RTNLGRP_IPV6_IFADDR); groups |= nl_mgrp(RTNLGRP_IPV4_ROUTE); groups |= nl_mgrp(RTNLGRP_IPV6_ROUTE); groups |= nl_mgrp(RTNLGRP_MPLS_ROUTE); groups |= nl_mgrp(RTNLGRP_IPV4_MROUTE); groups |= nl_mgrp(RTNLGRP_IPV6_MROUTE); groups |= nl_mgrp(RTNLGRP_IPV6_PREFIX); groups |= nl_mgrp(RTNLGRP_NEIGH); groups |= nl_mgrp(RTNLGRP_IPV4_NETCONF); groups |= nl_mgrp(RTNLGRP_IPV6_NETCONF); groups |= nl_mgrp(RTNLGRP_IPV4_RULE); groups |= nl_mgrp(RTNLGRP_IPV6_RULE); groups |= nl_mgrp(RTNLGRP_NSID); groups |= nl_mgrp(RTNLGRP_MPLS_NETCONF); rtnl_close(&rth); while (argc > 0) { if (matches(*argv, "file") == 0) { NEXT_ARG(); file = *argv; } else if (matches(*argv, "label") == 0) { prefix_banner = 1; } else if (matches(*argv, "link") == 0) { llink = 1; groups = 0; } else if (matches(*argv, "address") == 0) { laddr = 1; groups = 0; } else if (matches(*argv, "route") == 0) { lroute = 1; groups = 0; } else if (matches(*argv, "mroute") == 0) { lmroute = 1; groups = 0; } else if (matches(*argv, "prefix") == 0) { lprefix = 1; groups = 0; } else if (matches(*argv, "neigh") == 0) { lneigh = 1; groups = 0; } else if (matches(*argv, "netconf") == 0) { lnetconf = 1; groups = 0; } else if (matches(*argv, "rule") == 0) { lrule = 1; groups = 0; } else if (matches(*argv, "nsid") == 0) { lnsid = 1; groups = 0; } else if (strcmp(*argv, "all") == 0) { prefix_banner = 1; } else if (matches(*argv, "all-nsid") == 0) { listen_all_nsid = 1; } else if (matches(*argv, "help") == 0) { usage(); } else if (strcmp(*argv, "dev") == 0) { NEXT_ARG(); ifindex = ll_name_to_index(*argv); if (!ifindex) invarg("Device does not exist\n", *argv); } else { fprintf(stderr, "Argument \"%s\" is unknown, try \"ip monitor help\".\n", *argv); exit(-1); } argc--; argv++; } ipaddr_reset_filter(1, ifindex); iproute_reset_filter(ifindex); ipmroute_reset_filter(ifindex); ipneigh_reset_filter(ifindex); ipnetconf_reset_filter(ifindex); if (llink) groups |= nl_mgrp(RTNLGRP_LINK); if (laddr) { if (!preferred_family || preferred_family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_IFADDR); if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_IFADDR); } if (lroute) { if (!preferred_family || preferred_family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_ROUTE); if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_ROUTE); if (!preferred_family || preferred_family == AF_MPLS) groups |= nl_mgrp(RTNLGRP_MPLS_ROUTE); } if (lmroute) { if (!preferred_family || preferred_family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_MROUTE); if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_MROUTE); } if (lprefix) { if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_PREFIX); } if (lneigh) { groups |= nl_mgrp(RTNLGRP_NEIGH); } if (lnetconf) { if (!preferred_family || preferred_family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_NETCONF); if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_NETCONF); if (!preferred_family || preferred_family == AF_MPLS) groups |= nl_mgrp(RTNLGRP_MPLS_NETCONF); } if (lrule) { if (!preferred_family || preferred_family == AF_INET) groups |= nl_mgrp(RTNLGRP_IPV4_RULE); if (!preferred_family || preferred_family == AF_INET6) groups |= nl_mgrp(RTNLGRP_IPV6_RULE); } if (lnsid) { groups |= nl_mgrp(RTNLGRP_NSID); } if (file) { FILE *fp; int err; fp = fopen(file, "r"); if (fp == NULL) { perror("Cannot fopen"); exit(-1); } err = rtnl_from_file(fp, accept_msg, stdout); fclose(fp); return err; } if (rtnl_open(&rth, groups) < 0) exit(1); if (listen_all_nsid && rtnl_listen_all_nsid(&rth) < 0) exit(1); ll_init_map(&rth); netns_nsid_socket_init(); netns_map_init(); if (rtnl_listen(&rth, accept_msg, stdout) < 0) exit(2); return 0; }