]> git.ipfire.org Git - thirdparty/hostap.git/commitdiff
IEEE 802.11u: Add configuration and advertisement for Interworking
authorJouni Malinen <jouni@qca.qualcomm.com>
Fri, 23 Sep 2011 17:26:17 +0000 (20:26 +0300)
committerJouni Malinen <j@w1.fi>
Sun, 16 Oct 2011 20:55:34 +0000 (23:55 +0300)
hostapd/Makefile
hostapd/config_file.c
hostapd/defconfig
hostapd/hostapd.conf
src/ap/ap_config.h
src/ap/beacon.c
src/ap/ieee802_11.c
src/common/ieee802_11_defs.h

index 9664c028d8de592db5678237ebad001bc9790011..bc468c599e63516ca1943b7fe72127f8eac2a91c 100644 (file)
@@ -744,6 +744,10 @@ CFLAGS += -DCONFIG_P2P_MANAGER
 OBJS += ../src/ap/p2p_hostapd.o
 endif
 
+ifdef CONFIG_INTERWORKING
+CFLAGS += -DCONFIG_INTERWORKING
+endif
+
 ifdef CONFIG_WPA_CLI_EDIT
 OBJS_c += ../src/utils/edit.o
 else
index 6ffa98137c0d25706d13d0a70a6cee818b72e050..a148e399f55d2f28c040cecfb163cf08c957374e 100644 (file)
@@ -2058,6 +2058,38 @@ struct hostapd_config * hostapd_config_read(const char *fname)
                        extern int rsn_testing;
                        rsn_testing = atoi(pos);
 #endif /* CONFIG_RSN_TESTING */
