svn commit: r343320 - in projects/clang800-import: bin/csh bin/sh lib/libcapsicum sbin/devd sbin/ifconfig sbin/pfctl share/skel stand/mips/beri/boot2 sys/amd64/conf sys/amd64/linux sys/arm/allwinne...

Dimitry Andric dim at FreeBSD.org
Tue Jan 22 20:25:01 UTC 2019


Author: dim
Date: Tue Jan 22 20:24:58 2019
New Revision: 343320
URL: https://svnweb.freebsd.org/changeset/base/343320

Log:
  Merge ^/head r343202 through r343319.

Added:
  projects/clang800-import/sys/net80211/ieee80211_wps.h
     - copied unchanged from r343319, head/sys/net80211/ieee80211_wps.h
Modified:
  projects/clang800-import/bin/csh/csh.login
  projects/clang800-import/bin/csh/dot.cshrc
  projects/clang800-import/bin/sh/histedit.c
  projects/clang800-import/bin/sh/profile
  projects/clang800-import/lib/libcapsicum/capsicum_helpers.3
  projects/clang800-import/sbin/devd/devd.conf
  projects/clang800-import/sbin/ifconfig/ifieee80211.c
  projects/clang800-import/sbin/pfctl/pfctl.h
  projects/clang800-import/sbin/pfctl/pfctl_altq.c
  projects/clang800-import/sbin/pfctl/pfctl_parser.c
  projects/clang800-import/sbin/pfctl/pfctl_parser.h
  projects/clang800-import/share/skel/dot.cshrc
  projects/clang800-import/share/skel/dot.profile
  projects/clang800-import/stand/mips/beri/boot2/boot2.c
  projects/clang800-import/sys/amd64/conf/GENERIC
  projects/clang800-import/sys/amd64/linux/linux_machdep.c
  projects/clang800-import/sys/arm/allwinner/if_awg.c
  projects/clang800-import/sys/arm/conf/RK3188
  projects/clang800-import/sys/compat/linux/linux_ioctl.c
  projects/clang800-import/sys/compat/linux/linux_misc.c
  projects/clang800-import/sys/compat/ndis/kern_windrv.c
  projects/clang800-import/sys/compat/ndis/pe_var.h
  projects/clang800-import/sys/conf/NOTES
  projects/clang800-import/sys/conf/config.mk
  projects/clang800-import/sys/conf/options
  projects/clang800-import/sys/dev/cxgbe/t4_filter.c
  projects/clang800-import/sys/dev/cxgbe/t4_main.c
  projects/clang800-import/sys/dev/hwpmc/hwpmc_mod.c
  projects/clang800-import/sys/dev/iwm/if_iwm.c
  projects/clang800-import/sys/dev/iwn/if_iwn.c
  projects/clang800-import/sys/dev/ixgbe/ixgbe_82599.c
  projects/clang800-import/sys/dev/ixgbe/ixgbe_common.c
  projects/clang800-import/sys/dev/usb/quirk/usb_quirk.c
  projects/clang800-import/sys/dev/usb/usbdevs
  projects/clang800-import/sys/dev/usb/wlan/if_run.c
  projects/clang800-import/sys/dev/usb/wlan/if_urtw.c
  projects/clang800-import/sys/dev/usb/wlan/if_urtwvar.h
  projects/clang800-import/sys/dev/vmware/vmxnet3/if_vmx.c
  projects/clang800-import/sys/dev/vmware/vmxnet3/if_vmxvar.h
  projects/clang800-import/sys/fs/nfsserver/nfs_nfsdport.c
  projects/clang800-import/sys/fs/smbfs/smbfs_vnops.c
  projects/clang800-import/sys/i386/conf/GENERIC
  projects/clang800-import/sys/mips/conf/ERL
  projects/clang800-import/sys/mips/conf/OCTEON1
  projects/clang800-import/sys/modules/vmware/vmxnet3/Makefile
  projects/clang800-import/sys/net/if.c
  projects/clang800-import/sys/net/iflib.c
  projects/clang800-import/sys/net/iflib.h
  projects/clang800-import/sys/net80211/ieee80211.c
  projects/clang800-import/sys/net80211/ieee80211.h
  projects/clang800-import/sys/net80211/ieee80211_freebsd.c
  projects/clang800-import/sys/net80211/ieee80211_freebsd.h
  projects/clang800-import/sys/net80211/ieee80211_ioctl.c
  projects/clang800-import/sys/net80211/ieee80211_var.h
  projects/clang800-import/sys/netpfil/pf/pf_ioctl.c
  projects/clang800-import/sys/riscv/include/riscvreg.h
  projects/clang800-import/sys/riscv/riscv/copyinout.S
  projects/clang800-import/sys/sparc64/conf/GENERIC
  projects/clang800-import/sys/sys/param.h
  projects/clang800-import/sys/sys/rmlock.h
  projects/clang800-import/sys/sys/rwlock.h
  projects/clang800-import/tests/sys/netpfil/pf/ioctl/validation.c
  projects/clang800-import/tools/build/mk/OptionalObsoleteFiles.inc
  projects/clang800-import/tools/tools/nanobsd/pcengines/ALIX_DSK
  projects/clang800-import/usr.bin/cmp/cmp.c
  projects/clang800-import/usr.bin/cmp/tests/cmp_test2.sh
  projects/clang800-import/usr.bin/systat/devs.c
  projects/clang800-import/usr.bin/units/units.1
  projects/clang800-import/usr.sbin/freebsd-update/freebsd-update.sh
  projects/clang800-import/usr.sbin/kbdmap/kbdmap.c
Directory Properties:
  projects/clang800-import/   (props changed)

Modified: projects/clang800-import/bin/csh/csh.login
==============================================================================
--- projects/clang800-import/bin/csh/csh.login	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/bin/csh/csh.login	Tue Jan 22 20:24:58 2019	(r343320)
@@ -1,9 +1,6 @@
 # $FreeBSD$
 #
 # System-wide .login file for csh(1).
-# Uncomment this to give you the default 4.2 behavior, where disk
-# information is shown in K-Blocks
-# setenv BLOCKSIZE	K
 #
 # For the setting of languages and character sets please see
 # login.conf(5) and in particular the charset and lang options.

