From owner-p4-projects@FreeBSD.ORG Fri Nov 2 18:53:40 2007 Return-Path: Delivered-To: p4-projects@freebsd.org Received: by hub.freebsd.org (Postfix, from userid 32767) id F001E16A506; Fri, 2 Nov 2007 18:53:39 +0000 (UTC) Delivered-To: perforce@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id E6C6716A419 for ; Fri, 2 Nov 2007 18:53:38 +0000 (UTC) (envelope-from delphij@freebsd.org) Received: from repoman.freebsd.org (repoman.freebsd.org [IPv6:2001:4f8:fff6::29]) by mx1.freebsd.org (Postfix) with ESMTP id D374F13C45D for ; Fri, 2 Nov 2007 18:53:38 +0000 (UTC) (envelope-from delphij@freebsd.org) Received: from repoman.freebsd.org (localhost [127.0.0.1]) by repoman.freebsd.org (8.14.1/8.14.1) with ESMTP id lA2I0sgR071666 for ; Fri, 2 Nov 2007 18:00:54 GMT (envelope-from delphij@freebsd.org) Received: (from perforce@localhost) by repoman.freebsd.org (8.14.1/8.14.1/Submit) id lA2I0rx0071650 for perforce@freebsd.org; Fri, 2 Nov 2007 18:00:53 GMT (envelope-from delphij@freebsd.org) Date: Fri, 2 Nov 2007 18:00:53 GMT Message-Id: <200711021800.lA2I0rx0071650@repoman.freebsd.org> X-Authentication-Warning: repoman.freebsd.org: perforce set sender to delphij@freebsd.org using -f From: Xin LI To: Perforce Change Reviews Cc: Subject: PERFORCE change 128517 for review X-BeenThere: p4-projects@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: p4 projects tree changes List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 02 Nov 2007 18:53:40 -0000 http://perforce.freebsd.org/chv.cgi?CH=128517 Change 128517 by delphij@charlie on 2007/11/02 18:00:13 IFC Affected files ... .. //depot/projects/delphij_fork/Makefile.inc1#6 integrate .. //depot/projects/delphij_fork/bin/mv/mv.1#2 integrate .. //depot/projects/delphij_fork/include/_ctype.h#3 integrate .. //depot/projects/delphij_fork/lib/libthr/thread/thr_mutex.c#3 integrate .. //depot/projects/delphij_fork/libexec/Makefile#2 integrate .. //depot/projects/delphij_fork/sbin/gpt/boot.c#2 integrate .. //depot/projects/delphij_fork/sbin/gpt/gpt.c#3 integrate .. //depot/projects/delphij_fork/sbin/ifconfig/ifconfig.8#4 integrate .. //depot/projects/delphij_fork/sbin/ifconfig/ifieee80211.c#2 integrate .. //depot/projects/delphij_fork/sbin/route/route.8#2 integrate .. //depot/projects/delphij_fork/share/man/man3/queue.3#2 integrate .. //depot/projects/delphij_fork/share/man/man4/ng_car.4#2 integrate .. //depot/projects/delphij_fork/share/man/man4/ng_netflow.4#2 integrate .. //depot/projects/delphij_fork/share/man/man5/bluetooth.device.conf.5#2 integrate .. //depot/projects/delphij_fork/share/man/man5/xfs.5#2 integrate .. //depot/projects/delphij_fork/share/misc/committers-ports.dot#3 integrate .. //depot/projects/delphij_fork/sys/arm/arm/cpufunc.c#5 integrate .. //depot/projects/delphij_fork/sys/arm/include/cpuconf.h#3 integrate .. //depot/projects/delphij_fork/sys/compat/opensolaris/kern/opensolaris_vfs.c#2 integrate .. //depot/projects/delphij_fork/sys/conf/options.arm#3 integrate .. //depot/projects/delphij_fork/sys/contrib/opensolaris/uts/common/fs/zfs/zfs_znode.c#3 integrate .. //depot/projects/delphij_fork/sys/contrib/opensolaris/uts/common/fs/zfs/zvol.c#3 integrate .. //depot/projects/delphij_fork/sys/dev/aac/aac.c#3 integrate .. //depot/projects/delphij_fork/sys/dev/aac/aac_cam.c#2 integrate .. //depot/projects/delphij_fork/sys/dev/acpica/acpi_cpu.c#3 integrate .. //depot/projects/delphij_fork/sys/kern/kern_cpu.c#3 integrate .. //depot/projects/delphij_fork/sys/modules/Makefile#8 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211.h#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_freebsd.c#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_freebsd.h#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_ht.c#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_ht.h#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_input.c#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_ioctl.c#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_ioctl.h#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_node.c#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_node.h#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_output.c#4 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_proto.c#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_proto.h#3 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_scan_ap.c#2 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_scan_sta.c#4 integrate .. //depot/projects/delphij_fork/sys/net80211/ieee80211_var.h#3 integrate .. //depot/projects/delphij_fork/sys/netgraph/bluetooth/socket/ng_btsocket_l2cap.c#3 integrate .. //depot/projects/delphij_fork/sys/pci/agp.c#3 integrate .. //depot/projects/delphij_fork/sys/pci/agp_ali.c#2 integrate .. //depot/projects/delphij_fork/sys/pci/agp_amd.c#2 integrate .. //depot/projects/delphij_fork/sys/pci/agp_amd64.c#2 integrate .. //depot/projects/delphij_fork/sys/pci/agp_ati.c#2 integrate .. //depot/projects/delphij_fork/sys/pci/agp_i810.c#4 integrate .. //depot/projects/delphij_fork/sys/pci/agp_intel.c#2 integrate .. //depot/projects/delphij_fork/sys/pci/agp_nvidia.c#2 integrate .. //depot/projects/delphij_fork/sys/pci/agp_sis.c#2 integrate .. //depot/projects/delphij_fork/sys/pci/agp_via.c#3 integrate .. //depot/projects/delphij_fork/sys/pci/agppriv.h#3 integrate .. //depot/projects/delphij_fork/usr.bin/calendar/calendars/calendar.freebsd#4 integrate .. //depot/projects/delphij_fork/usr.bin/file2c/file2c.1#2 integrate .. //depot/projects/delphij_fork/usr.bin/file2c/file2c.c#2 integrate .. //depot/projects/delphij_fork/usr.bin/lockf/lockf.1#3 integrate .. //depot/projects/delphij_fork/usr.bin/make/make.1#2 integrate .. //depot/projects/delphij_fork/usr.bin/xstr/xstr.1#2 integrate .. //depot/projects/delphij_fork/usr.sbin/fwcontrol/fwcontrol.8#3 integrate .. //depot/projects/delphij_fork/usr.sbin/mtree/mtree.c#2 integrate .. //depot/projects/delphij_fork/usr.sbin/pciconf/cap.c#3 integrate .. //depot/projects/delphij_fork/usr.sbin/pciconf/pciconf.h#2 integrate .. //depot/projects/delphij_fork/usr.sbin/rpc.lockd/lockd.c#2 integrate .. //depot/projects/delphij_fork/usr.sbin/rpc.lockd/rpc.lockd.8#2 integrate .. //depot/projects/delphij_fork/usr.sbin/rpc.statd/rpc.statd.8#2 integrate .. //depot/projects/delphij_fork/usr.sbin/rpc.statd/statd.c#3 integrate .. //depot/projects/delphij_fork/usr.sbin/tcpdrop/tcpdrop.c#2 integrate Differences ... ==== //depot/projects/delphij_fork/Makefile.inc1#6 (text+ko) ==== @@ -1,5 +1,5 @@ # -# $FreeBSD: src/Makefile.inc1,v 1.589 2007/10/15 13:50:46 emaste Exp $ +# $FreeBSD: src/Makefile.inc1,v 1.590 2007/10/31 09:26:42 yar Exp $ # # Make command line options: # -DNO_CLEANDIR run ${MAKE} clean, instead of ${MAKE} cleandir @@ -159,7 +159,14 @@ STRICTTMPPATH= ${BPATH}:${XPATH} TMPPATH= ${STRICTTMPPATH}:${PATH} +# +# Avoid running mktemp(1) unless actually needed. +# It may not be functional, e.g., due to new ABI +# when in the middle of installing over this system. +# +.if make(distributeworld) || make(installworld) INSTALLTMP!= /usr/bin/mktemp -d -u -t install +.endif # # Building a world goes through the following stages @@ -265,14 +272,16 @@ .endif # install stage +IMAKEENV= ${CROSSENV} +IMAKE= ${IMAKEENV} ${MAKE} -f Makefile.inc1 .if empty(.MAKEFLAGS:M-n) -IMAKEENV= ${CROSSENV} \ - PATH=${STRICTTMPPATH}:${INSTALLTMP} +IMAKEENV+= PATH=${STRICTTMPPATH}:${INSTALLTMP} \ + LD_LIBRARY_PATH=${INSTALLTMP} \ + PATH_LOCALE=${INSTALLTMP}/locale +IMAKE+= __MAKE_SHELL=${INSTALLTMP}/sh .else -IMAKEENV= ${CROSSENV} \ - PATH=${TMPPATH}:${INSTALLTMP} +IMAKEENV+= PATH=${TMPPATH}:${INSTALLTMP} .endif -IMAKE= ${IMAKEENV} ${MAKE} -f Makefile.inc1 # kernel stage KMAKEENV= ${WMAKEENV} @@ -564,6 +573,14 @@ .endfor # +# Required install tools to be saved in a scratch dir for safety. +# +ITOOLS= [ awk cap_mkdb cat chflags chmod chown \ + date echo egrep find grep install-info \ + ln lockf make mkdir mtree mv pwd_mkdb rm sed sh sysctl \ + test true uname wc zic + +# # distributeworld # # Distributes everything compiled by a `buildworld'. @@ -574,19 +591,20 @@ # distributeworld installworld: installcheck mkdir -p ${INSTALLTMP} - for prog in [ awk cap_mkdb cat chflags chmod chown \ - date echo egrep find grep install-info \ - ln lockf make mkdir mtree mv pwd_mkdb rm sed sh sysctl \ - test true uname wc zic; do \ + for prog in ${ITOOLS}; do \ if progpath=`which $$prog`; then \ - cp $$progpath ${INSTALLTMP}; \ + progs="$$progs $$progpath"; \ else \ - echo "Required install tool $$prog not found" >&2; \ + echo "Required tool $$prog not found in PATH." >&2; \ exit 1; \ fi; \ - done - ${_+_}cd ${.CURDIR}; ${IMAKE} re${.TARGET:S/world$//} - rm -rf ${INSTALLTMP} + done; \ + cp $$progs ${INSTALLTMP}; \ + cp `ldd -f "%p\n" -f "%p\n" $$progs 2>/dev/null | \ + sort -u` ${INSTALLTMP} + cp -R $${PATH_LOCALE:-"/usr/share/locale"} ${INSTALLTMP}/locale + ${_+_}cd ${.CURDIR}; ${IMAKE} re${.TARGET:S/world$//}; \ + ${IMAKEENV} rm -rf ${INSTALLTMP} # installskel # ==== //depot/projects/delphij_fork/bin/mv/mv.1#2 (text+ko) ==== @@ -30,9 +30,9 @@ .\" SUCH DAMAGE. .\" .\" @(#)mv.1 8.1 (Berkeley) 5/31/93 -.\" $FreeBSD: src/bin/mv/mv.1,v 1.29 2007/05/12 22:18:27 pav Exp $ +.\" $FreeBSD: src/bin/mv/mv.1,v 1.30 2007/11/01 09:49:45 ru Exp $ .\" -.Dd July 9, 2002 +.Dd May 12, 2007 .Dt MV 1 .Os .Sh NAME ==== //depot/projects/delphij_fork/include/_ctype.h#3 (text+ko) ==== @@ -40,7 +40,7 @@ * * From @(#)ctype.h 8.4 (Berkeley) 1/21/94 * From FreeBSD: src/include/ctype.h,v 1.27 2004/06/23 07:11:39 tjr Exp - * $FreeBSD: src/include/_ctype.h,v 1.33 2007/10/27 22:32:27 ache Exp $ + * $FreeBSD: src/include/_ctype.h,v 1.34 2007/11/01 03:18:02 ache Exp $ */ #ifndef __CTYPE_H_ @@ -126,7 +126,7 @@ static __inline int __isctype(__ct_rune_t _c, unsigned long _f) { - return (_c & ~0x7F) ? 0 : + return (_c < 0 || _c >= 128) ? 0 : !!(_DefaultRuneLocale.__runetype[_c] & _f); } ==== //depot/projects/delphij_fork/lib/libthr/thread/thr_mutex.c#3 (text+ko) ==== @@ -30,7 +30,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $FreeBSD: src/lib/libthr/thread/thr_mutex.c,v 1.57 2007/10/30 09:24:23 kris Exp $ + * $FreeBSD: src/lib/libthr/thread/thr_mutex.c,v 1.60 2007/10/31 01:50:48 davidxu Exp $ */ #include "namespace.h" @@ -39,8 +39,6 @@ #include #include #include -#include -#include #include #include "un-namespace.h" @@ -67,6 +65,12 @@ #endif /* + * For adaptive mutexes, how many times to spin doing trylock2 + * before entering the kernel to block + */ +#define MUTEX_ADAPTIVE_SPINS 200 + +/* * Prototypes */ int __pthread_mutex_init(pthread_mutex_t *mutex, @@ -356,34 +360,56 @@ } else if (m->m_owner == curthread) { ret = mutex_self_lock(m, abstime); } else { - if (_thr_spinloops != 0 && _thr_is_smp && - !(m->m_lock.m_flags & UMUTEX_PRIO_PROTECT)) { - count = _thr_spinloops; - while (count && m->m_lock.m_owner != UMUTEX_UNOWNED) { - count--; + /* + * For adaptive mutexes, spin for a bit in the expectation + * that if the application requests this mutex type then + * the lock is likely to be released quickly and it is + * faster than entering the kernel + */ + if (m->m_lock.m_flags & UMUTEX_PRIO_PROTECT) + goto sleep_in_kernel; + + if (!_thr_is_smp) + goto yield_loop; + + if (m->m_type == PTHREAD_MUTEX_ADAPTIVE_NP) { + count = MUTEX_ADAPTIVE_SPINS; + + while (count--) { + ret = _thr_umutex_trylock2(&m->m_lock, id); + if (ret == 0) + break; CPU_SPINWAIT; } - if (count) { - ret = _thr_umutex_trylock2(&m->m_lock, id); - if (ret == 0) { - ENQUEUE_MUTEX(curthread, m); - return (ret); + if (ret == 0) + goto done; + } else { + if (_thr_spinloops != 0) { + count = _thr_spinloops; + while (count) { + if (m->m_lock.m_owner == UMUTEX_UNOWNED) { + ret = _thr_umutex_trylock2(&m->m_lock, id); + if (ret == 0) + goto done; + } + CPU_SPINWAIT; + count--; } } } +yield_loop: if (_thr_yieldloops != 0) { count = _thr_yieldloops; while (count--) { _sched_yield(); ret = _thr_umutex_trylock2(&m->m_lock, id); - if (ret == 0) { - ENQUEUE_MUTEX(curthread, m); - return (ret); - } + if (ret == 0) + goto done; } } +sleep_in_kernel: if (abstime == NULL) { ret = __thr_umutex_lock(&m->m_lock); } else if (__predict_false( @@ -401,6 +427,7 @@ if (ret == EINTR) ret = ETIMEDOUT; } +done: if (ret == 0) ENQUEUE_MUTEX(curthread, m); } ==== //depot/projects/delphij_fork/libexec/Makefile#2 (text+ko) ==== @@ -1,5 +1,5 @@ # @(#)Makefile 8.1 (Berkeley) 6/4/93 -# $FreeBSD: src/libexec/Makefile,v 1.77 2007/07/03 12:46:04 mlaier Exp $ +# $FreeBSD: src/libexec/Makefile,v 1.78 2007/10/31 11:19:32 yar Exp $ .include @@ -43,7 +43,7 @@ _tftp-proxy= tftp-proxy .endif -.if !defined(NO_PIC) +.if !defined(NO_PIC) && !defined(NO_RTLD) _rtld-elf= rtld-elf .endif ==== //depot/projects/delphij_fork/sbin/gpt/boot.c#2 (text+ko) ==== @@ -29,7 +29,7 @@ */ #include -__FBSDID("$FreeBSD: src/sbin/gpt/boot.c,v 1.1 2007/10/24 21:32:57 jhb Exp $"); +__FBSDID("$FreeBSD: src/sbin/gpt/boot.c,v 1.2 2007/11/01 20:06:12 jhb Exp $"); #include #include @@ -168,7 +168,6 @@ warn("unable to open GPT boot loader"); return; } - /* Fourth step: find an existing boot partition or create one. */ if (gpt_find(&boot_uuid, &gptboot) != 0) @@ -191,8 +190,14 @@ return; } - /* Fourth step, write out the gptboot binary to the boot partition. */ - buf = malloc(sb.st_size); + /* + * Fourth step, write out the gptboot binary to the boot partition. + * When writing to a disk device, the write must be sector aligned + * and not write to any partial sectors, so round up the buffer size + * to the next sector and zero it. + */ + bsize = (sb.st_size + secsz - 1) / secsz * secsz; + buf = calloc(1, bsize); nbytes = read(bfd, buf, sb.st_size); if (nbytes < 0) { warn("unable to read GPT boot loader"); @@ -209,12 +214,12 @@ device_name); return; } - nbytes = write(fd, buf, sb.st_size); + nbytes = write(fd, buf, bsize); if (nbytes < 0) { warn("unable to write GPT boot loader"); return; } - if (nbytes != sb.st_size) { + if (nbytes != bsize) { warnx("short write of GPT boot loader"); return; } ==== //depot/projects/delphij_fork/sbin/gpt/gpt.c#3 (text+ko) ==== @@ -27,7 +27,7 @@ */ #include -__FBSDID("$FreeBSD: src/sbin/gpt/gpt.c,v 1.17 2007/10/24 21:32:57 jhb Exp $"); +__FBSDID("$FreeBSD: src/sbin/gpt/gpt.c,v 1.18 2007/11/01 20:51:04 jhb Exp $"); #include #include @@ -585,10 +585,16 @@ if (gpt_mbr(fd, 0LL) == -1) goto close; - if (gpt_gpt(fd, 1LL) == -1) - goto close; - if (gpt_gpt(fd, mediasz / secsz - 1LL) == -1) - goto close; + + /* + * Don't look for a GPT unless we have a valid PMBR. + */ + if (map_find(MAP_TYPE_PMBR) != NULL) { + if (gpt_gpt(fd, 1LL) == -1) + goto close; + if (gpt_gpt(fd, mediasz / secsz - 1LL) == -1) + goto close; + } return (fd); ==== //depot/projects/delphij_fork/sbin/ifconfig/ifconfig.8#4 (text+ko) ==== @@ -26,9 +26,9 @@ .\" SUCH DAMAGE. .\" .\" From: @(#)ifconfig.8 8.3 (Berkeley) 1/5/94 -.\" $FreeBSD: src/sbin/ifconfig/ifconfig.8,v 1.142 2007/08/01 00:33:52 thompsa Exp $ +.\" $FreeBSD: src/sbin/ifconfig/ifconfig.8,v 1.143 2007/11/02 05:23:22 sam Exp $ .\" -.Dd July 8, 2007 +.Dd October 31, 2007 .Dt IFCONFIG 8 .Os .Sh NAME @@ -606,7 +606,7 @@ an access point will temporarily leave the channel to scan for neighboring stations. This allows a station to maintain a cache of nearby access points -so that roaming between access points can be done without doing +so that roaming between access points can be done without a lengthy scan operation. Background scanning is done only when a station is not busy and any outbound traffic will cancel a scan operation. @@ -637,7 +637,7 @@ The .Ar interval parameter is specified in seconds. -By default a background scanning is considered every 300 seconds (5 minutes). +By default a background scan is considered every 300 seconds (5 minutes). The .Ar interval may not be set to less than 15 seconds. @@ -817,7 +817,7 @@ To re-enable the broadcast of the SSID etc., use .Fl hidessid . .It Cm ff -Enable the user of Atheros Fast Frames when communicating with +Enable the use of Atheros Fast Frames when communicating with another Fast Frames-capable station. Fast Frames are an encapsulation technique by which two 802.3 frames are transmitted in a single 802.11 frame. @@ -863,6 +863,9 @@ on the channel. .Cm list freq is another way of requesting this information. +By default a compacted list of channels is displayed; if the +.Fl v +option is specified then all channels are shown. .It Cm list mac Display the current MAC Access Control List state. Each address is prefixed with a character that indicates the @@ -880,6 +883,8 @@ The .Fl v flag may be used to display long SSIDs. +.Fl v +also causes received information elements to be displayed symbolicaly. This information may be updated automatically by the adaptor and/or with a .Cm scan @@ -918,6 +923,11 @@ data frame. QoS encapsulation is enabled only when WME mode is enabled. .El +.Pp +By default information elements received from associated stations +are displayed in a short form; the +.Fl v +flag causes this information to be displayed symbolicaly. .It Cm list wme Display the current parameters to use when operating in WME mode. When WME mode is enabled for an adaptor this information will be @@ -991,7 +1001,7 @@ 802.11a BSS. The .Ar rssi -parameter specifies the receive signal strength in .5 dBm units +parameter specifies the receive signal strength in dBm units at which roaming should be considered. If the current rssi drops below this setting and background scanning is enabled, then the system will check if a more desirable access point is @@ -1177,8 +1187,8 @@ background scan operations. .It Cm stationname Ar name Set the name of this station. -It appears that the station name is not really part of the IEEE 802.11 -protocol though all interfaces seem to support it. +The station name is not part of the IEEE 802.11 +protocol though some interfaces support it. As such it only seems to be meaningful to identical or virtually identical equipment. Setting the station name is identical in syntax to setting the SSID. @@ -1186,9 +1196,7 @@ Set the power used to transmit frames. The .Ar power -argument -is a unitless value in the range 0 to 100 that is interpreted -by drivers to derive a device-specific value. +argument is specified in .5 dBm units. Out of range values are truncated. Typically only a few discreet power settings are available and the driver will use the setting closest to the specified value. ==== //depot/projects/delphij_fork/sbin/ifconfig/ifieee80211.c#2 (text+ko) ==== @@ -24,7 +24,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $FreeBSD: src/sbin/ifconfig/ifieee80211.c,v 1.47 2007/06/12 00:52:40 thompsa Exp $ + * $FreeBSD: src/sbin/ifconfig/ifieee80211.c,v 1.48 2007/11/02 05:24:57 sam Exp $ */ /*- @@ -91,9 +91,41 @@ #include #include #include +#include /* NB: for offsetof */ #include "ifconfig.h" +#define MAXCOL 78 +static int col; +static char spacer; + +static void LINE_INIT(char c); +static void LINE_BREAK(void); +static void LINE_CHECK(const char *fmt, ...); + +/* XXX need max array size */ +static const int htrates[16] = { + 13, /* IFM_IEEE80211_MCS0 */ + 26, /* IFM_IEEE80211_MCS1 */ + 39, /* IFM_IEEE80211_MCS2 */ + 52, /* IFM_IEEE80211_MCS3 */ + 78, /* IFM_IEEE80211_MCS4 */ + 104, /* IFM_IEEE80211_MCS5 */ + 117, /* IFM_IEEE80211_MCS6 */ + 130, /* IFM_IEEE80211_MCS7 */ + 26, /* IFM_IEEE80211_MCS8 */ + 52, /* IFM_IEEE80211_MCS9 */ + 78, /* IFM_IEEE80211_MCS10 */ + 104, /* IFM_IEEE80211_MCS11 */ + 156, /* IFM_IEEE80211_MCS12 */ + 208, /* IFM_IEEE80211_MCS13 */ + 234, /* IFM_IEEE80211_MCS14 */ + 260, /* IFM_IEEE80211_MCS15 */ +}; + +static int get80211(int s, int type, void *data, int len); +static int get80211len(int s, int type, void *data, int len, int *plen); +static int get80211val(int s, int type, int *val); static void set80211(int s, int type, int val, int len, void *data); static const char *get_string(const char *val, const char *sep, u_int8_t *buf, int *lenp); @@ -101,7 +133,21 @@ static struct ieee80211req_chaninfo chaninfo; static struct ifmediareq *ifmr; +static struct ieee80211_channel curchan; +static int gotcurchan = 0; +static int htconf = 0; +static int gothtconf = 0; +static void +gethtconf(int s) +{ + if (gothtconf) + return; + if (get80211val(s, IEEE80211_IOC_HTCONF, &htconf) < 0) + warn("unable to get HT configuration information"); + gothtconf = 1; +} + /* * Collect channel info from the kernel. We use this (mostly) * to handle mapping between frequency and IEEE channel number. @@ -109,19 +155,13 @@ static void getchaninfo(int s) { - struct ieee80211req ireq; - if (chaninfo.ic_nchans != 0) return; - (void) memset(&ireq, 0, sizeof(ireq)); - (void) strncpy(ireq.i_name, name, sizeof(ireq.i_name)); - ireq.i_type = IEEE80211_IOC_CHANINFO; - ireq.i_data = &chaninfo; - ireq.i_len = sizeof(chaninfo); - if (ioctl(s, SIOCG80211, &ireq) < 0) + if (get80211(s, IEEE80211_IOC_CHANINFO, &chaninfo, sizeof(chaninfo)) < 0) errx(1, "unable to get channel information"); ifmr = ifmedia_getstate(s); + gethtconf(s); } /* @@ -188,21 +228,25 @@ /* NB: we abitrarily pick HT40+ over HT40- */ if (chanmode != IFM_IEEE80211_11B) i = canpromote(i, IEEE80211_CHAN_B, IEEE80211_CHAN_G); - if (chanmode != IFM_IEEE80211_11G) { + if (chanmode != IFM_IEEE80211_11G && (htconf & 1)) { i = canpromote(i, IEEE80211_CHAN_G, IEEE80211_CHAN_G | IEEE80211_CHAN_HT20); - i = canpromote(i, IEEE80211_CHAN_G, - IEEE80211_CHAN_G | IEEE80211_CHAN_HT40D); - i = canpromote(i, IEEE80211_CHAN_G, - IEEE80211_CHAN_G | IEEE80211_CHAN_HT40U); + if (htconf & 2) { + i = canpromote(i, IEEE80211_CHAN_G, + IEEE80211_CHAN_G | IEEE80211_CHAN_HT40D); + i = canpromote(i, IEEE80211_CHAN_G, + IEEE80211_CHAN_G | IEEE80211_CHAN_HT40U); + } } - if (chanmode != IFM_IEEE80211_11A) { + if (chanmode != IFM_IEEE80211_11A && (htconf & 1)) { i = canpromote(i, IEEE80211_CHAN_A, IEEE80211_CHAN_A | IEEE80211_CHAN_HT20); - i = canpromote(i, IEEE80211_CHAN_A, - IEEE80211_CHAN_A | IEEE80211_CHAN_HT40D); - i = canpromote(i, IEEE80211_CHAN_A, - IEEE80211_CHAN_A | IEEE80211_CHAN_HT40U); + if (htconf & 2) { + i = canpromote(i, IEEE80211_CHAN_A, + IEEE80211_CHAN_A | IEEE80211_CHAN_HT40D); + i = canpromote(i, IEEE80211_CHAN_A, + IEEE80211_CHAN_A | IEEE80211_CHAN_HT40U); + } } return i; } @@ -244,7 +288,24 @@ return; } } - errx(1, "unknown/undefined channel number %d", ieee); + errx(1, "unknown/undefined channel number %d flags 0x%x", ieee, flags); +} + +static const struct ieee80211_channel * +getcurchan(int s) +{ + if (gotcurchan) + return &curchan; + if (get80211(s, IEEE80211_IOC_CURCHAN, &curchan, sizeof(curchan)) < 0) { + int val; + /* fall back to legacy ioctl */ + if (get80211val(s, IEEE80211_IOC_CHANNEL, &val) < 0) + errx(-1, "cannot figure out current channel"); + getchaninfo(s); + mapchan(&curchan, val, 0); + } + gotcurchan = 1; + return &curchan; } static int @@ -258,8 +319,8 @@ static int isanyarg(const char *arg) { - return (strcmp(arg, "-") == 0 || - strcasecmp(arg, "any") == 0 || strcasecmp(arg, "off") == 0); + return (strncmp(arg, "-", 1) == 0 || + strncasecmp(arg, "any", 3) == 0 || strncasecmp(arg, "off", 3) == 0); } static void @@ -310,9 +371,8 @@ * checked against the channel table fetched from the kernel. */ static int -getchannelflags(const char *val) +getchannelflags(const char *val, int freq) { -#define CHAN_HT_DEFAULT IEEE80211_CHAN_HT40U #define _CHAN_HT 0x80000000 const char *cp; int flags; @@ -352,7 +412,7 @@ flags |= IEEE80211_CHAN_STURBO; break; default: - errx(-1, "%s: Invalid channel attribute %c", + errx(-1, "%s: Invalid channel attribute %c\n", val, *cp); } } @@ -378,11 +438,9 @@ flags |= IEEE80211_CHAN_HT40U; else if (ep != NULL && *ep == '-') flags |= IEEE80211_CHAN_HT40D; - else /* NB: pick something */ - flags |= CHAN_HT_DEFAULT; break; default: - errx(-1, "%s: Invalid channel width", val); + errx(-1, "%s: Invalid channel width\n", val); } } /* @@ -404,11 +462,20 @@ * provide the default settings. */ flags &= ~_CHAN_HT; - if ((flags & IEEE80211_CHAN_HT) == 0) - flags |= CHAN_HT_DEFAULT; + if ((flags & IEEE80211_CHAN_HT) == 0) { + struct ieee80211_channel chan; + /* + * Consult the channel list to see if we can use + * HT40+ or HT40- (if both the map routines choose). + */ + if (freq > 255) + mapfreq(&chan, freq, 0); + else + mapchan(&chan, freq, 0); + flags |= (chan.ic_flags & IEEE80211_CHAN_HT); + } } return flags; -#undef CHAN_HT_DEFAULT #undef _CHAN_HT } @@ -419,10 +486,11 @@ memset(&chan, 0, sizeof(chan)); if (!isanyarg(val)) { - int v = atoi(val); - int flags = getchannelflags(val); + int v, flags; getchaninfo(s); + v = atoi(val); + flags = getchannelflags(val, v); if (v > 255) { /* treat as frequency */ mapfreq(&chan, v, flags); } else { @@ -612,7 +680,7 @@ mode = IEEE80211_PROTMODE_OFF; } else if (strcasecmp(val, "cts") == 0) { mode = IEEE80211_PROTMODE_CTS; - } else if (strcasecmp(val, "rtscts") == 0) { + } else if (strncasecmp(val, "rtscts", 3) == 0) { mode = IEEE80211_PROTMODE_RTSCTS; } else { errx(1, "unknown protection mode"); @@ -622,9 +690,31 @@ } static void +set80211htprotmode(const char *val, int d, int s, const struct afswtch *rafp) +{ + int mode; + + if (strcasecmp(val, "off") == 0) { + mode = IEEE80211_PROTMODE_OFF; + } else if (strncasecmp(val, "rts", 3) == 0) { + mode = IEEE80211_PROTMODE_RTSCTS; + } else { + errx(1, "unknown protection mode"); + } + + set80211(s, IEEE80211_IOC_HTPROTMODE, mode, 0, NULL); +} + +static void set80211txpower(const char *val, int d, int s, const struct afswtch *rafp) { - set80211(s, IEEE80211_IOC_TXPOWER, atoi(val), 0, NULL); + double v = atof(val); + int txpow; + + txpow = (int) (2*v); + if (txpow != 2*v) + errx(-1, "invalid tx power (must be .5 dBm units)"); + set80211(s, IEEE80211_IOC_TXPOWER, txpow, 0, NULL); } #define IEEE80211_ROAMING_DEVICE 0 @@ -692,7 +782,7 @@ memset(&chanlist, 0, sizeof(chanlist)); cp = temp; for (;;) { - int first, last, f; + int first, last, f, c; tp = strchr(cp, ','); if (tp != NULL) @@ -720,9 +810,10 @@ } if (tp == NULL) break; - while (isspace(*tp)) + c = *tp; + while (isspace(c)) tp++; - if (!isdigit(*tp)) + if (!isdigit(c)) break; cp = tp; } @@ -1017,6 +1108,181 @@ set80211(s, IEEE80211_IOC_DOTH, d, 0, NULL); } +static void +set80211shortgi(const char *val, int d, int s, const struct afswtch *rafp) +{ + set80211(s, IEEE80211_IOC_SHORTGI, + d ? (IEEE80211_HTCAP_SHORTGI20 | IEEE80211_HTCAP_SHORTGI40) : 0, + 0, NULL); +} + +static void +set80211ampdu(const char *val, int d, int s, const struct afswtch *rafp) +{ + int ampdu; + + if (get80211val(s, IEEE80211_IOC_AMPDU, &du) < 0) + errx(-1, "cannot get AMPDU setting"); + if (d < 0) { + d = -d; + ampdu &= ~d; + } else + ampdu |= d; + set80211(s, IEEE80211_IOC_AMPDU, ampdu, 0, NULL); +} + +static +DECL_CMD_FUNC(set80211ampdulimit, val, d) +{ + int v; + + switch (atoi(val)) { + case 8: + case 8*1024: + v = IEEE80211_HTCAP_MAXRXAMPDU_8K; + break; + case 16: + case 16*1024: + v = IEEE80211_HTCAP_MAXRXAMPDU_16K; + break; + case 32: + case 32*1024: + v = IEEE80211_HTCAP_MAXRXAMPDU_32K; + break; + case 64: + case 64*1024: + v = IEEE80211_HTCAP_MAXRXAMPDU_64K; + break; + default: + errx(-1, "invalid A-MPDU limit %s", val); + } + set80211(s, IEEE80211_IOC_AMPDU_LIMIT, v, 0, NULL); +} + +static +DECL_CMD_FUNC(set80211ampdudensity, val, d) +{ + int v; + + if (isanyarg(val)) + v = IEEE80211_HTCAP_MPDUDENSITY_NA; + else switch ((int)(atof(val)*4)) { + case 0: + v = IEEE80211_HTCAP_MPDUDENSITY_NA; + break; + case 1: + v = IEEE80211_HTCAP_MPDUDENSITY_025; + break; + case 2: + v = IEEE80211_HTCAP_MPDUDENSITY_05; + break; + case 4: + v = IEEE80211_HTCAP_MPDUDENSITY_1; + break; + case 8: + v = IEEE80211_HTCAP_MPDUDENSITY_2; + break; + case 16: + v = IEEE80211_HTCAP_MPDUDENSITY_4; + break; + case 32: + v = IEEE80211_HTCAP_MPDUDENSITY_8; + break; + case 64: + v = IEEE80211_HTCAP_MPDUDENSITY_16; + break; + default: + errx(-1, "invalid A-MPDU density %s", val); + } + set80211(s, IEEE80211_IOC_AMPDU_DENSITY, v, 0, NULL); +} + +static void +set80211amsdu(const char *val, int d, int s, const struct afswtch *rafp) +{ + int amsdu; + + if (get80211val(s, IEEE80211_IOC_AMSDU, &amsdu) < 0) + errx(-1, "cannot get AMSDU setting"); + if (d < 0) { + d = -d; + amsdu &= ~d; + } else + amsdu |= d; + set80211(s, IEEE80211_IOC_AMSDU, amsdu, 0, NULL); +} + +static +DECL_CMD_FUNC(set80211amsdulimit, val, d) +{ + set80211(s, IEEE80211_IOC_AMSDU_LIMIT, atoi(val), 0, NULL); +} + +static void +set80211puren(const char *val, int d, int s, const struct afswtch *rafp) +{ + set80211(s, IEEE80211_IOC_PUREN, d, 0, NULL); +} + +static void +set80211htcompat(const char *val, int d, int s, const struct afswtch *rafp) +{ + set80211(s, IEEE80211_IOC_HTCOMPAT, d, 0, NULL); +} + +static void +set80211htconf(const char *val, int d, int s, const struct afswtch *rafp) +{ + set80211(s, IEEE80211_IOC_HTCONF, d, 0, NULL); + htconf = d; +} + +static void +set80211inact(const char *val, int d, int s, const struct afswtch *rafp) +{ + set80211(s, IEEE80211_IOC_INACTIVITY, d, 0, NULL); +} + +static void +LINE_INIT(char c) +{ + spacer = c; + if (c == '\t') + col = 8; + else + col = 1; +} + +static void +LINE_BREAK(void) +{ + if (spacer != '\t') { + printf("\n"); + spacer = '\t'; + } + col = 8; /* 8-col tab */ +} + +static void +LINE_CHECK(const char *fmt, ...) +{ + char buf[80]; + va_list ap; + int n; + + va_start(ap, fmt); >>> TRUNCATED FOR MAIL (1000 lines) <<<