summaryrefslogtreecommitdiff
path: root/src/libstrongswan/crypto/hashers
diff options
context:
space:
mode:
Diffstat (limited to 'src/libstrongswan/crypto/hashers')
-rw-r--r--src/libstrongswan/crypto/hashers/hash_algorithm_set.c113
-rw-r--r--src/libstrongswan/crypto/hashers/hash_algorithm_set.h76
-rw-r--r--src/libstrongswan/crypto/hashers/hasher.c102
-rw-r--r--src/libstrongswan/crypto/hashers/hasher.h40
4 files changed, 304 insertions, 27 deletions
diff --git a/src/libstrongswan/crypto/hashers/hash_algorithm_set.c b/src/libstrongswan/crypto/hashers/hash_algorithm_set.c
new file mode 100644
index 000000000..93b67cb13
--- /dev/null
+++ b/src/libstrongswan/crypto/hashers/hash_algorithm_set.c
@@ -0,0 +1,113 @@
+/*
+ * Copyright (C) 2015 Tobias Brunner
+ * Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program 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 General Public License
+ * for more details.
+ */
+
+#include "hash_algorithm_set.h"
+
+#include <collections/array.h>
+
+typedef struct private_hash_algorithm_set_t private_hash_algorithm_set_t;
+
+struct private_hash_algorithm_set_t {
+
+ /**
+ * Public interface
+ */
+ hash_algorithm_set_t public;
+
+ /**
+ * Algorithms contained in the set
+ */
+ array_t *algorithms;
+};
+
+/**
+ * Sort hash algorithms
+ */
+static int hash_sort(const void *a, const void *b, void *user)
+{
+ const hash_algorithm_t *ha = a, *hb = b;
+ return *ha - *hb;
+}
+
+/**
+ * Find a hash algorithm
+ */
+static int hash_find(const void *a, const void *b)
+{
+ return hash_sort(a, b, NULL);
+}
+
+METHOD(hash_algorithm_set_t, contains, bool,
+ private_hash_algorithm_set_t *this, hash_algorithm_t hash)
+{
+ return array_bsearch(this->algorithms, &hash, hash_find, NULL) != -1;
+}
+
+METHOD(hash_algorithm_set_t, add, void,
+ private_hash_algorithm_set_t *this, hash_algorithm_t hash)
+{
+ if (!contains(this, hash))
+ {
+ array_insert(this->algorithms, ARRAY_TAIL, &hash);
+ array_sort(this->algorithms, hash_sort, NULL);
+ }
+}
+
+METHOD(hash_algorithm_set_t, count, int,
+ private_hash_algorithm_set_t *this)
+{
+ return array_count(this->algorithms);
+}
+
+static bool hash_filter(void *data, void **in, hash_algorithm_t *out)
+{
+ *out = **(hash_algorithm_t**)in;
+ return TRUE;
+}
+
+METHOD(hash_algorithm_set_t, create_enumerator, enumerator_t*,
+ private_hash_algorithm_set_t *this)
+{
+ return enumerator_create_filter(array_create_enumerator(this->algorithms),
+ (void*)hash_filter, NULL, NULL);
+}
+
+METHOD(hash_algorithm_set_t, destroy, void,
+ private_hash_algorithm_set_t *this)
+{
+ array_destroy(this->algorithms);
+ free(this);
+}
+
+/**
+ * Described in header
+ */
+hash_algorithm_set_t *hash_algorithm_set_create()
+{
+ private_hash_algorithm_set_t *this;
+
+ INIT(this,
+ .public = {
+ .add = _add,
+ .contains = _contains,
+ .count = _count,
+ .create_enumerator = _create_enumerator,
+ .destroy = _destroy,
+ },
+ .algorithms = array_create(sizeof(hash_algorithm_t), 0),
+ );
+
+ return &this->public;
+} \ No newline at end of file
diff --git a/src/libstrongswan/crypto/hashers/hash_algorithm_set.h b/src/libstrongswan/crypto/hashers/hash_algorithm_set.h
new file mode 100644
index 000000000..00e90cc2e
--- /dev/null
+++ b/src/libstrongswan/crypto/hashers/hash_algorithm_set.h
@@ -0,0 +1,76 @@
+/*
+ * Copyright (C) 2015 Tobias Brunner
+ * Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program 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 General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup hash_algorithm_set hash_algorithm_set
+ * @{ @ingroup crypto
+ */
+
+#ifndef HASH_ALGORITHM_SET_H_
+#define HASH_ALGORITHM_SET_H_
+
+typedef struct hash_algorithm_set_t hash_algorithm_set_t;
+
+#include <library.h>
+#include <crypto/hashers/hasher.h>
+
+/**
+ * A set of hash algorithms
+ */
+struct hash_algorithm_set_t {
+
+ /**
+ * Add the given algorithm to the set.
+ *
+ * @param alg hash algorithm
+ */
+ void (*add)(hash_algorithm_set_t *this, hash_algorithm_t alg);
+
+ /**
+ * Check if the given algorithm is contained in the set.
+ *
+ * @param alg hash algorithm
+ * @return TRUE if contained in set
+ */
+ bool (*contains)(hash_algorithm_set_t *this, hash_algorithm_t alg);
+
+ /**
+ * Number of hash algorithms contained in the set.
+ *
+ * @return number of algorithms
+ */
+ int (*count)(hash_algorithm_set_t *this);
+
+ /**
+ * Enumerate the algorithms contained in the set.
+ *
+ * @return enumerator over hash_algorithm_t (sorted by identifier)
+ */
+ enumerator_t *(*create_enumerator)(hash_algorithm_set_t *this);
+
+ /**
+ * Destroy a hash_algorithm_set_t instance
+ */
+ void (*destroy)(hash_algorithm_set_t *this);
+};
+
+/**
+ * Create a set of hash algorithms.
+ *
+ * @return hash_algorithm_set_t instance
+ */
+hash_algorithm_set_t *hash_algorithm_set_create();
+
+#endif /** HASH_ALGORITHM_SET_H_ @}*/
diff --git a/src/libstrongswan/crypto/hashers/hasher.c b/src/libstrongswan/crypto/hashers/hasher.c
index 13cbb5a59..38eebea9c 100644
--- a/src/libstrongswan/crypto/hashers/hasher.c
+++ b/src/libstrongswan/crypto/hashers/hasher.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2012 Tobias Brunner
+ * Copyright (C) 2012-2015 Tobias Brunner
* Copyright (C) 2005-2006 Martin Willi
* Copyright (C) 2005 Jan Hutter
* Hochschule fuer Technik Rapperswil
@@ -19,29 +19,31 @@
#include <asn1/oid.h>
-ENUM(hash_algorithm_names, HASH_UNKNOWN, HASH_SHA512,
+ENUM_BEGIN(hash_algorithm_names, HASH_SHA1, HASH_SHA512,
+ "HASH_SHA1",
+ "HASH_SHA256",
+ "HASH_SHA384",
+ "HASH_SHA512");
+ENUM_NEXT(hash_algorithm_names, HASH_UNKNOWN, HASH_SHA224, HASH_SHA512,
"HASH_UNKNOWN",
"HASH_MD2",
"HASH_MD4",
"HASH_MD5",
- "HASH_SHA1",
- "HASH_SHA224",
- "HASH_SHA256",
- "HASH_SHA384",
- "HASH_SHA512"
-);
+ "HASH_SHA224");
+ENUM_END(hash_algorithm_names, HASH_SHA224);
-ENUM(hash_algorithm_short_names, HASH_UNKNOWN, HASH_SHA512,
+ENUM_BEGIN(hash_algorithm_short_names, HASH_SHA1, HASH_SHA512,
+ "sha1",
+ "sha256",
+ "sha384",
+ "sha512");
+ENUM_NEXT(hash_algorithm_short_names, HASH_UNKNOWN, HASH_SHA224, HASH_SHA512,
"unknown",
"md2",
"md4",
"md5",
- "sha1",
- "sha224",
- "sha256",
- "sha384",
- "sha512"
-);
+ "sha224");
+ENUM_END(hash_algorithm_short_names, HASH_SHA224);
/*
* Described in header.
@@ -249,6 +251,28 @@ integrity_algorithm_t hasher_algorithm_to_integrity(hash_algorithm_t alg,
/*
* Described in header.
*/
+bool hasher_algorithm_for_ikev2(hash_algorithm_t alg)
+{
+ switch (alg)
+ {
+ case HASH_SHA1:
+ case HASH_SHA256:
+ case HASH_SHA384:
+ case HASH_SHA512:
+ return TRUE;
+ case HASH_UNKNOWN:
+ case HASH_MD2:
+ case HASH_MD4:
+ case HASH_MD5:
+ case HASH_SHA224:
+ break;
+ }
+ return FALSE;
+}
+
+/*
+ * Described in header.
+ */
int hasher_algorithm_to_oid(hash_algorithm_t alg)
{
int oid;
@@ -323,8 +347,56 @@ int hasher_signature_algorithm_to_oid(hash_algorithm_t alg, key_type_t key)
default:
return OID_UNKNOWN;
}
+ case KEY_BLISS:
+ switch (alg)
+ {
+ case HASH_SHA256:
+ return OID_BLISS_WITH_SHA256;
+ case HASH_SHA384:
+ return OID_BLISS_WITH_SHA384;
+ case HASH_SHA512:
+ return OID_BLISS_WITH_SHA512;
+ default:
+ return OID_UNKNOWN;
+ }
default:
return OID_UNKNOWN;
}
}
+/*
+ * Defined in header.
+ */
+hash_algorithm_t hasher_from_signature_scheme(signature_scheme_t scheme)
+{
+ switch (scheme)
+ {
+ case SIGN_UNKNOWN:
+ case SIGN_RSA_EMSA_PKCS1_NULL:
+ case SIGN_ECDSA_WITH_NULL:
+ break;
+ case SIGN_RSA_EMSA_PKCS1_MD5:
+ return HASH_MD5;
+ case SIGN_RSA_EMSA_PKCS1_SHA1:
+ case SIGN_ECDSA_WITH_SHA1_DER:
+ return HASH_SHA1;
+ case SIGN_RSA_EMSA_PKCS1_SHA224:
+ return HASH_SHA224;
+ case SIGN_RSA_EMSA_PKCS1_SHA256:
+ case SIGN_ECDSA_WITH_SHA256_DER:
+ case SIGN_ECDSA_256:
+ case SIGN_BLISS_WITH_SHA256:
+ return HASH_SHA256;
+ case SIGN_RSA_EMSA_PKCS1_SHA384:
+ case SIGN_ECDSA_WITH_SHA384_DER:
+ case SIGN_ECDSA_384:
+ case SIGN_BLISS_WITH_SHA384:
+ return HASH_SHA384;
+ case SIGN_RSA_EMSA_PKCS1_SHA512:
+ case SIGN_ECDSA_WITH_SHA512_DER:
+ case SIGN_ECDSA_521:
+ case SIGN_BLISS_WITH_SHA512:
+ return HASH_SHA512;
+ }
+ return HASH_UNKNOWN;
+}
diff --git a/src/libstrongswan/crypto/hashers/hasher.h b/src/libstrongswan/crypto/hashers/hasher.h
index 37ef0b6ab..772586308 100644
--- a/src/libstrongswan/crypto/hashers/hasher.h
+++ b/src/libstrongswan/crypto/hashers/hasher.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2012 Tobias Brunner
+ * Copyright (C) 2012-2015 Tobias Brunner
* Copyright (C) 2005-2006 Martin Willi
* Copyright (C) 2005 Jan Hutter
* Hochschule fuer Technik Rapperswil
@@ -32,19 +32,19 @@ typedef struct hasher_t hasher_t;
#include <credentials/keys/public_key.h>
/**
- * Algorithms to use for hashing.
+ * Hash algorithms as defined for IKEv2 by RFC 7427
*/
enum hash_algorithm_t {
- /** not specified hash function */
- HASH_UNKNOWN = 0,
- HASH_MD2 = 1,
- HASH_MD4 = 2,
- HASH_MD5 = 3,
- HASH_SHA1 = 4,
- HASH_SHA224 = 5,
- HASH_SHA256 = 6,
- HASH_SHA384 = 7,
- HASH_SHA512 = 8
+ HASH_SHA1 = 1,
+ HASH_SHA256 = 2,
+ HASH_SHA384 = 3,
+ HASH_SHA512 = 4,
+ /* use private use range for algorithms not defined/permitted by RFC 7427 */
+ HASH_UNKNOWN = 1024,
+ HASH_MD2 = 1025,
+ HASH_MD4 = 1026,
+ HASH_MD5 = 1027,
+ HASH_SHA224 = 1028,
};
#define HASH_SIZE_MD2 16
@@ -163,6 +163,14 @@ integrity_algorithm_t hasher_algorithm_to_integrity(hash_algorithm_t alg,
size_t length);
/**
+ * Check if the given algorithm may be used for IKEv2 signature authentication.
+ *
+ * @param alg hash algorithm
+ * @return TRUE if algorithm may be used, FALSE otherwise
+ */
+bool hasher_algorithm_for_ikev2(hash_algorithm_t alg);
+
+/**
* Conversion of hash algorithm into ASN.1 OID.
*
* @param alg hash algorithm
@@ -179,4 +187,12 @@ int hasher_algorithm_to_oid(hash_algorithm_t alg);
*/
int hasher_signature_algorithm_to_oid(hash_algorithm_t alg, key_type_t key);
+/**
+ * Determine the hash algorithm associated with a given signature scheme.
+ *
+ * @param scheme signature scheme
+ * @return hash algorithm (could be HASH_UNKNOWN)
+ */
+hash_algorithm_t hasher_from_signature_scheme(signature_scheme_t scheme);
+
#endif /** HASHER_H_ @}*/