pluto supports ECDSA authentication
authorAndreas Steffen <andreas.steffen@strongswan.org>
Fri, 12 Jun 2009 17:59:35 +0000 (19:59 +0200)
committerAndreas Steffen <andreas.steffen@strongswan.org>
Fri, 12 Jun 2009 17:59:49 +0000 (19:59 +0200)
25 files changed:
src/libstrongswan/credentials/keys/public_key.c
src/libstrongswan/credentials/keys/public_key.h
src/libstrongswan/plugins/agent/agent_private_key.c
src/libstrongswan/plugins/gcrypt/gcrypt_rsa_private_key.c
src/libstrongswan/plugins/gcrypt/gcrypt_rsa_public_key.c
src/libstrongswan/plugins/gmp/gmp_rsa_private_key.c
src/libstrongswan/plugins/gmp/gmp_rsa_public_key.c
src/libstrongswan/plugins/openssl/openssl_ec_private_key.c
src/libstrongswan/plugins/openssl/openssl_ec_public_key.c
src/libstrongswan/plugins/openssl/openssl_rsa_private_key.c
src/libstrongswan/plugins/openssl/openssl_rsa_public_key.c
src/pluto/connections.c
src/pluto/constants.c
src/pluto/constants.h
src/pluto/demux.c
src/pluto/ike_alg.c
src/pluto/ike_alg.h
src/pluto/ipsec_doi.c
src/pluto/kernel_alg.c
src/pluto/keys.c
src/pluto/spdb.c
src/starter/confread.c
src/starter/starterstroke.c
src/starter/starterwhack.c
src/whack/whack.c

