00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #include "includes.h"
00020
00021 #include "common.h"
00022 #include "eap_i.h"
00023 #ifdef TEST_PENDING_REQUEST
00024 #include "eloop.h"
00025 #endif
00026
00027
00028 #define EAP_VENDOR_ID 0xfffefd
00029 #define EAP_VENDOR_TYPE 0xfcfbfaf9
00030
00031
00032
00033
00034 struct eap_vendor_test_data {
00035 enum { INIT, CONFIRM, SUCCESS } state;
00036 int first_try;
00037 };
00038
00039
00040 static void * eap_vendor_test_init(struct eap_sm *sm)
00041 {
00042 struct eap_vendor_test_data *data;
00043 data = os_zalloc(sizeof(*data));
00044 if (data == NULL)
00045 return NULL;
00046 data->state = INIT;
00047 data->first_try = 1;
00048 return data;
00049 }
00050
00051
00052 static void eap_vendor_test_deinit(struct eap_sm *sm, void *priv)
00053 {
00054 struct eap_vendor_test_data *data = priv;
00055 os_free(data);
00056 }
00057
00058
00059 #ifdef TEST_PENDING_REQUEST
00060 static void eap_vendor_ready(void *eloop_ctx, void *timeout_ctx)
00061 {
00062 struct eap_sm *sm = eloop_ctx;
00063 wpa_printf(MSG_DEBUG, "EAP-VENDOR-TEST: Ready to re-process pending "
00064 "request");
00065 eap_notify_pending(sm);
00066 }
00067 #endif
00068
00069
00070 static struct wpabuf * eap_vendor_test_process(struct eap_sm *sm, void *priv,
00071 struct eap_method_ret *ret,
00072 const struct wpabuf *reqData)
00073 {
00074 struct eap_vendor_test_data *data = priv;
00075 struct wpabuf *resp;
00076 const u8 *pos;
00077 size_t len;
00078
00079 pos = eap_hdr_validate(EAP_VENDOR_ID, EAP_VENDOR_TYPE, reqData, &len);
00080 if (pos == NULL || len < 1) {
00081 ret->ignore = TRUE;
00082 return NULL;
00083 }
00084
00085 if (data->state == INIT && *pos != 1) {
00086 wpa_printf(MSG_DEBUG, "EAP-VENDOR-TEST: Unexpected message "
00087 "%d in INIT state", *pos);
00088 ret->ignore = TRUE;
00089 return NULL;
00090 }
00091
00092 if (data->state == CONFIRM && *pos != 3) {
00093 wpa_printf(MSG_DEBUG, "EAP-VENDOR-TEST: Unexpected message "
00094 "%d in CONFIRM state", *pos);
00095 ret->ignore = TRUE;
00096 return NULL;
00097 }
00098
00099 if (data->state == SUCCESS) {
00100 wpa_printf(MSG_DEBUG, "EAP-VENDOR-TEST: Unexpected message "
00101 "in SUCCESS state");
00102 ret->ignore = TRUE;
00103 return NULL;
00104 }
00105
00106 if (data->state == CONFIRM) {
00107 #ifdef TEST_PENDING_REQUEST
00108 if (data->first_try) {
00109 data->first_try = 0;
00110 wpa_printf(MSG_DEBUG, "EAP-VENDOR-TEST: Testing "
00111 "pending request");
00112 ret->ignore = TRUE;
00113 eloop_register_timeout(1, 0, eap_vendor_ready, sm,
00114 NULL);
00115 return NULL;
00116 }
00117 #endif
00118 }
00119
00120 ret->ignore = FALSE;
00121
00122 wpa_printf(MSG_DEBUG, "EAP-VENDOR-TEST: Generating Response");
00123 ret->allowNotifications = TRUE;
00124
00125 resp = eap_msg_alloc(EAP_VENDOR_ID, EAP_VENDOR_TYPE, 1,
00126 EAP_CODE_RESPONSE, eap_get_id(reqData));
00127 if (resp == NULL)
00128 return NULL;
00129
00130 if (data->state == INIT) {
00131 wpabuf_put_u8(resp, 2);
00132 data->state = CONFIRM;
00133 ret->methodState = METHOD_CONT;
00134 ret->decision = DECISION_FAIL;
00135 } else {
00136 wpabuf_put_u8(resp, 4);
00137 data->state = SUCCESS;
00138 ret->methodState = METHOD_DONE;
00139 ret->decision = DECISION_UNCOND_SUCC;
00140 }
00141
00142 return resp;
00143 }
00144
00145
00146 static Boolean eap_vendor_test_isKeyAvailable(struct eap_sm *sm, void *priv)
00147 {
00148 struct eap_vendor_test_data *data = priv;
00149 return data->state == SUCCESS;
00150 }
00151
00152
00153 static u8 * eap_vendor_test_getKey(struct eap_sm *sm, void *priv, size_t *len)
00154 {
00155 struct eap_vendor_test_data *data = priv;
00156 u8 *key;
00157 const int key_len = 64;
00158
00159 if (data->state != SUCCESS)
00160 return NULL;
00161
00162 key = os_malloc(key_len);
00163 if (key == NULL)
00164 return NULL;
00165
00166 os_memset(key, 0x11, key_len / 2);
00167 os_memset(key + key_len / 2, 0x22, key_len / 2);
00168 *len = key_len;
00169
00170 return key;
00171 }
00172
00173
00174 int eap_peer_vendor_test_register(void)
00175 {
00176 struct eap_method *eap;
00177 int ret;
00178
00179 eap = eap_peer_method_alloc(EAP_PEER_METHOD_INTERFACE_VERSION,
00180 EAP_VENDOR_ID, EAP_VENDOR_TYPE,
00181 "VENDOR-TEST");
00182 if (eap == NULL)
00183 return -1;
00184
00185 eap->init = eap_vendor_test_init;
00186 eap->deinit = eap_vendor_test_deinit;
00187 eap->process = eap_vendor_test_process;
00188 eap->isKeyAvailable = eap_vendor_test_isKeyAvailable;
00189 eap->getKey = eap_vendor_test_getKey;
00190
00191 ret = eap_peer_method_register(eap);
00192 if (ret)
00193 eap_peer_method_free(eap);
00194 return ret;
00195 }