Netdev List
 help / color / mirror / Atom feed
* [PATCH 0/2] ieee80211: Update generic definitions to latest specs - take #2
From: Gertjan van Wingerde @ 2005-06-03 20:31 UTC (permalink / raw)
  To: netdev; +Cc: jgarzik

Hi,

Following patches update the definitions of the generic ieee80211 stack 
to the latest versions
of the published 802.11x specification suite, and cleans up the long 
list of defines.

The set of patches is a resubmittal of my earlier patch, with the 
comments of Jiri Benc and Stephen
Hemminger fixed.

The patches need to be applied in order.

Thanks,

Gertjan van Wingerde

^ permalink raw reply

* [PATCH 1/2] ieee80211: Update generic definitions to latest specs - take #2
From: Gertjan van Wingerde @ 2005-06-03 20:31 UTC (permalink / raw)
  To: netdev; +Cc: jgarzik

[-- Attachment #1: Type: text/plain, Size: 259 bytes --]

Hi,

Attached patch updates the definitions of the generic ieee80211 stack to 
the latest versions of the published 802.11x specification suite.
Please review and apply.

Signed-off-by: Gertjan van Wingerde <gwingerde@home.nl>

Thanks,

Gertjan van Wingerde


[-- Attachment #2: ieee80211-new-definitions.diff --]
[-- Type: text/plain, Size: 10187 bytes --]

Index: include/net/ieee80211.h
===================================================================
--- 4b4ba76aa81b3627142787262fd2f8049dd3662d/include/net/ieee80211.h  (mode:100644)
+++ uncommitted/include/net/ieee80211.h  (mode:100644)
@@ -103,7 +103,7 @@
 #define	MAX_FRAG_THRESHOLD     2346U
 
 /* Frame control field constants */
-#define IEEE80211_FCTL_VERS		0x0002
+#define IEEE80211_FCTL_VERS		0x0003
 #define IEEE80211_FCTL_FTYPE		0x000c
 #define IEEE80211_FCTL_STYPE		0x00f0
 #define IEEE80211_FCTL_TODS		0x0100
@@ -111,8 +111,8 @@
 #define IEEE80211_FCTL_MOREFRAGS	0x0400
 #define IEEE80211_FCTL_RETRY		0x0800
 #define IEEE80211_FCTL_PM		0x1000
-#define IEEE80211_FCTL_MOREDATA	0x2000
-#define IEEE80211_FCTL_WEP		0x4000
+#define IEEE80211_FCTL_MOREDATA		0x2000
+#define IEEE80211_FCTL_PROTECTED	0x4000
 #define IEEE80211_FCTL_ORDER		0x8000
 
 #define IEEE80211_FTYPE_MGMT		0x0000
@@ -131,6 +131,7 @@
 #define IEEE80211_STYPE_DISASSOC	0x00A0
 #define IEEE80211_STYPE_AUTH		0x00B0
 #define IEEE80211_STYPE_DEAUTH		0x00C0
+#define IEEE80211_STYPE_ACTION		0x00D0
 
 /* control */
 #define IEEE80211_STYPE_PSPOLL		0x00A0
@@ -251,6 +252,7 @@
 
 #define SNAP_SIZE sizeof(struct ieee80211_snap_hdr)
 
+#define WLAN_FC_GET_VERS(fc) ((fc) & IEEE80211_FCTL_VERS)
 #define WLAN_FC_GET_TYPE(fc) ((fc) & IEEE80211_FCTL_FTYPE)
 #define WLAN_FC_GET_STYPE(fc) ((fc) & IEEE80211_FCTL_STYPE)
 
@@ -271,6 +273,9 @@
 #define WLAN_CAPABILITY_SHORT_PREAMBLE (1<<5)
 #define WLAN_CAPABILITY_PBCC (1<<6)
 #define WLAN_CAPABILITY_CHANNEL_AGILITY (1<<7)
+#define WLAN_CAPABILITY_SPECTRUM_MGMT (1<<8)
+#define WLAN_CAPABILITY_SHORT_SLOT_TIME (1<<10)
+#define WLAN_CAPABILITY_OSSS_OFDM (1<<13)
 
 /* Status codes */
 #define WLAN_STATUS_SUCCESS 0
@@ -285,9 +290,24 @@
 #define WLAN_STATUS_AP_UNABLE_TO_HANDLE_NEW_STA 17
 #define WLAN_STATUS_ASSOC_DENIED_RATES 18
 /* 802.11b */
-#define WLAN_STATUS_ASSOC_DENIED_NOSHORT 19
+#define WLAN_STATUS_ASSOC_DENIED_NOSHORTPREAMBLE 19
 #define WLAN_STATUS_ASSOC_DENIED_NOPBCC 20
 #define WLAN_STATUS_ASSOC_DENIED_NOAGILITY 21
+/* 802.11h */
+#define WLAN_STATUS_ASSOC_DENIED_NOSPECTRUM 22
+#define WLAN_STATUS_ASSOC_REJECTED_BAD_POWER 23
+#define WLAN_STATUS_ASSOC_REJECTED_BAD_SUPP_CHAN 24
+/* 802.11g */
+#define WLAN_STATUS_ASSOC_DENIED_NOSHORTTIME 25
+#define WLAN_STATUS_ASSOC_DENIED_NODSSSOFDM 26
+/* 802.11i */
+#define WLAN_STATUS_INVALID_IE 40
+#define WLAN_STATUS_INVALID_GROUP_CIPHER 41
+#define WLAN_STATUS_INVALID_PAIRWISE_CIPHER 42
+#define WLAN_STATUS_INVALID_AKMP 43
+#define WLAN_STATUS_UNSUPP_RSN_VERSION 44
+#define WLAN_STATUS_INVALID_RSN_IE_CAP 45
+#define WLAN_STATUS_CIPHER_SUITE_REJECTED 46
 
 /* Reason codes */
 #define WLAN_REASON_UNSPECIFIED 1
@@ -299,6 +319,22 @@
 #define WLAN_REASON_CLASS3_FRAME_FROM_NONASSOC_STA 7
 #define WLAN_REASON_DISASSOC_STA_HAS_LEFT 8
 #define WLAN_REASON_STA_REQ_ASSOC_WITHOUT_AUTH 9
+/* 802.11h */
+#define WLAN_REASON_DISASSOC_BAD_POWER 10
+#define WLAN_REASON_DISASSOC_BAD_SUPP_CHAN 11
+/* 802.11i */
+#define WLAN_REASON_INVALID_IE 13
+#define WLAN_REASON_MIC_FAILURE 14
+#define WLAN_REASON_4WAY_HANDSHAKE_TIMEOUT 15
+#define WLAN_REASON_GROUP_KEY_HANDSHAKE_TIMEOUT 16
+#define WLAN_REASON_IE_DIFFERENT 17
+#define WLAN_REASON_INVALID_GROUP_CIPHER 18
+#define WLAN_REASON_INVALID_PAIRWISE_CIPHER 19
+#define WLAN_REASON_INVALID_AKMP 20
+#define WLAN_REASON_UNSUPP_RSN_VERSION 21
+#define WLAN_REASON_INVALID_RSN_IE_CAP 22
+#define WLAN_REASON_IEEE8021X_FAILED 23
+#define WLAN_REASON_CIPHER_SUITE_REJECTED 24
 
 
 #define IEEE80211_STATMASK_SIGNAL (1<<0)
@@ -477,17 +513,32 @@
 #define BEACON_PROBE_SSID_ID_POSITION 12
 
 /* Management Frame Information Element Types */
-#define MFIE_TYPE_SSID       0
-#define MFIE_TYPE_RATES      1
-#define MFIE_TYPE_FH_SET     2
-#define MFIE_TYPE_DS_SET     3
-#define MFIE_TYPE_CF_SET     4
-#define MFIE_TYPE_TIM        5
-#define MFIE_TYPE_IBSS_SET   6
-#define MFIE_TYPE_CHALLENGE  16
-#define MFIE_TYPE_RSN	     48
-#define MFIE_TYPE_RATES_EX   50
-#define MFIE_TYPE_GENERIC    221
+#define MFIE_TYPE_SSID              0
+#define MFIE_TYPE_RATES             1
+#define MFIE_TYPE_FH_SET            2
+#define MFIE_TYPE_DS_SET            3
+#define MFIE_TYPE_CF_SET            4
+#define MFIE_TYPE_TIM               5
+#define MFIE_TYPE_IBSS_SET          6
+#define MFIE_TYPE_COUNTRY           7
+#define MFIE_TYPE_HOP_PARAMS        8
+#define MFIE_TYPE_HOP_TABLE         9
+#define MFIE_TYPE_REQUEST           10
+#define MFIE_TYPE_CHALLENGE         16
+#define MFIE_TYPE_POWER_CONSTRAINT  32
+#define MFIE_TYPE_POWER_CAPABILITY  33
+#define MFIE_TYPE_TPC_REQUEST       34
+#define MFIE_TYPE_TPC_REPORT        35
+#define MFIE_TYPE_SUPP_CHANNELS     36
+#define MFIE_TYPE_CSA               37
+#define MFIE_TYPE_MEASURE_REQUEST   38
+#define MFIE_TYPE_MEASURE_REPORT    39
+#define MFIE_TYPE_QUIET             40
+#define MFIE_TYPE_IBSS_DFS          41
+#define MFIE_TYPE_ERP_INFO          42
+#define MFIE_TYPE_RSN	            48
+#define MFIE_TYPE_RATES_EX          50
+#define MFIE_TYPE_GENERIC           221
 
 struct ieee80211_info_element_hdr {
 	u8 id;
Index: net/ieee80211/ieee80211_rx.c
===================================================================
--- 4b4ba76aa81b3627142787262fd2f8049dd3662d/net/ieee80211/ieee80211_rx.c  (mode:100644)
+++ uncommitted/net/ieee80211/ieee80211_rx.c  (mode:100644)
@@ -440,7 +440,7 @@
 			      crypt->ops->decrypt_mpdu == NULL))
 			crypt = NULL;
 
-		if (!crypt && (fc & IEEE80211_FCTL_WEP)) {
+		if (!crypt && (fc & IEEE80211_FCTL_PROTECTED)) {
 			/* This seems to be triggered by some (multicast?)
 			 * frames from other than current BSS, so just drop the
 			 * frames silently instead of filling system log with
@@ -456,7 +456,7 @@
 #ifdef NOT_YET
 	if (type != WLAN_FC_TYPE_DATA) {
 		if (type == WLAN_FC_TYPE_MGMT && stype == WLAN_FC_STYPE_AUTH &&
-		    fc & IEEE80211_FCTL_WEP && ieee->host_decrypt &&
+		    fc & IEEE80211_FCTL_PROTECTED && ieee->host_decrypt &&
 		    (keyidx = hostap_rx_frame_decrypt(ieee, skb, crypt)) < 0)
 		{
 			printk(KERN_DEBUG "%s: failed to decrypt mgmt::auth "
@@ -557,7 +557,7 @@
 
 	/* skb: hdr + (possibly fragmented, possibly encrypted) payload */
 
-	if (ieee->host_decrypt && (fc & IEEE80211_FCTL_WEP) &&
+	if (ieee->host_decrypt && (fc & IEEE80211_FCTL_PROTECTED) &&
 	    (keyidx = ieee80211_rx_frame_decrypt(ieee, skb, crypt)) < 0)
 		goto rx_dropped;
 
@@ -565,7 +565,7 @@
 
 	/* skb: hdr + (possibly fragmented) plaintext payload */
 	// PR: FIXME: hostap has additional conditions in the "if" below:
-	// ieee->host_decrypt && (fc & IEEE80211_FCTL_WEP) &&
+	// ieee->host_decrypt && (fc & IEEE80211_FCTL_PROTECTED) &&
 	if ((frag != 0 || (fc & IEEE80211_FCTL_MOREFRAGS))) {
 		int flen;
 		struct sk_buff *frag_skb = ieee80211_frag_cache_get(ieee, hdr);
@@ -621,12 +621,12 @@
 
 	/* skb: hdr + (possible reassembled) full MSDU payload; possibly still
 	 * encrypted/authenticated */
-	if (ieee->host_decrypt && (fc & IEEE80211_FCTL_WEP) &&
+	if (ieee->host_decrypt && (fc & IEEE80211_FCTL_PROTECTED) &&
 	    ieee80211_rx_frame_decrypt_msdu(ieee, skb, keyidx, crypt))
 		goto rx_dropped;
 
 	hdr = (struct ieee80211_hdr *) skb->data;
-	if (crypt && !(fc & IEEE80211_FCTL_WEP) && !ieee->open_wep) {
+	if (crypt && !(fc & IEEE80211_FCTL_PROTECTED) && !ieee->open_wep) {
 		if (/*ieee->ieee802_1x &&*/
 		    ieee80211_is_eapol_frame(ieee, skb)) {
 #ifdef CONFIG_IEEE80211_DEBUG
@@ -647,7 +647,7 @@
 	}
 
 #ifdef CONFIG_IEEE80211_DEBUG
-	if (crypt && !(fc & IEEE80211_FCTL_WEP) &&
+	if (crypt && !(fc & IEEE80211_FCTL_PROTECTED) &&
 	    ieee80211_is_eapol_frame(ieee, skb)) {
 			struct eapol *eap = (struct eapol *)(skb->data +
 				24);
@@ -656,7 +656,7 @@
 	}
 #endif
 
-	if (crypt && !(fc & IEEE80211_FCTL_WEP) && !ieee->open_wep &&
+	if (crypt && !(fc & IEEE80211_FCTL_PROTECTED) && !ieee->open_wep &&
 	    !ieee80211_is_eapol_frame(ieee, skb)) {
 		IEEE80211_DEBUG_DROP(
 			"dropped unencrypted RX data "
Index: net/ieee80211/ieee80211_tx.c
===================================================================
--- 4b4ba76aa81b3627142787262fd2f8049dd3662d/net/ieee80211/ieee80211_tx.c  (mode:100644)
+++ uncommitted/net/ieee80211/ieee80211_tx.c  (mode:100644)
@@ -314,7 +314,7 @@
 
 	if (encrypt)
 		fc = IEEE80211_FTYPE_DATA | IEEE80211_STYPE_DATA |
-			IEEE80211_FCTL_WEP;
+			IEEE80211_FCTL_PROTECTED;
 	else
 		fc = IEEE80211_FTYPE_DATA | IEEE80211_STYPE_DATA;
 
Index: drivers/net/wireless/atmel.c
===================================================================
--- 4b4ba76aa81b3627142787262fd2f8049dd3662d/drivers/net/wireless/atmel.c  (mode:100644)
+++ uncommitted/drivers/net/wireless/atmel.c  (mode:100644)
@@ -867,7 +867,7 @@
 	header.duration_id = 0;
 	header.seq_ctl = 0;
 	if (priv->wep_is_on)
-		frame_ctl |= IEEE80211_FCTL_WEP;
+		frame_ctl |= IEEE80211_FCTL_PROTECTED;
 	if (priv->operating_mode == IW_MODE_ADHOC) {
 		memcpy(&header.addr1, skb->data, 6);
 		memcpy(&header.addr2, dev->dev_addr, 6);
@@ -1117,7 +1117,7 @@
 		/* probe for CRC use here if needed  once five packets have arrived with
 		   the same crc status, we assume we know what's happening and stop probing */
 		if (priv->probe_crc) {
-			if (!priv->wep_is_on || !(frame_ctl & IEEE80211_FCTL_WEP)) {
+			if (!priv->wep_is_on || !(frame_ctl & IEEE80211_FCTL_PROTECTED)) {
 				priv->do_rx_crc = probe_crc(priv, rx_packet_loc, msdu_size);
 			} else {
 				priv->do_rx_crc = probe_crc(priv, rx_packet_loc + 24, msdu_size - 24);
@@ -1132,7 +1132,7 @@
 		}
 		    
 		/* don't CRC header when WEP in use */
-		if (priv->do_rx_crc && (!priv->wep_is_on || !(frame_ctl & IEEE80211_FCTL_WEP))) {
+		if (priv->do_rx_crc && (!priv->wep_is_on || !(frame_ctl & IEEE80211_FCTL_PROTECTED))) {
 			crc = crc32_le(0xffffffff, (unsigned char *)&header, 24);
 		}
 		msdu_size -= 24; /* header */
@@ -2677,7 +2677,7 @@
 		auth.alg = cpu_to_le16(C80211_MGMT_AAN_SHAREDKEY); 
 		/* no WEP for authentication frames with TrSeqNo 1 */
 		if (priv->CurrentAuthentTransactionSeqNum != 1)
-			header.frame_ctl |=  cpu_to_le16(IEEE80211_FCTL_WEP); 
+			header.frame_ctl |=  cpu_to_le16(IEEE80211_FCTL_PROTECTED); 
 	} else {
 		auth.alg = cpu_to_le16(C80211_MGMT_AAN_OPENSYSTEM);
 	}

^ permalink raw reply

* [PATCH 2/2] ieee80211: Update generic definitions to latest specs - take #2
From: Gertjan van Wingerde @ 2005-06-03 20:31 UTC (permalink / raw)
  To: netdev; +Cc: jgarzik

[-- Attachment #1: Type: text/plain, Size: 204 bytes --]

Hi,

Attached patch cleans up the long lists of #defines for status codes, 
reason codes, and information elements.

Signed-off-by: Gertjan van Wingerde <gwingerde@home.nl>

Thanks,

Gertjan van Wingerde

[-- Attachment #2: ieee80211-cleanup.diff --]
[-- Type: text/plain, Size: 6698 bytes --]

Index: include/net/ieee80211.h
===================================================================
--- eb77617da695526508e860d3775afc781de70dea/include/net/ieee80211.h  (mode:100644)
+++ uncommitted/include/net/ieee80211.h  (mode:100644)
@@ -278,63 +278,67 @@
 #define WLAN_CAPABILITY_OSSS_OFDM (1<<13)
 
 /* Status codes */
-#define WLAN_STATUS_SUCCESS 0
-#define WLAN_STATUS_UNSPECIFIED_FAILURE 1
-#define WLAN_STATUS_CAPS_UNSUPPORTED 10
-#define WLAN_STATUS_REASSOC_NO_ASSOC 11
-#define WLAN_STATUS_ASSOC_DENIED_UNSPEC 12
-#define WLAN_STATUS_NOT_SUPPORTED_AUTH_ALG 13
-#define WLAN_STATUS_UNKNOWN_AUTH_TRANSACTION 14
-#define WLAN_STATUS_CHALLENGE_FAIL 15
-#define WLAN_STATUS_AUTH_TIMEOUT 16
-#define WLAN_STATUS_AP_UNABLE_TO_HANDLE_NEW_STA 17
-#define WLAN_STATUS_ASSOC_DENIED_RATES 18
-/* 802.11b */
-#define WLAN_STATUS_ASSOC_DENIED_NOSHORTPREAMBLE 19
-#define WLAN_STATUS_ASSOC_DENIED_NOPBCC 20
-#define WLAN_STATUS_ASSOC_DENIED_NOAGILITY 21
-/* 802.11h */
-#define WLAN_STATUS_ASSOC_DENIED_NOSPECTRUM 22
-#define WLAN_STATUS_ASSOC_REJECTED_BAD_POWER 23
-#define WLAN_STATUS_ASSOC_REJECTED_BAD_SUPP_CHAN 24
-/* 802.11g */
-#define WLAN_STATUS_ASSOC_DENIED_NOSHORTTIME 25
-#define WLAN_STATUS_ASSOC_DENIED_NODSSSOFDM 26
-/* 802.11i */
-#define WLAN_STATUS_INVALID_IE 40
-#define WLAN_STATUS_INVALID_GROUP_CIPHER 41
-#define WLAN_STATUS_INVALID_PAIRWISE_CIPHER 42
-#define WLAN_STATUS_INVALID_AKMP 43
-#define WLAN_STATUS_UNSUPP_RSN_VERSION 44
-#define WLAN_STATUS_INVALID_RSN_IE_CAP 45
-#define WLAN_STATUS_CIPHER_SUITE_REJECTED 46
+enum ieee80211_statuscode {
+	WLAN_STATUS_SUCCESS = 0,
+	WLAN_STATUS_UNSPECIFIED_FAILURE = 1,
+	WLAN_STATUS_CAPS_UNSUPPORTED = 10,
+	WLAN_STATUS_REASSOC_NO_ASSOC = 11,
+	WLAN_STATUS_ASSOC_DENIED_UNSPEC = 12,
+	WLAN_STATUS_NOT_SUPPORTED_AUTH_ALG = 13,
+	WLAN_STATUS_UNKNOWN_AUTH_TRANSACTION = 14,
+	WLAN_STATUS_CHALLENGE_FAIL = 15,
+	WLAN_STATUS_AUTH_TIMEOUT = 16,
+	WLAN_STATUS_AP_UNABLE_TO_HANDLE_NEW_STA = 17,
+	WLAN_STATUS_ASSOC_DENIED_RATES = 18,
+	/* 802.11b */
+	WLAN_STATUS_ASSOC_DENIED_NOSHORTPREAMBLE = 19,
+	WLAN_STATUS_ASSOC_DENIED_NOPBCC = 20,
+	WLAN_STATUS_ASSOC_DENIED_NOAGILITY = 21,
+	/* 802.11h */
+	WLAN_STATUS_ASSOC_DENIED_NOSPECTRUM = 22,
+	WLAN_STATUS_ASSOC_REJECTED_BAD_POWER = 23,
+	WLAN_STATUS_ASSOC_REJECTED_BAD_SUPP_CHAN = 24,
+	/* 802.11g */
+	WLAN_STATUS_ASSOC_DENIED_NOSHORTTIME = 25,
+	WLAN_STATUS_ASSOC_DENIED_NODSSSOFDM = 26,
+	/* 802.11i */
+	WLAN_STATUS_INVALID_IE = 40,
+	WLAN_STATUS_INVALID_GROUP_CIPHER = 41,
+	WLAN_STATUS_INVALID_PAIRWISE_CIPHER = 42,
+	WLAN_STATUS_INVALID_AKMP = 43,
+	WLAN_STATUS_UNSUPP_RSN_VERSION = 44,
+	WLAN_STATUS_INVALID_RSN_IE_CAP = 45,
+	WLAN_STATUS_CIPHER_SUITE_REJECTED = 46,
+};
 
 /* Reason codes */
-#define WLAN_REASON_UNSPECIFIED 1
-#define WLAN_REASON_PREV_AUTH_NOT_VALID 2
-#define WLAN_REASON_DEAUTH_LEAVING 3
-#define WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY 4
-#define WLAN_REASON_DISASSOC_AP_BUSY 5
-#define WLAN_REASON_CLASS2_FRAME_FROM_NONAUTH_STA 6
-#define WLAN_REASON_CLASS3_FRAME_FROM_NONASSOC_STA 7
-#define WLAN_REASON_DISASSOC_STA_HAS_LEFT 8
-#define WLAN_REASON_STA_REQ_ASSOC_WITHOUT_AUTH 9
-/* 802.11h */
-#define WLAN_REASON_DISASSOC_BAD_POWER 10
-#define WLAN_REASON_DISASSOC_BAD_SUPP_CHAN 11
-/* 802.11i */
-#define WLAN_REASON_INVALID_IE 13
-#define WLAN_REASON_MIC_FAILURE 14
-#define WLAN_REASON_4WAY_HANDSHAKE_TIMEOUT 15
-#define WLAN_REASON_GROUP_KEY_HANDSHAKE_TIMEOUT 16
-#define WLAN_REASON_IE_DIFFERENT 17
-#define WLAN_REASON_INVALID_GROUP_CIPHER 18
-#define WLAN_REASON_INVALID_PAIRWISE_CIPHER 19
-#define WLAN_REASON_INVALID_AKMP 20
-#define WLAN_REASON_UNSUPP_RSN_VERSION 21
-#define WLAN_REASON_INVALID_RSN_IE_CAP 22
-#define WLAN_REASON_IEEE8021X_FAILED 23
-#define WLAN_REASON_CIPHER_SUITE_REJECTED 24
+enum ieee80211_reasoncode {
+	WLAN_REASON_UNSPECIFIED = 1,
+	WLAN_REASON_PREV_AUTH_NOT_VALID = 2,
+	WLAN_REASON_DEAUTH_LEAVING = 3,
+	WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY = 4,
+	WLAN_REASON_DISASSOC_AP_BUSY = 5,
+	WLAN_REASON_CLASS2_FRAME_FROM_NONAUTH_STA = 6,
+	WLAN_REASON_CLASS3_FRAME_FROM_NONASSOC_STA = 7,
+	WLAN_REASON_DISASSOC_STA_HAS_LEFT = 8,
+	WLAN_REASON_STA_REQ_ASSOC_WITHOUT_AUTH = 9,
+	/* 802.11h */
+	WLAN_REASON_DISASSOC_BAD_POWER = 10,
+	WLAN_REASON_DISASSOC_BAD_SUPP_CHAN = 11,
+	/* 802.11i */
+	WLAN_REASON_INVALID_IE = 13,
+	WLAN_REASON_MIC_FAILURE = 14,
+	WLAN_REASON_4WAY_HANDSHAKE_TIMEOUT = 15,
+	WLAN_REASON_GROUP_KEY_HANDSHAKE_TIMEOUT = 16,
+	WLAN_REASON_IE_DIFFERENT = 17,
+	WLAN_REASON_INVALID_GROUP_CIPHER = 18,
+	WLAN_REASON_INVALID_PAIRWISE_CIPHER = 19,
+	WLAN_REASON_INVALID_AKMP = 20,
+	WLAN_REASON_UNSUPP_RSN_VERSION = 21,
+	WLAN_REASON_INVALID_RSN_IE_CAP = 22,
+	WLAN_REASON_IEEE8021X_FAILED = 23,
+	WLAN_REASON_CIPHER_SUITE_REJECTED = 24,
+};
 
 
 #define IEEE80211_STATMASK_SIGNAL (1<<0)
@@ -513,32 +517,34 @@
 #define BEACON_PROBE_SSID_ID_POSITION 12
 
 /* Management Frame Information Element Types */
-#define MFIE_TYPE_SSID              0
-#define MFIE_TYPE_RATES             1
-#define MFIE_TYPE_FH_SET            2
-#define MFIE_TYPE_DS_SET            3
-#define MFIE_TYPE_CF_SET            4
-#define MFIE_TYPE_TIM               5
-#define MFIE_TYPE_IBSS_SET          6
-#define MFIE_TYPE_COUNTRY           7
-#define MFIE_TYPE_HOP_PARAMS        8
-#define MFIE_TYPE_HOP_TABLE         9
-#define MFIE_TYPE_REQUEST           10
-#define MFIE_TYPE_CHALLENGE         16
-#define MFIE_TYPE_POWER_CONSTRAINT  32
-#define MFIE_TYPE_POWER_CAPABILITY  33
-#define MFIE_TYPE_TPC_REQUEST       34
-#define MFIE_TYPE_TPC_REPORT        35
-#define MFIE_TYPE_SUPP_CHANNELS     36
-#define MFIE_TYPE_CSA               37
-#define MFIE_TYPE_MEASURE_REQUEST   38
-#define MFIE_TYPE_MEASURE_REPORT    39
-#define MFIE_TYPE_QUIET             40
-#define MFIE_TYPE_IBSS_DFS          41
-#define MFIE_TYPE_ERP_INFO          42
-#define MFIE_TYPE_RSN	            48
-#define MFIE_TYPE_RATES_EX          50
-#define MFIE_TYPE_GENERIC           221
+enum ieee80211_mfie {
+	MFIE_TYPE_SSID = 0,
+	MFIE_TYPE_RATES = 1,
+	MFIE_TYPE_FH_SET = 2,
+	MFIE_TYPE_DS_SET = 3,
+	MFIE_TYPE_CF_SET =  4,
+	MFIE_TYPE_TIM = 5,
+	MFIE_TYPE_IBSS_SET = 6,
+	MFIE_TYPE_COUNTRY = 7,
+	MFIE_TYPE_HOP_PARAMS = 8,
+	MFIE_TYPE_HOP_TABLE = 9,
+	MFIE_TYPE_REQUEST = 10,
+	MFIE_TYPE_CHALLENGE = 16,
+	MFIE_TYPE_POWER_CONSTRAINT = 32,
+	MFIE_TYPE_POWER_CAPABILITY = 33,
+	MFIE_TYPE_TPC_REQUEST = 34,
+	MFIE_TYPE_TPC_REPORT = 35,
+	MFIE_TYPE_SUPP_CHANNELS = 36,
+	MFIE_TYPE_CSA = 37,
+	MFIE_TYPE_MEASURE_REQUEST = 38,
+	MFIE_TYPE_MEASURE_REPORT = 39,
+	MFIE_TYPE_QUIET = 40,
+	MFIE_TYPE_IBSS_DFS = 41,
+	MFIE_TYPE_ERP_INFO = 42,
+	MFIE_TYPE_RSN = 48,
+	MFIE_TYPE_RATES_EX = 50,
+	MFIE_TYPE_GENERIC = 221,
+};
 
 struct ieee80211_info_element_hdr {
 	u8 id;

^ permalink raw reply

* Re: RFC: NAPI packet weighting patch
From: David S. Miller @ 2005-06-03 20:31 UTC (permalink / raw)
  To: hadi
  Cc: mitch.a.williams, john.ronciak, jdmason, shemminger, netdev,
	Robert.Olsson, ganesh.venkatesan, jesse.brandeburg
In-Reply-To: <1117828771.6071.77.camel@localhost.localdomain>

From: jamal <hadi@cyberus.ca>
Date: Fri, 03 Jun 2005 15:59:31 -0400

> But one that you could validate by putting proper hooks. As an example,
> try to restore a descriptor every time you pick one - for an example of
> this look at the sb1250 driver.

Yes, this in my mind is exactly the problem.  TG3 does this
properly, as do several other drivers.

You should never defer RX buffer replenishment, you should
always do it as you grab packets off of the ring.  You will
starve the chip otherwise.

^ permalink raw reply

* Re: RFC: NAPI packet weighting patch
From: Michael Chan @ 2005-06-03 20:35 UTC (permalink / raw)
  To: Lennert Buytenhek
  Cc: David S. Miller, mitch.a.williams, hadi, john.ronciak, jdmason,
	shemminger, netdev, Robert.Olsson, ganesh.venkatesan,
	jesse.brandeburg
In-Reply-To: <20050603205944.GC20623@xi.wantstofly.org>

On Fri, 2005-06-03 at 22:59 +0200, Lennert Buytenhek wrote:
> On Fri, Jun 03, 2005 at 12:49:29PM -0700, Michael Chan wrote:
> 
> > Yes, in tg3, rx buffers are replenished and put back into the ring
> > as completed packets are taken off the ring. But we don't tell the
> > chip about these new buffers until we get to the end of the loop,
> > potentially after a full quota of packets.
> 
> Which makes a lot more sense, since you'd rather do one MMIO write
> at the end of the loop than one per iteration, especially if your
> MMIO read (flush) latency is high.  (Any subsequent MMIO read will
> have to flush out all pending writes, which'll be slow if there's
> a lot of writes still in the queue.)
> 
I agree on the merit of issuing only one IO at the end. What I'm saying
is that doing so will make it similar to e1000 where all the buffers are
replenished at the end. Isn't that so or am I missing something?

By the way, in tg3 there is a buffer replenishment threshold programmed
to the chip and is currently set at rx_pending / 8 (200/8 = 25). This
means that the chip will replenish 25 rx buffers at a time.

^ permalink raw reply

* Re: RFC: NAPI packet weighting patch
From: Lennert Buytenhek @ 2005-06-03 20:59 UTC (permalink / raw)
  To: Michael Chan
  Cc: David S. Miller, mitch.a.williams, hadi, john.ronciak, jdmason,
	shemminger, netdev, Robert.Olsson, ganesh.venkatesan,
	jesse.brandeburg
In-Reply-To: <1117828169.4430.29.camel@rh4>

On Fri, Jun 03, 2005 at 12:49:29PM -0700, Michael Chan wrote:

> > E1000 processes the full QUOTA of RX packets,
> > _THEN_ replenishes with new RX buffers.  No wonder
> > the chip runs out of RX descriptors.
> > 
> > You should replenish _AS_ you grab RX packets
> > off the receive queue, just as tg3 does.
> 
> Yes, in tg3, rx buffers are replenished and put back into the ring
> as completed packets are taken off the ring. But we don't tell the
> chip about these new buffers until we get to the end of the loop,
> potentially after a full quota of packets.

Which makes a lot more sense, since you'd rather do one MMIO write
at the end of the loop than one per iteration, especially if your
MMIO read (flush) latency is high.  (Any subsequent MMIO read will
have to flush out all pending writes, which'll be slow if there's
a lot of writes still in the queue.)


--L

^ permalink raw reply

* Re: RFC: NAPI packet weighting patch
From: Edgar E Iglesias @ 2005-06-03 21:07 UTC (permalink / raw)
  To: Lennert Buytenhek
  Cc: Michael Chan, David S. Miller, mitch.a.williams, hadi,
	john.ronciak, jdmason, shemminger, netdev, Robert.Olsson,
	ganesh.venkatesan, jesse.brandeburg
In-Reply-To: <20050603205944.GC20623@xi.wantstofly.org>

On Fri, Jun 03, 2005 at 10:59:45PM +0200, Lennert Buytenhek wrote:
> On Fri, Jun 03, 2005 at 12:49:29PM -0700, Michael Chan wrote:
> 
> > > E1000 processes the full QUOTA of RX packets,
> > > _THEN_ replenishes with new RX buffers.  No wonder
> > > the chip runs out of RX descriptors.
> > > 
> > > You should replenish _AS_ you grab RX packets
> > > off the receive queue, just as tg3 does.
> > 
> > Yes, in tg3, rx buffers are replenished and put back into the ring
> > as completed packets are taken off the ring. But we don't tell the
> > chip about these new buffers until we get to the end of the loop,
> > potentially after a full quota of packets.
> 
> Which makes a lot more sense, since you'd rather do one MMIO write
> at the end of the loop than one per iteration, especially if your
> MMIO read (flush) latency is high.  (Any subsequent MMIO read will
> have to flush out all pending writes, which'll be slow if there's
> a lot of writes still in the queue.)
> 
> 
> --L

Maybe it would be better to put a fixed weight at this level, return
the descriptors to the HW after every X packets. That way you
can keep the NAPI weight at 64 (or what ever) and still give back 
descriptors to HW more often.

Best regards
-- 
        Programmer
        Edgar E Iglesias <edgar@axis.com> 46.46.272.1946

^ permalink raw reply

* Re: RFC: NAPI packet weighting patch
From: Jon Mason @ 2005-06-03 21:12 UTC (permalink / raw)
  To: David S. Miller
  Cc: hadi, mitch.a.williams, john.ronciak, shemminger, netdev,
	Robert.Olsson, ganesh.venkatesan, jesse.brandeburg
In-Reply-To: <20050603.133133.38710501.davem@davemloft.net>

On Friday 03 June 2005 03:31 pm, David S. Miller wrote:
> From: jamal <hadi@cyberus.ca>
> Date: Fri, 03 Jun 2005 15:59:31 -0400
>
> > But one that you could validate by putting proper hooks. As an example,
> > try to restore a descriptor every time you pick one - for an example of
> > this look at the sb1250 driver.
>
> Yes, this in my mind is exactly the problem.  TG3 does this
> properly, as do several other drivers.
>
> You should never defer RX buffer replenishment, you should
> always do it as you grab packets off of the ring.  You will
> starve the chip otherwise.

e1000 isn't the only driver to do things this way.  r8169, via-velocity, dl2k, 
and skge (and I'm sure many more).  Might be nice to perform a driver audit 
to see what drivers do this.
  

^ permalink raw reply

* [PATCHSET] PKT_SCHED related fixes and a meta ematch completion
From: Thomas Graf @ 2005-06-03 21:12 UTC (permalink / raw)
  To: davem; +Cc: netdev

Dave,

The following patchset fixes some serious bugs that prevent
the basic classifier and the meta ematch from working properly.
Patch 2 adds a few new meta collectors for socket attribtues which
I'd like to have in 2.6.12 as well. If you think this is too
intrusive (it isn't ;->) I'll resend patch 4 with offsets fixed.

Thanks.

^ permalink raw reply

* [PATCH 1/4] [PKT_SCHED] Fix typo in NET_EMATCH_STACK help text
From: Thomas Graf @ 2005-06-03 21:12 UTC (permalink / raw)
  To: davem; +Cc: netdev
In-Reply-To: <20050603211241.593114000@axs>

[-- Attachment #1: fix_ematch_kconfig_typo --]
[-- Type: text/plain, Size: 640 bytes --]

Spotted by Geert Uytterhoeven <geert@linux-m68k.org>.

Signed-off-by: Thomas Graf <tgraf@suug.ch>

Index: ematch/net/sched/Kconfig
===================================================================
--- ematch.orig/net/sched/Kconfig
+++ ematch/net/sched/Kconfig
@@ -405,7 +405,7 @@ config NET_EMATCH_STACK
 	---help---
 	  Size of the local stack variable used while evaluating the tree of
 	  ematches. Limits the depth of the tree, i.e. the number of
-	  encapsulated precedences. Every level requires 4 bytes of addtional
+	  encapsulated precedences. Every level requires 4 bytes of additional
 	  stack space.
 
 config NET_EMATCH_CMP

^ permalink raw reply

* [PATCH 2/4] [PKT_SCHED] Allow socket attributes to be matched on via meta ematch
From: Thomas Graf @ 2005-06-03 21:12 UTC (permalink / raw)
  To: davem; +Cc: netdev
In-Reply-To: <20050603211241.593114000@axs>

[-- Attachment #1: ematch_meta_sk --]
[-- Type: text/plain, Size: 10975 bytes --]

Adds meta collectors for all socket attributes that make sense
to be filtered upon. Some of them are only useful for debugging
but having them doesn't hurt.

Signed-off-by: Thomas Graf <tgraf@suug.ch>

Index: ematch/net/sched/em_meta.c
===================================================================
--- ematch.orig/net/sched/em_meta.c
+++ ematch/net/sched/em_meta.c
@@ -32,7 +32,7 @@
  * 	      +-----------+                           +-----------+
  * 	            |                                       |
  * 	            ---> meta_ops[INT][INDEV](...)          |
- *                            |                            |
+ *	                      |                             |
  * 	            -----------                             |
  * 	            V                                       V
  * 	      +-----------+                           +-----------+
@@ -70,6 +70,7 @@
 #include <net/dst.h>
 #include <net/route.h>
 #include <net/pkt_cls.h>
+#include <net/sock.h>
 
 struct meta_obj
 {
@@ -284,6 +285,214 @@ META_COLLECTOR(int_rtiif)
 }
 
 /**************************************************************************
+ * Socket Attributes
+ **************************************************************************/
+
+#define SKIP_NONLOCAL(skb)			\
+	if (unlikely(skb->sk == NULL)) {	\
+		*err = -1;			\
+		return;				\
+	}
+
+META_COLLECTOR(int_sk_family)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_family;
+}
+
+META_COLLECTOR(int_sk_state)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_state;
+}
+
+META_COLLECTOR(int_sk_reuse)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_reuse;
+}
+
+META_COLLECTOR(int_sk_bound_if)
+{
+	SKIP_NONLOCAL(skb);
+	/* No error if bound_dev_if is 0, legal userspace check */
+	dst->value = skb->sk->sk_bound_dev_if;
+}
+
+META_COLLECTOR(var_sk_bound_if)
+{
+	SKIP_NONLOCAL(skb);
+
+	 if (skb->sk->sk_bound_dev_if == 0) {
+		dst->value = (unsigned long) "any";
+		dst->len = 3;
+	 } else  {
+		struct net_device *dev;
+		
+		dev = dev_get_by_index(skb->sk->sk_bound_dev_if);
+		*err = var_dev(dev, dst);
+		if (dev)
+			dev_put(dev);
+	 }
+}
+
+META_COLLECTOR(int_sk_refcnt)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = atomic_read(&skb->sk->sk_refcnt);
+}
+
+META_COLLECTOR(int_sk_rcvbuf)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_rcvbuf;
+}
+
+META_COLLECTOR(int_sk_shutdown)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_shutdown;
+}
+
+META_COLLECTOR(int_sk_proto)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_protocol;
+}
+
+META_COLLECTOR(int_sk_type)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_type;
+}
+
+META_COLLECTOR(int_sk_rmem_alloc)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = atomic_read(&skb->sk->sk_rmem_alloc);
+}
+
+META_COLLECTOR(int_sk_wmem_alloc)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = atomic_read(&skb->sk->sk_wmem_alloc);
+}
+
+META_COLLECTOR(int_sk_omem_alloc)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = atomic_read(&skb->sk->sk_omem_alloc);
+}
+
+META_COLLECTOR(int_sk_rcv_qlen)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_receive_queue.qlen;
+}
+
+META_COLLECTOR(int_sk_snd_qlen)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_write_queue.qlen;
+}
+
+META_COLLECTOR(int_sk_wmem_queued)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_wmem_queued;
+}
+
+META_COLLECTOR(int_sk_fwd_alloc)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_forward_alloc;
+}
+
+META_COLLECTOR(int_sk_sndbuf)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_sndbuf;
+}
+
+META_COLLECTOR(int_sk_alloc)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_allocation;
+}
+
+META_COLLECTOR(int_sk_route_caps)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_route_caps;
+}
+
+META_COLLECTOR(int_sk_hashent)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_hashent;
+}
+
+META_COLLECTOR(int_sk_lingertime)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_lingertime / HZ;
+}
+
+META_COLLECTOR(int_sk_err_qlen)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_error_queue.qlen;
+}
+
+META_COLLECTOR(int_sk_ack_bl)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_ack_backlog;
+}
+
+META_COLLECTOR(int_sk_max_ack_bl)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_max_ack_backlog;
+}
+
+META_COLLECTOR(int_sk_prio)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_priority;
+}
+
+META_COLLECTOR(int_sk_rcvlowat)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_rcvlowat;
+}
+
+META_COLLECTOR(int_sk_rcvtimeo)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_rcvtimeo / HZ;
+}
+
+META_COLLECTOR(int_sk_sndtimeo)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_sndtimeo / HZ;
+}
+
+META_COLLECTOR(int_sk_sendmsg_off)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_sndmsg_off;
+}
+
+META_COLLECTOR(int_sk_write_pend)
+{
+	SKIP_NONLOCAL(skb);
+	dst->value = skb->sk->sk_write_pending;
+}
+
+/**************************************************************************
  * Meta value collectors assignment table
  **************************************************************************/
 
