/** * get_asymetric_start_key - GetAsymetricStartKey() - RFC 3079, Sect. 3.4 * @master_key: 16-octet MasterKey (IN) * @session_key: 8-to-16 octet SessionKey (OUT) * @session_key_len: SessionKeyLength (Length of session_key) (IN) * @is_send: IsSend (IN, BOOLEAN) * @is_server: IsServer (IN, BOOLEAN) * Returns: 0 on success, -1 on failure */ int get_asymetric_start_key(const u8 *master_key, u8 *session_key, size_t session_key_len, int is_send, int is_server) { static const u8 magic2[84] = { 0x4f, 0x6e, 0x20, 0x74, 0x68, 0x65, 0x20, 0x63, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x20, 0x73, 0x69, 0x64, 0x65, 0x2c, 0x20, 0x74, 0x68, 0x69, 0x73, 0x20, 0x69, 0x73, 0x20, 0x74, 0x68, 0x65, 0x20, 0x73, 0x65, 0x6e, 0x64, 0x20, 0x6b, 0x65, 0x79, 0x3b, 0x20, 0x6f, 0x6e, 0x20, 0x74, 0x68, 0x65, 0x20, 0x73, 0x65, 0x72, 0x76, 0x65, 0x72, 0x20, 0x73, 0x69, 0x64, 0x65, 0x2c, 0x20, 0x69, 0x74, 0x20, 0x69, 0x73, 0x20, 0x74, 0x68, 0x65, 0x20, 0x72, 0x65, 0x63, 0x65, 0x69, 0x76, 0x65, 0x20, 0x6b, 0x65, 0x79, 0x2e }; static const u8 magic3[84] = { 0x4f, 0x6e, 0x20, 0x74, 0x68, 0x65, 0x20, 0x63, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x20, 0x73, 0x69, 0x64, 0x65, 0x2c, 0x20, 0x74, 0x68, 0x69, 0x73, 0x20, 0x69, 0x73, 0x20, 0x74, 0x68, 0x65, 0x20, 0x72, 0x65, 0x63, 0x65, 0x69, 0x76, 0x65, 0x20, 0x6b, 0x65, 0x79, 0x3b, 0x20, 0x6f, 0x6e, 0x20, 0x74, 0x68, 0x65, 0x20, 0x73, 0x65, 0x72, 0x76, 0x65, 0x72, 0x20, 0x73, 0x69, 0x64, 0x65, 0x2c, 0x20, 0x69, 0x74, 0x20, 0x69, 0x73, 0x20, 0x74, 0x68, 0x65, 0x20, 0x73, 0x65, 0x6e, 0x64, 0x20, 0x6b, 0x65, 0x79, 0x2e }; static const u8 shs_pad1[40] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; static const u8 shs_pad2[40] = { 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2, 0xf2 }; u8 digest[SHA1_MAC_LEN]; const unsigned char *addr[4]; const size_t len[4] = { 16, 40, 84, 40 }; addr[0] = master_key; addr[1] = shs_pad1; if (is_send) { addr[2] = is_server ? magic3 : magic2; } else { addr[2] = is_server ? magic2 : magic3; } addr[3] = shs_pad2; if (sha1_vector(4, addr, len, digest)) return -1; if (session_key_len > SHA1_MAC_LEN) session_key_len = SHA1_MAC_LEN; os_memcpy(session_key, digest, session_key_len); return 0; }
static void eap_aka_add_checkcode(struct eap_aka_data *data, struct eap_sim_msg *msg) { const u8 *addr; size_t len; u8 hash[SHA256_MAC_LEN]; wpa_printf(MSG_DEBUG, " AT_CHECKCODE"); if (data->id_msgs == NULL) { /* * No EAP-AKA/Identity packets were exchanged - send empty * checkcode. */ eap_sim_msg_add(msg, EAP_SIM_AT_CHECKCODE, 0, NULL, 0); return; } /* Checkcode is SHA1/SHA256 hash over all EAP-AKA/Identity packets. */ addr = wpabuf_head(data->id_msgs); len = wpabuf_len(data->id_msgs); wpa_hexdump(MSG_MSGDUMP, "EAP-AKA: AT_CHECKCODE data", addr, len); #ifdef EAP_AKA_PRIME if (data->eap_method == EAP_TYPE_AKA_PRIME) sha256_vector(1, &addr, &len, hash); else #endif /* EAP_AKA_PRIME */ sha1_vector(1, &addr, &len, hash); eap_sim_msg_add(msg, EAP_SIM_AT_CHECKCODE, 0, hash, data->eap_method == EAP_TYPE_AKA_PRIME ? EAP_AKA_PRIME_CHECKCODE_LEN : EAP_AKA_CHECKCODE_LEN); }
void uuid_gen_mac_addr(const u8 *mac_addr, u8 *uuid) { const u8 *addr[2]; size_t len[2]; u8 hash[SHA1_MAC_LEN]; u8 nsid[16] = { 0x52, 0x64, 0x80, 0xf8, 0xc9, 0x9b, 0x4b, 0xe5, 0xa6, 0x55, 0x58, 0xed, 0x5f, 0x5d, 0x60, 0x84 }; addr[0] = nsid; len[0] = sizeof(nsid); addr[1] = mac_addr; len[1] = 6; sha1_vector(2, addr, len, hash); os_memcpy(uuid, hash, 16); /* Version: 5 = named-based version using SHA-1 */ uuid[6] = (5 << 4) | (uuid[6] & 0x0f); /* Variant specified in RFC 4122 */ uuid[8] = 0x80 | (uuid[8] & 0x3f); }
static int eap_gpsk_gkdf(const u8 *psk /* Y */, size_t psk_len, const u8 *data /* Z */, size_t data_len, u8 *buf, size_t len /* X */) { u8 *opos; size_t i, n, hashlen, left, clen; u8 ibuf[2], hash[SHA1_MAC_LEN]; const u8 *addr[3]; size_t vlen[3]; hashlen = SHA1_MAC_LEN; /* M_i = Hash-Function (i || Y || Z); */ addr[0] = ibuf; vlen[0] = sizeof(ibuf); addr[1] = psk; vlen[1] = psk_len; addr[2] = data; vlen[2] = data_len; opos = buf; left = len; n = (len + hashlen - 1) / hashlen; for (i = 1; i <= n; i++) { WPA_PUT_BE16(ibuf, i); sha1_vector(3, addr, vlen, hash); clen = left > hashlen ? hashlen : left; os_memcpy(opos, hash, clen); opos += clen; left -= clen; } return 0; }
void eap_sim_derive_mk(const u8 *identity, size_t identity_len, const u8 *nonce_mt, u16 selected_version, const u8 *ver_list, size_t ver_list_len, int num_chal, const u8 *kc, u8 *mk) { u8 sel_ver[2]; const unsigned char *addr[5]; size_t len[5]; addr[0] = identity; len[0] = identity_len; addr[1] = kc; len[1] = num_chal * EAP_SIM_KC_LEN; addr[2] = nonce_mt; len[2] = EAP_SIM_NONCE_MT_LEN; addr[3] = ver_list; len[3] = ver_list_len; addr[4] = sel_ver; len[4] = 2; WPA_PUT_BE16(sel_ver, selected_version); /* MK = SHA1(Identity|n*Kc|NONCE_MT|Version List|Selected Version) */ sha1_vector(5, addr, len, mk); wpa_hexdump_key(MSG_DEBUG, "EAP-SIM: MK", mk, EAP_SIM_MK_LEN); }
/** * generate_authenticator_response_pwhash - GenerateAuthenticatorResponse() - RFC 2759, Sect. 8.7 * @password_hash: 16-octet PasswordHash (IN) * @nt_response: 24-octet NT-Response (IN) * @peer_challenge: 16-octet PeerChallenge (IN) * @auth_challenge: 16-octet AuthenticatorChallenge (IN) * @username: 0-to-256-char UserName (IN) * @username_len: Length of username * @response: 20-octet AuthenticatorResponse (OUT) (note: this value is usually * encoded as a 42-octet ASCII string (S=hexdump_of_response) * Returns: 0 on success, -1 on failure */ int generate_authenticator_response_pwhash( const u8 *password_hash, const u8 *peer_challenge, const u8 *auth_challenge, const u8 *username, size_t username_len, const u8 *nt_response, u8 *response) { static const u8 magic1[39] = { 0x4D, 0x61, 0x67, 0x69, 0x63, 0x20, 0x73, 0x65, 0x72, 0x76, 0x65, 0x72, 0x20, 0x74, 0x6F, 0x20, 0x63, 0x6C, 0x69, 0x65, 0x6E, 0x74, 0x20, 0x73, 0x69, 0x67, 0x6E, 0x69, 0x6E, 0x67, 0x20, 0x63, 0x6F, 0x6E, 0x73, 0x74, 0x61, 0x6E, 0x74 }; static const u8 magic2[41] = { 0x50, 0x61, 0x64, 0x20, 0x74, 0x6F, 0x20, 0x6D, 0x61, 0x6B, 0x65, 0x20, 0x69, 0x74, 0x20, 0x64, 0x6F, 0x20, 0x6D, 0x6F, 0x72, 0x65, 0x20, 0x74, 0x68, 0x61, 0x6E, 0x20, 0x6F, 0x6E, 0x65, 0x20, 0x69, 0x74, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6F, 0x6E }; u8 password_hash_hash[16], challenge[8]; const unsigned char *addr1[3]; const size_t len1[3] = { 16, 24, sizeof(magic1) }; const unsigned char *addr2[3]; const size_t len2[3] = { SHA1_MAC_LEN, 8, sizeof(magic2) }; addr1[0] = password_hash_hash; addr1[1] = nt_response; addr1[2] = magic1; addr2[0] = response; addr2[1] = challenge; addr2[2] = magic2; if (hash_nt_password_hash(password_hash, password_hash_hash)) return -1; if (sha1_vector(3, addr1, len1, response)) return -1; if (challenge_hash(peer_challenge, auth_challenge, username, username_len, challenge)) return -1; return sha1_vector(3, addr2, len2, response); }
int eap_sim_derive_keys_reauth(u16 _counter, const u8 *identity, size_t identity_len, const u8 *nonce_s, const u8 *mk, u8 *msk, u8 *emsk) { u8 xkey[SHA1_MAC_LEN]; u8 buf[EAP_SIM_KEYING_DATA_LEN + EAP_EMSK_LEN + 32]; u8 counter[2]; const u8 *addr[4]; size_t len[4]; while (identity_len > 0 && identity[identity_len - 1] == 0) { wpa_printf(MSG_DEBUG, "EAP-SIM: Workaround - drop null " "character from the end of identity"); identity_len--; } addr[0] = identity; len[0] = identity_len; addr[1] = counter; len[1] = 2; addr[2] = nonce_s; len[2] = EAP_SIM_NONCE_S_LEN; addr[3] = mk; len[3] = EAP_SIM_MK_LEN; WPA_PUT_BE16(counter, _counter); wpa_printf(MSG_DEBUG, "EAP-SIM: Deriving keying data from reauth"); wpa_hexdump_ascii(MSG_DEBUG, "EAP-SIM: Identity", identity, identity_len); wpa_hexdump(MSG_DEBUG, "EAP-SIM: counter", counter, 2); wpa_hexdump(MSG_DEBUG, "EAP-SIM: NONCE_S", nonce_s, EAP_SIM_NONCE_S_LEN); wpa_hexdump_key(MSG_DEBUG, "EAP-SIM: MK", mk, EAP_SIM_MK_LEN); /* XKEY' = SHA1(Identity|counter|NONCE_S|MK) */ sha1_vector(4, addr, len, xkey); wpa_hexdump(MSG_DEBUG, "EAP-SIM: XKEY'", xkey, SHA1_MAC_LEN); if (eap_sim_prf(xkey, buf, sizeof(buf)) < 0) { wpa_printf(MSG_ERROR, "EAP-SIM: Failed to derive keys"); return -1; } if (msk) { os_memcpy(msk, buf, EAP_SIM_KEYING_DATA_LEN); wpa_hexdump(MSG_DEBUG, "EAP-SIM: keying material (MSK)", msk, EAP_SIM_KEYING_DATA_LEN); } if (emsk) { os_memcpy(emsk, buf + EAP_SIM_KEYING_DATA_LEN, EAP_EMSK_LEN); wpa_hexdump(MSG_DEBUG, "EAP-SIM: EMSK", emsk, EAP_EMSK_LEN); } os_memset(buf, 0, sizeof(buf)); return 0; }
static int eap_aka_verify_checkcode(struct eap_aka_data *data, const u8 *checkcode, size_t checkcode_len) { const u8 *addr; size_t len; u8 hash[SHA256_MAC_LEN]; size_t hash_len; if (checkcode == NULL) return -1; if (data->id_msgs == NULL) { if (checkcode_len != 0) { wpa_printf(MSG_DEBUG, "EAP-AKA: Checkcode from server " "indicates that AKA/Identity messages were " "used, but they were not"); return -1; } return 0; } hash_len = data->eap_method == EAP_TYPE_AKA_PRIME ? EAP_AKA_PRIME_CHECKCODE_LEN : EAP_AKA_CHECKCODE_LEN; if (checkcode_len != hash_len) { wpa_printf(MSG_DEBUG, "EAP-AKA: Checkcode from server " "indicates that AKA/Identity message were not " "used, but they were"); return -1; } /* Checkcode is SHA1/SHA256 hash over all EAP-AKA/Identity packets. */ addr = wpabuf_head(data->id_msgs); len = wpabuf_len(data->id_msgs); #ifdef EAP_AKA_PRIME if (data->eap_method == EAP_TYPE_AKA_PRIME) sha256_vector(1, &addr, &len, hash); else #endif /* EAP_AKA_PRIME */ sha1_vector(1, &addr, &len, hash); if (os_memcmp(hash, checkcode, hash_len) != 0) { wpa_printf(MSG_DEBUG, "EAP-AKA: Mismatch in AT_CHECKCODE"); return -1; } return 0; }
static void challenge_hash(const u8 *peer_challenge, const u8 *auth_challenge, const u8 *username, size_t username_len, u8 *challenge) { u8 hash[SHA1_MAC_LEN]; const unsigned char *addr[3]; size_t len[3]; addr[0] = peer_challenge; len[0] = 16; addr[1] = auth_challenge; len[1] = 16; addr[2] = username; len[2] = username_len; sha1_vector(3, addr, len, hash); os_memcpy(challenge, hash, 8); }
void eap_aka_derive_mk(const u8 *identity, size_t identity_len, const u8 *ik, const u8 *ck, u8 *mk) { const u8 *addr[3]; size_t len[3]; addr[0] = identity; len[0] = identity_len; addr[1] = ik; len[1] = EAP_AKA_IK_LEN; addr[2] = ck; len[2] = EAP_AKA_CK_LEN; /* MK = SHA1(Identity|IK|CK) */ sha1_vector(3, addr, len, mk); wpa_hexdump_key(MSG_DEBUG, "EAP-AKA: IK", ik, EAP_AKA_IK_LEN); wpa_hexdump_key(MSG_DEBUG, "EAP-AKA: CK", ck, EAP_AKA_CK_LEN); wpa_hexdump_key(MSG_DEBUG, "EAP-AKA: MK", mk, EAP_SIM_MK_LEN); }
void get_master_key(const u8 *password_hash_hash, const u8 *nt_response, u8 *master_key) { static const u8 magic1[27] = { 0x54, 0x68, 0x69, 0x73, 0x20, 0x69, 0x73, 0x20, 0x74, 0x68, 0x65, 0x20, 0x4d, 0x50, 0x50, 0x45, 0x20, 0x4d, 0x61, 0x73, 0x74, 0x65, 0x72, 0x20, 0x4b, 0x65, 0x79 }; const unsigned char *addr[3]; const size_t len[3] = { 16, 24, sizeof(magic1) }; u8 hash[SHA1_MAC_LEN]; addr[0] = password_hash_hash; addr[1] = nt_response; addr[2] = magic1; sha1_vector(3, addr, len, hash); os_memcpy(master_key, hash, 16); }
static int eap_aka_verify_checkcode(struct eap_aka_data *data, const u8 *checkcode, size_t checkcode_len) { const u8 *addr; size_t len; u8 hash[SHA1_MAC_LEN]; if (checkcode == NULL) return -1; if (data->id_msgs == NULL) { if (checkcode_len != 0) { wpa_printf(MSG_DEBUG, "EAP-AKA: Checkcode from server " "indicates that AKA/Identity messages were " "used, but they were not"); return -1; } return 0; } if (checkcode_len != EAP_AKA_CHECKCODE_LEN) { wpa_printf(MSG_DEBUG, "EAP-AKA: Checkcode from server " "indicates that AKA/Identity message were not " "used, but they were"); return -1; } /* Checkcode is SHA1 hash over all EAP-AKA/Identity packets. */ addr = wpabuf_head(data->id_msgs); len = wpabuf_len(data->id_msgs); sha1_vector(1, &addr, &len, hash); if (os_memcmp(hash, checkcode, EAP_AKA_CHECKCODE_LEN) != 0) { wpa_printf(MSG_DEBUG, "EAP-AKA: Mismatch in AT_CHECKCODE"); return -1; } return 0; }
static void eap_sim_derive_mk(struct eap_sim_data *data, const u8 *identity, size_t identity_len) { u8 sel_ver[2]; const unsigned char *addr[5]; size_t len[5]; addr[0] = identity; len[0] = identity_len; addr[1] = (u8 *) data->kc; len[1] = data->num_chal * KC_LEN; addr[2] = data->nonce_mt; len[2] = EAP_SIM_NONCE_MT_LEN; addr[3] = data->ver_list; len[3] = data->ver_list_len; addr[4] = sel_ver; len[4] = 2; WPA_PUT_BE16(sel_ver, data->selected_version); /* MK = SHA1(Identity|n*Kc|NONCE_MT|Version List|Selected Version) */ sha1_vector(5, addr, len, data->mk); wpa_hexdump_key(MSG_DEBUG, "EAP-SIM: MK", data->mk, EAP_SIM_MK_LEN); }
u32 mrvl_sha1_vector(size_t nmsg, const u8 *msg[], const size_t msglen[], u8 *mac, size_t maclen) { sha1_vector(nmsg, msg, msglen, mac); return 0; }
/** * hmac_sha1_vector - HMAC-SHA1 over data vector (RFC 2104) * @key: Key for HMAC operations * @key_len: Length of the key in bytes * @num_elem: Number of elements in the data vector * @addr: Pointers to the data areas * @len: Lengths of the data blocks * @mac: Buffer for the hash (20 bytes) * Returns: 0 on success, -1 on failure */ int hmac_sha1_vector(const u8 *key, size_t key_len, size_t num_elem, const u8 *addr[], const size_t *len, u8 *mac) { unsigned char k_pad[64]; /* padding - key XORd with ipad/opad */ unsigned char tk[20]; const u8 *_addr[6]; size_t _len[6], i; if (num_elem > 5) { /* * Fixed limit on the number of fragments to avoid having to * allocate memory (which could fail). */ return -1; } /* 大于64字节的计算其20字节的消息认证码 */ /* if key is longer than 64 bytes reset it to key = SHA1(key) */ if (key_len > 64) { if (sha1_vector(1, &key, &key_len, tk)) return -1; key = tk; key_len = 20; } /* the HMAC_SHA1 transform looks like: * * SHA1(K XOR opad, SHA1(K XOR ipad, text)) * * where K is an n byte key * ipad is the byte 0x36 repeated 64 times * opad is the byte 0x5c repeated 64 times * and text is the data being protected */ /* 补齐到64字节 */ /* start out by storing key in ipad */ os_memset(k_pad, 0, sizeof(k_pad)); os_memcpy(k_pad, key, key_len); /* XOR key with ipad values */ for (i = 0; i < 64; i++) k_pad[i] ^= 0x36; /* perform inner SHA1 */ _addr[0] = k_pad; _len[0] = 64; for (i = 0; i < num_elem; i++) { _addr[i + 1] = addr[i]; _len[i + 1] = len[i]; } /* 第1次计算 */ if (sha1_vector(1 + num_elem, _addr, _len, mac)) return -1; os_memset(k_pad, 0, sizeof(k_pad)); os_memcpy(k_pad, key, key_len); /* XOR key with opad values */ for (i = 0; i < 64; i++) k_pad[i] ^= 0x5c; /* perform outer SHA1 */ _addr[0] = k_pad; _len[0] = 64; _addr[1] = mac; _len[1] = SHA1_MAC_LEN; /* 第2次计算 */ return sha1_vector(2, _addr, _len, mac); }
void kr_hash_sha1_v(size_t num_msgs, const uint8_t *msgs[], const size_t *msg_lens, uint8_t *digest) { (void) sha1_vector(num_msgs, msgs, msg_lens, digest); }
static int cavp_rsa_sig_ver(const char *fname) { FILE *f; int ret = 0; char buf[15000], *pos, *pos2; u8 msg[200], n[512], s[512], em[512], e[512]; size_t msg_len = 0, n_len = 0, s_len = 0, em_len, e_len = 0; size_t tmp_len; char sha_alg[20]; int ok = 0; printf("CAVP RSA SigVer test vectors from %s\n", fname); f = fopen(fname, "r"); if (f == NULL) { printf("%s does not exist - cannot validate CAVP RSA SigVer test vectors\n", fname); return 0; } while (fgets(buf, sizeof(buf), f)) { pos = os_strchr(buf, '='); if (pos == NULL) continue; pos2 = pos - 1; while (pos2 >= buf && *pos2 == ' ') *pos2-- = '\0'; *pos++ = '\0'; while (*pos == ' ') *pos++ = '\0'; pos2 = os_strchr(pos, '\r'); if (!pos2) pos2 = os_strchr(pos, '\n'); if (pos2) *pos2 = '\0'; else pos2 = pos + os_strlen(pos); if (os_strcmp(buf, "SHAAlg") == 0) { os_strlcpy(sha_alg, pos, sizeof(sha_alg)); } else if (os_strcmp(buf, "Msg") == 0) { tmp_len = os_strlen(pos); if (tmp_len > sizeof(msg) * 2) { printf("Too long Msg\n"); return -1; } msg_len = tmp_len / 2; if (hexstr2bin(pos, msg, msg_len) < 0) { printf("Invalid hex string '%s'\n", pos); ret++; break; } } else if (os_strcmp(buf, "n") == 0) { tmp_len = os_strlen(pos); if (tmp_len > sizeof(n) * 2) { printf("Too long n\n"); return -1; } n_len = tmp_len / 2; if (hexstr2bin(pos, n, n_len) < 0) { printf("Invalid hex string '%s'\n", pos); ret++; break; } } else if (os_strcmp(buf, "e") == 0) { tmp_len = os_strlen(pos); if (tmp_len > sizeof(e) * 2) { printf("Too long e\n"); return -1; } e_len = tmp_len / 2; if (hexstr2bin(pos, e, e_len) < 0) { printf("Invalid hex string '%s'\n", pos); ret++; break; } } else if (os_strcmp(buf, "S") == 0) { tmp_len = os_strlen(pos); if (tmp_len > sizeof(s) * 2) { printf("Too long S\n"); return -1; } s_len = tmp_len / 2; if (hexstr2bin(pos, s, s_len) < 0) { printf("Invalid hex string '%s'\n", pos); ret++; break; } } else if (os_strncmp(buf, "EM", 2) == 0) { tmp_len = os_strlen(pos); if (tmp_len > sizeof(em) * 2) return -1; em_len = tmp_len / 2; if (hexstr2bin(pos, em, em_len) < 0) { printf("Invalid hex string '%s'\n", pos); ret++; break; } } else if (os_strcmp(buf, "Result") == 0) { const u8 *addr[1]; size_t len[1]; struct crypto_public_key *pk; int res; u8 hash[32]; size_t hash_len; const struct asn1_oid *alg; addr[0] = msg; len[0] = msg_len; if (os_strcmp(sha_alg, "SHA1") == 0) { if (sha1_vector(1, addr, len, hash) < 0) return -1; hash_len = 20; alg = &asn1_sha1_oid; } else if (os_strcmp(sha_alg, "SHA256") == 0) { if (sha256_vector(1, addr, len, hash) < 0) return -1; hash_len = 32; alg = &asn1_sha256_oid; } else { continue; } printf("\nExpected result: %s\n", pos); wpa_hexdump(MSG_INFO, "Hash(Msg)", hash, hash_len); pk = crypto_public_key_import_parts(n, n_len, e, e_len); if (pk == NULL) { printf("Failed to import public key\n"); ret++; continue; } res = pkcs1_v15_sig_ver(pk, s, s_len, alg, hash, hash_len); crypto_public_key_free(pk); if ((*pos == 'F' && !res) || (*pos != 'F' && res)) { printf("FAIL\n"); ret++; continue; } printf("PASS\n"); ok++; } } fclose(f); if (ret) printf("Test case failed\n"); else printf("%d test vectors OK\n", ok); return ret; }