From owner-freebsd-mobile Thu May 6 13:59:38 1999 Delivered-To: freebsd-mobile@freebsd.org Received: from dominator.eecs.harvard.edu (dominator.eecs.harvard.edu [140.247.60.28]) by hub.freebsd.org (Postfix) with SMTP id 6398D15BE8 for ; Thu, 6 May 1999 13:59:26 -0700 (PDT) (envelope-from karp@eecs.harvard.edu) Received: (from karp@localhost) by dominator.eecs.harvard.edu (8.6.12/8.6.12) id QAA32433; Thu, 6 May 1999 16:59:25 -0400 Date: Thu, 6 May 1999 16:59:25 -0400 From: Brad Karp Message-Id: <199905062059.QAA32433@dominator.eecs.harvard.edu> To: freebsd-mobile@freebsd.org Subject: if_wi Lucent WaveLAN driver: patches and power management Cc: wpaul@ctr.columbia.edu Sender: owner-freebsd-mobile@FreeBSD.ORG Precedence: bulk X-Loop: FreeBSD.org For anyone who's interested: Bill Paul's WaveLAN 802.11 PC-Card driver, if_wi, was committed before I announced my own driver for this hardware. His driver is not a port of the Linux driver, and so is not GPL'ed, and is less gross, not having started from the nasty Lucent/Linux codebase. I found a couple byte-order bugs in the if_wi driver, that caused coredumps in the user-level configuration program wicontrol, and also resulted in configuration information being improperly written to the card. I submitted patches for these, and Bill's committed them to -current. After those patches, I've verified that this driver works great with WavePoint II base stations. (Bill had asked me to verify this, since I have a base station and he does not.) I'm still in denial over having produced my driver for naught, so in the effort to contribute some shred, here's an enhancement to Bill's driver you might all want: power management support! In short: the WaveLAN PC-Card supports a protocol of alternating sleep/wake, in the interest of saving power, at the expense of some increased receive latency. To use this, you *must* use the card with a base station (the protocol requires the base station's cooperation, and doesn't work in ad-hoc mode), and you need WavePoint firmware 2.03 or newer, and WaveLAN PC-Card firmware 2.00 or newer. (Lower revs, and the WaveLAN card will silently ignore your request to do power management.) Below are patches to add support for power management to Bill's driver. It defaults to off; change it to on with "wicontrol -i wi0 -P 1". You can also change the sleep interval. Longer means more power saving, but worse worst-case receive latency. Shorter, vice-versa. The sleep interval can be changed with "wicontrol -i wi0 -S " (where i is an integer number of milliseconds; 100 ms is the default). Enjoy, -Brad, karp@eecs.harvard.edu --- wi.orig/usr/sbin/wicontrol/wicontrol.c Wed May 5 11:13:18 1999 +++ wi/usr/sbin/wicontrol/wicontrol.c Thu May 6 16:42:40 1999 @@ -308,6 +308,8 @@ { WI_RID_RTS_THRESH, WI_WORDS, "RTS/CTS handshake threshold:\t\t"}, { WI_RID_CREATE_IBSS, WI_BOOL, "Create IBSS:\t\t\t\t" }, { WI_RID_SYSTEM_SCALE, WI_WORDS, "Access point density:\t\t\t" }, + { WI_RID_PM_ENABLED, WI_WORDS, "Power Mgmt (1=on, 0=off):\t\t" }, + { WI_RID_MAX_SLEEP, WI_WORDS, "Max sleep time:\t\t\t\t" }, { 0, NULL } }; @@ -426,6 +428,8 @@ fprintf(stderr, "\t%s -i iface -m mac address\n", p); fprintf(stderr, "\t%s -i iface -d max data length\n", p); fprintf(stderr, "\t%s -i iface -r RTS threshold\n", p); + fprintf(stderr, "\t%s -i iface -P power mgmt\n", p); + fprintf(stderr, "\t%s -i iface -S max sleep duration\n", p); exit(1); } @@ -438,7 +442,7 @@ char *iface = NULL; char *p = argv[0]; - while((ch = getopt(argc, argv, "hoc:d:i:p:r:q:t:n:s:m:")) != -1) { + while((ch = getopt(argc, argv, "hoc:d:i:p:r:q:t:n:s:m:P:S:")) != -1) { switch(ch) { case 'o': wi_dumpstats(iface); @@ -481,6 +485,14 @@ break; case 'q': wi_setstr(iface, WI_RID_OWN_SSID, optarg); + exit(0); + break; + case 'S': + wi_setword(iface, WI_RID_MAX_SLEEP, atoi(optarg)); + exit(0); + break; + case 'P': + wi_setword(iface, WI_RID_PM_ENABLED, atoi(optarg)); exit(0); break; case 'h': --- wi.orig/sys/i386/isa/if_wi.c Wed May 5 11:12:16 1999 +++ /sys/i386/isa/if_wi.c Thu May 6 16:47:07 1999 @@ -323,12 +323,14 @@ sizeof(WI_DEFAULT_IBSS) - 1); sc->wi_portnum = WI_DEFAULT_PORT; sc->wi_ptype = WI_PORTTYPE_ADHOC; sc->wi_ap_density = WI_DEFAULT_AP_DENSITY; sc->wi_rts_thresh = WI_DEFAULT_RTS_THRESH; sc->wi_tx_rate = WI_DEFAULT_TX_RATE; sc->wi_max_data_len = WI_DEFAULT_DATALEN; sc->wi_create_ibss = WI_DEFAULT_CREATE_IBSS; + sc->wi_pm_enabled = WI_DEFAULT_PM_ENABLED; + sc->wi_max_sleep = WI_DEFAULT_MAX_SLEEP; bzero((char *)&sc->wi_stats, sizeof(sc->wi_stats)); @@ -953,6 +955,12 @@ bzero(sc->wi_ibss_name, sizeof(sc->wi_ibss_name)); bcopy((char *)&wreq->wi_val[1], sc->wi_ibss_name, 30); break; + case WI_RID_PM_ENABLED: + sc->wi_pm_enabled = wreq->wi_val[0]; + break; + case WI_RID_MAX_SLEEP: + sc->wi_max_sleep = wreq->wi_val[0]; + break; default: break; } @@ -1087,6 +1095,12 @@ /* Access point density */ WI_SETVAL(WI_RID_SYSTEM_SCALE, sc->wi_ap_density); + + /* Power Management Enabled */ + WI_SETVAL(WI_RID_PM_ENABLED, sc->wi_pm_enabled); + + /* Power Management Max Sleep */ + WI_SETVAL(WI_RID_MAX_SLEEP, sc->wi_max_sleep); /* Specify the IBSS name */ WI_SETSTR(WI_RID_OWN_SSID, sc->wi_ibss_name); --- wi.orig/sys/i386/isa/if_wireg.h Wed May 5 11:12:21 1999 +++ /sys/i386/isa/if_wireg.h Thu May 6 16:46:34 1999 @@ -73,6 +73,8 @@ u_int16_t wi_ap_density; u_int16_t wi_tx_rate; u_int16_t wi_create_ibss; + u_int16_t wi_pm_enabled; + u_int16_t wi_max_sleep; char wi_node_name[32]; char wi_net_name[32]; char wi_ibss_name[32]; @@ -111,6 +113,10 @@ #define WI_DEFAULT_IBSS "FreeBSD IBSS" +#define WI_DEFAULT_PM_ENABLED 0 + +#define WI_DEFAULT_MAX_SLEEP 100 + /* * register space access macros */ @@ -461,7 +467,17 @@ /* * Frame data size. */ #define WI_RID_MAX_DATALEN 0xFC07 + +/* + * ESS power management enable + */ +#define WI_RID_PM_ENABLED 0xFC09 + +/* + * ESS max PM sleep interval + */ +#define WI_RID_MAX_SLEEP 0xFC0C /* * Set our station name. To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-mobile" in the body of the message