@@ -293,41 +502,75 @@ struct meta_ops
 			       struct meta_value *, struct meta_obj *, int *);
 };
 
+#define META_ID(name) TCF_META_ID_##name
+#define META_FUNC(name) { .get = meta_##name }
+
 /* Meta value operations table listing all meta value collectors and
  * assigns them to a type and meta id. */
 static struct meta_ops __meta_ops[TCF_META_TYPE_MAX+1][TCF_META_ID_MAX+1] = {
 	[TCF_META_TYPE_VAR] = {
-		[TCF_META_ID_DEV]	= { .get = meta_var_dev },
-		[TCF_META_ID_INDEV]	= { .get = meta_var_indev },
-		[TCF_META_ID_REALDEV]	= { .get = meta_var_realdev }
+		[META_ID(DEV)]			= META_FUNC(var_dev),
+		[META_ID(INDEV)]		= META_FUNC(var_indev),
+		[META_ID(REALDEV)]		= META_FUNC(var_realdev),
+		[META_ID(SK_BOUND_IF)] 		= META_FUNC(var_sk_bound_if),
 	},
 	[TCF_META_TYPE_INT] = {
-		[TCF_META_ID_RANDOM]	= { .get = meta_int_random },
-		[TCF_META_ID_LOADAVG_0]	= { .get = meta_int_loadavg_0 },
-		[TCF_META_ID_LOADAVG_1]	= { .get = meta_int_loadavg_1 },
-		[TCF_META_ID_LOADAVG_2]	= { .get = meta_int_loadavg_2 },
-		[TCF_META_ID_DEV]	= { .get = meta_int_dev },
-		[TCF_META_ID_INDEV]	= { .get = meta_int_indev },
-		[TCF_META_ID_REALDEV]	= { .get = meta_int_realdev },
-		[TCF_META_ID_PRIORITY]	= { .get = meta_int_priority },
-		[TCF_META_ID_PROTOCOL]	= { .get = meta_int_protocol },
-		[TCF_META_ID_SECURITY]	= { .get = meta_int_security },
-		[TCF_META_ID_PKTTYPE]	= { .get = meta_int_pkttype },
-		[TCF_META_ID_PKTLEN]	= { .get = meta_int_pktlen },
-		[TCF_META_ID_DATALEN]	= { .get = meta_int_datalen },
-		[TCF_META_ID_MACLEN]	= { .get = meta_int_maclen },
+		[META_ID(RANDOM)]		= META_FUNC(int_random),
+		[META_ID(LOADAVG_0)]		= META_FUNC(int_loadavg_0),
+		[META_ID(LOADAVG_1)]		= META_FUNC(int_loadavg_1),
+		[META_ID(LOADAVG_2)]		= META_FUNC(int_loadavg_2),
+		[META_ID(DEV)]			= META_FUNC(int_dev),
+		[META_ID(INDEV)]		= META_FUNC(int_indev),
+		[META_ID(REALDEV)]		= META_FUNC(int_realdev),
+		[META_ID(PRIORITY)]		= META_FUNC(int_priority),
+		[META_ID(PROTOCOL)]		= META_FUNC(int_protocol),
+		[META_ID(SECURITY)]		= META_FUNC(int_security),
+		[META_ID(PKTTYPE)]		= META_FUNC(int_pkttype),
+		[META_ID(PKTLEN)]		= META_FUNC(int_pktlen),
+		[META_ID(DATALEN)]		= META_FUNC(int_datalen),
+		[META_ID(MACLEN)]		= META_FUNC(int_maclen),
 #ifdef CONFIG_NETFILTER
-		[TCF_META_ID_NFMARK]	= { .get = meta_int_nfmark },
+		[META_ID(NFMARK)]		= META_FUNC(int_nfmark),
 #endif
-		[TCF_META_ID_TCINDEX]	= { .get = meta_int_tcindex },
+		[META_ID(TCINDEX)]		= META_FUNC(int_tcindex),
 #ifdef CONFIG_NET_CLS_ACT
-		[TCF_META_ID_TCVERDICT]	= { .get = meta_int_tcverd },
-		[TCF_META_ID_TCCLASSID]	= { .get = meta_int_tcclassid },
+		[META_ID(TCVERDICT)]		= META_FUNC(int_tcverd),
+		[META_ID(TCCLASSID)]		= META_FUNC(int_tcclassid),
 #endif
 #ifdef CONFIG_NET_CLS_ROUTE
-		[TCF_META_ID_RTCLASSID]	= { .get = meta_int_rtclassid },
+		[META_ID(RTCLASSID)]		= META_FUNC(int_rtclassid),
 #endif
-		[TCF_META_ID_RTIIF]	= { .get = meta_int_rtiif }
+		[META_ID(RTIIF)]		= META_FUNC(int_rtiif),
+		[META_ID(SK_FAMILY)]		= META_FUNC(int_sk_family),
+		[META_ID(SK_STATE)]		= META_FUNC(int_sk_state),
+		[META_ID(SK_REUSE)]		= META_FUNC(int_sk_reuse),
+		[META_ID(SK_BOUND_IF)]		= META_FUNC(int_sk_bound_if),
+		[META_ID(SK_REFCNT)]		= META_FUNC(int_sk_refcnt),
+		[META_ID(SK_RCVBUF)]		= META_FUNC(int_sk_rcvbuf),
+		[META_ID(SK_SNDBUF)]		= META_FUNC(int_sk_sndbuf),
+		[META_ID(SK_SHUTDOWN)]		= META_FUNC(int_sk_shutdown),
+		[META_ID(SK_PROTO)]		= META_FUNC(int_sk_proto),
+		[META_ID(SK_TYPE)]		= META_FUNC(int_sk_type),
+		[META_ID(SK_RMEM_ALLOC)]	= META_FUNC(int_sk_rmem_alloc),
+		[META_ID(SK_WMEM_ALLOC)]	= META_FUNC(int_sk_wmem_alloc),
+		[META_ID(SK_OMEM_ALLOC)]	= META_FUNC(int_sk_omem_alloc),
+		[META_ID(SK_WMEM_QUEUED)]	= META_FUNC(int_sk_wmem_queued),
+		[META_ID(SK_RCV_QLEN)]		= META_FUNC(int_sk_rcv_qlen),
+		[META_ID(SK_SND_QLEN)]		= META_FUNC(int_sk_snd_qlen),
+		[META_ID(SK_ERR_QLEN)]		= META_FUNC(int_sk_err_qlen),
+		[META_ID(SK_FORWARD_ALLOCS)]	= META_FUNC(int_sk_fwd_alloc),
+		[META_ID(SK_ALLOCS)]		= META_FUNC(int_sk_alloc),
+		[META_ID(SK_ROUTE_CAPS)]	= META_FUNC(int_sk_route_caps),
+		[META_ID(SK_HASHENT)]		= META_FUNC(int_sk_hashent),
+		[META_ID(SK_LINGERTIME)]	= META_FUNC(int_sk_lingertime),
+		[META_ID(SK_ACK_BACKLOG)]	= META_FUNC(int_sk_ack_bl),
+		[META_ID(SK_MAX_ACK_BACKLOG)]	= META_FUNC(int_sk_max_ack_bl),
+		[META_ID(SK_PRIO)]		= META_FUNC(int_sk_prio),
+		[META_ID(SK_RCVLOWAT)]		= META_FUNC(int_sk_rcvlowat),
+		[META_ID(SK_RCVTIMEO)]		= META_FUNC(int_sk_rcvtimeo),
+		[META_ID(SK_SNDTIMEO)]		= META_FUNC(int_sk_sndtimeo),
+		[META_ID(SK_SENDMSG_OFF)]	= META_FUNC(int_sk_sendmsg_off),
+		[META_ID(SK_WRITE_PENDING)]	= META_FUNC(int_sk_write_pend),
 	}
 };
 