+#ifdef CONFIG_INTERWORKING
+               } else if (os_strcmp(buf, "interworking") == 0) {
+                       bss->interworking = atoi(pos);
+               } else if (os_strcmp(buf, "access_network_type") == 0) {
+                       bss->access_network_type = atoi(pos);
+                       if (bss->access_network_type < 0 ||
+                           bss->access_network_type > 15) {
+                               wpa_printf(MSG_ERROR, "Line %d: invalid "
+                                          "access_network_type", line);
+                               errors++;
+                       }
+               } else if (os_strcmp(buf, "internet") == 0) {
+                       bss->internet = atoi(pos);
+               } else if (os_strcmp(buf, "asra") == 0) {
+                       bss->asra = atoi(pos);
+               } else if (os_strcmp(buf, "esr") == 0) {
+                       bss->esr = atoi(pos);
+               } else if (os_strcmp(buf, "uesa") == 0) {
+                       bss->uesa = atoi(pos);
+               } else if (os_strcmp(buf, "venue_group") == 0) {
+                       bss->venue_group = atoi(pos);
+                       bss->venue_info_set = 1;
+               } else if (os_strcmp(buf, "venue_type") == 0) {
+                       bss->venue_type = atoi(pos);
+                       bss->venue_info_set = 1;
+               } else if (os_strcmp(buf, "hessid") == 0) {
+                       if (hwaddr_aton(pos, bss->hessid)) {
+                               wpa_printf(MSG_ERROR, "Line %d: invalid "
+                                          "hessid", line);
+                               errors++;
+                       }
+#endif /* CONFIG_INTERWORKING */
                } else {
                        wpa_printf(MSG_ERROR, "Line %d: unknown configuration "
                                   "item '%s'", line, buf);
index 97af2d3fc4960e98131a86b8f012a8b80c937794..36f286f0c51719da58449a95968d12cec3fbd059 100644 (file)
@@ -236,3 +236,8 @@ CONFIG_IPV6=y
 # can be configured to include faster routines for exptmod, sqr, and div to
 # speed up DH and RSA calculation considerably
 #CONFIG_INTERNAL_LIBTOMMATH_FAST=y
+
+# Interworking (IEEE 802.11u)
+# This can be used to enable functionality to improve interworking with
+# external networks.
+#CONFIG_INTERWORKING=y
index 5384ee793231aeee270a341330e4b4b5e0ce5173..be0272060aa9108c296c698b2a8b715bd9279e46 100644 (file)
@@ -1023,6 +1023,55 @@ own_ip_addr=127.0.0.1
 # Prohibit use of TDLS Channel Switching in this BSS
 #tdls_prohibit_chan_switch=1
 
+##### IEEE 802.11u-2011 #######################################################
+
+# Enable Interworking service
+#interworking=1
+
+# Access Network Type
+# 0 = Private network
+# 1 = Private network with guest access
+# 2 = Chargeable public network
+# 3 = Free public network
+# 4 = Personal device network
+# 5 = Emergency services only network
+# 14 = Test or experimental
+# 15 = Wildcard
+#access_network_type=0
+
+# Whether the network provides connectivity to the Internet
+# 0 = Unspecified
+# 1 = Network provides connectivity to the Internet
+#internet=1
+
+# Additional Step Required for Access
+# Note: This is only used with open network, i.e., ASRA shall ne set to 0 if
+# RSN is used.
+#asra=0
+
+# Emergency services reachable
+#esr=0
+
+# Unauthenticated emergency service accessible
+#uesa=0
+
+# Venue Info (optional)
+# The available values are defined in IEEE Std 802.11u-2011, 7.3.1.34.
+# Example values (group,type):
+# 0,0 = Unspecified
+# 1,7 = Convention Center
+# 1,13 = Coffee Shop
+# 2,0 = Unspecified Business
+# 7,1  Private Residence
+#venue_group=7
+#venue_type=1
+
+# Homogeneous ESS identifier (optional; dot11HESSID)
+# If set, this shall be identifical to one of the BSSIDs in the homogeneous
+# ESS and this shall be set to the same value across all BSSs in homogeneous
+# ESS.
+#hessid=02:03:04:05:06:07
+
 ##### Multiple BSSID support ##################################################
 #
 # Above configuration is using the default interface (wlan#, or multi-SSID VLAN
index 09eed5abd4e47c5800317c1910384c9925ca51e6..46975f7749c3270d2374b8d848cff651dc045d08 100644 (file)
@@ -334,6 +334,18 @@ struct hostapd_bss_config {
 #define TDLS_PROHIBIT_CHAN_SWITCH BIT(1)
        int tdls;
        int disable_11n;
+
+       /* IEEE 802.11u - Interworking */
+       int interworking;
+       int access_network_type;
+       int internet;
+       int asra;
+       int esr;
+       int uesa;
+       int venue_info_set;
+       u8 venue_group;
+       u8 venue_type;
+       u8 hessid[ETH_ALEN];
 };
 
 
index 7a4b267bbad5481e2ea388177102c3c7ff010a68..4fd403335969bf5f0b52c26544267ee7e2b5e56a 100644 (file)
@@ -197,6 +197,46 @@ static u8 * hostapd_eid_wpa(struct hostapd_data *hapd, u8 *eid, size_t len,
 }
 
 
+static u8 * hostapd_eid_interworking(struct hostapd_data *hapd, u8 *eid)
+{
+       u8 *pos = eid;
+#ifdef CONFIG_INTERWORKING
+       u8 *len;
+
+       if (!hapd->conf->interworking)
+               return eid;
+
+       *pos++ = WLAN_EID_INTERWORKING;
+       len = pos++;
+
+       *pos = hapd->conf->access_network_type;
+       if (hapd->conf->internet)
+               *pos |= INTERWORKING_ANO_INTERNET;
+       if (hapd->conf->asra)
+               *pos |= INTERWORKING_ANO_ASRA;
+       if (hapd->conf->esr)
+               *pos |= INTERWORKING_ANO_ESR;
+       if (hapd->conf->uesa)
+               *pos |= INTERWORKING_ANO_UESA;
+       pos++;
+
+       if (hapd->conf->venue_info_set) {
+               *pos++ = hapd->conf->venue_group;
+               *pos++ = hapd->conf->venue_type;
+       }
+
+       if (!is_zero_ether_addr(hapd->conf->hessid)) {
+               os_memcpy(pos, hapd->conf->hessid, ETH_ALEN);
+               pos += ETH_ALEN;
+       }
+
+       *len = pos - len - 1;
+#endif /* CONFIG_INTERWORKING */
+
+       return pos;
+}
+
+
 void handle_probe_req(struct hostapd_data *hapd,
                      const struct ieee80211_mgmt *mgmt, size_t len)
 {
@@ -356,6 +396,8 @@ void handle_probe_req(struct hostapd_data *hapd,
 
        pos = hostapd_eid_ext_capab(hapd, pos);
 
+       pos = hostapd_eid_interworking(hapd, pos);
+
        /* Wi-Fi Alliance WMM */
        pos = hostapd_eid_wmm(hapd, pos);
 
@@ -486,6 +528,8 @@ void ieee802_11_set_beacon(struct hostapd_data *hapd)
 
        tailpos = hostapd_eid_ext_capab(hapd, tailpos);
 
+       tailpos = hostapd_eid_interworking(hapd, tailpos);
+
        /* Wi-Fi Alliance WMM */
        tailpos = hostapd_eid_wmm(hapd, tailpos);
 
index 7293957a4ada61c236f04cbb66495b5403691d4f..8e43015502e2bda01b0f7eb469c7fad161f14a06 100644 (file)
@@ -166,17 +166,28 @@ u16 hostapd_own_capab_info(struct hostapd_data *hapd, struct sta_info *sta,
 u8 * hostapd_eid_ext_capab(struct hostapd_data *hapd, u8 *eid)
 {
        u8 *pos = eid;
+       u8 len = 0;
 
-       if ((hapd->conf->tdls & (TDLS_PROHIBIT | TDLS_PROHIBIT_CHAN_SWITCH)) ==
-           0)
+       if (hapd->conf->tdls & (TDLS_PROHIBIT | TDLS_PROHIBIT_CHAN_SWITCH))
+               len = 5;
+       if (len < 4 && hapd->conf->interworking)
+               len = 4;
+       if (len == 0)
                return eid;
 
        *pos++ = WLAN_EID_EXT_CAPAB;
-       *pos++ = 5;
-       *pos++ = 0x00;
+       *pos++ = len;
        *pos++ = 0x00;
        *pos++ = 0x00;
        *pos++ = 0x00;
+
+       *pos = 0x00;
+       if (hapd->conf->interworking)
+               *pos |= 0x80; /* Bit 31 - Interworking */
+       pos++;
+
+       if (len < 5)
+               return pos;
        *pos = 0x00;
        if (hapd->conf->tdls & TDLS_PROHIBIT)
                *pos |= 0x40; /* Bit 38 - TDLS Prohibited */
index 1c3d3cf8ee498855ef8fcc446f8fec592854851a..e510245546b57725aa05280e799c06b05be9bf62 100644 (file)
 #define WLAN_EID_OVERLAPPING_BSS_SCAN_PARAMS 74
 #define WLAN_EID_MMIE 76
 #define WLAN_EID_LINK_ID 101
+#define WLAN_EID_INTERWORKING 107
 #define WLAN_EID_ADV_PROTO 108
 #define WLAN_EID_EXT_CAPAB 127
 #define WLAN_EID_VENDOR_SPECIFIC 221
 #define WLAN_TIMEOUT_KEY_LIFETIME 2
 #define WLAN_TIMEOUT_ASSOC_COMEBACK 3
 
+/* Interworking element (IEEE 802.11u) - Access Network Options */
+#define INTERWORKING_ANO_ACCESS_NETWORK_MASK 0x0f
+#define INTERWORKING_ANO_INTERNET 0x10
+#define INTERWORKING_ANO_ASRA 0x20
+#define INTERWORKING_ANO_ESR 0x40
+#define INTERWORKING_ANO_UESA 0x80
+
 /* Advertisement Protocol ID definitions (IEEE Std 802.11u-2011) */
 enum adv_proto_id {
        ACCESS_NETWORK_QUERY_PROTOCOL = 0,