dockapps/wmwifi/src/wireless.c
2014-10-05 19:18:49 +01:00

162 lines
3.8 KiB
C

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <X11/X.h>
#include <X11/xpm.h>
#include "wmwifi.h"
#include <net/ethernet.h>
#include <linux/if.h>
#include <linux/socket.h>
#include <linux/wireless.h>
/*
* This is my quick and dirty way of accessing the Linux Wireless Extensions
* from the /proc/net/wireless interface.
* Open the file, and get the Interface name, link, level, and noise.
* - Jess
*/
int get_wifi_info(struct wifi *wfi)
{
struct iwreq wrq;
struct iw_range range;
int skfd;
float ret;
int i;
FILE *fp;
char buff[1024] = "";
if (fp = fopen("/proc/net/wireless", "r")) {
//if (fp = fopen("./demo.txt", "r")) {
for (i = 0; i < (wfi->ifnum + 3); i++) {
fgets(buff, sizeof(buff), fp);
buff[strlen(buff) + 1] = '\0';
}
fclose(fp);
} else {
wfi->max_qual = -1;
fprintf(stdout,
"ERROR: Cannot Open Linux Wireless Extensions!\n\b");
// exit(1);
}
sscanf(buff, "%s %*s %f %d", &wfi->ifname, &wfi->link, &wfi->level);
/* Don't know why I have to make a second call to sscanf
* to pull wfi->noise, but for some wierd reason I cannot
* pull it above along with the other stats.
*/
sscanf(buff, "%*s %*s %*s %*s %d", &wfi->noise);
/* Thanks to Jeroen Nijhof <jnijhof@nijhofnet.nl>
* for catching this, I guess I overlooked it.
* Strip out the trailing ':' if exists.
*/
if (wfi->ifname[strlen(wfi->ifname) - 1] == ':') {
wfi->ifname[strlen(wfi->ifname) - 1] = '\0';
}
memset(&wfi->essid, 0, IW_ESSID_MAX_SIZE + 1);
skfd = socket(AF_INET, SOCK_DGRAM, 0);
memset(&range, 0, sizeof(struct iw_range));
wrq.u.data.pointer = (caddr_t) & range;
wrq.u.data.length = sizeof(struct iw_range);
wrq.u.data.flags = 0;
strncpy(wrq.ifr_name, wfi->ifname, IFNAMSIZ);
ret = ioctl(skfd, SIOCGIWRANGE, &wrq);
if (ret > -1) {
ret = range.max_qual.qual;
} else {
fprintf(stdout, "ERROR\n");
/* Maybe put auto-learning HERE? */
}
wfi->max_qual = ret;
wrq.u.essid.pointer = (caddr_t) wfi->essid;
wrq.u.essid.length = IW_ESSID_MAX_SIZE + 1;
wrq.u.essid.flags = 0;
ret = ioctl(skfd, SIOCGIWESSID, &wrq);
ret = ioctl(skfd, SIOCGIWRATE, &wrq);
memcpy(&(wfi->bitrate), &(wrq.u.bitrate), sizeof(struct iw_param));
if (strlen(wfi->essid) < 1) {
strcpy(wfi->essid, "not_set");
}
if (wfi->link > wfi->max_link) {
wfi->max_link = wfi->link;
}
if (wfi->max_link > wfi->max_qual) {
wfi->max_qual = wfi->max_link;
}
/*
* For debugging purposes.
* Check these values against /proc/net/wireless and
* iwconfig
*
fprintf(stdout, "wfi->ifname -> %s\n", wfi->ifname);
fprintf(stdout, "wfi->max_qual -> %f\n", wfi->max_qual);
fprintf(stdout, "wfi->essid -> %s\n", wfi->essid);
fprintf(stdout, "wfi->link -> %f\n", wfi->link);
fprintf(stdout, "wfi->level -> %d\n", wfi->level);
fprintf(stdout, "wfi->noise -> %d\n", wfi->noise - 0x100);
fprintf(stdout, "wfi->bitrate -> %d\n", wfi->bitrate.value);
fprintf(stdout, "wfi->max_link -> %.f\n", wfi->max_link);
*/
close(skfd);
return ret;
}
void next_if(struct wifi *wfi)
{
int max;
max = get_max_ifs();
wfi->max_link = 0;
if (wfi->ifnum < max) {
wfi->ifnum++;
} else {
wfi->ifnum = 0;
}
}
/* Not used anymore, how many mouse button's do
* you have?
*/
void last_if(struct wifi *wfi)
{
int max;
max = get_max_ifs();
wfi->max_link = 0;
if (wfi->ifnum > 0) {
wfi->ifnum--;
} else {
wfi->ifnum = max;
}
}
int get_max_ifs(void)
{
FILE *fp;
char buff[255];
int i = 0;
if (fp = fopen("/proc/net/wireless", "r")) {
//if (fp = fopen("./demo.txt", "r")) {
for (i = -3; fgets(buff, sizeof(buff), fp); i++) {
}
fclose(fp);
}
return i;
}