Index: ematch/include/linux/tc_ematch/tc_em_meta.h
===================================================================
--- ematch.orig/include/linux/tc_ematch/tc_em_meta.h
+++ ematch/include/linux/tc_ematch/tc_em_meta.h
@@ -56,6 +56,36 @@ enum
 	TCF_META_ID_TCCLASSID,
 	TCF_META_ID_RTCLASSID,
 	TCF_META_ID_RTIIF,
+	TCF_META_ID_SK_FAMILY,
+	TCF_META_ID_SK_STATE,
+	TCF_META_ID_SK_REUSE,
+	TCF_META_ID_SK_BOUND_IF,
+	TCF_META_ID_SK_REFCNT,
+	TCF_META_ID_SK_SHUTDOWN,
+	TCF_META_ID_SK_PROTO,
+	TCF_META_ID_SK_TYPE,
+	TCF_META_ID_SK_RCVBUF,
+	TCF_META_ID_SK_RMEM_ALLOC,
+	TCF_META_ID_SK_WMEM_ALLOC,
+	TCF_META_ID_SK_OMEM_ALLOC,
+	TCF_META_ID_SK_WMEM_QUEUED,
+	TCF_META_ID_SK_RCV_QLEN,
+	TCF_META_ID_SK_SND_QLEN,
+ 	TCF_META_ID_SK_ERR_QLEN,
+	TCF_META_ID_SK_FORWARD_ALLOCS,
+	TCF_META_ID_SK_SNDBUF,
+ 	TCF_META_ID_SK_ALLOCS,
+ 	TCF_META_ID_SK_ROUTE_CAPS,
+ 	TCF_META_ID_SK_HASHENT,
+ 	TCF_META_ID_SK_LINGERTIME,
+ 	TCF_META_ID_SK_ACK_BACKLOG,
+ 	TCF_META_ID_SK_MAX_ACK_BACKLOG,
+ 	TCF_META_ID_SK_PRIO,
+ 	TCF_META_ID_SK_RCVLOWAT,
+ 	TCF_META_ID_SK_RCVTIMEO,
+ 	TCF_META_ID_SK_SNDTIMEO,
+ 	TCF_META_ID_SK_SENDMSG_OFF,
+ 	TCF_META_ID_SK_WRITE_PENDING,
 	__TCF_META_ID_MAX
 };
 #define TCF_META_ID_MAX (__TCF_META_ID_MAX - 1)

