/* 1.5.3-GBPPR */ /**************************************************************** * This file is just the front-end application for * configuring the driver. Nothing too special. * * *****************************************************************/ #include #include #include #include #include #include #ifdef CONFIG_NET_RADIO /* If wireless extension exist in the kernel */ /* #include don't include for now ... */ #endif /* CONFIG_NET_RADIO */ #include "lld.h" #include "proxcfg.h" #define SPACE printf(" ") #define TAB printf("\t") #define RETURN printf("\n") #ifndef WIRELESS_EXT /* reversed logic on purpose because we aren't ready for proxcfg to use the extensions */ struct rl2_ioctl_info *ioc; struct ifreq ifr; unsigned char CardMode; void PrintCommonInfo (void); void PrintUsage (void); void atomac (unsigned_8 * string, unsigned_8 * mac); int main (int argc, char *argv[]) { int s, i, j; unsigned int resetLLD = CLEAR; unsigned int printinfoflag = CLEAR; unsigned char data_string[21]; unsigned int data_val, seed, ntval; ioc = (struct rl2_ioctl_info *) &ifr.ifr_data; /**************************************************************** Print usage if called for ****************************************************************/ if (argc == 1 || !strcmp (argv[1], "--help")) { PrintUsage (); return 0; } /**************************************************************** Open a socket to the driver ****************************************************************/ s = socket (AF_INET, SOCK_DGRAM, 0); if (s == -1) { perror ("socket:"); exit (1); } /**************************************************************** Check for some default stuff. We take eth0 as a default or print out info if you didn't try to set a parameter. ****************************************************************/ if (!strcmp (argv[1], "dev")) { if (argc >= 3) { strcpy (ifr.ifr_name, argv[2]); if (argc == 3) printinfoflag = SET; i = 3; } else { strcpy (ifr.ifr_name, "eth0"); i = 2; printinfoflag = SET; } } else { strcpy (ifr.ifr_name, "eth0"); i = 1; } /**************************************************************** This parses the arguments and makes the call to set the parameter via dev ioctl to lls.c. In general, LLDReset we try to call only once so we note if it's needed and call once at the end after parsing all the parameters. ****************************************************************/ for (; i < argc; i++) { /* this is an old parameter. Just leaving in for backward compatibility */ if (!strcmp (argv[i], "info")) { printinfoflag = SET; resetLLD = CLEAR; } else if (!strcmp (argv[i], "secid")) { ioc->cmd = SET_SECID; ioc->data = data_string; /* SET ID */ if (++i >= argc) { PrintUsage (); exit (1); } strcpy (data_string, argv[i]); resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "nwid")) { ioc->cmd = SET_SECID; ioc->data = data_string; /* SET ID */ if (++i >= argc) { PrintUsage (); exit (1); } strcpy (data_string, argv[i]); resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "msta")) { ioc->cmd = SET_NODETYPE; ioc->data = (unsigned char *) &data_val; data_val = 2; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "alt")) { ioc->cmd = SET_NODETYPE; ioc->data = (unsigned char *) &data_val; data_val = 1; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "sta")) { ioc->cmd = SET_NODETYPE; ioc->data = (unsigned char *) &data_val; data_val = 0; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "domain")) { ioc->cmd = SET_DOMAIN; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } data_val = atoi (argv[i]); resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "channel")) { ioc->cmd = SET_CHANNEL; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } data_val = atoi (argv[i]); resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "sub")) { ioc->cmd = SET_SUBCHANNEL; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } data_val = atoi (argv[i]); resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "roamconfig")) { ioc->cmd = SET_ROAM_CONFIG; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } data_val = 1; if (!strcmp (argv[i], "slow")) data_val = 0; if (!strcmp (argv[i], "norm")) data_val = 1; if (!strcmp (argv[i], "fast")) data_val = 2; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "MAC")) { ioc->cmd = SET_MAC_OPT; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } data_val = 2; if (!strcmp (argv[i], "vlite")) data_val = 0; if (!strcmp (argv[i], "lite")) data_val = 1; if (!strcmp (argv[i], "norm")) data_val = 2; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "name")) { ioc->cmd = SET_MASTERNAME; ioc->data = data_string; if (++i >= argc) { PrintUsage (); exit (1); } strcpy (data_string, argv[i]); resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "debug")) { ioc->cmd = SET_DEBUG; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } if (!strcmp (argv[i], "on")) data_val = FLAGSET; else data_val = CLEAR; printinfoflag = SET; } else if (!strcmp (argv[i], "peer-to-peer")) { ioc->cmd = SET_PEER_TO_PEER; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } if (!strcmp (argv[i], "on")) data_val = 1; else data_val = 0; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "ITO")) { int tmp; ioc->cmd = SET_ITO; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } data_val = atoi (argv[i]); resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "roam")) { ioc->cmd = SET_DISABLE_ROAM; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } if (!strcmp (argv[i], "disable")) data_val = 1; else data_val = 0; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "bridge")) { ioc->cmd = SET_BRIDGING; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } if (!strcmp (argv[i], "disable")) data_val = 0; else data_val = 1; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "bfreq")) { ioc->cmd = SET_BFREQ; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } data_val = atoi (argv[i]); resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "hop")) { ioc->cmd = SET_HOP_PERIOD; ioc->data = (unsigned char *) &data_val; if (++i >= argc) { PrintUsage (); exit (1); } data_val = 1; if (!strcmp (argv[i], "100")) data_val = 0; if (!strcmp (argv[i], "200")) data_val = 1; if (!strcmp (argv[i], "400")) data_val = 2; if (!strcmp (argv[i], "20")) data_val = 3; resetLLD = SET; printinfoflag = SET; } else if (!strcmp (argv[i], "node")) { if (++i >= argc) { PrintUsage (); exit (1); } ioc->cmd = SET_NODE_OVERRIDE; ioc->data = data_string; atomac (argv[i], data_string); resetLLD = SET; printinfoflag = SET; } else { PrintUsage (); exit (1); } if (ioctl (s, SIOCDEVPRIVATE, &ifr) == -1) { perror ("proxcfg: ioctl"); PrintUsage (); exit (1); } } /**************************************************************** We try to reset only once. It takes a second or two and becomes a hassle if we were to call after every parameter. ****************************************************************/ if (resetLLD) { ioc->cmd = SET_LLDRESET; if (ioctl (s, SIOCDEVPRIVATE, &ifr) == -1) { perror ("ioctl"); exit (1); } } /**************************************************************** The reset of this prints out the current configuration Note that printing to the log is done by lls.c ****************************************************************/ if (printinfoflag) { ioc->cmd = GET_DRIVERVERSION; ioc->data = data_string; if (ioctl (s, SIOCDEVPRIVATE, &ifr) == -1) { perror ("ioctl"); exit (1); } PrintCommonInfo (); /* Everything before this is common for all cards. After this, we need to use CardMode (openair|homerf) and ntval to decide what's useful to print. */ if (CardMode == 0) { /* OpenAir */ ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_DOMAIN; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Domain : %s%d%s\n", BLD, *ioc->data, CLR); } ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_NODETYPE; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Node type : %s%s%s\n", BLD, nodetypes[ntval = *ioc->data], CLR); if (ntval != 0) { /* not a station */ if (CardMode == 0) { ioc->data = data_string; ioc->cmd = GET_MASTERNAME; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Master name : %s%s%s\n", BLD, ioc->data, CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_CHANNEL; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Channel : %s%d%s\n", BLD, *ioc->data, CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_SUBCHANNEL; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Subchannel : %s%d%s\n", BLD, *ioc->data, CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_MAC_OPT; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" MAC optimize : %s%s%s\t[Very light | Light | Normal]\n", BLD, macconfigtypes[*ioc->data], CLR); } else printf (" "); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_HOP_PERIOD; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Hopping period : %s%s%s\t[20 | 100 | 200 | 400]\n", BLD, hoptypes[*ioc->data], CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_BFREQ; ioctl (s, SIOCDEVPRIVATE, &ifr); printf ("Beacon frequency : %s%d%s\n", BLD, *ioc->data, CLR); } printf ("\n"); if (ntval != 2) { /* not a master */ ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_SYNCSTATE; ioctl (s, SIOCDEVPRIVATE, &ifr); if (*ioc->data) { printf (" Sync'd master : "); if (CardMode == 0) { ioc->data = data_string; ioc->cmd = GET_MSTASYNCNAME; ioctl (s, SIOCDEVPRIVATE, &ifr); printf ("%s%s%s\t", BLD, ioc->data, CLR); } printf ("(MAC address : "); ioc->data = data_string; ioc->cmd = GET_MSTAADDR; ioctl (s, SIOCDEVPRIVATE, &ifr); for (j = 0; j < 5; j++) printf ("%s%2.2x:", BLD, ioc->data[j]); printf ("%2.2x%s)\n", ioc->data[j], CLR); /* add sync-to network id? */ if (CardMode == 0) { ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_MSTASYNCCHANNEL; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Channel : %s%d%s\n", BLD, *ioc->data, CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_MSTASYNCSUBCHANNEL; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Subchannel : %s%d%s\n", BLD, *ioc->data, CLR); } } else printf (" %sOut of sync with the master!%s\n", BLINKRED, CLR); RETURN; ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_PEER_TO_PEER; ioctl (s, SIOCDEVPRIVATE, &ifr); if (*ioc->data) printf (" Peer-to-Peer : %sEnabled%s\n", YEL, CLR); else printf (" Peer-to-Peer : %sDisabled%s\n", YEL, CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_ITO; ioctl (s, SIOCDEVPRIVATE, &ifr); printf ("Inactivity timeout : %s%d%s\n", YEL, *ioc->data, CLR); if (CardMode == 0) { ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_ROAM_CONFIG; ioctl (s, SIOCDEVPRIVATE, &ifr); printf ("Roam configuration : %s%s%s\t", YEL, roamtypes[*ioc->data], CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_DISABLE_ROAM; ioctl (s, SIOCDEVPRIVATE, &ifr); if (*ioc->data) printf ("(Roaming : %sDisabled%s)\n", YEL, CLR); else printf ("(Roaming : %sEnabled%s)\n", YEL, CLR); } RETURN; } /* for all cards */ ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_DEBUG; ioctl (s, SIOCDEVPRIVATE, &ifr); if (*ioc->data) printf (" Debugging : %sEnabled%s\n", YEL, CLR); else printf (" Debugging : %sDisabled%s\n", YEL, CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_BRIDGING; ioctl (s, SIOCDEVPRIVATE, &ifr); if (*ioc->data) printf (" Bridging : %sEnabled%s\n"); else printf (" Bridging : %sDisabled%s\n", YEL, CLR); } RETURN; return 0; } void PrintUsage (void) { fprintf (stderr, "Usage:\tproxcfg\t--help\n"); fprintf (stderr, "\tproxcfg\t[dev {ifname}] [sta|alt|msta] [domain {d}]\n"); fprintf (stderr, "\t\t[secid {password}] [nwid {network ID}\n"); fprintf (stderr, "\t\t[channel {c}] [sub {s}] [name {name}]\n"); fprintf (stderr, "\t\t[roamconfig (slow|norm|fast)] [MAC (vlite|lite|norm)]\n"); fprintf (stderr, "\t\t[debug (on|off)] [peer-to-peer (on|off)]\n"); fprintf (stderr, "\t\t[ITO {seconds}] [roam (enable|disable)]\n"); fprintf (stderr, "\t\t[bridge (enable|disable)]\n"); fprintf (stderr, "\t\t[hop (20|100|200|400)]\n"); /* fprintf(stderr, "\t\t[bfreq {beacon frequency}]\n"); fprintf(stderr, "\t\t[node {xx xx xx xx xx xx}]\n"); */ } void PrintCommonInfo (void) { int s, j; char data_string[21]; unsigned int data_val, CardName; s = socket (AF_INET, SOCK_DGRAM, 0); ioc = (struct rl2_ioctl_info *) &ifr.ifr_data; ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_CARD_NAME; ioctl (s, SIOCDEVPRIVATE, &ifr); printf ("\nInformation for a %s%s%s", MAG, card_types[CardName = *ioc->data], CLR); printf (" on device %s%s%s\n\n", MAG, ifr.ifr_name, CLR); ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_PROTO_MODE; ioctl (s, SIOCDEVPRIVATE, &ifr); if (CardMode = (unsigned char) *ioc->data) printf (" Protocol mode : %sHome RF%s\n", CYN, BLD); else printf (" Protocol mode : %sOpenAir%s\n", CYN, CLR); if (CardName >= 6) { ioc->data = (unsigned char *) &data_val; ioc->cmd = GET_CARD_CONFIG; ioctl (s, SIOCDEVPRIVATE, &ifr); TAB; printf ("Card Configuration:%s", CardConfig[*ioc->data]); RETURN; } ioc->data = data_string; ioc->cmd = GET_DRIVERVERSION; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Driver : %s%s%s\n", CYN, ioc->data, CLR); ioc->data = data_string; ioc->cmd = GET_ROMVERSION; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Firmware : %s%s%s\n", CYN, ioc->data, CLR); ioc->data = data_string; ioc->cmd = GET_ADDR; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" MAC address : "); for (j = 0; j < 5; j++) printf ("%s%2.2x:", CYN, ioc->data[j]); printf ("%2.2x%s\n", ioc->data[j], CLR); ioc->data = data_string; ioc->cmd = GET_CC; ioctl (s, SIOCDEVPRIVATE, &ifr); printf (" Country code : %s%2.2x-%2.2x%s\n\n", CYN, ioc->data[0], ioc->data[1], CLR); } void atomac (unsigned_8 * string, unsigned_8 * mac) { unsigned_8 index, j, k, digit; for (j = 0; j < 6; j++) { mac[j] = 0; for (k = 0; k < 2; k++) { index = 2 * j + k; if ((digit = *(string + index) - '0') < 10); else if (((digit = *(string + index) - 'a' + 10) >= 0xa) && (digit <= 0xf)); else if (((digit = *(string + index) - 'A' + 10) >= 0xa) && (digit <= 0xf)); else digit = 0; mac[j] += ((digit &= 0x0f) << ((1 - k) * 4)); } } } #else /* * Hack my way... Jean II * Compile with -lm */ #include /*#include */ #include /*#include */ #include #include #include #include #include #include #include #include #include #include /* Some usefull constants */ #define KILO 1e3 #define MEGA 1e6 #define GIGA 1e9 typedef struct iw_statistics iwstats; typedef struct iw_range iwrange; typedef struct iw_freq iwfreq; /* Structure for storing all wireless information for each device */ struct wireless_info { char dev[IFNAMSIZ]; /* Interface name (device) */ char name[12]; /* Wireless name */ int has_nwid; int nwid_on; u_long nwid; /* Network ID */ int has_freq; float freq; /* Frequency/channel */ int has_sens; u_long sens; /* sensitivity */ int has_enc; int enc_method; /* encoding method or off */ long long enc_key; /* key used */ /* Stats */ iwstats stats; int has_stats; iwrange range; int has_range; }; int skfd = -1; /* generic raw socket desc. */ int ipx_sock = -1; /* IPX socket */ int ax25_sock = -1; /* AX.25 socket */ int inet_sock = -1; /* INET socket */ int ddp_sock = -1; /* Appletalk DDP socket */ static void iw_usage (void) { fprintf (stderr, "Usage: proxcfg interface\n"); fprintf (stderr, " [domain NN]\n"); fprintf (stderr, " [freq N.NN[k, M or G]]\n"); fprintf (stderr, " [sens N]\n"); fprintf (stderr, " [enc NNNN-NNNN]\n"); exit (1); } static void print_info (struct wireless_info *info) { /* Display device name */ printf ("%-8.8s ", info->dev); /* Display wireless name */ printf ("%s ", info->name); /* Display Network ID */ printf ("NWID:%lX ", info->nwid); /* Display frequency / channel */ printf ("Channel:%g ", info->freq); printf ("\n"); if (info->has_stats) { if (info->has_range) printf (" Link quality:%d/%d Signal level:%d/%d Noise level:%d/%d\n", info->stats.qual.qual, info->range.max_qual.qual, info->stats.qual.level, info->range.max_qual.level, info->stats.qual.noise, info->range.max_qual.noise); else printf (" Link quality:%d Signal level:%d Noise level:%d\n", info->stats.qual.qual, info->stats.qual.level, info->stats.qual.noise); printf (" Rx invalid nwid:%d invalid crypt:%d invalid misc:%d\n", info->stats.discard.nwid, info->stats.discard.code, info->stats.discard.misc); } printf ("\n"); } static int if_getstats (char *ifname, iwstats * stats) { FILE *f = fopen ("/proc/net/wireless", "r"); char buf[256]; char *bp; if (f == NULL) return -1; while (fgets (buf, 255, f)) { bp = buf; while (*bp && isspace (*bp)) bp++; if (strncmp (bp, ifname, strlen (ifname)) == 0 && bp[strlen (ifname)] == ':') { bp = strchr (bp, ':'); bp++; bp = strtok (bp, " ."); sscanf (bp, "%X", &stats->status); bp = strtok (NULL, " ."); sscanf (bp, "%d", &stats->qual.qual); bp = strtok (NULL, " ."); sscanf (bp, "%d", &stats->qual.level); bp = strtok (NULL, " ."); sscanf (bp, "%d", &stats->qual.noise); bp = strtok (NULL, " ."); sscanf (bp, "%d", &stats->discard.nwid); bp = strtok (NULL, " ."); sscanf (bp, "%d", &stats->discard.code); bp = strtok (NULL, " ."); sscanf (bp, "%d", &stats->discard.misc); fclose (f); return 0; } } fclose (f); return 0; } /* Get wireless informations & config from the device driver */ static int get_info (char *ifname, struct wireless_info *info) { struct iwreq wrq; memset ((char *) info, 0, sizeof (struct wireless_info)); /* Get device name */ strcpy (info->dev, ifname); /* Get wireless name */ strcpy (wrq.ifr_name, ifname); if (ioctl (skfd, SIOCGIWNAME, &wrq) < 0) /* If no wireless name : no wireless extensions */ return (-1); else strcpy (info->name, wrq.u.name); /* Get network ID */ strcpy (wrq.ifr_name, ifname); if (ioctl (skfd, SIOCGIWNWID, &wrq) >= 0) { info->has_nwid = 1; info->nwid_on = wrq.u.nwid.on; info->nwid = wrq.u.nwid.nwid; } /* Get frequency / channel */ strcpy (wrq.ifr_name, ifname); if (ioctl (skfd, SIOCGIWFREQ, &wrq) >= 0) { info->has_freq = 1; } /* Get sensitivity */ strcpy (wrq.ifr_name, ifname); if (ioctl (skfd, SIOCGIWSENS, &wrq) >= 0) { info->has_sens = 1; info->sens = wrq.u.sensitivity; } /* Get encryption information */ strcpy (wrq.ifr_name, ifname); if (ioctl (skfd, SIOCGIWENCODE, &wrq) >= 0) { info->has_enc = 1; info->enc_method = wrq.u.encoding.method; info->enc_key = wrq.u.encoding.code; } /* Get stats */ if (if_getstats (ifname, &(info->stats)) == 0) { info->has_stats = 1; } /* Get ranges */ strcpy (wrq.ifr_name, ifname); wrq.u.data.pointer = (caddr_t) & (info->range); wrq.u.data.length = 0; wrq.u.data.flags = 0; if (ioctl (skfd, SIOCGIWRANGE, &wrq) >= 0) { info->has_range = 1; } return (0); } static int set_info (char *args[], /* Command line args */ int count, /* Args count */ char *ifname) /* Dev name */ { struct iwreq wrq; int i; /* Set dev name */ strncpy (wrq.ifr_name, ifname, IFNAMSIZ); /* List of frequencies and channel numbers */ if ((!strncmp (args[0], "list_freq", 9)) || (!strcmp (args[0], "list_channel"))) { float freq; struct iw_range range; int k; if (count > 1) iw_usage (); wrq.u.data.pointer = (caddr_t) & range; wrq.u.data.length = 0; wrq.u.data.flags = 0; if (ioctl (skfd, SIOCGIWRANGE, &wrq) < 0) { fprintf (stderr, "SIOCGIWRANGE: %s\n", strerror (errno)); return (-1); } printf ("%d channels", range.num_channels); if (range.num_frequency != 0) printf (" ; available frequencies :"); for (k = 0; k < range.num_frequency; k++) { if (freq > GIGA) printf (" %gGHz ", freq / GIGA); else if (freq > MEGA) printf (" %gMHz ", freq / MEGA); else printf (" %gkHz ", freq / KILO); } printf ("\n"); return 0; /* no more arg */ } /* The other args on the line specify options to be set... */ for (i = 0; i < count; i++) { /* Set network ID */ if ((!strcmp (args[i], "nwid")) || (!strcmp (args[i], "domain"))) { i++; if (i >= count) iw_usage (); if (!strcasecmp (args[i], "off")) wrq.u.nwid.on = 0; else if (!strcasecmp (args[i], "on")) { /* Get old nwid */ if (ioctl (skfd, SIOCGIWNWID, &wrq) < 0) { fprintf (stderr, "SIOCGIWNWID: %s\n", strerror (errno)); return (-1); } strcpy (wrq.ifr_name, ifname); wrq.u.nwid.on = 1; } else if (sscanf (args[i], "%lX", &(wrq.u.nwid.nwid)) != 1) iw_usage (); else wrq.u.nwid.on = 1; if (ioctl (skfd, SIOCSIWNWID, &wrq) < 0) { fprintf (stderr, "SIOCSIWNWID: %s\n", strerror (errno)); return (-1); } continue; } /* Set frequency / channel */ if ((!strncmp (args[i], "freq", 4)) || (!strcmp (args[i], "channel"))) { float freq; if (++i >= count) iw_usage (); if (sscanf (args[i], "%g", &(freq)) != 1) iw_usage (); if (index (args[i], 'G')) freq *= GIGA; if (index (args[i], 'M')) freq *= MEGA; if (index (args[i], 'k')) freq *= KILO; if (ioctl (skfd, SIOCSIWFREQ, &wrq) < 0) { fprintf (stderr, "SIOCSIWFREQ: %s\n", strerror (errno)); return (-1); } continue; } /* Set sensitivity */ if (!strncmp (args[i], "sens", 4)) { if (++i >= count) iw_usage (); if (sscanf (args[i], "%ld", &(wrq.u.sensitivity)) != 1) iw_usage (); if (ioctl (skfd, SIOCSIWSENS, &wrq) < 0) { fprintf (stderr, "SIOCSIWSENS: %s\n", strerror (errno)); return (-1); } continue; } /* Set encryption stuff */ if (!strncmp (args[i], "enc", 3)) { unsigned long long key = 0; if (++i >= count) iw_usage (); if (!strcasecmp (args[i], "off")) wrq.u.encoding.method = 0; else { if (!strcasecmp (args[i], "on")) { /* Get old encryption information */ if (ioctl (skfd, SIOCGIWENCODE, &wrq) < 0) { fprintf (stderr, "SIOCGIWENCODE: %s\n", strerror (errno)); return (-1); } strcpy (wrq.ifr_name, ifname); } else { char *buff; char *p; u_long temp; p = buff = malloc (strlen (args[i] + 1)); strcpy (buff, args[i]); p = strtok (buff, "-:;.,*#"); while (p != (char *) NULL) { key = key << 16; if (sscanf (p, "%lX", &temp) != 1) iw_usage (); key += temp; p = strtok ((char *) NULL, "-:;.,*#"); } free (buff); wrq.u.encoding.code = key; } /* TODO : check for "(method)" in args list */ wrq.u.encoding.method = 1; } if (ioctl (skfd, SIOCSIWENCODE, &wrq) < 0) { fprintf (stderr, "SIOCSIWENCODE(%d): %s\n", errno, strerror (errno)); return (-1); } continue; } /* Here we have an unrecognised arg... */ fprintf (stderr, "Invalid argument : %s\n", args[i]); iw_usage (); return (-1); } /* for(index ... */ return (0); } static void print_devices (char *ifname) { char buff[1024]; struct wireless_info info; struct ifconf ifc; struct ifreq *ifr; int i; if (ifname == (char *) NULL) { ifc.ifc_len = sizeof (buff); ifc.ifc_buf = buff; if (ioctl (skfd, SIOCGIFCONF, &ifc) < 0) { fprintf (stderr, "SIOCGIFCONF: %s\n", strerror (errno)); return; } ifr = ifc.ifc_req; for (i = ifc.ifc_len / sizeof (struct ifreq); --i >= 0; ifr++) { if (get_info (ifr->ifr_name, &info) < 0) { /* Could skip this message ? */ fprintf (stderr, "%-8.8s no wireless extensions.\n\n", ifr->ifr_name); continue; } print_info (&info); } } else { if (get_info (ifname, &info) < 0) { fprintf (stderr, "%s: no wireless extensions.\n", ifname); iw_usage (); } else print_info (&info); } } static int sockets_open () { inet_sock = socket (AF_INET, SOCK_DGRAM, 0); ipx_sock = socket (AF_IPX, SOCK_DGRAM, 0); ax25_sock = socket (AF_AX25, SOCK_DGRAM, 0); ddp_sock = socket (AF_APPLETALK, SOCK_DGRAM, 0); /* * Now pick any (exisiting) useful socket family for generic queries */ if (inet_sock != -1) return inet_sock; if (ipx_sock != -1) return ipx_sock; if (ax25_sock != -1) return ax25_sock; /* * If this is -1 we have no known network layers and its time to jump. */ return ddp_sock; } int main (int argc, char **argv) { int goterr = 0; /* Create a channel to the NET kernel. */ if ((skfd = sockets_open ()) < 0) { perror ("socket"); exit (-1); } /* No argument : show the list of all device + info */ if (argc == 1) { print_devices ((char *) NULL); close (skfd); exit (0); } /* The device name must be the first argument */ if (argc == 2) { print_devices (argv[1]); close (skfd); exit (0); } /* The other args on the line specify options to be set... */ goterr = set_info (argv + 2, argc - 2, argv[1]); /* Close the socket. */ close (skfd); return (goterr); } #endif /* WIRELESS_EXT */