summaryrefslogtreecommitdiff
path: root/usr.sbin/hostapd/handle.c
diff options
context:
space:
mode:
authorReyk Floeter <reyk@cvs.openbsd.org>2005-09-30 16:50:04 +0000
committerReyk Floeter <reyk@cvs.openbsd.org>2005-09-30 16:50:04 +0000
commit6bd954e164539db60d4af401780384d6a7c13b39 (patch)
tree1e585148910e904d12c143e07d2fa50b6ada1b27 /usr.sbin/hostapd/handle.c
parentf90eba61558219c16a257f4788d9167eb3fbd7d6 (diff)
implement a way to match IEEE 802.11 flooding. this will help to detect
known DoS attacks, like de-auth flooding against wireless networks. an example is provided in the manual page. "or could you just got for it?", deraadt@
Diffstat (limited to 'usr.sbin/hostapd/handle.c')
-rw-r--r--usr.sbin/hostapd/handle.c39
1 files changed, 35 insertions, 4 deletions
diff --git a/usr.sbin/hostapd/handle.c b/usr.sbin/hostapd/handle.c
index 5ce37022dc4..3a2a78734b9 100644
--- a/usr.sbin/hostapd/handle.c
+++ b/usr.sbin/hostapd/handle.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: handle.c,v 1.2 2005/07/04 16:48:55 reyk Exp $ */
+/* $OpenBSD: handle.c,v 1.3 2005/09/30 16:50:03 reyk Exp $ */
/*
* Copyright (c) 2005 Reyk Floeter <reyk@vantronix.net>
@@ -107,7 +107,7 @@ hostapd_handle_frame(struct hostapd_config *cfg, struct hostapd_frame *frame,
u_int8_t *wfrom, *wto, *wbssid;
struct timeval t_now;
u_int32_t flags;
- int offset;
+ int offset, min_rate = 0;
if ((offset = hostapd_apme_offset(cfg, buf, len)) < 0)
return (0);
@@ -116,9 +116,11 @@ hostapd_handle_frame(struct hostapd_config *cfg, struct hostapd_frame *frame,
mh = &frame->f_frame;
flags = frame->f_flags;
+ /* Get timestamp */
+ gettimeofday(&t_now, NULL);
+
/* Handle optional limit */
if (frame->f_limit.tv_sec || frame->f_limit.tv_usec) {
- gettimeofday(&t_now, NULL);
if (timercmp(&t_now, &frame->f_then, <))
return (0);
timeradd(&t_now, &frame->f_limit, &frame->f_then);
@@ -193,10 +195,34 @@ hostapd_handle_frame(struct hostapd_config *cfg, struct hostapd_frame *frame,
if ((flags & HOSTAPD_FRAME_F_M) != 0)
return (0);
+ /* Handle optional minimal rate */
+ if (frame->f_rate && frame->f_rate_intval) {
+ frame->f_rate_delay = t_now.tv_sec - frame->f_last.tv_sec;
+ if (frame->f_rate_delay < frame->f_rate_intval) {
+ frame->f_rate_cnt++;
+ if (frame->f_rate_cnt < frame->f_rate)
+ min_rate = 1;
+ } else {
+ min_rate = 1;
+ frame->f_rate_cnt = 0;
+ }
+ }
+
+ /* Update timestamp for the last match of this event */
+ if (frame->f_rate_cnt == 0 || min_rate == 0)
+ bcopy(&t_now, &frame->f_last, sizeof(struct timeval));
+
+ /* Return if the minimal rate is not reached, yet */
+ if (min_rate)
+ return (0);
+
if (hostapd_handle_action(cfg, frame, wfrom, wto, wbssid, buf,
len) != 0)
return (0);
+ /* Reset minimal rate counter after successfully handled the frame */
+ frame->f_rate_cnt = 0;
+
return ((frame->f_flags & HOSTAPD_FRAME_F_RET_M) >>
HOSTAPD_FRAME_F_RET_S);
}
@@ -228,7 +254,12 @@ hostapd_handle_action(struct hostapd_config *cfg, struct hostapd_frame *frame,
case HOSTAPD_ACTION_LOG:
/* Log frame to syslog/stderr */
- hostapd_printf("%s: ", cfg->c_apme_iface);
+ if (frame->f_rate && frame->f_rate_intval) {
+ hostapd_printf("%s: (rate: %ld/%ld sec) ",
+ cfg->c_apme_iface, frame->f_rate_cnt,
+ frame->f_rate_delay + 1);
+ } else
+ hostapd_printf("%s: ", cfg->c_apme_iface);
hostapd_print_ieee80211(cfg->c_apme_dlt, frame->f_action_flags &
HOSTAPD_ACTION_VERBOSE, buf, len);