^ permalink raw reply

* [PATCH 3/4] [PKT_SCHED] Dump classification result for basic classifier
From: Thomas Graf @ 2005-06-03 21:12 UTC (permalink / raw)
  To: davem; +Cc: netdev
In-Reply-To: <20050603211241.593114000@axs>

[-- Attachment #1: cls_basic_dump_classid --]
[-- Type: text/plain, Size: 578 bytes --]

Signed-off-by: Thomas Graf <tgraf@suug.ch>

Index: ematch/net/sched/cls_basic.c
===================================================================
--- ematch.orig/net/sched/cls_basic.c
+++ ematch/net/sched/cls_basic.c
@@ -261,6 +261,9 @@ static int basic_dump(struct tcf_proto *
 	rta = (struct rtattr *) b;
 	RTA_PUT(skb, TCA_OPTIONS, 0, NULL);
 
+	if (f->res.classid)
+		RTA_PUT_U32(skb, TCA_BASIC_CLASSID, f->res.classid);
+
 	if (tcf_exts_dump(skb, &f->exts, &basic_ext_map) < 0 ||
 	    tcf_em_tree_dump(skb, &f->ematches, TCA_BASIC_EMATCHES) < 0)
 		goto rtattr_failure;

^ permalink raw reply

* [PATCH 4/4] [PKT_SCHED] Fix numeric comparison in meta ematch
From: Thomas Graf @ 2005-06-03 21:12 UTC (permalink / raw)
  To: davem; +Cc: netdev
In-Reply-To: <20050603211241.593114000@axs>

[-- Attachment #1: meta_compare_fix --]
[-- Type: text/plain, Size: 645 bytes --]

This patch is brought to you by the department of applied stupidity.

Signed-off-by: Thomas Graf <tgraf@suug.ch>

Index: ematch/net/sched/em_meta.c
===================================================================
--- ematch.orig/net/sched/em_meta.c
+++ ematch/net/sched/em_meta.c
@@ -639,9 +639,9 @@ static int meta_int_compare(struct meta_
 	/* Let gcc optimize it, the unlikely is not really based on
 	 * some numbers but jump free code for mismatches seems
 	 * more logical. */
-	if (unlikely(a == b))
+	if (unlikely(a->value == b->value))
 		return 0;
-	else if (a < b)
+	else if (a->value < b->value)
 		return -1;
 	else
 		return 1;

^ permalink raw reply

* Re: 2.6.12-rc5-mm2: "bic unavailable using TCP reno" messages
From: Stephen Hemminger @ 2005-06-03 21:37 UTC (permalink / raw)
  To: Adrian Bunk, Baruch Even; +Cc: Andrew Morton, linux-kernel, netdev
In-Reply-To: <20050602203823.GI4992@stusta.de>

Here is what I am working on as better way to make the sysctl selection.
I am not totally happy with the way the default congestion control value is determined
by the load order. But it does seem good that if you load "tcp_xxx" module and it
registers it becomes the default.

Index: 2.6.12-rc5-tcp3/include/net/tcp.h
===================================================================
--- 2.6.12-rc5-tcp3.orig/include/net/tcp.h
+++ 2.6.12-rc5-tcp3/include/net/tcp.h
@@ -1242,6 +1242,8 @@ extern int tcp_register_congestion_contr
 extern void tcp_unregister_congestion_control(struct tcp_congestion_ops *type);
 extern void tcp_init_congestion_control(struct tcp_sock *tp);
 extern void tcp_release_congestion_control(struct tcp_sock *tp);
+extern int tcp_set_congestion_control(const char *name);
+extern void tcp_get_congestion_control(char *name);
 
 extern struct tcp_congestion_ops tcp_reno;
 extern u32 tcp_reno_ssthresh(struct tcp_sock *tp);
Index: 2.6.12-rc5-tcp3/net/ipv4/tcp_cong.c
===================================================================
--- 2.6.12-rc5-tcp3.orig/net/ipv4/tcp_cong.c
+++ 2.6.12-rc5-tcp3/net/ipv4/tcp_cong.c
@@ -13,8 +13,6 @@
 #include <linux/list.h>
 #include <net/tcp.h>
 
-char sysctl_tcp_congestion_control[TCP_CA_NAME_MAX] = "bic";
-
 static DEFINE_SPINLOCK(tcp_cong_list_lock);
 static LIST_HEAD(tcp_cong_list);
 
@@ -23,7 +21,7 @@ static struct tcp_congestion_ops *tcp_ca
 {
 	struct tcp_congestion_ops *e;
 
-	list_for_each_entry_rcu(e, &tcp_cong_list, list) {
+	list_for_each_entry(e, &tcp_cong_list, list) {
 		if (strcmp(e->name, name) == 0) 
 			return e;
 	}
@@ -46,7 +44,7 @@ int tcp_register_congestion_control(stru
 		return -EINVAL;
 	}
 
-	spin_lock_irq(&tcp_cong_list_lock);
+	spin_lock(&tcp_cong_list_lock);
 	if (tcp_ca_find(ca->name)) {
 		printk(KERN_NOTICE "TCP %s already registered\n", ca->name);
 		ret = -EEXIST;
@@ -54,7 +52,7 @@ int tcp_register_congestion_control(stru
 		list_add_rcu(&ca->list, &tcp_cong_list);
 		printk(KERN_INFO "TCP %s registered\n", ca->name);
 	}
-	spin_unlock_irq(&tcp_cong_list_lock);
+	spin_unlock(&tcp_cong_list_lock);
 	
 	return ret;
 }
@@ -69,7 +67,6 @@ EXPORT_SYMBOL_GPL(tcp_register_congestio
 void tcp_unregister_congestion_control(struct tcp_congestion_ops *ca)
 {
 	spin_lock(&tcp_cong_list_lock);
-	BUG_ON(!tcp_ca_find(ca->name));
 	list_del_rcu(&ca->list);
 	spin_unlock(&tcp_cong_list_lock);
 }
@@ -78,34 +75,22 @@ EXPORT_SYMBOL_GPL(tcp_unregister_congest
 /* Assign choice of congestion control. */
 void tcp_init_congestion_control(struct tcp_sock *tp)
 {
-	const char *cong_proto = sysctl_tcp_congestion_control;
 	struct tcp_congestion_ops *ca;
 
 	rcu_read_lock();
-	ca = tcp_ca_find(cong_proto);
-#ifdef CONFIG_KMOD
-	if (!ca) {
-		/* autoload and try again */
-		rcu_read_unlock();
-		request_module("tcp_%s",  cong_proto);
-		rcu_read_lock();
-
-		ca = tcp_ca_find(cong_proto);
-	}
-#endif
-
-	/* If selection doesn't exist or is being removed use Reno */
-	if (!ca || !try_module_get(ca->owner)) {
-		if (net_ratelimit())
-			printk(KERN_WARNING "%s unavailable using TCP reno\n",
-			       cong_proto);
-		ca = &tcp_reno;
-	} 
-	tp->ca_ops = ca;
-	rcu_read_unlock();
+	tp->ca_ops = NULL;
+	list_for_each_entry_rcu(ca, &tcp_cong_list, list) {
+		if (try_module_get(ca->owner)) {
+			tp->ca_ops = ca;
+			break;
+		}
 
-	if (ca->init)
-		ca->init(tp);
+	}
+
+	/* We will always have reno to fallback on. */
+	if (tp->ca_ops->init)
+		tp->ca_ops->init(tp);
+	rcu_read_unlock();
 }
 EXPORT_SYMBOL(tcp_init_congestion_control);
 
@@ -122,6 +107,36 @@ void tcp_release_congestion_control(stru
 	}
 }
 
+/* Used by sysctl to change default congestion control */
+int tcp_set_congestion_control(const char *name)
+{
+	struct tcp_congestion_ops *ca;
+	int ret = -ENOENT;
+
+	spin_lock(&tcp_cong_list_lock);
+	ca = tcp_ca_find(name);
+	if (ca) {
+		list_move(&ca->list, &tcp_cong_list);
+		ret = 0;
+	}
+	spin_unlock(&tcp_cong_list_lock);
+
+	return ret;
+}
+
+/* Get current default congestion control */
+void tcp_get_congestion_control(char *name)
+{
+	struct tcp_congestion_ops *ca;
+	/* We will always have reno... */
+	BUG_ON(list_empty(&tcp_cong_list));
+
+	rcu_read_lock();
+	ca = list_entry(tcp_cong_list.next, struct tcp_congestion_ops, list);
+	strncpy(name, ca->name, TCP_CA_NAME_MAX);
+	rcu_read_lock();
+}
+
 /*
  * TCP Reno congestion control
  * This is special case used for fallback as well.
Index: 2.6.12-rc5-tcp3/net/ipv4/sysctl_net_ipv4.c
===================================================================
--- 2.6.12-rc5-tcp3.orig/net/ipv4/sysctl_net_ipv4.c
+++ 2.6.12-rc5-tcp3/net/ipv4/sysctl_net_ipv4.c
@@ -48,9 +48,6 @@ extern int inet_peer_maxttl;
 extern int inet_peer_gc_mintime;
 extern int inet_peer_gc_maxtime;
 
-/* From tcp_input.c */
-extern char sysctl_tcp_congestion_control[TCP_CA_NAME_MAX];
-
 #ifdef CONFIG_SYSCTL
 static int tcp_retr1_max = 255; 
 static int ip_local_port_range_min[] = { 1, 1 };
@@ -120,6 +117,52 @@ static int ipv4_sysctl_forward_strategy(
 	return 1;
 }
 
+static int proc_tcp_congestion_control(ctl_table *ctl, int write, struct file * filp,
+				       void __user *buffer, size_t *lenp, loff_t *ppos)
+{
+	char val[TCP_CA_NAME_MAX];
+	ctl_table tbl = {
+		.data = val,
+		.maxlen = TCP_CA_NAME_MAX,
+	};
+	int ret;
+
+	tcp_get_congestion_control(val);
+	
+	ret = proc_dostring(&tbl, write, filp, buffer, lenp, ppos);
+	if (write && ret == 0) {
+		ret = tcp_set_congestion_control(val);
+#ifdef CONFIG_KMOD
+		if (ret == -ENOENT) {
+			request_module("tcp_%s", val);
+			ret = tcp_set_congestion_control(val);
+		}
+#endif
+	}
+	return ret;
+}
+
+int sysctl_tcp_congestion_control(ctl_table *table, int __user *name, int nlen,
+				  void __user *oldval, size_t __user *oldlenp,
+				  void __user *newval, size_t newlen, 
+				  void **context)
+{
+	char val[TCP_CA_NAME_MAX];
+	ctl_table tbl = {
+		.data = val,
+		.maxlen = TCP_CA_NAME_MAX,
+	};
+	int ret;
+
+	tcp_get_congestion_control(val);
+	ret = sysctl_string(&tbl, name, nlen, oldval, oldlenp, newval, newlen,
+			    context);
+	if (ret == 0 && newval && newlen)
+		ret = tcp_set_congestion_control(val);
+	return ret;
+}
+
+
 ctl_table ipv4_table[] = {
         {
 		.ctl_name	= NET_IPV4_TCP_TIMESTAMPS,
@@ -624,11 +667,10 @@ ctl_table ipv4_table[] = {
 	{
 		.ctl_name	= NET_TCP_CONG_CONTROL,
 		.procname	= "tcp_congestion_control",
-		.data		= &sysctl_tcp_congestion_control,
-		.maxlen		= TCP_CA_NAME_MAX,
 		.mode		= 0644,
-		.proc_handler	= &proc_dostring,
-		.strategy	= &sysctl_string,
+		.maxlen		= TCP_CA_NAME_MAX,
+		.proc_handler	= &proc_tcp_congestion_control,
+		.strategy	= &sysctl_tcp_congestion_control,
 	},
 
 	{ .ctl_name = 0 }

^ permalink raw reply

* Re: RFC: NAPI packet weighting patch
From: jamal @ 2005-06-03 22:29 UTC (permalink / raw)
  To: Michael Chan
  Cc: Lennert Buytenhek, David S. Miller, mitch.a.williams,
	john.ronciak, jdmason, shemminger, netdev, Robert.Olsson,
	ganesh.venkatesan, jesse.brandeburg
In-Reply-To: <1117830922.4430.44.camel@rh4>

On Fri, 2005-03-06 at 13:35 -0700, Michael Chan wrote:
> On Fri, 2005-06-03 at 22:59 +0200, Lennert Buytenhek wrote:

> > Which makes a lot more sense, since you'd rather do one MMIO write
> > at the end of the loop than one per iteration, especially if your
> > MMIO read (flush) latency is high.  (Any subsequent MMIO read will
> > have to flush out all pending writes, which'll be slow if there's
> > a lot of writes still in the queue.)
> > 
> I agree on the merit of issuing only one IO at the end. What I'm saying
> is that doing so will make it similar to e1000 where all the buffers are
> replenished at the end. Isn't that so or am I missing something?
> 

I think the main issue would be a lot less CPU used in your case
(because of the single MMIO).

> By the way, in tg3 there is a buffer replenishment threshold programmed
> to the chip and is currently set at rx_pending / 8 (200/8 = 25). This
> means that the chip will replenish 25 rx buffers at a time.
> 

So when you write the MMIO, 25 buffers are replenished or is this auto
magically happening in the background? Sounds like a neat feature either
way.

cheers,
jamal

^ permalink raw reply

* Re: 2.6.12-rc5-mm2: "bic unavailable using TCP reno" messages
From: Baruch Even @ 2005-06-03 22:32 UTC (permalink / raw)
  To: Stephen Hemminger; +Cc: Adrian Bunk, Andrew Morton, linux-kernel, netdev
In-Reply-To: <20050603143702.0422101d@dxpl.pdx.osdl.net>

Stephen Hemminger wrote:
> Here is what I am working on as better way to make the sysctl selection.
> I am not totally happy with the way the default congestion control value is determined
> by the load order. But it does seem good that if you load "tcp_xxx" module and it
> registers it becomes the default.

Looks good.

> @@ -120,6 +117,52 @@ static int ipv4_sysctl_forward_strategy(
>  	return 1;
>  }
>  
> +static int proc_tcp_congestion_control(ctl_table *ctl, int write, struct file * filp,
> +				       void __user *buffer, size_t *lenp, loff_t *ppos)
> +{
> +	char val[TCP_CA_NAME_MAX];
> +	ctl_table tbl = {
> +		.data = val,
> +		.maxlen = TCP_CA_NAME_MAX,
> +	};
> +	int ret;
> +
> +	tcp_get_congestion_control(val);

Maybe we should call this tcp_get_current_congestion_control(), the
current name implies (to me) that you give it a name and it returns the
the ca struct. get_current might also just return the current one and
the strcpy can be done here.

Otherwise you probably should document the tcp_get_congestion_control()
to say what size of string it accepts.

Baruch

^ permalink raw reply

* Re: [PATCH][5/5] RapidIO support: net driver over messaging
From: Matt Porter @ 2005-06-03 22:43 UTC (permalink / raw)
  To: Stephen Hemminger
  Cc: akpm, netdev, linux-kernel, torvalds, linuxppc-embedded, jgarzik
In-Reply-To: <20050602150543.7e4326b6@dxpl.pdx.osdl.net>

On Thu, Jun 02, 2005 at 03:05:43PM -0700, Stephen Hemminger wrote:
> How much is this like ethernet? does it still do ARP?

It's nothing like Ethernet, the only relation is that an Ethernet network
driver is easy to implement over top of raw message ports on a switched
fabric network. It gives easy access to RIO messaging from userspace
without inventing a new interface.

ARP works by the driver emulating a broadcast over RIO by sending the
same ARP packet to each node that is participating in the rionet. Nodes
join/leave the rionet by sending RIO-specific doorbell messages to
potential participants on the switched fabric. A table is kept to
flag active participants such that a fast lookup can be made to translate
the dst MAC address to a RIO device struct that is used to actually
send the Ethernet packet encapsulated into a standard RIO message
to the appropriate node(s).

> Can it do promiscious receive?

No.

> > +LIST_HEAD(rionet_peers);
> 
> Does this have to be global?

Nope, should be static. Fixing.

> Not sure about the locking of this stuff, are you
> relying on the RTNL?

Yes, last I looked that was sufficient for all the entry points.
I protect the driver-specific data (tx skb rings, etc.) with
a private lock.
 
> > +
> > +static int rionet_change_mtu(struct net_device *ndev, int new_mtu)
> > +{
> > +	struct rionet_private *rnet = ndev->priv;
> > +
> > +	if (netif_msg_drv(rnet))
> > +		printk(KERN_WARNING
> > +		       "%s: rionet_change_mtu(): not implemented\n", DRV_NAME);
> > +
> > +	return 0;
> > +}
> 
> If you can allow any mtu then don't need this at all.
> Or if you are limited then better return an error for bad values.

Ok, I do have a upper limit of 4082 as the RIO messages have a
max 4096 byte payload. That's the default on open as well. I'll
fix this up.

> > +static void rionet_set_multicast_list(struct net_device *ndev)
> > +{
> > +	struct rionet_private *rnet = ndev->priv;
> > +
> > +	if (netif_msg_drv(rnet))
> > +		printk(KERN_WARNING
> > +		       "%s: rionet_set_multicast_list(): not implemented\n",
> > +		       DRV_NAME);
> > +}
> 
> If you can't handle it then just leave dev->set_multicast_list
> as NULL and all attempts to add or delete will get -EINVAL

Will do. It was a placeholder at one point when I thought I might
emulate multicast in the driver...it's fallen down my priority
list.

> > +
> > +static int rionet_open(struct net_device *ndev)
> > +{
> 
> 
> > +	/* Initialize inbound message ring */
> > +	for (i = 0; i < RIONET_RX_RING_SIZE; i++)
> > +		rnet->rx_skb[i] = NULL;
> > +	rnet->rx_slot = 0;
> > +	rionet_rx_fill(ndev, 0);
> > +
> > +	rnet->tx_slot = 0;
> > +	rnet->tx_cnt = 0;
> > +	rnet->ack_slot = 0;
> > +
> > +	spin_lock_init(&rnet->lock);
> > +
> > +	rnet->msg_enable = RIONET_DEFAULT_MSGLEVEL;
> 
> Better to do all initialization of the per device data
> in the place it is allocated (rio_setup_netdev)

Right, will do.

> > +static int rionet_ioctl(struct net_device *ndev, struct ifreq *rq, int cmd)
> > +{
> > +	return -EOPNOTSUPP;
> > +}
> 
> Unneeded, if dev->do_ioctl is NULL, then all private ioctl's will
> return -EINVAL that is what you want.

Ah, ok. Good, none of the MII stuff applies in this case.
 
> > +static u32 rionet_get_link(struct net_device *ndev)
> > +{
> > +	return netif_carrier_ok(ndev);
> > +}
> 
> Use ethtool_op_get_link

Ok

<snip>

> > +	/* Fill in the driver function table */
> > +	ndev->open = &rionet_open;
> > +	ndev->hard_start_xmit = &rionet_start_xmit;
> > +	ndev->stop = &rionet_close;
> > +	ndev->get_stats = &rionet_stats;
> > +	ndev->change_mtu = &rionet_change_mtu;
> > +	ndev->set_mac_address = &rionet_set_mac_address;
> > +	ndev->set_multicast_list = &rionet_set_multicast_list;
> > +	ndev->do_ioctl = &rionet_ioctl;
> > +	SET_ETHTOOL_OPS(ndev, &rionet_ethtool_ops);
> > +
> > +	ndev->mtu = RIO_MAX_MSG_SIZE - 14;
> > +
> > +	SET_MODULE_OWNER(ndev);
> 
> Can you set any ndev->features to get better performance. 
> 	Can you take >32bit data addresses? then set HIGHDMA
> 	You are doing your on locking, can you use LLTX?
> 	Does the hardware support scatter gather?

Some of these get tricky.  In general, rionet could support
SG and with driver help we can flag IP_CSUM. In practice, the
current generation MPC85xx HW on my development system have
some problems with their message port dma queues. In short,
their implementation is such that the arch-specific code is
forced to do a copy of the skb on both tx and rx. Because of
this, adding SG/IP_CSUM doesn't have any value yet...it'll make
sense to add the addtional features once we get a platform with
better messaging hardware. HIGHDMA may not be suitable on all
platforms. Since rionet sits on top of a hardware abstraction,
it doesn't have full knowledge of the DMA capabilities of the
hardware. We can eventually have some interfaces to the arch
code to learn that info, but it's not there yet.  I have to
look into LLTX, I know what it stands for, but I'm not sure
of the details.  Do you have a good LLTX example reference?

That said, my goal is to enable as many features as possible
when we have hw to take advantage of them.

-Matt

^ permalink raw reply

* Unitialized queue_lock oops?
From: Phil Oester @ 2005-06-03 23:24 UTC (permalink / raw)
  To: netdev

In my ongoing attempts to migrate to anything higher than 2.6.10,
I decided to retest 2.6.11-rc2 but backout the problematic LLTX
patch.  I also enabled spinlock debugging, and hit an odd BUG.

Full oops output below, but the summary is:
	kernel BUG at include/asm/spinlock.h:92!

which is here:
	BUG_ON(lock->magic != SPINLOCK_MAGIC);

And we got there via dev_queue_xmit:
                /* Grab device queue */
                spin_lock(&dev->queue_lock);
-- no complaints yet, so queue_lock must be initialized here
                rc = q->enqueue(skb, q);

                qdisc_run(dev);
-- qdisc_run drops queue_lock briefly - it get mangled while it's dropped?
                spin_unlock(&dev->queue_lock); 
-- now we hit the BUG - queue_lock->magic != SPINLOCK_MAGIC.


I know the proposed LLTX changes were meant to address a race while
the queue_lock was dropped - is the above another illustration of the
race potential?

Phil

kernel BUG at include/asm/spinlock.h:92!
invalid operand: 0000 [#1]
SMP DEBUG_PAGEALLOC
CPU:    1
EIP:    0060:[<c0289dc4>]    Not tainted VLI
EFLAGS: 00010217   (2.6.11-rc2) 
EIP is at _spin_unlock+0x24/0x30
eax: f7ae7ec0   ebx: f6d5ff00   ecx: f6d5ffbc   edx: f7ae7ec0
esi: f7ae3800   edi: c4a45f50   ebp: c0333d64   esp: c0333d64
ds: 007b   es: 007b   ss: 0068
Process swapper (pid: 0, threadinfo=c0333000 task=c198aaf0)
Stack: c0333d88 c023168a c0272eea f7ae3800 f7ae35bc 00000000 f590c89c f590c888 
       c63cc020 c0333da8 c0249873 c02497c0 f590c888 c4a45f50 00000000 00000004 
       00000002 c0333ddc c023b61e 00000000 f7ae3800 c0333dcc c02497c0 80000000 
Call Trace:
 [<c010322a>] show_stack+0x7a/0x90
 [<c01033ad>] show_registers+0x14d/0x1b0
 [<c01035b9>] die+0xf9/0x180
 [<c01039e9>] do_invalid_op+0xa9/0xc0
 [<c0102ebb>] error_code+0x2b/0x30
 [<c023168a>] dev_queue_xmit+0x20a/0x290
 [<c0249873>] ip_finish_output2+0xb3/0x1c0
 [<c023b61e>] nf_hook_slow+0xae/0xe0
 [<c024734e>] ip_finish_output+0x1ee/0x200
 [<c0245d3c>] ip_forward_finish+0x2c/0x50
 [<c023b61e>] nf_hook_slow+0xae/0xe0
 [<c0245c7c>] ip_forward+0x19c/0x230
 [<c0244ad8>] ip_rcv_finish+0x1b8/0x230
 [<c023b61e>] nf_hook_slow+0xae/0xe0
 [<c0244715>] ip_rcv+0x3b5/0x470
 [<c0231bea>] netif_receive_skb+0x13a/0x190
 [<c01f9ca6>] e1000_clean_rx_irq+0x156/0x480
 [<c01f9895>] e1000_clean+0x45/0xf0
 [<c0231df0>] net_rx_action+0x90/0x130
 [<c011a878>] __do_softirq+0xb8/0xd0
 [<c010478d>] do_softirq+0x4d/0x60
 =======================
 [<c0104668>] do_IRQ+0x68/0xa0
 [<c0102d86>] common_interrupt+0x1a/0x20
 [<c010059f>] cpu_idle+0x5f/0x70
 [<00000000>] 0x0
 [<c198bfbc>] 0xc198bfbc
Code: 8d bc 27 00 00 00 00 55 89 c2 89 e5 81 78 04 ad 4e ad de 75 16 0f b6 02 84 c0 7f 05 c6 02 01 
5d c3 0f 0b 5d 00 08 9b 29 c0 eb f1 <0f> 0b 5c 00 08 9b 29 c0 eb e0 89 f6 55 89 e5 f0 81 00 00 00 00 

^ permalink raw reply

* Re: RFC: NAPI packet weighting patch
From: Lennert Buytenhek @ 2005-06-03 23:26 UTC (permalink / raw)
  To: Michael Chan
  Cc: David S. Miller, mitch.a.williams, hadi, john.ronciak, jdmason,
	shemminger, netdev, Robert.Olsson, ganesh.venkatesan,
	jesse.brandeburg
In-Reply-To: <1117830922.4430.44.camel@rh4>

On Fri, Jun 03, 2005 at 01:35:22PM -0700, Michael Chan wrote:

> > > Yes, in tg3, rx buffers are replenished and put back into the ring
> > > as completed packets are taken off the ring. But we don't tell the
> > > chip about these new buffers until we get to the end of the loop,
> > > potentially after a full quota of packets.
> > 
> > Which makes a lot more sense, since you'd rather do one MMIO write
> > at the end of the loop than one per iteration, especially if your
> > MMIO read (flush) latency is high.  (Any subsequent MMIO read will
> > have to flush out all pending writes, which'll be slow if there's
> > a lot of writes still in the queue.)
> 
> I agree on the merit of issuing only one IO at the end. What I'm saying
> is that doing so will make it similar to e1000 where all the buffers are
> replenished at the end. Isn't that so or am I missing something?

I think you're right: for e1000 as well as tg3, the NIC cannot use
the new RX buffers until the CPU breaks out of the poll loop.

I don't understand why reducing the weight apparently makes the e1000
go faster.  Perhaps as Robert said, the RX ring is not big enough and
that's why feeding RX buffers back to the chip more agressively might
help prevent overruns?

I would say that running with a N+64-entry RX ring and a weight of 64
should not show any worse behavior than running with a N+16-entry RX
ring with a weight of 16.  If anything, weight=64 should show _better_
performance than weight=16.  Something else must be going on.


--L

^ permalink raw reply

* Re: RFC: NAPI packet weighting patch
From: Lennert Buytenhek @ 2005-06-03 23:30 UTC (permalink / raw)
  To: Edgar E Iglesias
  Cc: Michael Chan, David S. Miller, mitch.a.williams, hadi,
	john.ronciak, jdmason, shemminger, netdev, Robert.Olsson,
	ganesh.venkatesan, jesse.brandeburg
In-Reply-To: <20050603210701.GA3263@edgar.se.axis.com>

On Fri, Jun 03, 2005 at 11:07:01PM +0200, Edgar E Iglesias wrote:

> > > Yes, in tg3, rx buffers are replenished and put back into the ring
> > > as completed packets are taken off the ring. But we don't tell the
> > > chip about these new buffers until we get to the end of the loop,
> > > potentially after a full quota of packets.
> > 
> > Which makes a lot more sense, since you'd rather do one MMIO write
> > at the end of the loop than one per iteration, especially if your
> > MMIO read (flush) latency is high.  (Any subsequent MMIO read will
> > have to flush out all pending writes, which'll be slow if there's
> > a lot of writes still in the queue.)
> 
> Maybe it would be better to put a fixed weight at this level, return
> the descriptors to the HW after every X packets. That way you
> can keep the NAPI weight at 64 (or what ever) and still give back 
> descriptors to HW more often.

For this scheme to make any difference at all, the RX ring must be
overflowing in the case where we refill the RX ring only once every
64 packets.

If the RX ring _is_ overflowing but the system is otherwise capable of
keeping up with the receive rate (i.e. the packet service times as seen
by the NIC have a high variance), simply make the RX ring bigger.

I don't see what's going on.


--L

^ permalink raw reply

* [RFC] Replace scatterlist with crypto_frag
From: Herbert Xu @ 2005-06-03 23:46 UTC (permalink / raw)
  To: David S. Miller, James Morris, Linux Crypto Mailing List, netdev

Hi:

I was looking at how we can move the IPsec input/output processing out
of the critical section protected by the spin locks on the xfrm_state.
This is useful because it would allow concurrent processing of IPsec
packets for the same SA.  It is also necessary if we're ever going to
add support for asynchronous crypto to IPsec.

The first requirement for this is that we need to stop using data that
is shared across a single SA in the IPsec input/output routines.  The
biggest hurdle there as it stands is sgbuf in esp_data.  This was
introduced to reduce stack usage in esp_input/esp_output as sgbuf
would consume up to 64 bytes of space.

In order to move it back onto the stack (so we can run these things
in parallel), I'm thinking of reducing the size of the scatterlist
structure itself.

The Crypto API doesn't need all the data contained in a scatterlist
structure.  For instance, it has no need for anything to do with DMA.
When we implement hardware crypto (which might do DMA), they're going
to have their own lists of descriptors so they can't use the scatterlist
as is anyway.

The skb_frag_t structure on the other hand is much more suited for
our purpose.  It is only half the size of scatterlist on i386.

So what do you think about introducing a new crypto_frag structure
which looks like this:

struct crypto_frag {
	struct page *page;
	u16 offset;
	u16 length;
};

We could then move sgbuf back into esp_input/esp_output at the cost
of 32 bytes of stack.  Is this stack cost acceptable?

Cheers,
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply

* Re: Unitialized queue_lock oops?
From: Herbert Xu @ 2005-06-03 23:51 UTC (permalink / raw)
  To: Phil Oester; +Cc: netdev
In-Reply-To: <20050603232413.GA29308@linuxace.com>

Phil Oester <kernel@linuxace.com> wrote:
> 
> I know the proposed LLTX changes were meant to address a race while
> the queue_lock was dropped - is the above another illustration of the
> race potential?

I'd say that either you're using a dodgy qdisc, or your hardware is
just stuffed.  That is, if you are using the default qdisc, you should
start looking at replacing pieces of the hardware to find the problem.

Cheers,
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply

* Re: Unitialized queue_lock oops?
From: Phil Oester @ 2005-06-04  0:00 UTC (permalink / raw)
  To: Herbert Xu; +Cc: netdev
In-Reply-To: <E1DeLwo-0005GI-00@gondolin.me.apana.org.au>

On Sat, Jun 04, 2005 at 09:51:30AM +1000, Herbert Xu wrote:
> I'd say that either you're using a dodgy qdisc, or your hardware is
> just stuffed.  That is, if you are using the default qdisc, you should
> start looking at replacing pieces of the hardware to find the problem.

Yes, default qdisc.  Interesting that 2.6.10 is rock solid on the same
hardware...oh well.

Phil

^ permalink raw reply

* Re: [RFC] Replace scatterlist with crypto_frag
From: Jeff Garzik @ 2005-06-04  0:02 UTC (permalink / raw)
  To: Herbert Xu
  Cc: David S. Miller, James Morris, Linux Crypto Mailing List, netdev
In-Reply-To: <20050603234623.GA20088@gondor.apana.org.au>

Herbert Xu wrote:
> The Crypto API doesn't need all the data contained in a scatterlist
> structure.  For instance, it has no need for anything to do with DMA.
> When we implement hardware crypto (which might do DMA), they're going
> to have their own lists of descriptors so they can't use the scatterlist
> as is anyway.


I'm not sure I agree with this.

A standard feature of struct scatterlist is having the DMA mappings 
right next to the kernel virtual address/length info.  Drivers use the 
arch-specific DMA-mapped part of struct scatterlist to fill the 
hardware-specific descriptions with addresses and other info.

Since you -will- have to DMA map buffers before passing them to 
hardware, it seems like struct scatterlist is much more appropriate than 
  crypto_frag when dealing with hardware.

For pure software implementations, I don't see why you can't just ignore 
the extra fields that each arch puts into struct scatterlist.

	Jeff

^ permalink raw reply

* Automated linux kernel testing results
From: Nivedita Singhvi @ 2005-06-04  0:20 UTC (permalink / raw)
  To: netdev

For those who don't read lkml, I thought I'd point to
Martin Bligh's post regarding automated testing being
set up, since some people on this list were interested.

http://marc.theaimsgroup.com/?l=linux-kernel&m=111775021327595&w=2

Networking tests are in plan...

thanks,
Nivedita

--------------------------

OK, I've finally got this to the point where I can publish it.

http://ftp.kernel.org/pub/linux/kernel/people/mbligh/abat/regression_matrix.html


Currently it builds and boots any mainline, -mjb, -mm kernel within
about 15 minutes of release. runs dbench, tbench, kernbench, reaim and fsx.
Currently I'm using a 4x AMD64 box, a 16x NUMA-Q, 4x NUMA-Q, 32x x440
(ia32)
PPC64 Power 5 LPAR, PPC64 Power 4 LPAR, and PPC64 Power 4 bare metal
system.
The config files it uses are linked by the machine names in the column
headers.

Thanks to all the other IBM people who've worked on the ABAT test system
that this stuff relies on - too many to list, but especially Andy, Adam,
and Enrique, who have fixed endless bugs, and put up with my incessant
bitching about it all not working as it should ;-)

Clicking on the failure ones error codes should take you to somewhere
vaguely helpful to diagnose it. Clicking on the job number just below
that takes you to the info I'm publishing right now, which should
include perf results and profiles, etc. I'll add graphs, etc later,
comparing performance across kernels (I have them ... just not automated).

^ permalink raw reply


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox