Home | History | Annotate | Line # | Download | only in ifconfig
env.c revision 1.1
      1 #include <errno.h>
      2 #include <string.h>
      3 #include <stdlib.h>
      4 #include <util.h>
      5 
      6 #include <net/if.h>
      7 #include <sys/socket.h>
      8 #include <sys/ioctl.h>
      9 
     10 #include "env.h"
     11 #include "util.h"
     12 
     13 prop_dictionary_t
     14 prop_dictionary_augment(prop_dictionary_t bottom, prop_dictionary_t top)
     15 {
     16 	prop_object_iterator_t i;
     17 	prop_dictionary_t d;
     18 	prop_object_t ko, o;
     19 	prop_dictionary_keysym_t k;
     20 	const char *key;
     21 
     22 	d = prop_dictionary_copy_mutable(bottom);
     23 
     24 	i = prop_dictionary_iterator(top);
     25 
     26 	while ((ko = prop_object_iterator_next(i)) != NULL) {
     27 		k = (prop_dictionary_keysym_t)ko;
     28 		key = prop_dictionary_keysym_cstring_nocopy(k);
     29 		o = prop_dictionary_get_keysym(top, k);
     30 		if (o == NULL || !prop_dictionary_set(d, key, o)) {
     31 			prop_object_release((prop_object_t)d);
     32 			d = NULL;
     33 			break;
     34 		}
     35 	}
     36 	prop_object_iterator_release(i);
     37 	prop_dictionary_make_immutable(d);
     38 	return d;
     39 }
     40 
     41 int
     42 getifflags(prop_dictionary_t env, prop_dictionary_t oenv,
     43     unsigned short *flagsp)
     44 {
     45 	struct ifreq ifr;
     46 	prop_number_t num;
     47 	const char *ifname;
     48 	int s;
     49 
     50 	num = (prop_number_t)prop_dictionary_get(env, "ifflags");
     51 
     52 	if (num != NULL) {
     53 		*flagsp = (unsigned short)prop_number_integer_value(num);
     54 		return 0;
     55 	}
     56 
     57 	if ((s = getsock(AF_UNSPEC)) == -1)
     58 		return -1;
     59 
     60 	if ((ifname = getifname(env)) == NULL)
     61 		return -1;
     62 
     63 	memset(&ifr, 0, sizeof(ifr));
     64 	estrlcpy(ifr.ifr_name, ifname, sizeof(ifr.ifr_name));
     65 	if (ioctl(s, SIOCGIFFLAGS, &ifr) == -1)
     66 		return -1;
     67 
     68 	*flagsp = (unsigned short)ifr.ifr_flags;
     69 
     70 	num = prop_number_create_unsigned_integer(
     71 	    (unsigned short)ifr.ifr_flags);
     72 	(void)prop_dictionary_set(oenv, "ifflags", num);
     73 	prop_object_release((prop_object_t)num);
     74 
     75 	return 0;
     76 }
     77 
     78 const char *
     79 getifinfo(prop_dictionary_t env, prop_dictionary_t oenv, unsigned short *flagsp)
     80 {
     81 	if (getifflags(env, oenv, flagsp) == -1)
     82 		return NULL;
     83 
     84 	return getifname(env);
     85 }
     86 
     87 const char *
     88 getifname(prop_dictionary_t env)
     89 {
     90 	prop_string_t str;
     91 
     92 	str = (prop_string_t)prop_dictionary_get(env, "if");
     93 	if (str == NULL)
     94 		return NULL;
     95 	return prop_string_cstring_nocopy(str);
     96 }
     97 
     98 ssize_t
     99 getargdata(prop_dictionary_t env, const char *key, uint8_t *buf, size_t buflen)
    100 {
    101 	prop_data_t data;
    102 	size_t datalen;
    103 
    104 	data = (prop_data_t)prop_dictionary_get(env, key);
    105 	if (data == NULL) {
    106 		errno = ENOENT;
    107 		return -1;
    108 	}
    109 	datalen = prop_data_size(data);
    110 	if (datalen > buflen) {
    111 		errno = ENAMETOOLONG;
    112 		return -1;
    113 	}
    114 	memset(buf, 0, buflen);
    115 	memcpy(buf, prop_data_data_nocopy(data), datalen);
    116 	return datalen;
    117 }
    118 
    119 ssize_t
    120 getargstr(prop_dictionary_t env, const char *key, char *buf, size_t buflen)
    121 {
    122 	prop_data_t data;
    123 	size_t datalen;
    124 
    125 	data = (prop_data_t)prop_dictionary_get(env, "bssid");
    126 	if (data == NULL) {
    127 		errno = ENOENT;
    128 		return -1;
    129 	}
    130 	datalen = prop_data_size(data);
    131 	if (datalen >= buflen) {
    132 		errno = ENAMETOOLONG;
    133 		return -1;
    134 	}
    135 	memset(buf, 0, buflen);
    136 	memcpy(buf, prop_data_data_nocopy(data), datalen);
    137 	return datalen;
    138 }
    139 
    140 int
    141 getaf(prop_dictionary_t env)
    142 {
    143 	prop_number_t num;
    144 
    145 	num = (prop_number_t)prop_dictionary_get(env, "af");
    146 	if (num == NULL) {
    147 		errno = ENOENT;
    148 		return -1;
    149 	}
    150 	return (int)prop_number_integer_value(num);
    151 }
    152