completed support of AUTHZ_CA_CERT and AUTHZ_CA_CERT_NAME attributes
authorAndreas Steffen <andreas.steffen@strongswan.org>
Tue, 26 Aug 2008 05:15:34 +0000 (05:15 -0000)
committerAndreas Steffen <andreas.steffen@strongswan.org>
Tue, 26 Aug 2008 05:15:34 +0000 (05:15 -0000)
src/charon/credentials/credential_manager.c
src/charon/plugins/stroke/stroke_config.c
src/charon/plugins/stroke/stroke_list.c
src/charon/sa/tasks/ike_cert_pre.c

index 9902e40..48d066e 100644 (file)
@@ -1181,6 +1181,7 @@ static bool trusted_enumerate(trusted_enumerator_t *this,
                                verify_trust_chain(this->this, this->pretrusted, this->auth,
                                                                   TRUE, this->crl, this->ocsp))
                        {
+                               this->auth->add_item(this->auth, AUTHZ_CA_CERT, this->pretrusted);
                                DBG1(DBG_CFG, "  using trusted certificate \"%D\"",
                                         this->pretrusted->get_subject(this->pretrusted));
                                *cert = this->pretrusted;
index 9df19dc..e9a9cc9 100644 (file)
@@ -335,7 +335,9 @@ static ike_cfg_t *build_ike_cfg(private_stroke_config_t *this, stroke_msg_t *msg
  * build a peer_cfg from a stroke msg
  */
 static peer_cfg_t *build_peer_cfg(private_stroke_config_t *this,
-                                                                 stroke_msg_t *msg, ike_cfg_t *ike_cfg)
+                                                                 stroke_msg_t *msg, ike_cfg_t *ike_cfg,
+                                                                 identification_t **my_issuer,
+                                                                 identification_t **other_issuer)
 {
        identification_t *me, *other, *peer_id = NULL;
        peer_cfg_t *mediated_by = NULL;
@@ -420,6 +422,9 @@ static peer_cfg_t *build_peer_cfg(private_stroke_config_t *this,
                cert = this->cred->load_peer(this->cred, msg->add_conn.me.cert);
                if (cert)
                {
+                       identification_t *issuer = cert->get_issuer(cert);
+
+                       *my_issuer = issuer->clone(issuer); 
                        this->ca->check_for_hash_and_url(this->ca, cert);
                        me = update_peerid(cert, me);
                        cert->destroy(cert);
@@ -430,6 +435,9 @@ static peer_cfg_t *build_peer_cfg(private_stroke_config_t *this,
                cert = this->cred->load_peer(this->cred, msg->add_conn.other.cert);
                if (cert)
                {
+                       identification_t *issuer = cert->get_issuer(cert);
+
+                       *other_issuer = issuer->clone(issuer); 
                        other = update_peerid(cert, other);
                        cert->destroy(cert);
                }
@@ -511,9 +519,11 @@ static peer_cfg_t *build_peer_cfg(private_stroke_config_t *this,
  * fill in auth_info from stroke message
  */
 static void build_auth_info(private_stroke_config_t *this,
-                                                       stroke_msg_t *msg, auth_info_t *auth)
+                                                       stroke_msg_t *msg, auth_info_t *auth,
+                                                       identification_t *my_ca,
+                                                       identification_t *other_ca)
 {
-       identification_t *my_ca = NULL, *other_ca = NULL, *id;
+       identification_t *id;
        bool my_ca_same = FALSE;
        bool other_ca_same = FALSE;
        cert_validation_t valid;
@@ -539,6 +549,11 @@ static void build_auth_info(private_stroke_config_t *this,
        
        if (msg->add_conn.me.ca)
        {
+               if (my_ca)
+               {
+                       my_ca->destroy(my_ca);
+                       my_ca = NULL;
+               }
                if (streq(msg->add_conn.me.ca, "%same"))
                {
                        my_ca_same = TRUE;
@@ -548,8 +563,14 @@ static void build_auth_info(private_stroke_config_t *this,
                        my_ca = identification_create_from_string(msg->add_conn.me.ca);
                }
        }
+
        if (msg->add_conn.other.ca)
        {
+               if (other_ca)
+               {
+                       other_ca->destroy(other_ca);
+                       other_ca = NULL;
+               }
                if (streq(msg->add_conn.other.ca, "%same"))
                {
                        other_ca_same = TRUE;
@@ -559,6 +580,7 @@ static void build_auth_info(private_stroke_config_t *this,
                        other_ca = identification_create_from_string(msg->add_conn.other.ca);
                }
        }
+
        if (other_ca_same && my_ca)
        {
                other_ca = my_ca->clone(my_ca);
@@ -584,6 +606,7 @@ static void build_auth_info(private_stroke_config_t *this,
                }
                other_ca->destroy(other_ca);
        }
+
        if (my_ca)
        {
                DBG2(DBG_CFG, "  my ca:    %D", my_ca);
@@ -737,6 +760,7 @@ static void add(private_stroke_config_t *this, stroke_msg_t *msg)
        ike_cfg_t *ike_cfg, *existing_ike;
        peer_cfg_t *peer_cfg, *existing;
        child_cfg_t *child_cfg;
+       identification_t *my_issuer = NULL, *other_issuer = NULL;
        enumerator_t *enumerator;
        bool use_existing = FALSE;
 
@@ -745,14 +769,15 @@ static void add(private_stroke_config_t *this, stroke_msg_t *msg)
        {
                return;
        }
-       peer_cfg = build_peer_cfg(this, msg, ike_cfg);
+       peer_cfg = build_peer_cfg(this, msg, ike_cfg, &my_issuer, &other_issuer);
        if (!peer_cfg)
        {
                ike_cfg->destroy(ike_cfg);
                return;
        }
        
-       build_auth_info(this, msg, peer_cfg->get_auth(peer_cfg));
+       build_auth_info(this, msg, peer_cfg->get_auth(peer_cfg),
+                                       my_issuer, other_issuer);
        enumerator = create_peer_cfg_enumerator(this, NULL, NULL);
        while (enumerator->enumerate(enumerator, &existing))
        {
index 9e2418f..03c6ba1 100644 (file)
@@ -236,7 +236,6 @@ static void status(private_stroke_list_t *this, stroke_msg_t *msg, FILE *out, bo
        
        if (all)
        {
-               identification_t *any_issuer = identification_create_from_string("%any");
                peer_cfg_t *peer_cfg;
                char *plugin;
                host_t *host;
@@ -274,11 +273,12 @@ static void status(private_stroke_list_t *this, stroke_msg_t *msg, FILE *out, bo
                enumerator = charon->backends->create_peer_cfg_enumerator(charon->backends);
                while (enumerator->enumerate(enumerator, (void**)&peer_cfg))
                {
+                       void *ptr;
+                       certificate_t *cert;
                        auth_item_t item;
                        auth_info_t *auth;
                        enumerator_t *auth_enumerator;
-                       certificate_t *cert;
-                       identification_t *my_issuer = NULL, *other_issuer = NULL;
+                       identification_t *my_ca = NULL, *other_ca = NULL;
 
                        if (peer_cfg->get_ike_version(peer_cfg) != 2 ||
                                (name && !streq(name, peer_cfg->get_name(peer_cfg))))
@@ -289,15 +289,23 @@ static void status(private_stroke_list_t *this, stroke_msg_t *msg, FILE *out, bo
                        /* determine any required CAs */
                        auth = peer_cfg->get_auth(peer_cfg);
                        auth_enumerator = auth->create_item_enumerator(auth);
-                       while (auth_enumerator->enumerate(auth_enumerator, &item, &cert))
+                       while (auth_enumerator->enumerate(auth_enumerator, &item, &ptr))
                        {
                                switch (item)
                                {
                                        case AUTHN_CA_CERT:
-                                               my_issuer = cert->get_subject(cert);
+                                               cert = (certificate_t *)ptr;
+                                               my_ca = cert->get_subject(cert);
+                                               break;
+                                       case AUTHN_CA_CERT_NAME:
+                                               my_ca = (identification_t *)ptr;
                                                break;
                                        case AUTHZ_CA_CERT:
-                                               other_issuer = cert->get_subject(cert);
+                                               cert = (certificate_t *)ptr;
+                                               other_ca = cert->get_subject(cert);
+                                               break;
+                                       case AUTHZ_CA_CERT_NAME:
+                                               other_ca = (identification_t *)ptr;
                                                break;
                                        default:
                                                break;
@@ -309,11 +317,25 @@ static void status(private_stroke_list_t *this, stroke_msg_t *msg, FILE *out, bo
                        fprintf(out, "%12s:  %s[%D]...%s[%D]\n", peer_cfg->get_name(peer_cfg),
                                        ike_cfg->get_my_addr(ike_cfg), peer_cfg->get_my_id(peer_cfg),
                                        ike_cfg->get_other_addr(ike_cfg), peer_cfg->get_other_id(peer_cfg));
-                       if (my_issuer || other_issuer)
+                       if (my_ca || other_ca)
                        {
-                               fprintf(out, "%12s:  CAs: \"%D\"...\"%D\"\n", peer_cfg->get_name(peer_cfg),
-                                               my_issuer? my_issuer:any_issuer,
-                                               other_issuer? other_issuer:any_issuer);                         
+                               fprintf(out, "%12s:  CAs: ", peer_cfg->get_name(peer_cfg));
+                               if (my_ca)
+                               {
+                                       fprintf(out, "\"%D\"...", my_ca);
+                               }
+                               else
+                               {
+                                       fprintf(out, "%%any...");
+                               }
+                               if (other_ca)
+                               {
+                                       fprintf(out, "\"%D\"\n", other_ca);
+                               }
+                               else
+                               {
+                                       fprintf(out, "%%any\n");
+                               }
                        }
                        fprintf(out, "%12s:  %N authentication",  peer_cfg->get_name(peer_cfg),
                                        auth_class_names, get_auth_class(peer_cfg));
@@ -348,7 +370,6 @@ static void status(private_stroke_list_t *this, stroke_msg_t *msg, FILE *out, bo
                        children->destroy(children);
                }
                enumerator->destroy(enumerator);
-               any_issuer->destroy(any_issuer);
        }
        
        fprintf(out, "Security Associations:\n");
index 9e11f30..79bc4f6 100644 (file)
@@ -336,20 +336,37 @@ static void build_certreqs(private_ike_cert_pre_t *this, message_t *message)
        peer_cfg = this->ike_sa->get_peer_cfg(this->ike_sa);
        if (peer_cfg)
        {
+               void *ptr;
+               identification_t *id;
                auth_item_t item;
                auth_info_t *auth = peer_cfg->get_auth(peer_cfg);
+               enumerator_t *auth_enumerator = auth->create_item_enumerator(auth);
 
-               enumerator = auth->create_item_enumerator(auth);
-               while (enumerator->enumerate(enumerator, &item, &cert))
+               while (auth_enumerator->enumerate(auth_enumerator, &item, &ptr))
                {
-                       if (item == AUTHZ_CA_CERT)
+                       switch (item)
                        {
-                               restricted = TRUE;
-                               add_certreq_payload(message, &x509_req, cert);
+                               case AUTHZ_CA_CERT:
+                                       cert = (certificate_t *)ptr;
+                                       add_certreq_payload(message, &x509_req, cert);
+                                       restricted = TRUE;
+                                       break;
+                               case AUTHZ_CA_CERT_NAME:
+                                       id = (identification_t *)ptr;
+                                       enumerator = charon->credentials->create_cert_enumerator(
+                                                       charon->credentials, CERT_ANY, KEY_ANY, id, TRUE);
+                                       while (enumerator->enumerate(enumerator, &cert, TRUE))
+                                       {
+                                               add_certreq_payload(message, &x509_req, cert);
+                                               restricted = TRUE;
+                                       }
+                                       enumerator->destroy(enumerator);
+                                       break;
+                               default:
+                                       break;
                        }
-                       /* TODO: handle AUTHZ_CA_CERT_NAME case */
                }
-               enumerator->destroy(enumerator);
+               auth_enumerator->destroy(auth_enumerator);
        }
                
        if (!restricted)