void conf_interfaces(FILE *output, char *only) { int ifs, flags, ippntd, br; char *lladdr; char ifdescr[IFDESCRSIZE]; struct if_nameindex *ifn_list, *ifnp; struct ifreq ifr, ifrdesc; struct if_data if_data; if ((ifn_list = if_nameindex()) == NULL) { printf("%% conf_interfaces: if_nameindex failed\n"); return; } if ((ifs = socket(AF_INET, SOCK_DGRAM, 0)) < 0) { printf("%% conf_interfaces socket: %s\n", strerror(errno)); if_freenameindex(ifn_list); return; } for (ifnp = ifn_list; ifnp->if_name != NULL; ifnp++) { if (only && !isprefix(only, ifnp->if_name)) /* only display interfaces which start with ... */ continue; if (!only && islateif(ifnp->if_name)) /* interface prefixes to exclude on generic run */ continue; strlcpy(ifr.ifr_name, ifnp->if_name, sizeof(ifr.ifr_name)); if (ioctl(ifs, SIOCGIFFLAGS, (caddr_t)&ifr) < 0) { printf("%% conf: SIOCGIFFLAGS: %s\n", strerror(errno)); continue; } flags = ifr.ifr_flags; ifr.ifr_data = (caddr_t)&if_data; if (ioctl(ifs, SIOCGIFDATA, (caddr_t)&ifr) < 0) { printf("%% conf: SIOCGIFDATA: %s\n", strerror(errno)); continue; } /* The output order is important! */ /* set interface/bridge mode */ if (!(br = is_bridge(ifs, ifnp->if_name))) br = 0; fprintf(output, "%s %s\n", br ? "bridge" : "interface", ifnp->if_name); /* * description, if available * copied straight from ifconfig.c */ memset(&ifrdesc, 0, sizeof(ifrdesc)); strlcpy(ifrdesc.ifr_name, ifnp->if_name, sizeof(ifrdesc.ifr_name)); ifrdesc.ifr_data = (caddr_t)&ifdescr; if (ioctl(ifs, SIOCGIFDESCR, &ifrdesc) == 0 && strlen(ifrdesc.ifr_data)) fprintf(output, " description %s\n", ifrdesc.ifr_data); if ((lladdr = get_hwdaddr(ifnp->if_name)) != NULL) conf_db_single(output, "lladdr", lladdr, ifnp->if_name); conf_db_single(output, "rtadvd", NULL, ifnp->if_name); conf_vnetid(output, ifs, ifnp->if_name); conf_parent(output, ifs, ifnp->if_name); conf_rdomain(output, ifs, ifnp->if_name); conf_intrtlabel(output, ifs, ifnp->if_name); conf_intgroup(output, ifs, ifnp->if_name); conf_carp(output, ifs, ifnp->if_name); ippntd = conf_ifaddr_dhcp(output, ifnp->if_name, flags); if (br) { conf_brcfg(output, ifs, ifn_list, ifnp->if_name); } else { char tmp[24]; conf_media_status(output, ifs, ifnp->if_name); conf_ifmetrics(output, ifs, if_data, ifnp->if_name); conf_keepalive(output, ifs, ifnp->if_name); conf_pfsync(output, ifs, ifnp->if_name); conf_trunk(output, ifs, ifnp->if_name); conf_pflow(output, ifs, ifnp->if_name); conf_ifxflags(output, ifs, ifnp->if_name); if (timeslot_status(ifs, ifnp->if_name, tmp, sizeof(tmp)) == 1) fprintf(output, " timeslots %s\n", tmp); if (conf_dhcrelay(ifnp->if_name, tmp, sizeof(tmp)) > 0) fprintf(output, " dhcrelay %s\n", tmp); conf_sppp(output, ifs, ifnp->if_name); conf_pppoe(output, ifs, ifnp->if_name); } conf_ifflags(output, flags, ifnp->if_name, ippntd); } close(ifs); if_freenameindex(ifn_list); }
void conf_interfaces(FILE *output, char *only) { FILE *dhcpif; int ifs, flags, ippntd, br; char leasefile[sizeof(LEASEPREFIX)+1+IFNAMSIZ]; char *lladdr; char ifdescr[IFDESCRSIZE]; struct if_nameindex *ifn_list, *ifnp; struct ifreq ifr, ifrdesc; struct if_data if_data; struct vlanreq vreq; if ((ifn_list = if_nameindex()) == NULL) { printf("%% conf_interfaces: if_nameindex failed\n"); return; } if ((ifs = socket(AF_INET, SOCK_DGRAM, 0)) < 0) { printf("%% conf_interfaces socket: %s\n", strerror(errno)); if_freenameindex(ifn_list); return; } for (ifnp = ifn_list; ifnp->if_name != NULL; ifnp++) { if (only && !isprefix(only, ifnp->if_name)) /* only display interfaces which start with ... */ continue; if (!only && islateif(ifnp->if_name)) /* interface prefixes to exclude on generic run */ continue; strlcpy(ifr.ifr_name, ifnp->if_name, sizeof(ifr.ifr_name)); if (ioctl(ifs, SIOCGIFFLAGS, (caddr_t)&ifr) < 0) { printf("%% conf: SIOCGIFFLAGS: %s\n", strerror(errno)); continue; } flags = ifr.ifr_flags; ifr.ifr_data = (caddr_t)&if_data; if (ioctl(ifs, SIOCGIFDATA, (caddr_t)&ifr) < 0) { printf("%% conf: SIOCGIFDATA: %s\n", strerror(errno)); continue; } /* * Keep in mind that the order in which things are displayed * here is important. For instance, we want to setup the * vlan tag before setting the IP address since the vlan * must know what parent to inherit the parent interface * flags from before it is brought up. Another example of * this would be that we need to setup the members on a * bridge before we setup flags on them. */ /* * set interface/bridge mode */ if (!(br = is_bridge(ifs, ifnp->if_name))) br = 0; fprintf(output, "%s %s\n", br ? "bridge" : "interface", ifnp->if_name); /* * description, if available * copied straight from ifconfig.c */ memset(&ifrdesc, 0, sizeof(ifrdesc)); strlcpy(ifrdesc.ifr_name, ifnp->if_name, sizeof(ifrdesc.ifr_name)); ifrdesc.ifr_data = (caddr_t)&ifdescr; if (ioctl(ifs, SIOCGIFDESCR, &ifrdesc) == 0 && strlen(ifrdesc.ifr_data)) fprintf(output, " description %s\n", ifrdesc.ifr_data); /* * print lladdr if necessary */ if ((lladdr = get_hwdaddr(ifnp->if_name)) != NULL) { /* We assume lladdr only useful if we can get_hwdaddr */ StringList *hwdaddr; hwdaddr = sl_init(); if (db_select_flag_x_ctl(hwdaddr, "lladdr", ifnp->if_name) < 0) { printf("%% lladdr database select failed\n"); } if (hwdaddr->sl_cur > 0 && (strcmp(hwdaddr->sl_str[0], lladdr) != 0)) fprintf(output, " lladdr %s\n", lladdr); sl_free(hwdaddr, 1); } /* * print vlan tag, parent if available. if a tag is set * but there is no parent, discard. */ bzero(&vreq, sizeof(struct vlanreq)); ifr.ifr_data = (caddr_t)&vreq; if (ioctl(ifs, SIOCGETVLAN, (caddr_t)&ifr) != -1) { if(vreq.vlr_tag && (vreq.vlr_parent[0] != '\0')) { fprintf(output, " vlan %d parent %s", vreq.vlr_tag, vreq.vlr_parent); fprintf(output, "\n"); } } conf_rdomain(output, ifs, ifnp->if_name); conf_intrtlabel(output, ifs, ifnp->if_name); conf_intgroup(output, ifs, ifnp->if_name); snprintf(leasefile, sizeof(leasefile), "%s.%s", LEASEPREFIX, ifnp->if_name); if ((dhcpif = fopen(leasefile, "r"))) { fprintf(output, " ip dhcp\n"); fclose(dhcpif); conf_ifaddrs(output, ifnp->if_name, flags, AF_INET6); ippntd = 1; } else { ippntd = conf_ifaddrs(output, ifnp->if_name, flags, 0); } if (br) { conf_brcfg(output, ifs, ifn_list, ifnp->if_name); } else { char tmp[24]; conf_media_status(output, ifs, ifnp->if_name); conf_ifmetrics(output, ifs, if_data, ifnp->if_name); conf_keepalive(output, ifs, ifnp->if_name); conf_pfsync(output, ifs, ifnp->if_name); conf_carp(output, ifs, ifnp->if_name); conf_trunk(output, ifs, ifnp->if_name); conf_pflow(output, ifs, ifnp->if_name); conf_ifxflags(output, ifs, ifnp->if_name); if (timeslot_status(ifs, ifnp->if_name, tmp, sizeof(tmp)) == 1) fprintf(output, " timeslots %s\n", tmp); if (conf_dhcrelay(ifnp->if_name, tmp, sizeof(tmp)) > 0) fprintf(output, " dhcrelay %s\n", tmp); } /* * print various flags */ if (flags & IFF_DEBUG) fprintf(output, " debug\n"); if (flags & (IFF_LINK0|IFF_LINK1|IFF_LINK2)) { fprintf(output, " link "); if(flags & IFF_LINK0) fprintf(output, "0 "); if(flags & IFF_LINK1) fprintf(output, "1 "); if(flags & IFF_LINK2) fprintf(output, "2"); fprintf(output, "\n"); } if (flags & IFF_NOARP) fprintf(output, " no arp\n"); /* * ip X/Y turns the interface up (just like 'no shutdown') * ...but if we never had an ip address set and the interface * is up, we need to save this state explicitly. */ if (!ippntd && (flags & IFF_UP)) fprintf(output, " no shutdown\n"); else if (!(flags & IFF_UP)) fprintf(output, " shutdown\n"); fprintf(output, "!\n"); } close(ifs); if_freenameindex(ifn_list); }