index 6ae3050..c94c27f 100644 (file)
@@ -25,13 +25,13 @@ ENUM(key_type_names, KEY_RSA, KEY_DSA,
 
 ENUM(signature_scheme_names, SIGN_UNKNOWN, SIGN_ECDSA_521,
        "UNKNOWN",
-       "DEFAULT",
        "RSA_EMSA_PKCS1_NULL",
        "RSA_EMSA_PKCS1_MD5",
        "RSA_EMSA_PKCS1_SHA1",
        "RSA_EMSA_PKCS1_SHA256",
        "RSA_EMSA_PKCS1_SHA384",
        "RSA_EMSA_PKCS1_SHA512",
+       "ECDSA_WITH_NULL",
        "ECDSA_WITH_SHA1",
        "ECDSA-256",
        "ECDSA-384",
index 473a432..c58531b 100644 (file)
@@ -60,8 +60,6 @@ extern enum_name_t *key_type_names;
 enum signature_scheme_t {
        /** Unknown signature scheme                                       */
        SIGN_UNKNOWN,
-       /** Default scheme of the underlying crypto system                 */
-       SIGN_DEFAULT,
        /** EMSA-PKCS1_v1.5 signature over digest without digestInfo       */
        SIGN_RSA_EMSA_PKCS1_NULL,
        /** EMSA-PKCS1_v1.5 signature as in PKCS#1 using RSA and MD5       */
@@ -74,6 +72,8 @@ enum signature_scheme_t {
        SIGN_RSA_EMSA_PKCS1_SHA384,
        /** EMSA-PKCS1_v1.5 signature as in PKCS#1 using RSA and SHA-512   */
        SIGN_RSA_EMSA_PKCS1_SHA512,
+       /** ECDSA over precomputed digest                                  */
+       SIGN_ECDSA_WITH_NULL,
        /** ECDSA with SHA-1                                               */
        SIGN_ECDSA_WITH_SHA1,
        /** ECDSA on the P-256 curve with SHA-256 as in RFC 4754           */
index 97ca9dc..ffdc6d7 100644 (file)
@@ -269,7 +269,7 @@ static bool sign(private_agent_private_key_t *this, signature_scheme_t scheme,
        char buf[2048];
        chunk_t blob = chunk_from_buf(buf);
        
-       if (scheme != SIGN_DEFAULT && scheme != SIGN_RSA_EMSA_PKCS1_SHA1)
+       if (scheme != SIGN_RSA_EMSA_PKCS1_SHA1)
        {
                DBG1("signature scheme %N not supported by ssh-agent",
                         signature_scheme_names, scheme);
index 4ee431a..d622a1f 100644 (file)
@@ -144,8 +144,6 @@ static bool sign(private_gcrypt_rsa_private_key_t *this, signature_scheme_t sche
 {
        switch (scheme)
        {
-               case SIGN_DEFAULT:
-                       /* default is EMSA-PKCS1 using SHA1 */
                case SIGN_RSA_EMSA_PKCS1_SHA1:
                        return sign_pkcs1(this, HASH_SHA1, "sha1", data, sig);
                case SIGN_RSA_EMSA_PKCS1_SHA256:
index bdb5d7f..ad02d3a 100644 (file)
@@ -138,8 +138,6 @@ static bool verify(private_gcrypt_rsa_public_key_t *this,
                        return verify_pkcs1(this, HASH_SHA384, "sha384", data, signature);
                case SIGN_RSA_EMSA_PKCS1_SHA512:
                        return verify_pkcs1(this, HASH_SHA512, "sha512", data, signature);
-               case SIGN_DEFAULT:
-                       /* parsing hash OID currently not supported by gcrypt, fall */
                default:
                        DBG1("signature scheme %N not supported in RSA",
                                 signature_scheme_names, scheme);
index b395a80..dec4e46 100644 (file)
@@ -292,7 +292,6 @@ static bool sign(private_gmp_rsa_private_key_t *this, signature_scheme_t scheme,
        {
                case SIGN_RSA_EMSA_PKCS1_NULL:
                        return build_emsa_pkcs1_signature(this, HASH_UNKNOWN, data, signature);
-               case SIGN_DEFAULT:
                case SIGN_RSA_EMSA_PKCS1_SHA1:
                        return build_emsa_pkcs1_signature(this, HASH_SHA1, data, signature);
                case SIGN_RSA_EMSA_PKCS1_SHA256:
index 725e1f9..e241dba 100644 (file)
@@ -299,7 +299,6 @@ static bool verify(private_gmp_rsa_public_key_t *this, signature_scheme_t scheme
 {
        switch (scheme)
        {
-               case SIGN_DEFAULT:
                case SIGN_RSA_EMSA_PKCS1_NULL:
                        return verify_emsa_pkcs1_signature(this, HASH_UNKNOWN, data, signature);
                case SIGN_RSA_EMSA_PKCS1_MD5:
index de9733a..d6b442a 100644 (file)
@@ -128,36 +128,18 @@ static bool sig2chunk(const EC_GROUP *group, ECDSA_SIG *sig, chunk_t *chunk)
  * Build the signature
  */
 static bool build_signature(private_openssl_ec_private_key_t *this,
-                                                       int hash_type, chunk_t data, chunk_t *signature)
+                                                       chunk_t hash, chunk_t *signature)
 {
-       chunk_t hash = chunk_empty;
-       ECDSA_SIG *sig;
-       bool ret = FALSE;
-       
-       if (!openssl_hash_chunk(hash_type, data, &hash))
-       {
-               return FALSE;
-       }
-       
-       sig = ECDSA_do_sign(hash.ptr, hash.len, this->ec);
+       ECDSA_SIG *sig = ECDSA_do_sign(hash.ptr, hash.len, this->ec);
+       bool success;
+
        if (!sig)
        {
-               goto error;
-       }
-       
-       if (!sig2chunk(EC_KEY_get0_group(this->ec), sig, signature))
-       {
-               goto error;
-       }
-       
-       ret = TRUE;
-error:
-       chunk_free(&hash);
-       if (sig)
-       {
-               ECDSA_SIG_free(sig);
+               return FALSE;
        }
-       return ret;
+       success = sig2chunk(EC_KEY_get0_group(this->ec), sig, signature);
+       ECDSA_SIG_free(sig);
+       return success;
 }
 
 /**
@@ -174,36 +156,51 @@ static key_type_t get_type(private_openssl_ec_private_key_t *this)
 static bool sign(private_openssl_ec_private_key_t *this, signature_scheme_t scheme, 
                                 chunk_t data, chunk_t *signature)
 {
-       EC_GROUP *req_group;
-       const EC_GROUP *my_group;
-       int hash, curve;
-       
-       if (!lookup_scheme(scheme, &hash, &curve))
-       {
-               DBG1("signature scheme %N not supported in EC",
-                                signature_scheme_names, scheme);
-               return FALSE;
-       }
-       
-       req_group = EC_GROUP_new_by_curve_name(curve);
-       if (!req_group)
+       bool success;
+
+       if (scheme == SIGN_ECDSA_WITH_NULL)
        {
-               DBG1("signature scheme %N not supported in EC (required curve not supported)",
-                                signature_scheme_names, scheme);
-               return FALSE;
+               success = build_signature(this, data, signature);
        }
-       
-       my_group = EC_KEY_get0_group(this->ec);
-       if (EC_GROUP_cmp(my_group, req_group, NULL) != 0)
+       else
        {
-               DBG1("signature scheme %N not supported by private key",
-                                signature_scheme_names, scheme);
-               return FALSE;
-       }
+               EC_GROUP *req_group;
+               const EC_GROUP *my_group;
+               chunk_t hash = chunk_empty;
+               int hash_type, curve;
+
+               if (!lookup_scheme(scheme, &hash_type, &curve))
+               {
+                       DBG1("signature scheme %N not supported in EC",
+                                        signature_scheme_names, scheme);
+                       return FALSE;
+               }
        
-       EC_GROUP_free(req_group);
+               req_group = EC_GROUP_new_by_curve_name(curve);
+               if (!req_group)
+               {
+                       DBG1("signature scheme %N not supported in EC (required curve not supported)",
+                                        signature_scheme_names, scheme);
+                       return FALSE;
+               }
        
-       return build_signature(this, hash, data, signature);
+               my_group = EC_KEY_get0_group(this->ec);
+               if (EC_GROUP_cmp(my_group, req_group, NULL) != 0)
+               {
+                       DBG1("signature scheme %N not supported by private key",
+                                        signature_scheme_names, scheme);
+                       return FALSE;
+               }
+               EC_GROUP_free(req_group);
+
+               if (!openssl_hash_chunk(hash_type, data, &hash))
+               {
+                       return FALSE;
+               }
+               success = build_signature(this, hash, signature);
+               chunk_free(&hash);
+       }       
+       return success;
 }
 
 /**
index 780e675..635a106 100644 (file)
@@ -73,9 +73,16 @@ static bool verify_signature(private_openssl_ec_public_key_t *this,
        ECDSA_SIG *sig;
        bool valid = FALSE;
        
-       if (!openssl_hash_chunk(hash_type, data, &hash))
+       if (hash_type == NID_undef)
        {
-               return FALSE;
+               hash = data;
+       }
+       else
+       {
+               if (!openssl_hash_chunk(hash_type, data, &hash))
+               {
+                       return FALSE;
+               }
        }
        
        sig = ECDSA_SIG_new();
@@ -88,7 +95,6 @@ static bool verify_signature(private_openssl_ec_public_key_t *this,
        {
                goto error;
        }
-       
        valid = (ECDSA_do_verify(hash.ptr, hash.len, sig, this->ec) == 1);
        
 error:
@@ -96,7 +102,10 @@ error:
        {
                ECDSA_SIG_free(sig);
        }
-       chunk_free(&hash);
+       if (hash_type != NID_undef)
+       {
+               chunk_free(&hash);
+       }
        return valid;
 }
 
@@ -158,6 +167,8 @@ static bool verify(private_openssl_ec_public_key_t *this, signature_scheme_t sch
 {
        switch (scheme)
        {
+               case SIGN_ECDSA_WITH_NULL:
+                       return verify_signature(this, NID_undef, data, signature);
                case SIGN_ECDSA_WITH_SHA1:
                        return verify_default_signature(this, data, signature);
                case SIGN_ECDSA_256:
index 6ed999f..6959130 100644 (file)
@@ -162,7 +162,6 @@ static bool sign(private_openssl_rsa_private_key_t *this, signature_scheme_t sch
        {
                case SIGN_RSA_EMSA_PKCS1_NULL:
                        return build_emsa_pkcs1_signature(this, NID_undef, data, signature);
-               case SIGN_DEFAULT:
                case SIGN_RSA_EMSA_PKCS1_SHA1:
                        return build_emsa_pkcs1_signature(this, NID_sha1, data, signature);
                case SIGN_RSA_EMSA_PKCS1_SHA256:
index f891802..89912f2 100644 (file)
@@ -139,7 +139,6 @@ static bool verify(private_openssl_rsa_public_key_t *this, signature_scheme_t sc
 {
        switch (scheme)
        {
-               case SIGN_DEFAULT:
                case SIGN_RSA_EMSA_PKCS1_NULL:
                        return verify_emsa_pkcs1_signature(this, NID_undef, data, signature);
                case SIGN_RSA_EMSA_PKCS1_SHA1:
index bdfdc10..2d62c81 100644 (file)
@@ -997,7 +997,7 @@ add_connection(const whack_message_t *wm)
                                if (c->alg_info_esp)
                                        alg_info_snprint(buf, sizeof(buf)
                                                        ,(struct alg_info *)c->alg_info_esp);
-                               DBG_log("esp string values: %s", buf);
+                               DBG_log("esp proposal: %s", buf);
                        )
                        if (c->alg_info_esp)
                        {
@@ -1024,7 +1024,7 @@ add_connection(const whack_message_t *wm)
                                if (c->alg_info_ike)
                                        alg_info_snprint(buf, sizeof(buf)
                                                        , (struct alg_info *)c->alg_info_ike);
-                               DBG_log("ike string values: %s", buf);
+                               DBG_log("ike proposal: %s", buf);
                        )
                        if (c->alg_info_ike)
                        {
@@ -3301,19 +3301,25 @@ refine_host_connection(const struct state *st, const struct id *peer_id
                 * we just used it to decode the current message!
                 */
                if (psk == NULL)
+               {
                        return NULL;        /* cannot determine PSK! */
+               }
                break;
        case XAUTHInitPreShared:
        case XAUTHRespPreShared:
                auth_policy = POLICY_XAUTH_PSK;
                psk = get_preshared_secret(c);
                if (psk == NULL)
+               {
                        return NULL;        /* cannot determine PSK! */
+               }
                break;
        case OAKLEY_RSA_SIG:
-               auth_policy = POLICY_RSASIG;
+       case OAKLEY_ECDSA_256:
+       case OAKLEY_ECDSA_384:
+       case OAKLEY_ECDSA_512:
+               auth_policy = POLICY_PUBKEY;
                break;
-       case XAUTHInitRSA:
        case XAUTHRespRSA:
                auth_policy = POLICY_XAUTH_RSASIG;
                break;
@@ -3397,6 +3403,9 @@ refine_host_connection(const struct state *st, const struct id *peer_id
                                break;
 
                        case OAKLEY_RSA_SIG:
+                       case OAKLEY_ECDSA_256:
+                       case OAKLEY_ECDSA_384:
+                       case OAKLEY_ECDSA_512:
                        case XAUTHInitRSA:
                        case XAUTHRespRSA:
                                /*
index ae58d90..f96134b 100644 (file)
@@ -472,7 +472,7 @@ ENUM(cert_policy_names, CERT_ALWAYS_SEND, CERT_NEVER_SEND,
 
 const char *const sa_policy_bit_names[] = {
        "PSK",
-       "RSASIG",
+       "PUBKEY",
        "ENCRYPT",
        "AUTHENTICATE",
        "COMPRESS",
@@ -495,7 +495,6 @@ const char *const sa_policy_bit_names[] = {
        "DONTREAUTH",
        "BEET",
        "MOBIKE",
-       "ECDSA",
        "PROXY",
        NULL
 };
@@ -849,13 +848,17 @@ enum_names oakley_hash_names =
 /* Oakley Authentication Method attribute */
 
 static const char *const oakley_auth_name1[] = {
-       "OAKLEY_PRESHARED_KEY",
-       "OAKLEY_DSS_SIG",
-       "OAKLEY_RSA_SIG",
-       "OAKLEY_RSA_ENC",
-       "OAKLEY_RSA_ENC_REV",
-       "OAKLEY_ELGAMAL_ENC",
-       "OAKLEY_ELGAMAL_ENC_REV",
+       "PRESHARED_KEY",
+       "DSS_SIG",
+       "RSA_SIG",
+       "RSA_ENC",
+       "RSA_ENC_REV",
+       "ELGAMAL_ENC",
+       "ELGAMAL_ENC_REV",
+       "ECDSA_SIG",
+       "ECDSA_256_SIG",
+       "ECDSA_384_SIG",
+       "ECDSA_512_SIG",   
 };
 
 static const char *const oakley_auth_name2[] = {
@@ -879,7 +882,7 @@ static const char *const oakley_auth_name3[] = {
 };
 
 static enum_names oakley_auth_names1 =
-       { OAKLEY_PRESHARED_KEY, OAKLEY_ELGAMAL_ENC_REV
+       { OAKLEY_PRESHARED_KEY, OAKLEY_ECDSA_512
                , oakley_auth_name1, NULL };
 
 static enum_names oakley_auth_names2 =
@@ -1079,8 +1082,7 @@ aftoinfo(int af)
        }
 }
 
-bool
-subnetisnone(const ip_subnet *sn)
+bool subnetisnone(const ip_subnet *sn)
 {
        ip_address base;
 
@@ -1174,8 +1176,7 @@ const char *const natt_type_bitnames[] = {
 
 /* look up enum names in an enum_names */
 
-const char *
-enum_name(enum_names *ed, unsigned long val)
+const char* enum_name(enum_names *ed, unsigned long val)
 {
        enum_names  *p;
 
@@ -1237,8 +1238,7 @@ enum_search(enum_names *ed, const char *str)
  * Result may be in STATIC buffer!
  * Note: prettypolicy depends on internal details.
  */
-const char *
-bitnamesof(const char *const table[], lset_t val)
+const char* bitnamesof(const char *const table[], lset_t val)
 {
        char *p = bitnamesbuf;
        lset_t bit;
@@ -1285,8 +1285,7 @@ bitnamesof(const char *const table[], lset_t val)
 /* print a policy: like bitnamesof, but it also does the non-bitfields.
  * Suppress the shunt and fail fields if 0.
  */
-const char *
-prettypolicy(lset_t policy)
+const char* prettypolicy(lset_t policy)
 {
        const char *bn = bitnamesof(sa_policy_bit_names
                , policy & ~(POLICY_SHUNT_MASK | POLICY_FAIL_MASK));
@@ -1319,8 +1318,7 @@ prettypolicy(lset_t policy)
 
 /* test a set by seeing if all bits have names */
 
-bool
-testset(const char *const table[], lset_t val)
+bool testset(const char *const table[], lset_t val)
 {
        lset_t bit;
        const char *const *tp;
@@ -1353,8 +1351,7 @@ const char *sparse_name(sparse_names sd, unsigned long val)
 /* find or construct a string to describe an sparse value
  * Result may be in STATIC buffer!
  */
-const char *
-sparse_val_show(sparse_names sd, unsigned long val)
+const char* sparse_val_show(sparse_names sd, unsigned long val)
 {
        const char *p = sparse_name(sd, val);
 
index 7fdf5d6..84c7b1d 100644 (file)
@@ -724,10 +724,10 @@ extern const char *prettypolicy(lset_t policy);
 
 /* ISAKMP auth techniques (none means never negotiate) */
 #define POLICY_PSK           LELEM(0)
-#define POLICY_RSASIG        LELEM(1)
+#define POLICY_PUBKEY        LELEM(1)
 
 #define POLICY_ISAKMP_SHIFT     0       /* log2(POLICY_PSK) */
-#define POLICY_ID_AUTH_MASK     (POLICY_PSK | POLICY_RSASIG | POLICY_XAUTH_PSK | POLICY_XAUTH_RSASIG)
+#define POLICY_ID_AUTH_MASK     (POLICY_PSK | POLICY_PUBKEY | POLICY_XAUTH_PSK | POLICY_XAUTH_RSASIG)
 #define POLICY_ISAKMP_MASK      POLICY_ID_AUTH_MASK     /* all so far */
 
 /* Quick Mode (IPSEC) attributes */
@@ -776,8 +776,7 @@ extern const char *prettypolicy(lset_t policy);
 #define POLICY_BEET             LELEM(22)       /* bound end2end tunnel, IKEv2 */
 #define POLICY_MOBIKE           LELEM(23)       /* enable MOBIKE for IKEv2  */
 #define POLICY_FORCE_ENCAP      LELEM(24)       /* force UDP encapsulation (IKEv2)  */
-#define POLICY_ECDSASIG         LELEM(25)       /* ECDSA signature (IKEv2) */
-#define POLICY_PROXY            LELEM(26)       /* proxy transport mode (MIPv6) */
+#define POLICY_PROXY            LELEM(25)       /* proxy transport mode (MIPv6) */
 
 /* Any IPsec policy?  If not, a connection description
  * is only for ISAKMP SA, not IPSEC SA.  (A pun, I admit.)
@@ -979,8 +978,12 @@ extern enum_names oakley_auth_names;
 #define OAKLEY_RSA_ENC_REV         5
 #define OAKLEY_ELGAMAL_ENC         6
 #define OAKLEY_ELGAMAL_ENC_REV     7
+#define OAKLEY_ECDSA_SIG           8
+#define OAKLEY_ECDSA_256           9
+#define OAKLEY_ECDSA_384          10
+#define OAKLEY_ECDSA_512          11
 
-#define OAKLEY_AUTH_ROOF           8    /* roof on auth values THAT WE SUPPORT */
+#define OAKLEY_AUTH_ROOF          12    /* roof on auth values THAT WE SUPPORT */
 
 #define HybridInitRSA                   64221
 #define HybridRespRSA                   64222
index 53b44a0..83bcffb 100644 (file)
@@ -188,7 +188,9 @@ struct state_microcode {
  */
 #define SMF_ALL_AUTH    LRANGE(0, OAKLEY_AUTH_ROOF-1)
 #define SMF_PSK_AUTH    LELEM(OAKLEY_PRESHARED_KEY)
-#define SMF_DS_AUTH     (LELEM(OAKLEY_DSS_SIG) | LELEM(OAKLEY_RSA_SIG))
+#define SMF_DS_AUTH     (LELEM(OAKLEY_DSS_SIG)   | LELEM(OAKLEY_RSA_SIG)   | \
+                                                LELEM(OAKLEY_ECDSA_SIG) | LELEM(OAKLEY_ECDSA_256) | \
+                                                LELEM(OAKLEY_ECDSA_384) | LELEM(OAKLEY_ECDSA_512))
 #define SMF_PKE_AUTH    (LELEM(OAKLEY_RSA_ENC) | LELEM(OAKLEY_ELGAMAL_ENC))
 #define SMF_RPKE_AUTH   (LELEM(OAKLEY_RSA_ENC_REV) | LELEM(OAKLEY_ELGAMAL_ENC_REV))
 
index a03612b..17f9991 100644 (file)
@@ -30,9 +30,9 @@
 #include "constants.h"
 #include "defs.h"
 #include "crypto.h"
-
 #include "state.h"
 #include "packet.h"
+#include "keys.h"
 #include "log.h"
 #include "whack.h"
 #include "spdb.h"
@@ -141,8 +141,9 @@ const struct dh_desc *ike_alg_pfsgroup(struct connection *c, lset_t policy)
 /**
  * Create an OAKLEY proposal based on alg_info and policy
  */
-struct db_context *ike_alg_db_new(struct alg_info_ike *ai , lset_t policy)
+struct db_context *ike_alg_db_new(struct connection *c, lset_t policy)
 {
+       struct alg_info_ike *ai = c->alg_info_ike;
        struct db_context *db_ctx = NULL;
        struct ike_info *ike_info;
        struct encrypt_desc *enc_desc;
@@ -189,14 +190,47 @@ struct db_context *ike_alg_db_new(struct alg_info_ike *ai , lset_t policy)
                }
                enc_desc = ike_alg_get_crypter(ealg);
 
-               if (policy & POLICY_RSASIG)
+               if (policy & POLICY_PUBKEY)
                {
+                       int auth_method = 0;
+                       private_key_t *key = get_private_key(c);
+
+                       if (key == NULL)
+                       {
+                               continue;
+                       }
+                       switch (key->get_type(key))
+                       {
+                               case KEY_RSA:
+                                       auth_method = OAKLEY_RSA_SIG;
+                                       break;
+                               case KEY_ECDSA:
+                                       switch (key->get_keysize(key))
+                                       {
+                                               case 32:
+                                                       auth_method = OAKLEY_ECDSA_256;
+                                                       break;
+                                               case 48:
+                                                       auth_method = OAKLEY_ECDSA_384;
+                                                       break;
+                                               case 66:
+                                                       auth_method = OAKLEY_ECDSA_512;
+                                                       break;
+                                               default:
+                                                       continue;
+                                       }
+                                       break;
+                               default:
+                                       continue;
+                       }
                        db_trans_add(db_ctx, KEY_IKE);
                        db_attr_add_values(db_ctx, OAKLEY_ENCRYPTION_ALGORITHM, ealg);
                        db_attr_add_values(db_ctx, OAKLEY_HASH_ALGORITHM, halg);
                        if (eklen)
+                       {
                                db_attr_add_values(db_ctx, OAKLEY_KEY_LENGTH, eklen);
-                       db_attr_add_values(db_ctx, OAKLEY_AUTHENTICATION_METHOD, OAKLEY_RSA_SIG);
+                       }
+                       db_attr_add_values(db_ctx, OAKLEY_AUTHENTICATION_METHOD, auth_method);
                        db_attr_add_values(db_ctx, OAKLEY_GROUP_DESCRIPTION, modp);
                }
 
@@ -206,7 +240,9 @@ struct db_context *ike_alg_db_new(struct alg_info_ike *ai , lset_t policy)
                        db_attr_add_values(db_ctx, OAKLEY_ENCRYPTION_ALGORITHM, ealg);
                        db_attr_add_values(db_ctx, OAKLEY_HASH_ALGORITHM, halg);
                        if (eklen)
+                       {
                                db_attr_add_values(db_ctx, OAKLEY_KEY_LENGTH, eklen);
+                       }
                        db_attr_add_values(db_ctx, OAKLEY_AUTHENTICATION_METHOD, OAKLEY_PRESHARED_KEY);
                        db_attr_add_values(db_ctx, OAKLEY_GROUP_DESCRIPTION, modp);
                }
@@ -217,7 +253,9 @@ struct db_context *ike_alg_db_new(struct alg_info_ike *ai , lset_t policy)
                        db_attr_add_values(db_ctx, OAKLEY_ENCRYPTION_ALGORITHM, ealg);
                        db_attr_add_values(db_ctx, OAKLEY_HASH_ALGORITHM, halg);
                        if (eklen)
+                       {
                                db_attr_add_values(db_ctx, OAKLEY_KEY_LENGTH, eklen);
+                       }
                        db_attr_add_values(db_ctx, OAKLEY_AUTHENTICATION_METHOD
                                , is_xauth_server ? XAUTHRespRSA : XAUTHInitRSA);
                        db_attr_add_values(db_ctx, OAKLEY_GROUP_DESCRIPTION, modp);
@@ -229,7 +267,9 @@ struct db_context *ike_alg_db_new(struct alg_info_ike *ai , lset_t policy)
                        db_attr_add_values(db_ctx, OAKLEY_ENCRYPTION_ALGORITHM, ealg);
                        db_attr_add_values(db_ctx, OAKLEY_HASH_ALGORITHM, halg);
                        if (eklen)
+                       {
                                db_attr_add_values(db_ctx, OAKLEY_KEY_LENGTH, eklen);
+                       }
                        db_attr_add_values(db_ctx, OAKLEY_AUTHENTICATION_METHOD
                                , is_xauth_server ? XAUTHRespPreShared : XAUTHInitPreShared);
                        db_attr_add_values(db_ctx, OAKLEY_GROUP_DESCRIPTION, modp);
index c4a03cf..458d14c 100644 (file)
@@ -62,7 +62,7 @@ extern struct hash_desc *ike_alg_get_hasher(u_int alg);
 extern struct encrypt_desc *ike_alg_get_crypter(u_int alg);
 extern struct dh_desc *ike_alg_get_dh_group(u_int alg);
 extern const struct dh_desc* ike_alg_pfsgroup(struct connection *c, lset_t policy);
-extern struct db_context * ike_alg_db_new(struct alg_info_ike *ai, lset_t policy);
+extern struct db_context * ike_alg_db_new(struct connection *c, lset_t policy);
 extern void ike_alg_list(void);
 extern void ike_alg_show_connection(struct connection *c, const char *instance);
 extern bool ike_alg_ok_final(u_int ealg, u_int key_len, u_int aalg, u_int group
index 2a9d9d4..286b7fb 100644 (file)
@@ -1208,6 +1208,9 @@ static bool generate_skeyids_iv(struct state *st)
                        break;
 
                case OAKLEY_RSA_SIG:
+               case OAKLEY_ECDSA_256:
+               case OAKLEY_ECDSA_384:
+               case OAKLEY_ECDSA_512:
                case XAUTHInitRSA:
                case XAUTHRespRSA:
                        if (!skeyid_digisig(st))
@@ -1354,7 +1357,7 @@ static bool generate_skeyids_iv(struct state *st)
  * If hashus argument is TRUE, we're generating a hash for our end.
  * See RFC2409 IKE 5.
  */
- static size_t main_mode_hash(struct state *st, u_char *hash_val, bool hashi,
+ static void main_mode_hash(struct state *st, chunk_t *hash, bool hashi,
                                                         const pb_stream *idpl)
 {
        chunk_t icookie = { st->st_icookie, COOKIE_SIZE };
@@ -1365,9 +1368,21 @@ static bool generate_skeyids_iv(struct state *st)
                                                pbs_offset(idpl) - sizeof(struct isakmp_generic) };
        pseudo_random_function_t prf_alg;
        prf_t *prf;
-       size_t prf_block_size;
 
-       prf_alg = oakley_to_prf(st->st_oakley.hash);
+       switch (st->st_oakley.auth)
+       {
+               case OAKLEY_ECDSA_256:
+                       prf_alg = PRF_HMAC_SHA2_256;
+                       break;
+               case OAKLEY_ECDSA_384:
+                       prf_alg = PRF_HMAC_SHA2_384;
+                       break;
+               case OAKLEY_ECDSA_512:
+                       prf_alg = PRF_HMAC_SHA2_512;
+                       break;
+               default:
+                       prf_alg = oakley_to_prf(st->st_oakley.hash);
+       }
        prf = lib->crypto->create_prf(lib->crypto, prf_alg);
        prf->set_key(prf, st->st_skeyid);
 
@@ -1396,11 +1411,9 @@ static bool generate_skeyids_iv(struct state *st)
         * we use the bytes as they appear on the wire to avoid
         * "spelling problems".
         */
-       prf->get_bytes(prf, id_body, hash_val);
-       prf_block_size = prf->get_block_size(prf);
+       prf->get_bytes(prf, id_body, hash->ptr);
+       hash->len = prf->get_block_size(prf);
        prf->destroy(prf);
-
-       return prf_block_size;
 }
 
 /* Create a public key signature of a hash.
@@ -1408,30 +1421,27 @@ static bool generate_skeyids_iv(struct state *st)
  * Use PKCS#1 version 1.5 encryption of hash (called
  * RSAES-PKCS1-V1_5) in PKCS#2.
  */
-static size_t sign_hash(struct connection *c, u_char sig_val[RSA_MAX_OCTETS],
-                                               u_char *hash_val, size_t hash_len)
+static size_t sign_hash(signature_scheme_t scheme, struct connection *c,
+                                               u_char sig_val[RSA_MAX_OCTETS], chunk_t hash)
 {
        size_t sz = 0;
        smartcard_t *sc = c->spd.this.sc;
 
        if (sc == NULL)             /* no smartcard */
        {
-               chunk_t hash, sig;
+               chunk_t sig;
                private_key_t *private = get_private_key(c);
 
                if (private == NULL)
                {
                        return 0;   /* failure: no key to use */
                }
-               sz = private->get_keysize(private);
-               passert(RSA_MIN_OCTETS <= sz && 4 + hash_len < sz && sz <= RSA_MAX_OCTETS);
-               hash = chunk_create(hash_val, hash_len);
-               sig  = chunk_create(sig_val, sz);
-               if (!private->sign(private, SIGN_RSA_EMSA_PKCS1_NULL, hash, &sig))
+               if (!private->sign(private, scheme, hash, &sig))
                {
                        return 0;
                }
-               memcpy(sig_val, sig.ptr, sz);
+               memcpy(sig_val, sig.ptr, sig.len);
+               sz = sig.len;
                free(sig.ptr);
        }
        else if (sc->valid) /* if valid pin then sign hash on the smartcard */
@@ -1457,7 +1467,7 @@ static size_t sign_hash(struct connection *c, u_char sig_val[RSA_MAX_OCTETS],
                        DBG_log("signing hash with RSA key from smartcard (slot: %d, id: %s)"
                                , (int)sc->slot, sc->id)
                )
-               sz = scx_sign_hash(sc, hash_val, hash_len, sig_val, sz) ? sz : 0;
+               sz = scx_sign_hash(sc, hash.ptr, hash.len, sig_val, sz) ? sz : 0;
                if (!pkcs11_keep_state)
                        scx_release_context(sc);
                unlock_certs_and_keys("sign_hash");
@@ -1485,14 +1495,18 @@ struct tac_state {
 static bool take_a_crack(struct tac_state *s, pubkey_t *kr)
 {
        public_key_t *pub_key = kr->public_key;
-       identification_t *keyid = pub_key->get_id(pub_key, ID_PUBKEY_SHA1);
+       identification_t *keyid = pub_key->get_id(pub_key, ID_PUBKEY_INFO_SHA1);
+       signature_scheme_t scheme;
 
+       scheme = (s->st->st_oakley.auth == OAKLEY_RSA_SIG) ?
+                                       SIGN_RSA_EMSA_PKCS1_NULL : SIGN_ECDSA_WITH_NULL;
        s->tried_cnt++;
 
-       if (pub_key->verify(pub_key, SIGN_RSA_EMSA_PKCS1_NULL, s->hash, s->sig))
+       if (pub_key->verify(pub_key, scheme, s->hash, s->sig))
        {
                DBG(DBG_CRYPT | DBG_CONTROL,
-                       DBG_log("signature check passed with keyid %Y", keyid)
+                       DBG_log("%s check passed with keyid %Y",
+                                       enum_show(&oakley_auth_names, s->st->st_oakley.auth), keyid)
                )
                unreference_key(&s->st->st_peer_pubkey);
                s->st->st_peer_pubkey = reference_key(kr);
@@ -1501,25 +1515,26 @@ static bool take_a_crack(struct tac_state *s, pubkey_t *kr)
        else
        {
                DBG(DBG_CRYPT,
-                       DBG_log("signature check failed with keyid %Y", keyid)
+                       DBG_log("%s check failed with keyid %Y",
+                                       enum_show(&oakley_auth_names, s->st->st_oakley.auth), keyid)
                )
                return FALSE;
        }
 }
 
-static stf_status RSA_check_signature(const struct id* peer, struct state *st,
-                                                                         u_char hash_val[MAX_DIGEST_LEN],
-                                                                         size_t hash_len, const pb_stream *sig_pbs,
+static stf_status check_signature(key_type_t key_type, const struct id* peer,
+                                                                 struct state *st, chunk_t hash,
+                                                                 const pb_stream *sig_pbs,
 #ifdef USE_KEYRR
-                                                                         const pubkey_list_t *keys_from_dns,
+                                                                 const pubkey_list_t *keys_from_dns,
 #endif /* USE_KEYRR */
-                                                                         const struct gw_info *gateways_from_dns)
+                                                                 const struct gw_info *gateways_from_dns)
 {
        const struct connection *c = st->st_connection;
        struct tac_state s;
 
        s.st = st;
-       s.hash = chunk_create(hash_val, hash_len);
+       s.hash = hash;
        s.sig  = chunk_create(sig_pbs->cur, pbs_left(sig_pbs));
        s.tried_cnt = 0;
 
@@ -1550,7 +1565,7 @@ static stf_status RSA_check_signature(const struct id* peer, struct state *st,
                        pubkey_t *key = p->key;
                        key_type_t type = key->public_key->get_type(key->public_key);
 
-                       if (type == KEY_RSA && same_id(peer, &key->id))
+                       if (type == key_type && same_id(peer, &key->id))
                        {
                                time_t now = time(NULL);
 
@@ -2775,6 +2790,23 @@ static void compute_keymats(struct state *st)
                compute_proto_keymat(st, PROTO_IPSEC_ESP, &st->st_esp);
 }
 
+static bool uses_pubkey_auth(int auth)
+{
+       switch (auth)
+       {
+               case OAKLEY_RSA_SIG:
+               case OAKLEY_ECDSA_SIG:
+               case OAKLEY_ECDSA_256:
+               case OAKLEY_ECDSA_384:
+               case OAKLEY_ECDSA_512:
+               case XAUTHInitRSA:
+               case XAUTHRespRSA:
+                       return TRUE;
+               default:
+                       return FALSE;
+       }
+}
+
 /* State Transition Functions.
  *
  * The definition of state_microcode_table in demux.c is a good
@@ -3170,11 +3202,9 @@ stf_status main_inI2_outR2(struct msg_digest *md)
        struct state *const st = md->st;
        pb_stream *keyex_pbs = &md->chain[ISAKMP_NEXT_KE]->pbs;
 
-       /* send CR if auth is RSA and no preloaded RSA public key exists*/
-       bool RSA_auth = st->st_oakley.auth == OAKLEY_RSA_SIG
-                                || st->st_oakley.auth == XAUTHInitRSA
-                                || st->st_oakley.auth == XAUTHRespRSA;
-       bool send_cr = !no_cr_send && RSA_auth && !has_preloaded_public_key(st);
+       /* send CR if auth is RSA or ECDSA and no preloaded public key exists*/
+       bool pubkey_auth = uses_pubkey_auth(st->st_oakley.auth);
+       bool send_cr = !no_cr_send && pubkey_auth && !has_preloaded_public_key(st);
 
        u_int8_t np = ISAKMP_NEXT_NONE;
 
@@ -3314,12 +3344,9 @@ stf_status main_inR2_outI3(struct msg_digest *md)
        certpolicy_t cert_policy = st->st_connection->spd.this.sendcert;
        cert_t mycert = st->st_connection->spd.this.cert;
        bool requested, send_cert, send_cr;
+       bool pubkey_auth = uses_pubkey_auth(st->st_oakley.auth);
 
-       bool RSA_auth = st->st_oakley.auth == OAKLEY_RSA_SIG
-                                || st->st_oakley.auth == XAUTHInitRSA
-                                || st->st_oakley.auth == XAUTHRespRSA;
-
-       int auth_payload = RSA_auth ? ISAKMP_NEXT_SIG : ISAKMP_NEXT_HASH;
+       int auth_payload = pubkey_auth ? ISAKMP_NEXT_SIG : ISAKMP_NEXT_HASH;
 
        /* KE in */
        RETURN_STF_FAILURE(accept_KE(&st->st_gr, "Gr", st->st_oakley.group, keyex_pbs));
@@ -3342,7 +3369,7 @@ stf_status main_inR2_outI3(struct msg_digest *md)
         */
        requested = cert_policy == CERT_SEND_IF_ASKED
                                && st->st_connection->got_certrequest;
-       send_cert = RSA_auth && mycert.type != CERT_NONE
+       send_cert = pubkey_auth && mycert.type != CERT_NONE
                                && (cert_policy == CERT_ALWAYS_SEND || requested);
 
        /* send certificate request if we don't have a preloaded RSA public key */
@@ -3385,7 +3412,7 @@ stf_status main_inR2_outI3(struct msg_digest *md)
        }
 
        /* CERT out */
-       if (RSA_auth)
+       if (pubkey_auth)
        {
                DBG(DBG_CONTROL,
                        DBG_log("our certificate policy is %N", cert_policy_names, cert_policy)
@@ -3429,23 +3456,30 @@ stf_status main_inR2_outI3(struct msg_digest *md)
 
    /* HASH_I or SIG_I out */
        {
-               u_char hash_val[MAX_DIGEST_LEN];
-               size_t hash_len = main_mode_hash(st, hash_val, TRUE, &id_pbs);
+               u_char hash_buf[MAX_DIGEST_LEN];
+               chunk_t hash = chunk_from_buf(hash_buf);
+
+               main_mode_hash(st, &hash, TRUE, &id_pbs);
 
                if (auth_payload == ISAKMP_NEXT_HASH)
                {
                        /* HASH_I out */
-                       if (!out_generic_raw(ISAKMP_NEXT_NONE, &isakmp_hash_desc, &md->rbody
-                       , hash_val, hash_len, "HASH_I"))
+                       if (!out_generic_raw(ISAKMP_NEXT_NONE, &isakmp_hash_desc, &md->rbody,
+                                                                hash.ptr, hash.len, "HASH_I"))
+                       {
                                return STF_INTERNAL_ERROR;
+                       }
                }
                else
                {
                        /* SIG_I out */
                        u_char sig_val[RSA_MAX_OCTETS];
-                       size_t sig_len = sign_hash(st->st_connection, sig_val, hash_val,
-                                                                          hash_len);
+                       signature_scheme_t scheme;
+                       size_t sig_len;
 
+                       scheme = (st->st_oakley.auth == OAKLEY_RSA_SIG) ?
+                                                       SIGN_RSA_EMSA_PKCS1_NULL : SIGN_ECDSA_WITH_NULL;
+                       sig_len = sign_hash(scheme, st->st_connection, sig_val, hash);
                        if (sig_len == 0)
                        {
                                loglog(RC_LOG_SERIOUS, "unable to locate my private key for signature");
@@ -3514,9 +3548,9 @@ main_id_and_auth(struct msg_digest *md
                                 , const struct key_continuation *kc    /* current state, can be NULL */
 )
 {
+       u_char hash_buf[MAX_DIGEST_LEN];
+       chunk_t hash = chunk_from_buf(hash_buf);
        struct state *st = md->st;
-       u_char hash_val[MAX_DIGEST_LEN];
-       size_t hash_len;
        struct id peer;
        stf_status r = STF_OK;
 
@@ -3533,7 +3567,7 @@ main_id_and_auth(struct msg_digest *md
                u_int8_t *old_cur = idpl->cur;
 
                idpl->cur = idpl->roof;
-               hash_len = main_mode_hash(st, hash_val, !initiator, idpl);
+               main_mode_hash(st, &hash, !initiator, idpl);
                idpl->cur = old_cur;
        }
 
@@ -3545,8 +3579,8 @@ main_id_and_auth(struct msg_digest *md
                {
                        pb_stream *const hash_pbs = &md->chain[ISAKMP_NEXT_HASH]->pbs;
 
-                       if (pbs_left(hash_pbs) != hash_len
-                       || memcmp(hash_pbs->cur, hash_val, hash_len) != 0)
+                       if (pbs_left(hash_pbs) != hash.len
+                       || memcmp(hash_pbs->cur, hash.ptr, hash.len) != 0)
                        {
                                DBG_cond_dump(DBG_CRYPT, "received HASH:"
                                        , hash_pbs->cur, pbs_left(hash_pbs));
@@ -3560,14 +3594,14 @@ main_id_and_auth(struct msg_digest *md
        case OAKLEY_RSA_SIG:
        case XAUTHInitRSA:
        case XAUTHRespRSA:
-               r = RSA_check_signature(&peer, st, hash_val, hash_len
-                       , &md->chain[ISAKMP_NEXT_SIG]->pbs
+               r = check_signature(KEY_RSA, &peer, st, hash,
+                                &md->chain[ISAKMP_NEXT_SIG]->pbs,
 #ifdef USE_KEYRR
-                       , kc == NULL? NULL : kc->ac.keys_from_dns
+                               kc == NULL? NULL : kc->ac.keys_from_dns,
 #endif /* USE_KEYRR */
-                       , kc == NULL? NULL : kc->ac.gateways_from_dns
+                               kc == NULL? NULL : kc->ac.gateways_from_dns
                        );
-
+       
                if (r == STF_SUSPEND)
                {
                        /* initiate/resume asynchronous DNS lookup for key */
@@ -3622,6 +3656,17 @@ main_id_and_auth(struct msg_digest *md
                }
                break;
 
+       case OAKLEY_ECDSA_256:
+       case OAKLEY_ECDSA_384:
+       case OAKLEY_ECDSA_512:
+               r = check_signature(KEY_ECDSA, &peer, st, hash,
+                                                       &md->chain[ISAKMP_NEXT_SIG]->pbs,
+#ifdef USE_KEYRR
+                                                       NULL,
+#endif /* USE_KEYRR */
+                                                       NULL);
+               break;
+
        default:
                bad_case(st->st_oakley.auth);
        }
@@ -3732,9 +3777,7 @@ main_inI3_outR3_tail(struct msg_digest *md
        pb_stream r_id_pbs; /* ID Payload; also used for hash calculation */
        certpolicy_t cert_policy;
        cert_t mycert;
-       bool RSA_auth;
-       bool send_cert;
-       bool requested;
+       bool pubkey_auth, send_cert, requested;
 
        /* ID and HASH_I or SIG_I in
         * Note: this may switch the connection being used!
@@ -3748,19 +3791,16 @@ main_inI3_outR3_tail(struct msg_digest *md
                        return r;
        }
 
-       /* send certificate if auth is RSA, we have one and we want
-        * or are requested to send it
+       /* send certificate if pubkey authentication is used, we have one
+        * and we want or are requested to send it
         */
        cert_policy = st->st_connection->spd.this.sendcert;
        mycert = st->st_connection->spd.this.cert;
        requested = cert_policy == CERT_SEND_IF_ASKED
                                && st->st_connection->got_certrequest;
-       RSA_auth = st->st_oakley.auth == OAKLEY_RSA_SIG
-                       || st->st_oakley.auth == XAUTHInitRSA
-                       || st->st_oakley.auth == XAUTHRespRSA;
-       send_cert = RSA_auth
-                               && mycert.type != CERT_NONE
-                               && (cert_policy == CERT_ALWAYS_SEND || requested);
+       pubkey_auth = uses_pubkey_auth(st->st_oakley.auth);
+       send_cert = pubkey_auth && mycert.type != CERT_NONE &&
+                               (cert_policy == CERT_ALWAYS_SEND || requested);
 
        /*************** build output packet HDR*;IDir;HASH/SIG_R ***************/
        /* proccess_packet() would automatically generate the HDR*
@@ -3776,7 +3816,7 @@ main_inI3_outR3_tail(struct msg_digest *md
         */
        echo_hdr(md, TRUE, ISAKMP_NEXT_ID);
 
-       auth_payload = RSA_auth ? ISAKMP_NEXT_SIG : ISAKMP_NEXT_HASH;
+       auth_payload = pubkey_auth ? ISAKMP_NEXT_SIG : ISAKMP_NEXT_HASH;
 
        /* IDir out */
        {
@@ -3795,7 +3835,7 @@ main_inI3_outR3_tail(struct msg_digest *md
        }
 
        /* CERT out */
-       if (RSA_auth)
+       if (pubkey_auth)
        {
                DBG(DBG_CONTROL,
                        DBG_log("our certificate policy is %N", cert_policy_names, cert_policy)
@@ -3831,23 +3871,30 @@ main_inI3_outR3_tail(struct msg_digest *md
 
        /* HASH_R or SIG_R out */
        {
-               u_char hash_val[MAX_DIGEST_LEN];
-               size_t hash_len = main_mode_hash(st, hash_val, FALSE, &r_id_pbs);
+               u_char hash_buf[MAX_DIGEST_LEN];
+               chunk_t hash = chunk_from_buf(hash_buf);
+
+               main_mode_hash(st, &hash, FALSE, &r_id_pbs);
 
                if (auth_payload == ISAKMP_NEXT_HASH)
                {
                        /* HASH_R out */
-                       if (!out_generic_raw(ISAKMP_NEXT_NONE, &isakmp_hash_desc, &md->rbody
-                       , hash_val, hash_len, "HASH_R"))
+                       if (!out_generic_raw(ISAKMP_NEXT_NONE, &isakmp_hash_desc, &md->rbody,
+                                                                hash.ptr, hash.len, "HASH_R"))
+                       {
                                return STF_INTERNAL_ERROR;
+                       }
                }
                else
                {
                        /* SIG_R out */
                        u_char sig_val[RSA_MAX_OCTETS];
-                       size_t sig_len = sign_hash(st->st_connection, sig_val, hash_val,
-                                                                          hash_len);
+                       signature_scheme_t scheme;
+                       size_t sig_len;
 
+                       scheme = (st->st_oakley.auth == OAKLEY_RSA_SIG) ?
+                                                       SIGN_RSA_EMSA_PKCS1_NULL : SIGN_ECDSA_WITH_NULL;
+                       sig_len = sign_hash(scheme, st->st_connection, sig_val, hash);
                        if (sig_len == 0)
                        {
                                loglog(RC_LOG_SERIOUS, "unable to locate my private key for signature");
index d5301c6..1590bdf 100644 (file)
@@ -660,20 +660,14 @@ struct db_context* kernel_alg_db_new(struct alg_info_esp *alg_info,
 {
        const struct esp_info *esp_info;
        struct esp_info tmp_esp_info;
-       struct db_context *ctx_new=NULL;
-       struct db_trans *t;
+       struct db_context *ctx_new = NULL;
        struct db_prop  *prop;
-       u_int trans_cnt;
-       int tn = 0;
+       u_int trans_cnt = esp_ealg_num * esp_aalg_num;
 
        if (!(policy & POLICY_ENCRYPT))     /* not possible, I think  */
+       {
                return NULL;
-
-       trans_cnt = esp_ealg_num * esp_aalg_num;
-       DBG(DBG_EMITTING,
-               DBG_log("kernel_alg_db_prop_new() initial trans_cnt=%d"
-                               , trans_cnt)
-       )
+       }
 
        /* pass aprox. number of transforms and attributes */
        ctx_new = db_prop_new(PROTO_IPSEC_ESP, trans_cnt, trans_cnt * 2);
@@ -716,26 +710,7 @@ struct db_context* kernel_alg_db_new(struct alg_info_esp *alg_info,
                        }
                }
        }
-
        prop = db_prop_get(ctx_new);
-
-       DBG(DBG_CONTROL|DBG_EMITTING,
-               DBG_log("kernel_alg_db_prop_new() "
-                               "will return p_new->protoid=%d, p_new->trans_cnt=%d"
-                               , prop->protoid, prop->trans_cnt)
-       )
-
-       for (t = prop->trans, tn = 0; tn < prop->trans_cnt; tn++)
-       {
-               DBG(DBG_CONTROL|DBG_EMITTING,
-                       DBG_log("kernel_alg_db_prop_new() "
-                                       "    trans[%d]: transid=%d, attr_cnt=%d, "
-                                       "attrs[0].type=%d, attrs[0].val=%d"
-                                       , tn
-                                       , t[tn].transid, t[tn].attr_cnt
-                                       , t[tn].attrs[0].type, t[tn].attrs[0].val)
-               )
-       }
        return ctx_new;
 }
 
index c494b8b..6dfbd67 100644 (file)
@@ -258,8 +258,8 @@ const chunk_t* get_preshared_secret(const struct connection *c)
        return s == NULL? NULL : &s->u.preshared_secret;
 }
 
-/* check the existence of an RSA private key matching an RSA public
- * key contained in an X.509 or OpenPGP certificate
+/* check the existence of a private key matching a public key contained
+ * in an X.509 or OpenPGP certificate
  */
 bool has_private_key(cert_t cert)
 {
@@ -280,7 +280,7 @@ bool has_private_key(cert_t cert)
 }
 
 /*
- * get the matching RSA private key belonging to a given X.509 certificate
+ * get the matching private key belonging to a given X.509 certificate
  */
 private_key_t* get_x509_private_key(const x509cert_t *cert)
 {
@@ -297,7 +297,7 @@ private_key_t* get_x509_private_key(const x509cert_t *cert)
        return NULL;
 }
 
-/* find the appropriate RSA private key (see get_secret).
+/* find the appropriate private key (see get_secret).
  * Failure is indicated by a NULL pointer.
  */
 private_key_t* get_private_key(const struct connection *c)
index 723124d..630c7f8 100644 (file)
@@ -321,7 +321,7 @@ out_sa(pb_stream *outs
 
                                                alg_info_snprint(buf, sizeof (buf),
                                                                (struct alg_info *)st->st_connection->alg_info_esp);
-                                               DBG_log(buf);
+                                               DBG_log("esp proposal: %s", buf);
                                        }
                                )
                                db_ctx = kernel_alg_db_new(st->st_connection->alg_info_esp, st->st_policy);
@@ -345,10 +345,10 @@ out_sa(pb_stream *outs
 
                                                alg_info_snprint(buf, sizeof (buf),
                                                                (struct alg_info *)st->st_connection->alg_info_ike);
-                                               DBG_log(buf);
+                                               DBG_log("ike proposal: %s", buf);
                                        }
                                )
-                               db_ctx = ike_alg_db_new(st->st_connection->alg_info_ike, st->st_policy);
+                               db_ctx = ike_alg_db_new(st->st_connection, st->st_policy);
                                p = db_prop_get(db_ctx);
 
                                if (!p || p->trans_cnt == 0)
@@ -794,7 +794,10 @@ parse_isakmp_policy(pb_stream *proposal_pbs
                                        *policy |= POLICY_PSK;
                                        break;
                                case OAKLEY_RSA_SIG:
-                                       *policy |= POLICY_RSASIG;
+                               case OAKLEY_ECDSA_256:
+                               case OAKLEY_ECDSA_384:
+                               case OAKLEY_ECDSA_512:
+                                       *policy |= POLICY_PUBKEY;
                                        break;
                                case XAUTHInitPreShared:
                                        *policy |= POLICY_XAUTH_SERVER;
@@ -978,7 +981,7 @@ parse_isakmp_sa_body(u_int32_t ipsecdoisit
                                        case OAKLEY_PRESHARED_KEY:
                                                if ((iap & POLICY_PSK) == LEMPTY)
                                                {
-                                                       ugh = "policy does not allow OAKLEY_PRESHARED_KEY authentication";
+                                                       ugh = "policy does not allow pre-shared key authentication";
                                                }
                                                else
                                                {
@@ -1009,14 +1012,16 @@ parse_isakmp_sa_body(u_int32_t ipsecdoisit
                                                }
                                                break;
                                        case OAKLEY_RSA_SIG:
-                                               /* Accept if policy specifies RSASIG or is default */
-                                               if ((iap & POLICY_RSASIG) == LEMPTY)
+                                       case OAKLEY_ECDSA_256:
+                                       case OAKLEY_ECDSA_384:
+                                       case OAKLEY_ECDSA_512:
+                                               if ((iap & POLICY_PUBKEY) == LEMPTY)
                                                {
-                                                       ugh = "policy does not allow OAKLEY_RSA_SIG authentication";
+                                                       ugh = "policy does not allow public key authentication";
                                                }
                                                else
                                                {
-                                                       ta.auth = OAKLEY_RSA_SIG;
+                                                       ta.auth = val;
                                                }
                                                break;
                                        case XAUTHInitRSA:
index 97050ff..5fd2b9f 100644 (file)
@@ -32,8 +32,8 @@
 /* strings containing a colon are interpreted as an IPv6 address */
 #define ip_version(string)     (strchr(string, '.') ? AF_INET : AF_INET6)
 
-static const char ike_defaults[] = "aes128-sha-modp2048";
-static const char esp_defaults[] = "aes128-sha1, 3des-md5";
+static const char ike_defaults[] = "aes128-sha1-modp2048,3des-sha1-modp1536";
+static const char esp_defaults[] = "aes128-sha1,3des-sha1";
 
 static const char firewall_defaults[] = "ipsec _updown iptables";
 
@@ -70,7 +70,7 @@ static void default_values(starter_config_t *cfg)
        cfg->conn_default.seen    = LEMPTY;
        cfg->conn_default.startup = STARTUP_NO;
        cfg->conn_default.state   = STATE_IGNORE;
-       cfg->conn_default.policy  = POLICY_ENCRYPT | POLICY_TUNNEL | POLICY_RSASIG |
+       cfg->conn_default.policy  = POLICY_ENCRYPT | POLICY_TUNNEL | POLICY_PUBKEY |
                                                                POLICY_PFS | POLICY_MOBIKE;
 
        cfg->conn_default.ike                   = clone_str(ike_defaults);
@@ -555,18 +555,16 @@ load_conn(starter_conn_t *conn, kw_list_t *kw, starter_config_t *cfg)
                                /* also handles the cases secret|rsasig and rsasig|secret */
                                for (;;)
                                {
-                                       if (streq(value, "rsa") || streq(value, "rsasig"))
+                                       if (streq(value, "rsa")   || streq(value, "rsasig")   ||
+                                               streq(value, "ecdsa") || streq(value, "ecdsasig") ||
+                                               streq(value, "pubkey"))
                                        {
-                                               conn->policy |= POLICY_RSASIG | POLICY_ENCRYPT;
+                                               conn->policy |= POLICY_PUBKEY | POLICY_ENCRYPT;
                                        }
                                        else if (streq(value, "secret") || streq(value, "psk"))
                                        {
                                                conn->policy |= POLICY_PSK | POLICY_ENCRYPT;
                                        }
-                                       else if (streq(value, "ecdsa") || streq(value, "ecdsasig"))
-                                       {
-                                               conn->policy |= POLICY_ECDSASIG | POLICY_ENCRYPT;
-                                       }
                                        else if (streq(value, "xauthrsasig"))
                                        {
                                                conn->policy |= POLICY_XAUTH_RSASIG | POLICY_ENCRYPT;
index 4e8f7f8..054e37f 100644 (file)
@@ -239,7 +239,7 @@ int starter_stroke_add_conn(starter_config_t *cfg, starter_conn_t *conn)
        msg.add_conn.name = push_string(&msg, connection_name(conn));
        
        /* PUBKEY is preferred to PSK and EAP */
-       if (conn->policy & POLICY_RSASIG || conn->policy & POLICY_ECDSASIG)
+       if (conn->policy & POLICY_PUBKEY)
        {
                msg.add_conn.auth_method = AUTH_PUBKEY;
        }
index 9e53cc7..44b442a 100644 (file)
@@ -323,7 +323,7 @@ starter_whack_add_conn(starter_conn_t *conn)
 
        r =  send_whack_msg(&msg);
 
-       if (r == 0 && (conn->policy & POLICY_RSASIG))
+       if (r == 0 && (conn->policy & POLICY_PUBKEY))
        {
                r += starter_whack_add_pubkey (conn, &conn->left, "left");
                r += starter_whack_add_pubkey (conn, &conn->right, "right");
index 4c3083b..dd7f772 100644 (file)
@@ -1634,8 +1634,8 @@ int main(int argc, char **argv)
 
                if (msg.policy & POLICY_OPPO)
                {
-                       if ((msg.policy & (POLICY_PSK | POLICY_RSASIG)) != POLICY_RSASIG)
-                               diag("only RSASIG is supported for opportunism");
+                       if ((msg.policy & (POLICY_PSK | POLICY_PUBKEY)) != POLICY_PUBKEY)
+                               diag("only PUBKEY is supported for opportunism");
                        if ((msg.policy & POLICY_PFS) == 0)
                                diag("PFS required for opportunism");
                        if ((msg.policy & POLICY_ENCRYPT) == 0)