From b615a6f4e05c1db7f0237a2596c5d6db28446767 Mon Sep 17 00:00:00 2001 From: Marcel Holtmann Date: Sat, 27 Dec 2014 06:44:04 +0100 Subject: [PATCH] core: Add support for HMAC MD5 helper function --- Makefile.am | 1 + src/md5.c | 93 +++++++++++++++++++++++++++++++++++++++++++++++++++++ src/md5.h | 26 +++++++++++++++ 3 files changed, 120 insertions(+) create mode 100644 src/md5.c create mode 100644 src/md5.h diff --git a/Makefile.am b/Makefile.am index dbd18537..8cb3b37c 100644 --- a/Makefile.am +++ b/Makefile.am @@ -43,6 +43,7 @@ src_iwd_SOURCES = src/main.c linux/nl80211.h linux/kdbus.h \ src/kdbus.h src/kdbus.c \ src/netdev.h src/netdev.c \ src/wiphy.h src/wiphy.c \ + src/md5.h src/md5.c \ src/sha1.h src/sha1.c \ src/ie.h src/ie.c \ src/dbus.h src/dbus.c \ diff --git a/src/md5.c b/src/md5.c new file mode 100644 index 00000000..994818d7 --- /dev/null +++ b/src/md5.c @@ -0,0 +1,93 @@ +/* + * + * Wireless daemon for Linux + * + * Copyright (C) 2013-2014 Intel Corporation. All rights reserved. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + +#ifdef HAVE_CONFIG_H +#include +#endif + +#include +#include + +#include "src/md5.h" + +#define MD5_MAC_LEN 16 + +static void __hmac_md5(struct l_checksum *checksum, + const void *key, size_t key_len, + const void *data, size_t data_len, void *output) +{ + unsigned char ipad[64]; + unsigned char opad[64]; + unsigned char digest[MD5_MAC_LEN]; + int i; + + /* if key is longer than 64 bytes reset it to key=MD5(key) */ + if (key_len > 64) { + l_checksum_update(checksum, key, key_len); + l_checksum_get_digest(checksum, digest, MD5_MAC_LEN); + + l_checksum_reset(checksum); + + key = digest; + key_len = MD5_MAC_LEN; + } + + /* start out by storing key in pads */ + memset(ipad, 0, sizeof(ipad)); + memset(opad, 0, sizeof(opad)); + memcpy(ipad, key, key_len); + memcpy(opad, key, key_len); + + /* XOR key with ipad and opad values */ + for (i = 0; i < 64; i++) { + ipad[i] ^= 0x36; + opad[i] ^= 0x5c; + } + + /* perform inner MD5 */ + l_checksum_update(checksum, ipad, sizeof(ipad)); + l_checksum_update(checksum, data, data_len); + l_checksum_get_digest(checksum, digest, MD5_MAC_LEN); + + l_checksum_reset(checksum); + + /* perform outer MD5 */ + l_checksum_update(checksum, opad, sizeof(opad)); + l_checksum_update(checksum, digest, MD5_MAC_LEN); + l_checksum_get_digest(checksum, output, MD5_MAC_LEN); + + l_checksum_reset(checksum); +} + +bool hmac_md5(const void *key, size_t key_len, + const void *data, size_t data_len, void *output, size_t size) +{ + struct l_checksum *checksum; + + checksum = l_checksum_new(L_CHECKSUM_MD5); + + __hmac_md5(checksum, key, key_len, data, data_len, output); + + l_checksum_free(checksum); + + return true; +} diff --git a/src/md5.h b/src/md5.h new file mode 100644 index 00000000..e96509ba --- /dev/null +++ b/src/md5.h @@ -0,0 +1,26 @@ +/* + * + * Wireless daemon for Linux + * + * Copyright (C) 2013-2014 Intel Corporation. All rights reserved. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * + */ + +#include + +bool hmac_md5(const void *key, size_t key_len, + const void *data, size_t data_len, void *output, size_t size);