Support for RADIUS ACLs with drivers that do not use hostapd MLME
authorChris Zimmermann <cbzimmermann@mac.com>
Wed, 12 Mar 2008 09:43:55 +0000 (11:43 +0200)
committerJouni Malinen <j@w1.fi>
Wed, 12 Mar 2008 09:43:55 +0000 (11:43 +0200)
Sam Leffler <sam@errno.com>:
Attached are changes from Chris Zimmerman (cc'd) to allow drivers to handle
radius ACL's.  The patch is against 0.5.10 but I suspect will also apply to
your latest code.  These mods enable radius acl support in freebsd w/ my
vap code.

You may want to do the changes to ieee802_11_auth.c differently as they
currently require all participating drivers to work the same.  You might be
able to check the return value from hostapd_set_radius_acl_auth and use
that to decide whether the alternate code should be run so you can have 1
driver using this stuff while the other does not.

(jm: Added without more dynamic check for now; in addition, none of the
current in-tree driver wrappers actually implement these handlers, so this
is in preparation for future changes)

hostapd/Makefile
hostapd/defconfig
hostapd/driver.h
hostapd/ieee802_11_auth.c

index 343c8db..7f0fb2a 100644 (file)
@@ -454,6 +454,10 @@ ifdef CONFIG_IPV6
 CFLAGS += -DCONFIG_IPV6
 endif
 
+ifdef CONFIG_DRIVER_RADIUS_ACL
+CFLAGS += -DCONFIG_DRIVER_RADIUS_ACL
+endif
+
 ifdef CONFIG_FULL_DYNAMIC_VLAN
 # define CONFIG_FULL_DYNAMIC_VLAN to have hostapd manipulate bridges
 # and vlan interfaces for the vlan feature.
index 623f86a..4cfaee9 100644 (file)
@@ -120,3 +120,7 @@ CONFIG_IPV6=y
 # IEEE 802.11r. This draft is still subject to change, so it should be noted
 # that this version may not comply with the final standard.
 #CONFIG_IEEE80211R=y
+
+# Use the hostapd's IEEE 802.11 authentication (ACL), but without
+# the IEEE 802.11 Management capability (e.g., madwifi or FreeBSD/net80211)
+#CONFIG_DRIVER_RADIUS_ACL=y
index 8502a74..f76d2d4 100644 (file)
@@ -159,6 +159,10 @@ struct wpa_driver_ops {
 
        int (*send_ether)(void *priv, const u8 *dst, const u8 *src, u16 proto,
                          const u8 *data, size_t data_len);
+
+       int (*set_radius_acl_auth)(void *priv, const u8 *mac, int accepted, 
+                                  u32 session_timeout);
+       int (*set_radius_acl_expire)(void *priv, const u8 *mac);
 };
 
 static inline void *
@@ -678,4 +682,23 @@ hostapd_driver_commit(struct hostapd_data *hapd)
        return hapd->driver->commit(hapd->drv_priv);
 }
 
+static inline int
+hostapd_set_radius_acl_auth(struct hostapd_data *hapd, const u8 *mac,
+                           int accepted, u32 session_timeout)
+{
+       if (hapd->driver == NULL || hapd->driver->set_radius_acl_auth == NULL)
+               return 0;
+       return hapd->driver->set_radius_acl_auth(hapd->drv_priv, mac, accepted,
+                                                session_timeout);
+}
+
+static inline int
+hostapd_set_radius_acl_expire(struct hostapd_data *hapd, const u8 *mac)
+{
+       if (hapd->driver == NULL ||
+           hapd->driver->set_radius_acl_expire == NULL)
+               return 0;
+       return hapd->driver->set_radius_acl_expire(hapd->drv_priv, mac);
+}
+
 #endif /* DRIVER_H */
index bbdf9f9..86f71b3 100644 (file)
@@ -22,6 +22,7 @@
 #include "radius/radius.h"
 #include "radius/radius_client.h"
 #include "eloop.h"
+#include "driver.h"
 
 #define RADIUS_ACL_TIMEOUT 30
 
@@ -293,7 +294,9 @@ static void hostapd_acl_expire_cache(struct hostapd_data *hapd, time_t now)
                                prev->next = entry->next;
                        else
                                hapd->acl_cache = entry->next;
-
+#ifdef CONFIG_DRIVER_RADIUS_ACL
+                       hostapd_set_radius_acl_expire(hapd, entry->addr);
+#endif /* CONFIG_DRIVER_RADIUS_ACL */
                        tmp = entry;
                        entry = entry->next;
                        os_free(tmp);
@@ -417,11 +420,16 @@ hostapd_acl_recv_radius(struct radius_msg *msg, struct radius_msg *req,
        cache->next = hapd->acl_cache;
        hapd->acl_cache = cache;
 
+#ifdef CONFIG_DRIVER_RADIUS_ACL
+       hostapd_set_radius_acl_auth(hapd, query->addr, cache->accepted,
+                                   cache->session_timeout);
+#else /* CONFIG_DRIVER_RADIUS_ACL */
        /* Re-send original authentication frame for 802.11 processing */
        wpa_printf(MSG_DEBUG, "Re-sending authentication frame after "
                   "successful RADIUS ACL query");
        ieee802_11_mgmt(hapd, query->auth_msg, query->auth_msg_len,
                        WLAN_FC_STYPE_AUTH, NULL);
+#endif /* CONFIG_DRIVER_RADIUS_ACL */
 
  done:
        if (prev == NULL)