Browse Source

TDLS: Allow TDLS to be disabled at runtime for testing purposes

Control interface command 'SET tdls_disabled <1/0>' can now be used
to disable/enable TDLS at runtime. This is mainly for testing
purposes.
Jouni Malinen 14 years ago
parent
commit
b8f64582e3
5 changed files with 37 additions and 1 deletions
  1. 3 1
      src/drivers/driver.h
  2. 21 0
      src/rsn_supp/tdls.c
  3. 1 0
      src/rsn_supp/wpa.h
  4. 1 0
      src/rsn_supp/wpa_i.h
  5. 11 0
      wpa_supplicant/ctrl_iface.c

+ 3 - 1
src/drivers/driver.h

@@ -699,7 +699,9 @@ enum tdls_oper {
 	TDLS_SETUP,
 	TDLS_TEARDOWN,
 	TDLS_ENABLE_LINK,
-	TDLS_DISABLE_LINK
+	TDLS_DISABLE_LINK,
+	TDLS_ENABLE,
+	TDLS_DISABLE
 };
 
 /**

+ 21 - 0
src/rsn_supp/tdls.c

@@ -625,6 +625,9 @@ int wpa_tdls_recv_teardown_notify(struct wpa_sm *sm, const u8 *addr,
 	u8 *rbuf, *pos;
 	int ielen;
 
+	if (sm->tdls_disabled)
+		return -1;
+
 	/* Find the node and free from the list */
 	for (peer = sm->tdls; peer; peer = peer->next) {
 		if (os_memcmp(peer->addr, addr, ETH_ALEN) == 0)
@@ -1825,6 +1828,9 @@ int wpa_tdls_start(struct wpa_sm *sm, const u8 *addr)
 	struct wpa_tdls_peer *peer;
 	int tdls_prohibited = sm->tdls_prohibited;
 
+	if (sm->tdls_disabled)
+		return -1;
+
 #ifdef CONFIG_TDLS_TESTING
 	if ((tdls_testing & TDLS_TESTING_IGNORE_AP_PROHIBIT) &&
 	    tdls_prohibited) {
@@ -1869,6 +1875,9 @@ int wpa_tdls_reneg(struct wpa_sm *sm, const u8 *addr)
 {
 	struct wpa_tdls_peer *peer;
 
+	if (sm->tdls_disabled)
+		return -1;
+
 	for (peer = sm->tdls; peer; peer = peer->next) {
 		if (os_memcmp(peer->addr, addr, ETH_ALEN) == 0)
 			break;
@@ -1895,6 +1904,11 @@ static void wpa_supplicant_rx_tdls(void *ctx, const u8 *src_addr,
 	wpa_hexdump(MSG_DEBUG, "TDLS: Received Data frame encapsulation",
 		    buf, len);
 
+	if (sm->tdls_disabled) {
+		wpa_printf(MSG_DEBUG, "TDLS: Discard message - TDLS disabled");
+		return;
+	}
+
 	if (os_memcmp(src_addr, sm->own_addr, ETH_ALEN) == 0) {
 		wpa_printf(MSG_DEBUG, "TDLS: Discard copy of own message");
 		return;
@@ -2051,3 +2065,10 @@ void wpa_tdls_assoc_resp_ies(struct wpa_sm *sm, const u8 *ies, size_t len)
 		sm->tdls_prohibited = 1;
 	}
 }
+
+
+void wpa_tdls_enable(struct wpa_sm *sm, int enabled)
+{
+	wpa_printf(MSG_DEBUG, "TDLS: %s", enabled ? "enabled" : "disabled");
+	sm->tdls_disabled = !enabled;
+}

+ 1 - 0
src/rsn_supp/wpa.h

@@ -346,5 +346,6 @@ int wpa_tdls_recv_teardown_notify(struct wpa_sm *sm, const u8 *addr,
 				  u16 reason_code);
 int wpa_tdls_init(struct wpa_sm *sm);
 void wpa_tdls_deinit(struct wpa_sm *sm);
+void wpa_tdls_enable(struct wpa_sm *sm, int enabled);
 
 #endif /* WPA_H */

+ 1 - 0
src/rsn_supp/wpa_i.h

@@ -97,6 +97,7 @@ struct wpa_sm {
 #ifdef CONFIG_TDLS
 	struct wpa_tdls_peer *tdls;
 	int tdls_prohibited;
+	int tdls_disabled;
 #endif /* CONFIG_TDLS */
 
 #ifdef CONFIG_IEEE80211R

+ 11 - 0
wpa_supplicant/ctrl_iface.c

@@ -114,6 +114,17 @@ static int wpa_supplicant_ctrl_iface_set(struct wpa_supplicant *wpa_s,
 		tdls_testing = strtol(value, NULL, 0);
 		wpa_printf(MSG_DEBUG, "TDLS: tdls_testing=0x%x", tdls_testing);
 #endif /* CONFIG_TDLS_TESTING */
+#ifdef CONFIG_TDLS
+	} else if (os_strcasecmp(cmd, "tdls_disabled") == 0) {
+		int disabled = atoi(value);
+		wpa_printf(MSG_DEBUG, "TDLS: tdls_disabled=%d", disabled);
+		if (disabled) {
+			if (wpa_drv_tdls_oper(wpa_s, TDLS_DISABLE, NULL) < 0)
+				ret = -1;
+		} else if (wpa_drv_tdls_oper(wpa_s, TDLS_ENABLE, NULL) < 0)
+			ret = -1;
+		wpa_tdls_enable(wpa_s->wpa, !disabled);
+#endif /* CONFIG_TDLS */
 	} else {
 		value[-1] = '=';
 		ret = wpa_config_process_global(wpa_s->conf, cmd, -1);