Modified: projects/clang800-import/bin/csh/dot.cshrc
==============================================================================
--- projects/clang800-import/bin/csh/dot.cshrc	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/bin/csh/dot.cshrc	Tue Jan 22 20:24:58 2019	(r343320)
@@ -19,7 +19,6 @@ set path = (/sbin /bin /usr/sbin /usr/bin /usr/local/s
 
 setenv	EDITOR	vi
 setenv	PAGER	less
-setenv	BLOCKSIZE	K
 
 if ($?prompt) then
 	# An interactive shell -- set some stuff up

Modified: projects/clang800-import/bin/sh/histedit.c
==============================================================================
--- projects/clang800-import/bin/sh/histedit.c	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/bin/sh/histedit.c	Tue Jan 22 20:24:58 2019	(r343320)
@@ -67,7 +67,7 @@ __FBSDID("$FreeBSD$");
 History *hist;	/* history cookie */
 EditLine *el;	/* editline cookie */
 int displayhist;
-static FILE *el_in, *el_out, *el_err;
+static FILE *el_in, *el_out;
 
 static char *fc_replace(const char *, char *, char *);
 static int not_fcnumber(const char *);
@@ -106,18 +106,16 @@ histedit(void)
 			INTOFF;
 			if (el_in == NULL)
 				el_in = fdopen(0, "r");
-			if (el_err == NULL)
-				el_err = fdopen(1, "w");
 			if (el_out == NULL)
 				el_out = fdopen(2, "w");
-			if (el_in == NULL || el_err == NULL || el_out == NULL)
+			if (el_in == NULL || el_out == NULL)
 				goto bad;
 			term = lookupvar("TERM");
 			if (term)
 				setenv("TERM", term, 1);
 			else
 				unsetenv("TERM");
-			el = el_init(arg0, el_in, el_out, el_err);
+			el = el_init(arg0, el_in, el_out, el_out);
 			if (el != NULL) {
 				if (hist)
 					el_set(el, EL_HIST, history, hist);

Modified: projects/clang800-import/bin/sh/profile
==============================================================================
--- projects/clang800-import/bin/sh/profile	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/bin/sh/profile	Tue Jan 22 20:24:58 2019	(r343320)
@@ -2,10 +2,6 @@
 #
 # System-wide .profile file for sh(1).
 #
-# Uncomment this to give you the default 4.2 behavior, where disk
-# information is shown in K-Blocks
-# BLOCKSIZE=K; export BLOCKSIZE
-#
 # For the setting of languages and character sets please see
 # login.conf(5) and in particular the charset and lang options.
 # For full locales list check /usr/share/locale/*

Modified: projects/clang800-import/lib/libcapsicum/capsicum_helpers.3
==============================================================================
--- projects/clang800-import/lib/libcapsicum/capsicum_helpers.3	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/lib/libcapsicum/capsicum_helpers.3	Tue Jan 22 20:24:58 2019	(r343320)
@@ -24,7 +24,7 @@
 .\"
 .\" $FreeBSD$
 .\"
-.Dd November 4, 2018
+.Dd January 21, 2019
 .Dt CAPSICUM_HELPERS 3
 .Os
 .Sh NAME
@@ -50,11 +50,13 @@
 .Ft int
 .Fn caph_enter_casper "void"
 .Ft int
-.Fn caph_rights_limit "inf fd" "const cap_righst_t *rights"
+.Fn caph_rights_limit "int fd" "const cap_righst_t *rights"
 .Ft int
-.Fn caph_ioctls_limit "inf fd" "const unsigned long *cmds" "size_t ncmds"
+.Fn caph_ioctls_limit "int fd" "const unsigned long *cmds" "size_t ncmds"
 .Ft int
-.Fn caph_fcntls_limit "inf fd" "uint32_t fcntlrights"
+.Fn caph_fcntls_limit "int fd" "uint32_t fcntlrights"
+.Ft int
+.Fn caph_limit_stream "int fd" "int flags"
 .Ft int
 .Fn caph_limit_stdin "void"
 .Ft int

Modified: projects/clang800-import/sbin/devd/devd.conf
==============================================================================
--- projects/clang800-import/sbin/devd/devd.conf	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/sbin/devd/devd.conf	Tue Jan 22 20:24:58 2019	(r343320)
@@ -23,8 +23,8 @@ options {
 		esp|ida|iir|ips|isp|mlx|mly|mpr|mps|mpt|sym|trm)\
 		[0-9]+";
 	set wifi-driver-regex
-		"(ath|bwi|bwn|ipw|iwi|iwm|iwn|malo|mwl|ral|rsu|rtwn|rum|run|\
-		uath|upgt|ural|urtw|wi|wpi|wtap|zyd)[0-9]+";
+		"(ath|bwi|bwn|ipw|iwi|iwm|iwn|malo|mwl|otus|ral|rsu|rtwn|rum|\
+		run|uath|upgt|ural|urtw|wi|wpi|wtap|zyd)[0-9]+";
 };
 
 # Note that the attach/detach with the highest value wins, so that one can
@@ -43,7 +43,7 @@ options {
 #
 notify 0 {
 	match "system"		"IFNET";
-	match "subsystem"	"!usbus[0-9]+";
+	match "subsystem"	"(?!usbus[0-9]+|?!wlan[0-9]+)";
 	match "type"		"ATTACH";
 	action "/etc/pccard_ether $subsystem start";
 };

Modified: projects/clang800-import/sbin/ifconfig/ifieee80211.c
==============================================================================
--- projects/clang800-import/sbin/ifconfig/ifieee80211.c	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/sbin/ifconfig/ifieee80211.c	Tue Jan 22 20:24:58 2019	(r343320)
@@ -77,6 +77,7 @@
 #include <net80211/ieee80211_superg.h>
 #include <net80211/ieee80211_tdma.h>
 #include <net80211/ieee80211_mesh.h>
+#include <net80211/ieee80211_wps.h>
 
 #include <assert.h>
 #include <ctype.h>
@@ -3129,13 +3130,6 @@ printrsnie(const char *tag, const u_int8_t *ie, size_t
 	}
 }
 
-/* XXX move to a public include file */
-#define IEEE80211_WPS_DEV_PASS_ID	0x1012
-#define IEEE80211_WPS_SELECTED_REG	0x1041
-#define IEEE80211_WPS_SETUP_STATE	0x1044
-#define IEEE80211_WPS_UUID_E		0x1047
-#define IEEE80211_WPS_VERSION		0x104a
-
 #define BE_READ_2(p)					\
 	((u_int16_t)					\
 	 ((((const u_int8_t *)(p))[1]      ) |		\
@@ -3157,6 +3151,7 @@ printwpsie(const char *tag, const u_int8_t *ie, size_t
 			"R"	/* Registrar-specified */
 		};
 		int n;
+		int f;
 
 		ie +=6, len -= 4;		/* NB: len is payload only */
 
@@ -3165,6 +3160,7 @@ printwpsie(const char *tag, const u_int8_t *ie, size_t
 		while (len) {
 			uint16_t tlv_type = BE_READ_2(ie);
 			uint16_t tlv_len  = BE_READ_2(ie + 2);
+			uint16_t cfg_mthd;
 
 			/* some devices broadcast invalid WPS frames */
 			if (tlv_len > len) {
@@ -3177,30 +3173,191 @@ printwpsie(const char *tag, const u_int8_t *ie, size_t
 			ie += 4, len -= 4;
 
 			switch (tlv_type) {
-			case IEEE80211_WPS_VERSION:
+			case IEEE80211_WPS_ATTR_VERSION:
 				printf("v:%d.%d", *ie >> 4, *ie & 0xf);
 				break;
-			case IEEE80211_WPS_SETUP_STATE:
-				/* Only 1 and 2 are valid */
-				if (*ie == 0 || *ie >= 3)
-					printf(" state:B");
+			case IEEE80211_WPS_ATTR_AP_SETUP_LOCKED:
+				printf(" ap_setup:%s", *ie ? "locked" :
+				    "unlocked");
+				break;
+			case IEEE80211_WPS_ATTR_CONFIG_METHODS:
+			case IEEE80211_WPS_ATTR_SELECTED_REGISTRAR_CONFIG_METHODS:
+				if (tlv_type == IEEE80211_WPS_ATTR_SELECTED_REGISTRAR_CONFIG_METHODS)
+					printf(" sel_reg_cfg_mthd:");
 				else
-					printf(" st:%s", *ie == 1 ? "N" : "C");
+					printf(" cfg_mthd:" );
+				cfg_mthd = BE_READ_2(ie);
+				f = 0;
+				for (n = 15; n >= 0; n--) {
+					if (f) {
+						printf(",");
+						f = 0;
+					}
+					switch (cfg_mthd & (1 << n)) {
+					case 0:
+						break;
+					case IEEE80211_WPS_CONFIG_USBA:
+						printf("usba");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_ETHERNET:
+						printf("ethernet");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_LABEL:
+						printf("label");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_DISPLAY:
+						if (!(cfg_mthd &
+						    (IEEE80211_WPS_CONFIG_VIRT_DISPLAY |
+						    IEEE80211_WPS_CONFIG_PHY_DISPLAY)))
+						    {
+							printf("display");
+							f++;
+						}
+						break;
+					case IEEE80211_WPS_CONFIG_EXT_NFC_TOKEN:
+						printf("ext_nfc_tokenk");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_INT_NFC_TOKEN:
+						printf("int_nfc_token");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_NFC_INTERFACE:
+						printf("nfc_interface");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_PUSHBUTTON:
+						if (!(cfg_mthd &
+						    (IEEE80211_WPS_CONFIG_VIRT_PUSHBUTTON |
+						    IEEE80211_WPS_CONFIG_PHY_PUSHBUTTON))) {
+							printf("push_button");
+							f++;
+						}
+						break;
+					case IEEE80211_WPS_CONFIG_KEYPAD:
+						printf("keypad");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_VIRT_PUSHBUTTON:
+						printf("virtual_push_button");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_PHY_PUSHBUTTON:
+						printf("physical_push_button");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_P2PS:
+						printf("p2ps");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_VIRT_DISPLAY:
+						printf("virtual_display");
+						f++;
+						break;
+					case IEEE80211_WPS_CONFIG_PHY_DISPLAY:
+						printf("physical_display");
+						f++;
+						break;
+					default:
+						printf("unknown_wps_config<%04x>",
+						    cfg_mthd & (1 << n));
+						f++;
+						break;
+					}
+				}
 				break;
-			case IEEE80211_WPS_SELECTED_REG:
-				printf(" sel:%s", *ie ? "T" : "F");
+			case IEEE80211_WPS_ATTR_DEV_NAME:
+				printf(" device_name:<%.*s>", tlv_len, ie);
 				break;
-			case IEEE80211_WPS_DEV_PASS_ID:
+			case IEEE80211_WPS_ATTR_DEV_PASSWORD_ID:
 				n = LE_READ_2(ie);
 				if (n < nitems(dev_pass_id))
 					printf(" dpi:%s", dev_pass_id[n]);
 				break;
-			case IEEE80211_WPS_UUID_E:
+			case IEEE80211_WPS_ATTR_MANUFACTURER:
+				printf(" manufacturer:<%.*s>", tlv_len, ie);
+				break;
+			case IEEE80211_WPS_ATTR_MODEL_NAME:
+				printf(" model_name:<%.*s>", tlv_len, ie);
+				break;
+			case IEEE80211_WPS_ATTR_MODEL_NUMBER:
+				printf(" model_number:<%.*s>", tlv_len, ie);
+				break;
+			case IEEE80211_WPS_ATTR_PRIMARY_DEV_TYPE:
+				printf(" prim_dev:");
+				for (n = 0; n < tlv_len; n++)
+					printf("%02x", ie[n]);
+				break;
+			case IEEE80211_WPS_ATTR_RF_BANDS:
+				printf(" rf:");
+				f = 0;
+				for (n = 7; n >= 0; n--) {
+					if (f) {
+						printf(",");
+						f = 0;
+					}
+					switch (*ie & (1 << n)) {
+					case 0:
+						break;
+					case IEEE80211_WPS_RF_BAND_24GHZ:
+						printf("2.4Ghz");
+						f++;
+						break;
+					case IEEE80211_WPS_RF_BAND_50GHZ:
+						printf("5Ghz");
+						f++;
+						break;
+					case IEEE80211_WPS_RF_BAND_600GHZ:
+						printf("60Ghz");
+						f++;
+						break;
+					default:
+						printf("unknown<%02x>",
+						    *ie & (1 << n));
+						f++;
+						break;
+					}
+				}
+				break;
+			case IEEE80211_WPS_ATTR_RESPONSE_TYPE:
+				printf(" resp_type:0x%02x", *ie);
+				break;
+			case IEEE80211_WPS_ATTR_SELECTED_REGISTRAR:
+				printf(" sel:%s", *ie ? "T" : "F");
+				break;
+			case IEEE80211_WPS_ATTR_SERIAL_NUMBER:
+				printf(" serial_number:<%.*s>", tlv_len, ie);
+				break;
+			case IEEE80211_WPS_ATTR_UUID_E:
 				printf(" uuid-e:");
 				for (n = 0; n < (tlv_len - 1); n++)
 					printf("%02x-", ie[n]);
 				printf("%02x", ie[n]);
 				break;
+			case IEEE80211_WPS_ATTR_VENDOR_EXT:
+				printf(" vendor:");
+				for (n = 0; n < tlv_len; n++)
+					printf("%02x", ie[n]);
+				break;
+			case IEEE80211_WPS_ATTR_WPS_STATE:
+				switch (*ie) {
+				case IEEE80211_WPS_STATE_NOT_CONFIGURED:
+					printf(" state:N");
+					break;
+				case IEEE80211_WPS_STATE_CONFIGURED:
+					printf(" state:C");
+					break;
+				default:
+					printf(" state:B<%02x>", *ie);
+					break;
+				}
+				break;
+			default:
+				printf(" unknown_wps_attr:0x%x", tlv_type);
+				break;
 			}
 			ie += tlv_len, len -= tlv_len;
 		}
@@ -3353,6 +3510,7 @@ iswpsoui(const uint8_t *frm)
 static const char *
 iename(int elemid)
 {
+	static char iename_buf[64];
 	switch (elemid) {
 	case IEEE80211_ELEMID_FHPARMS:	return " FHPARMS";
 	case IEEE80211_ELEMID_CFPARMS:	return " CFPARMS";
@@ -3370,10 +3528,21 @@ iename(int elemid)
 	case IEEE80211_ELEMID_MEASREP:	return " MEASREP";
 	case IEEE80211_ELEMID_QUIET:	return " QUIET";
 	case IEEE80211_ELEMID_IBSSDFS:	return " IBSSDFS";
+	case IEEE80211_ELEMID_RESERVED_47:
+					return " RESERVED_47";
+	case IEEE80211_ELEMID_MOBILITY_DOMAIN:
+					return " MOBILITY_DOMAIN";
+	case IEEE80211_ELEMID_RRM_ENACAPS:
+					return " RRM_ENCAPS";
+	case IEEE80211_ELEMID_OVERLAP_BSS_SCAN_PARAM:
+					return " OVERLAP_BSS";
 	case IEEE80211_ELEMID_TPC:	return " TPC";
 	case IEEE80211_ELEMID_CCKM:	return " CCKM";
+	case IEEE80211_ELEMID_EXTCAP:	return " EXTCAP";
 	}
-	return " ???";
+	snprintf(iename_buf, sizeof(iename_buf), " UNKNOWN_ELEMID_%d",
+	    elemid);
+	return (const char *) iename_buf;
 }
 
 static void

Modified: projects/clang800-import/sbin/pfctl/pfctl.h
==============================================================================
--- projects/clang800-import/sbin/pfctl/pfctl.h	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/sbin/pfctl/pfctl.h	Tue Jan 22 20:24:58 2019	(r343320)
@@ -114,7 +114,6 @@ extern	int loadopt;
 
 int		 check_commit_altq(int, int);
 void		 pfaltq_store(struct pf_altq *);
-struct pf_altq	*pfaltq_lookup(const char *);
 char		*rate2str(double);
 
 void	 print_addr(struct pf_addr_wrap *, sa_family_t, int);

Modified: projects/clang800-import/sbin/pfctl/pfctl_altq.c
==============================================================================
--- projects/clang800-import/sbin/pfctl/pfctl_altq.c	Tue Jan 22 20:24:10 2019	(r343319)
+++ projects/clang800-import/sbin/pfctl/pfctl_altq.c	Tue Jan 22 20:24:58 2019	(r343320)
@@ -24,6 +24,7 @@ __FBSDID("$FreeBSD$");
 #define PFIOC_USE_LATEST
 
 #include <sys/types.h>
+#include <sys/bitset.h>
 #include <sys/ioctl.h>
 #include <sys/socket.h>
 
@@ -36,6 +37,7 @@ __FBSDID("$FreeBSD$");
 #include <inttypes.h>
 #include <limits.h>
 #include <math.h>
+#include <search.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
@@ -53,38 +55,44 @@ __FBSDID("$FreeBSD$");
 
 #define is_sc_null(sc)	(((sc) == NULL) || ((sc)->m1 == 0 && (sc)->m2 == 0))
 
-static TAILQ_HEAD(altqs, pf_altq) altqs = TAILQ_HEAD_INITIALIZER(altqs);
-static LIST_HEAD(gen_sc, segment) rtsc, lssc;
+static STAILQ_HEAD(interfaces, pfctl_altq) interfaces = STAILQ_HEAD_INITIALIZER(interfaces);
+static struct hsearch_data queue_map;
+static struct hsearch_data if_map;
+static struct hsearch_data qid_map;
 
-struct pf_altq	*qname_to_pfaltq(const char *, const char *);
-u_int32_t	 qname_to_qid(const char *);
+static struct pfctl_altq *pfaltq_lookup(char *ifname);
+static struct pfctl_altq *qname_to_pfaltq(const char *, const char *);
+static u_int32_t	 qname_to_qid(char *);
 
-static int	eval_pfqueue_cbq(struct pfctl *, struct pf_altq *);
+static int	eval_pfqueue_cbq(struct pfctl *, struct pf_altq *,
+		    struct pfctl_altq *);
 static int	cbq_compute_idletime(struct pfctl *, struct pf_altq *);
-static int	check_commit_cbq(int, int, struct pf_altq *);
+static int	check_commit_cbq(int, int, struct pfctl_altq *);
 static int	print_cbq_opts(const struct pf_altq *);
 
 static int	print_codel_opts(const struct pf_altq *,
 		    const struct node_queue_opt *);
 
-static int	eval_pfqueue_priq(struct pfctl *, struct pf_altq *);
-static int	check_commit_priq(int, int, struct pf_altq *);
+static int	eval_pfqueue_priq(struct pfctl *, struct pf_altq *,
+		    struct pfctl_altq *);
+static int	check_commit_priq(int, int, struct pfctl_altq *);
 static int	print_priq_opts(const struct pf_altq *);
 
-static int	eval_pfqueue_hfsc(struct pfctl *, struct pf_altq *);
-static int	check_commit_hfsc(int, int, struct pf_altq *);
+static int	eval_pfqueue_hfsc(struct pfctl *, struct pf_altq *,
+		    struct pfctl_altq *, struct pfctl_altq *);
+static int	check_commit_hfsc(int, int, struct pfctl_altq *);
 static int	print_hfsc_opts(const struct pf_altq *,
 		    const struct node_queue_opt *);
 
-static int	eval_pfqueue_fairq(struct pfctl *, struct pf_altq *);
+static int	eval_pfqueue_fairq(struct pfctl *, struct pf_altq *,
+		    struct pfctl_altq *, struct pfctl_altq *);
 static int	print_fairq_opts(const struct pf_altq *,
 		    const struct node_queue_opt *);
-static int	check_commit_fairq(int, int, struct pf_altq *);
+static int	check_commit_fairq(int, int, struct pfctl_altq *);
 
 static void		 gsc_add_sc(struct gen_sc *, struct service_curve *);
 static int		 is_gsc_under_sc(struct gen_sc *,
 			     struct service_curve *);
-static void		 gsc_destroy(struct gen_sc *);
 static struct segment	*gsc_getentry(struct gen_sc *, double);
 static int		 gsc_add_seg(struct gen_sc *, double, double, double,
 			     double);
@@ -104,59 +112,101 @@ void		 print_hfsc_sc(const char *, u_int, u_int, u_int
 void		 print_fairq_sc(const char *, u_int, u_int, u_int,
 		     const struct node_fairq_sc *);
 
+static __attribute__((constructor)) void
+pfctl_altq_init(void)
+{
+	/*
+	 * As hdestroy() will never be called on these tables, it will be
+	 * safe to use references into the stored data as keys.
+	 */
+	if (hcreate_r(0, &queue_map) == 0)
+		err(1, "Failed to create altq queue map");
+	if (hcreate_r(0, &if_map) == 0)
+		err(1, "Failed to create altq interface map");
+	if (hcreate_r(0, &qid_map) == 0)
+		err(1, "Failed to create altq queue id map");
+}
+
 void
 pfaltq_store(struct pf_altq *a)
 {
-	struct pf_altq	*altq;
-
+	struct pfctl_altq	*altq;
+	ENTRY 			 item;
+	ENTRY			*ret_item;
+	size_t			 key_size;
+	
 	if ((altq = malloc(sizeof(*altq))) == NULL)
-		err(1, "malloc");
-	memcpy(altq, a, sizeof(struct pf_altq));
-	TAILQ_INSERT_TAIL(&altqs, altq, entries);
+		err(1, "queue malloc");
+	memcpy(&altq->pa, a, sizeof(struct pf_altq));
+	memset(&altq->meta, 0, sizeof(altq->meta));
+
+	if (a->qname[0] == 0) {
+		item.key = altq->pa.ifname;
+		item.data = altq;
+		if (hsearch_r(item, ENTER, &ret_item, &if_map) == 0)
+			err(1, "interface map insert");
+		STAILQ_INSERT_TAIL(&interfaces, altq, meta.link);
+	} else {
+		key_size = sizeof(a->ifname) + sizeof(a->qname);
+		if ((item.key = malloc(key_size)) == NULL)
+			err(1, "queue map key malloc");
+		snprintf(item.key, key_size, "%s:%s", a->ifname, a->qname);
+		item.data = altq;
+		if (hsearch_r(item, ENTER, &ret_item, &queue_map) == 0)
+			err(1, "queue map insert");
+
+		item.key = altq->pa.qname;
+		item.data = &altq->pa.qid;
+		if (hsearch_r(item, ENTER, &ret_item, &qid_map) == 0)
+			err(1, "qid map insert");
+	}
 }
 
-struct pf_altq *
-pfaltq_lookup(const char *ifname)
+static struct pfctl_altq *
+pfaltq_lookup(char *ifname)
 {
-	struct pf_altq	*altq;
+	ENTRY	 item;
+	ENTRY	*ret_item;
 
-	TAILQ_FOREACH(altq, &altqs, entries) {
-		if (strncmp(ifname, altq->ifname, IFNAMSIZ) == 0 &&
-		    altq->qname[0] == 0)
-			return (altq);
-	}
-	return (NULL);
+	item.key = ifname;
+	if (hsearch_r(item, FIND, &ret_item, &if_map) == 0)
+		return (NULL);
+
+	return (ret_item->data);
 }
 
-struct pf_altq *
+static struct pfctl_altq *
 qname_to_pfaltq(const char *qname, const char *ifname)
 {
-	struct pf_altq	*altq;
+	ENTRY	 item;
+	ENTRY	*ret_item;
+	char	 key[IFNAMSIZ + PF_QNAME_SIZE];
 
-	TAILQ_FOREACH(altq, &altqs, entries) {
-		if (strncmp(ifname, altq->ifname, IFNAMSIZ) == 0 &&
-		    strncmp(qname, altq->qname, PF_QNAME_SIZE) == 0)
-			return (altq);
-	}
-	return (NULL);
+	item.key = key;
+	snprintf(item.key, sizeof(key), "%s:%s", ifname, qname);
+	if (hsearch_r(item, FIND, &ret_item, &queue_map) == 0)
+		return (NULL);
+
+	return (ret_item->data);
 }
 
-u_int32_t
-qname_to_qid(const char *qname)
+static u_int32_t
+qname_to_qid(char *qname)
 {
-	struct pf_altq	*altq;
-
+	ENTRY	 item;
+	ENTRY	*ret_item;
+	uint32_t qid;
+	
 	/*
 	 * We guarantee that same named queues on different interfaces
-	 * have the same qid, so we do NOT need to limit matching on
-	 * one interface!
+	 * have the same qid.
 	 */
+	item.key = qname;
+	if (hsearch_r(item, FIND, &ret_item, &qid_map) == 0)
+		return (0);
 
-	TAILQ_FOREACH(altq, &altqs, entries) {
-		if (strncmp(qname, altq->qname, PF_QNAME_SIZE) == 0)
-			return (altq->qid);
-	}
-	return (0);
+	qid = *(uint32_t *)ret_item->data;
+	return (qid);
 }
 
 void
@@ -315,28 +365,26 @@ eval_pfaltq(struct pfctl *pf, struct pf_altq *pa, stru
 int
 check_commit_altq(int dev, int opts)
 {
-	struct pf_altq	*altq;
-	int		 error = 0;
+	struct pfctl_altq	*if_ppa;
+	int			 error = 0;
 
 	/* call the discipline check for each interface. */
-	TAILQ_FOREACH(altq, &altqs, entries) {
-		if (altq->qname[0] == 0) {
-			switch (altq->scheduler) {
-			case ALTQT_CBQ:
-				error = check_commit_cbq(dev, opts, altq);
-				break;
-			case ALTQT_PRIQ:
-				error = check_commit_priq(dev, opts, altq);
-				break;
-			case ALTQT_HFSC:
-				error = check_commit_hfsc(dev, opts, altq);
-				break;
-			case ALTQT_FAIRQ:
-				error = check_commit_fairq(dev, opts, altq);
-				break;
-			default:
-				break;
-			}
+	STAILQ_FOREACH(if_ppa, &interfaces, meta.link) {
+		switch (if_ppa->pa.scheduler) {
+		case ALTQT_CBQ:
+			error = check_commit_cbq(dev, opts, if_ppa);
+			break;
+		case ALTQT_PRIQ:
+			error = check_commit_priq(dev, opts, if_ppa);
+			break;
+		case ALTQT_HFSC:
+			error = check_commit_hfsc(dev, opts, if_ppa);
+			break;
+		case ALTQT_FAIRQ:
+			error = check_commit_fairq(dev, opts, if_ppa);
+			break;
+		default:
+			break;
 		}
 	}
 	return (error);
@@ -350,17 +398,16 @@ eval_pfqueue(struct pfctl *pf, struct pf_altq *pa, str
     struct node_queue_opt *opts)
 {
 	/* should be merged with expand_queue */
-	struct pf_altq	*if_pa, *parent, *altq;
-	u_int64_t	 bwsum;
-	int		 error = 0;
+	struct pfctl_altq	*if_ppa, *parent;
+	int		 	 error = 0;
 
 	/* find the corresponding interface and copy fields used by queues */
-	if ((if_pa = pfaltq_lookup(pa->ifname)) == NULL) {
+	if ((if_ppa = pfaltq_lookup(pa->ifname)) == NULL) {
 		fprintf(stderr, "altq not defined on %s\n", pa->ifname);
 		return (1);
 	}
-	pa->scheduler = if_pa->scheduler;
-	pa->ifbandwidth = if_pa->ifbandwidth;
+	pa->scheduler = if_ppa->pa.scheduler;
+	pa->ifbandwidth = if_ppa->pa.ifbandwidth;
 
 	if (qname_to_pfaltq(pa->qname, pa->ifname) != NULL) {
 		fprintf(stderr, "queue %s already exists on interface %s\n",
@@ -377,16 +424,32 @@ eval_pfqueue(struct pfctl *pf, struct pf_altq *pa, str
 			    pa->parent, pa->qname);
 			return (1);
 		}
-		pa->parent_qid = parent->qid;
+		pa->parent_qid = parent->pa.qid;
 	}
 	if (pa->qlimit == 0)
 		pa->qlimit = DEFAULT_QLIMIT;
 
+	if (eval_queue_opts(pa, opts,
+		parent == NULL ? pa->ifbandwidth : parent->pa.bandwidth))
+		return (1);
+
 	if (pa->scheduler == ALTQT_CBQ || pa->scheduler == ALTQT_HFSC ||
 		pa->scheduler == ALTQT_FAIRQ) {
 		pa->bandwidth = eval_bwspec(bw,
-		    parent == NULL ? pa->ifbandwidth : parent->bandwidth);
+		    parent == NULL ? pa->ifbandwidth : parent->pa.bandwidth);
 
+		/*
+		 * For HFSC, if the linkshare service curve m2 parameter is
+		 * set, it overrides the provided queue bandwidth parameter,
+		 * so adjust the queue bandwidth parameter accordingly here
+		 * to avoid false positives in the total child bandwidth
+		 * check below.
+		 */
+		if ((pa->scheduler == ALTQT_HFSC) &&
+		    (pa->pq_u.hfsc_opts.lssc_m2 != 0)) {
+			pa->bandwidth = pa->pq_u.hfsc_opts.lssc_m2;
+		}
+
 		if (pa->bandwidth > pa->ifbandwidth) {
 			fprintf(stderr, "bandwidth for %s higher than "
 			    "interface\n", pa->qname);
@@ -394,44 +457,36 @@ eval_pfqueue(struct pfctl *pf, struct pf_altq *pa, str
 		}
 		/* check the sum of the child bandwidth is under parent's */
 		if (parent != NULL) {
-			if (pa->bandwidth > parent->bandwidth) {
+			if (pa->bandwidth > parent->pa.bandwidth) {
 				warnx("bandwidth for %s higher than parent",
 				    pa->qname);
 				return (1);
 			}
-			bwsum = 0;
-			TAILQ_FOREACH(altq, &altqs, entries) {
-				if (strncmp(altq->ifname, pa->ifname,
-				    IFNAMSIZ) == 0 &&
-				    altq->qname[0] != 0 &&
-				    strncmp(altq->parent, pa->parent,
-				    PF_QNAME_SIZE) == 0)
-					bwsum += altq->bandwidth;
+			parent->meta.bwsum += pa->bandwidth;
+			if (parent->meta.bwsum > parent->pa.bandwidth) {
+				warnx("the sum of the child bandwidth (%" PRIu64
+				    ") higher than parent \"%s\" (%" PRIu64 ")",
+				    parent->meta.bwsum, parent->pa.qname,
+				    parent->pa.bandwidth);
 			}
-			bwsum += pa->bandwidth;
-			if (bwsum > parent->bandwidth) {
-				warnx("the sum of the child bandwidth higher"
-				    " than parent \"%s\"", parent->qname);
-			}
 		}
 	}
 
-	if (eval_queue_opts(pa, opts,
-		parent == NULL ? pa->ifbandwidth : parent->bandwidth))
-		return (1);
-
+	if (parent != NULL)
+		parent->meta.children++;
+	
 	switch (pa->scheduler) {
 	case ALTQT_CBQ:
-		error = eval_pfqueue_cbq(pf, pa);
+		error = eval_pfqueue_cbq(pf, pa, if_ppa);
 		break;
 	case ALTQT_PRIQ:
-		error = eval_pfqueue_priq(pf, pa);
+		error = eval_pfqueue_priq(pf, pa, if_ppa);
 		break;
 	case ALTQT_HFSC:
-		error = eval_pfqueue_hfsc(pf, pa);
+		error = eval_pfqueue_hfsc(pf, pa, if_ppa, parent);
 		break;
 	case ALTQT_FAIRQ:
-		error = eval_pfqueue_fairq(pf, pa);
+		error = eval_pfqueue_fairq(pf, pa, if_ppa, parent);
 		break;
 	default:
 		break;
@@ -446,7 +501,7 @@ eval_pfqueue(struct pfctl *pf, struct pf_altq *pa, str
 #define	RM_NS_PER_SEC	(1000000000)
 
 static int
-eval_pfqueue_cbq(struct pfctl *pf, struct pf_altq *pa)
+eval_pfqueue_cbq(struct pfctl *pf, struct pf_altq *pa, struct pfctl_altq *if_ppa)
 {
 	struct cbq_opts	*opts;
 	u_int		 ifmtu;
@@ -476,6 +531,11 @@ eval_pfqueue_cbq(struct pfctl *pf, struct pf_altq *pa)
 	if (pa->parent[0] == 0)
 		opts->flags |= (CBQCLF_ROOTCLASS | CBQCLF_WRR);
 
+	if (pa->pq_u.cbq_opts.flags & CBQCLF_ROOTCLASS)
+		if_ppa->meta.root_classes++;
+	if (pa->pq_u.cbq_opts.flags & CBQCLF_DEFCLASS)
+		if_ppa->meta.default_classes++;
+	
 	cbq_compute_idletime(pf, pa);
 	return (0);
 }
@@ -568,33 +628,20 @@ cbq_compute_idletime(struct pfctl *pf, struct pf_altq 
 }
 
 static int
-check_commit_cbq(int dev, int opts, struct pf_altq *pa)
+check_commit_cbq(int dev, int opts, struct pfctl_altq *if_ppa)
 {
-	struct pf_altq	*altq;
-	int		 root_class, default_class;
-	int		 error = 0;
+	int	error = 0;
 
 	/*
 	 * check if cbq has one root queue and one default queue
 	 * for this interface
 	 */
-	root_class = default_class = 0;
-	TAILQ_FOREACH(altq, &altqs, entries) {
-		if (strncmp(altq->ifname, pa->ifname, IFNAMSIZ) != 0)
-			continue;
-		if (altq->qname[0] == 0)  /* this is for interface */
-			continue;
-		if (altq->pq_u.cbq_opts.flags & CBQCLF_ROOTCLASS)
-			root_class++;
-		if (altq->pq_u.cbq_opts.flags & CBQCLF_DEFCLASS)
-			default_class++;
-	}
-	if (root_class != 1) {
-		warnx("should have one root queue on %s", pa->ifname);
+	if (if_ppa->meta.root_classes != 1) {
+		warnx("should have one root queue on %s", if_ppa->pa.ifname);
 		error++;
 	}
-	if (default_class != 1) {
-		warnx("should have one default queue on %s", pa->ifname);
+	if (if_ppa->meta.default_classes != 1) {
+		warnx("should have one default queue on %s", if_ppa->pa.ifname);
 		error++;
 	}
 	return (error);
@@ -641,51 +688,37 @@ print_cbq_opts(const struct pf_altq *a)
  * PRIQ support functions
  */
 static int
-eval_pfqueue_priq(struct pfctl *pf, struct pf_altq *pa)
+eval_pfqueue_priq(struct pfctl *pf, struct pf_altq *pa, struct pfctl_altq *if_ppa)
 {
-	struct pf_altq	*altq;
 
 	if (pa->priority >= PRIQ_MAXPRI) {
 		warnx("priority out of range: max %d", PRIQ_MAXPRI - 1);
 		return (-1);
 	}
-	/* the priority should be unique for the interface */
-	TAILQ_FOREACH(altq, &altqs, entries) {
-		if (strncmp(altq->ifname, pa->ifname, IFNAMSIZ) == 0 &&
-		    altq->qname[0] != 0 && altq->priority == pa->priority) {
-			warnx("%s and %s have the same priority",
-			    altq->qname, pa->qname);
-			return (-1);
-		}
-	}
+	if (BIT_ISSET(QPRI_BITSET_SIZE, pa->priority, &if_ppa->meta.qpris)) {
+		warnx("%s does not have a unique priority on interface %s",
+		    pa->qname, pa->ifname);
+		return (-1);
+	} else
+		BIT_SET(QPRI_BITSET_SIZE, pa->priority, &if_ppa->meta.qpris);
 
+	if (pa->pq_u.priq_opts.flags & PRCF_DEFAULTCLASS)
+		if_ppa->meta.default_classes++;
 	return (0);
 }
 
 static int
-check_commit_priq(int dev, int opts, struct pf_altq *pa)
+check_commit_priq(int dev, int opts, struct pfctl_altq *if_ppa)
 {
-	struct pf_altq	*altq;
-	int		 default_class;
-	int		 error = 0;
 
 	/*
 	 * check if priq has one default class for this interface
 	 */
-	default_class = 0;
-	TAILQ_FOREACH(altq, &altqs, entries) {
-		if (strncmp(altq->ifname, pa->ifname, IFNAMSIZ) != 0)
-			continue;
-		if (altq->qname[0] == 0)  /* this is for interface */
-			continue;
-		if (altq->pq_u.priq_opts.flags & PRCF_DEFAULTCLASS)
-			default_class++;
+	if (if_ppa->meta.default_classes != 1) {
+		warnx("should have one default queue on %s", if_ppa->pa.ifname);
+		return (1);
 	}
-	if (default_class != 1) {
-		warnx("should have one default queue on %s", pa->ifname);
-		error++;
-	}
-	return (error);
+	return (0);
 }
 
 static int
@@ -720,15 +753,15 @@ print_priq_opts(const struct pf_altq *a)
  * HFSC support functions
  */
 static int
-eval_pfqueue_hfsc(struct pfctl *pf, struct pf_altq *pa)
+eval_pfqueue_hfsc(struct pfctl *pf, struct pf_altq *pa, struct pfctl_altq *if_ppa,
+    struct pfctl_altq *parent)
 {
-	struct pf_altq		*altq, *parent;
 	struct hfsc_opts_v1	*opts;
 	struct service_curve	 sc;
 
 	opts = &pa->pq_u.hfsc_opts;
 
-	if (pa->parent[0] == 0) {
+	if (parent == NULL) {
 		/* root queue */
 		opts->lssc_m1 = pa->ifbandwidth;
 		opts->lssc_m2 = pa->ifbandwidth;
@@ -736,9 +769,21 @@ eval_pfqueue_hfsc(struct pfctl *pf, struct pf_altq *pa
 		return (0);
 	}
 
-	LIST_INIT(&rtsc);
-	LIST_INIT(&lssc);
+	/* First child initializes the parent's service curve accumulators. */
+	if (parent->meta.children == 1) {
+		LIST_INIT(&parent->meta.rtsc);
+		LIST_INIT(&parent->meta.lssc);
+	}
 
+	if (parent->pa.pq_u.hfsc_opts.flags & HFCF_DEFAULTCLASS) {
+		warnx("adding %s would make default queue %s not a leaf",
+		    pa->qname, pa->parent);
+		return (-1);
+	}
+
+	if (pa->pq_u.hfsc_opts.flags & HFCF_DEFAULTCLASS)
+		if_ppa->meta.default_classes++;
+	
 	/* if link_share is not specified, use bandwidth */
 	if (opts->lssc_m2 == 0)
 		opts->lssc_m2 = pa->bandwidth;
@@ -768,51 +813,22 @@ eval_pfqueue_hfsc(struct pfctl *pf, struct pf_altq *pa
 	 * be smaller than the interface bandwidth, and the upper-limit should
 	 * be larger than the real-time service curve when both are defined.
 	 */
-	parent = qname_to_pfaltq(pa->parent, pa->ifname);
-	if (parent == NULL)
-		errx(1, "parent %s not found for %s", pa->parent, pa->qname);
-
-	TAILQ_FOREACH(altq, &altqs, entries) {
-		if (strncmp(altq->ifname, pa->ifname, IFNAMSIZ) != 0)
-			continue;
-		if (altq->qname[0] == 0)  /* this is for interface */
-			continue;
-
-		/* if the class has a real-time service curve, add it. */
-		if (opts->rtsc_m2 != 0 && altq->pq_u.hfsc_opts.rtsc_m2 != 0) {
-			sc.m1 = altq->pq_u.hfsc_opts.rtsc_m1;
-			sc.d = altq->pq_u.hfsc_opts.rtsc_d;
-			sc.m2 = altq->pq_u.hfsc_opts.rtsc_m2;
-			gsc_add_sc(&rtsc, &sc);
-		}
-
-		if (strncmp(altq->parent, pa->parent, PF_QNAME_SIZE) != 0)
-			continue;
-
-		/* if the class has a linkshare service curve, add it. */
-		if (opts->lssc_m2 != 0 && altq->pq_u.hfsc_opts.lssc_m2 != 0) {
-			sc.m1 = altq->pq_u.hfsc_opts.lssc_m1;
-			sc.d = altq->pq_u.hfsc_opts.lssc_d;
-			sc.m2 = altq->pq_u.hfsc_opts.lssc_m2;
-			gsc_add_sc(&lssc, &sc);
-		}
-	}
-
+	
 	/* check the real-time service curve.  reserve 20% of interface bw */
 	if (opts->rtsc_m2 != 0) {
 		/* add this queue to the sum */
 		sc.m1 = opts->rtsc_m1;
 		sc.d = opts->rtsc_d;
 		sc.m2 = opts->rtsc_m2;
-		gsc_add_sc(&rtsc, &sc);
+		gsc_add_sc(&parent->meta.rtsc, &sc);
 		/* compare the sum with 80% of the interface */
 		sc.m1 = 0;
 		sc.d = 0;
 		sc.m2 = pa->ifbandwidth / 100 * 80;
-		if (!is_gsc_under_sc(&rtsc, &sc)) {
+		if (!is_gsc_under_sc(&parent->meta.rtsc, &sc)) {
 			warnx("real-time sc exceeds 80%% of the interface "
 			    "bandwidth (%s)", rate2str((double)sc.m2));
-			goto err_ret;
+			return (-1);
 		}
 	}

*** DIFF OUTPUT TRUNCATED AT 1000 LINES ***


More information about the svn-src-projects mailing list