[14/15] mka: consider missing MKPDU parameter sets a failure

Message ID 20180302201103.16264-15-msiedzik@extremenetworks.com
State New
Headers show
Series
  • MKA bugfixes and enhancements
Related show

Commit Message

Michael Siedzik March 2, 2018, 8:11 p.m.
From: Mike Siedzik <msiedzik@extremenetworks.com>

The previous commit introduced parameter set error checking.  This
commit extends upon that by considering missing parameter sets a
failure.

Two checks are added by this commit.  First, verify that live peers
start encoding MKA_SAK_USE within a reasonable amount of time after
going live (10 MKPDUs).  Second, verify that once a live peer starts
encoding MKA_SAK_USE it continues to do so indefinitely.

Signed-off-by: Michael Siedzik <msiedzik@extremenetworks.com>
---
 src/pae/ieee802_1x_kay.c   | 31 ++++++++++++++++++++++++++++++-
 src/pae/ieee802_1x_kay_i.h |  1 +
 2 files changed, 31 insertions(+), 1 deletion(-)

--
2.11.1

Patch

diff --git a/src/pae/ieee802_1x_kay.c b/src/pae/ieee802_1x_kay.c
index 7945cc898..4323b6dc0 100644
--- a/src/pae/ieee802_1x_kay.c
+++ b/src/pae/ieee802_1x_kay.c
@@ -27,6 +27,8 @@ 
 #define DEFAULT_ICV_LEN                16
 #define MAX_ICV_LEN            32  /* 32 bytes, 256 bits */

+#define MAX_MISSING_SAK_USE 10  /* Accept up to 10 inbound MKPDU's w/o SAK-USE before dropping */
+
 #define PENDING_PN_EXHAUSTION 0xC0000000

 #define MKA_ALIGN_LENGTH(len) (((len) + 0x3) & ~0x3)
@@ -562,6 +564,7 @@  ieee802_1x_kay_create_peer(const u8 *mi, u32 mn)
        peer->mn = mn;
        peer->expire = time(NULL) + MKA_LIFE_TIME / 1000;
        peer->sak_used = FALSE;
+       peer->missing_sak_use_count = 0;

        return peer;
 }
@@ -3155,8 +3158,34 @@  static int ieee802_1x_kay_decode_mkpdu(struct ieee802_1x_kay *kay,
                return -1;
        }

+       /* Detect missing parameter sets */
+       peer = ieee802_1x_kay_get_live_peer(participant, participant->current_peer_id.mi);
+       if (peer) {
+               /* MKPDU is from live peer */
+               if (!handled[MKA_SAK_USE]) {
+                       /* Once a live peer starts sending SAK-USE, it should be sent
+                        * every time. */
+                       if (peer->sak_used) {
+                               wpa_printf(MSG_INFO, "KaY: Discarding Rx MKPDU: Live Peer stopped sending SAK-USE");
+                               return -1;
+                       }
+
+                       /* Live peer is probably hung if it hasn't sent SAK-USE
+                        * after a reasonable number of MKPDU's. Drop the MKPDU,
+                        * which will eventually force an timeout. */
+                       if (++peer->missing_sak_use_count > MAX_MISSING_SAK_USE) {
+                               wpa_printf(MSG_INFO, "KaY: Discarding Rx MKPDU: Live Peer not sending SAK-USE");
+                               return -1;
+                       }
+               } else {
+                       peer->missing_sak_use_count = 0;
+               }
+       } else {
+               /* MKPDU is from new or potential peer */
+               peer = ieee802_1x_kay_get_peer(participant, participant->current_peer_id.mi);
+       }
+
        /* Only update live peer watchdog after successful decode of all parameter sets */
-       peer = ieee802_1x_kay_get_peer(participant, participant->current_peer_id.mi);
        if (peer)
                peer->expire = time(NULL) + MKA_LIFE_TIME / 1000;

diff --git a/src/pae/ieee802_1x_kay_i.h b/src/pae/ieee802_1x_kay_i.h
index c10851d2d..33c5b721b 100644
--- a/src/pae/ieee802_1x_kay_i.h
+++ b/src/pae/ieee802_1x_kay_i.h
@@ -51,6 +51,7 @@  struct ieee802_1x_kay_peer {
        Boolean macsec_desired;
        enum macsec_cap macsec_capability;
        Boolean sak_used;
+       int missing_sak_use_count;
        struct dl_list list;
 };