aboutsummaryrefslogtreecommitdiffstats
path: root/src/eap_common
diff options
context:
space:
mode:
authorJouni Malinen <j@w1.fi>2014-11-29 19:28:24 (GMT)
committerJouni Malinen <j@w1.fi>2014-12-04 10:08:59 (GMT)
commite2ee327b191d2c64c31f3f535cc42e955fb084a4 (patch)
tree0a14d095aee9a36f55936b372490d42a78f9fc38 /src/eap_common
parent0087061de779a40bb0fe13f598a6b96136804d09 (diff)
downloadhostap-e2ee327b191d2c64c31f3f535cc42e955fb084a4.zip
hostap-e2ee327b191d2c64c31f3f535cc42e955fb084a4.tar.gz
hostap-e2ee327b191d2c64c31f3f535cc42e955fb084a4.tar.bz2
ERP: Add TV/TLV parser
This is needed for ERP implementation on both the server/authenticator and peer side. Signed-off-by: Jouni Malinen <j@w1.fi>
Diffstat (limited to 'src/eap_common')
-rw-r--r--src/eap_common/eap_common.c85
-rw-r--r--src/eap_common/eap_common.h12
2 files changed, 95 insertions, 2 deletions
diff --git a/src/eap_common/eap_common.c b/src/eap_common/eap_common.c
index 7b077cb..1de1328 100644
--- a/src/eap_common/eap_common.c
+++ b/src/eap_common/eap_common.c
@@ -1,6 +1,6 @@
/*
* EAP common peer/server definitions
- * Copyright (c) 2004-2012, Jouni Malinen <j@w1.fi>
+ * Copyright (c) 2004-2014, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
@@ -203,3 +203,86 @@ EapType eap_get_type(const struct wpabuf *msg)
return ((const u8 *) wpabuf_head(msg))[sizeof(struct eap_hdr)];
}
+
+
+#ifdef CONFIG_ERP
+int erp_parse_tlvs(const u8 *pos, const u8 *end, struct erp_tlvs *tlvs,
+ int stop_at_keyname)
+{
+ os_memset(tlvs, 0, sizeof(*tlvs));
+
+ while (pos < end) {
+ u8 tlv_type, tlv_len;
+
+ tlv_type = *pos++;
+ switch (tlv_type) {
+ case EAP_ERP_TV_RRK_LIFETIME:
+ case EAP_ERP_TV_RMSK_LIFETIME:
+ /* 4-octet TV */
+ if (pos + 4 > end) {
+ wpa_printf(MSG_DEBUG, "EAP: Too short TV");
+ return -1;
+ }
+ pos += 4;
+ break;
+ case EAP_ERP_TLV_DOMAIN_NAME:
+ case EAP_ERP_TLV_KEYNAME_NAI:
+ case EAP_ERP_TLV_CRYPTOSUITES:
+ case EAP_ERP_TLV_AUTHORIZATION_INDICATION:
+ case EAP_ERP_TLV_CALLED_STATION_ID:
+ case EAP_ERP_TLV_CALLING_STATION_ID:
+ case EAP_ERP_TLV_NAS_IDENTIFIER:
+ case EAP_ERP_TLV_NAS_IP_ADDRESS:
+ case EAP_ERP_TLV_NAS_IPV6_ADDRESS:
+ if (pos >= end) {
+ wpa_printf(MSG_DEBUG, "EAP: Too short TLV");
+ return -1;
+ }
+ tlv_len = *pos++;
+ if (tlv_len > (unsigned) (end - pos)) {
+ wpa_printf(MSG_DEBUG, "EAP: Truncated TLV");
+ return -1;
+ }
+ if (tlv_type == EAP_ERP_TLV_KEYNAME_NAI) {
+ if (tlvs->keyname) {
+ wpa_printf(MSG_DEBUG,
+ "EAP: More than one keyName-NAI");
+ return -1;
+ }
+ tlvs->keyname = pos;
+ tlvs->keyname_len = tlv_len;
+ if (stop_at_keyname)
+ return 0;
+ } else if (tlv_type == EAP_ERP_TLV_DOMAIN_NAME) {
+ tlvs->domain = pos;
+ tlvs->domain_len = tlv_len;
+ }
+ pos += tlv_len;
+ break;
+ default:
+ if (tlv_type >= 128 && tlv_type <= 191) {
+ /* Undefined TLV */
+ if (pos >= end) {
+ wpa_printf(MSG_DEBUG,
+ "EAP: Too short TLV");
+ return -1;
+ }
+ tlv_len = *pos++;
+ if (tlv_len > (unsigned) (end - pos)) {
+ wpa_printf(MSG_DEBUG,
+ "EAP: Truncated TLV");
+ return -1;
+ }
+ pos += tlv_len;
+ break;
+ }
+ wpa_printf(MSG_DEBUG, "EAP: Unknown TV/TLV type %u",
+ tlv_type);
+ pos = end;
+ break;
+ }
+ }
+
+ return 0;
+}
+#endif /* CONFIG_ERP */
diff --git a/src/eap_common/eap_common.h b/src/eap_common/eap_common.h
index 8850c1f..e62f167 100644
--- a/src/eap_common/eap_common.h
+++ b/src/eap_common/eap_common.h
@@ -1,6 +1,6 @@
/*
* EAP common peer/server definitions
- * Copyright (c) 2004-2012, Jouni Malinen <j@w1.fi>
+ * Copyright (c) 2004-2014, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
@@ -11,6 +11,14 @@
#include "wpabuf.h"
+struct erp_tlvs {
+ const u8 *keyname;
+ const u8 *domain;
+
+ u8 keyname_len;
+ u8 domain_len;
+};
+
int eap_hdr_len_valid(const struct wpabuf *msg, size_t min_payload);
const u8 * eap_hdr_validate(int vendor, EapType eap_type,
const struct wpabuf *msg, size_t *plen);
@@ -19,5 +27,7 @@ struct wpabuf * eap_msg_alloc(int vendor, EapType type, size_t payload_len,
void eap_update_len(struct wpabuf *msg);
u8 eap_get_id(const struct wpabuf *msg);
EapType eap_get_type(const struct wpabuf *msg);
+int erp_parse_tlvs(const u8 *pos, const u8 *end, struct erp_tlvs *tlvs,
+ int stop_at_keyname);
#endif /* EAP_COMMON_H */