]> git.ipfire.org Git - thirdparty/strongswan.git/commitdiff
kernel-interface: Raise expires with a proto/SPI/dst tuple instead of reqid
authorMartin Willi <martin@revosec.ch>
Mon, 27 Oct 2014 14:07:05 +0000 (15:07 +0100)
committerMartin Willi <martin@revosec.ch>
Fri, 20 Feb 2015 12:34:50 +0000 (13:34 +0100)
20 files changed:
src/conftest/actions.c
src/frontends/android/jni/libandroidbridge/kernel/android_ipsec.c
src/libcharon/kernel/kernel_handler.c
src/libcharon/plugins/kernel_libipsec/kernel_libipsec_ipsec.c
src/libcharon/plugins/kernel_wfp/kernel_wfp_ipsec.c
src/libcharon/plugins/stroke/stroke_control.c
src/libcharon/processing/jobs/delete_child_sa_job.c
src/libcharon/processing/jobs/delete_child_sa_job.h
src/libcharon/processing/jobs/rekey_child_sa_job.c
src/libcharon/processing/jobs/rekey_child_sa_job.h
src/libcharon/sa/ikev2/tasks/child_rekey.c
src/libhydra/kernel/kernel_interface.c
src/libhydra/kernel/kernel_interface.h
src/libhydra/kernel/kernel_listener.h
src/libhydra/plugins/kernel_netlink/kernel_netlink_ipsec.c
src/libhydra/plugins/kernel_pfkey/kernel_pfkey_ipsec.c
src/libipsec/ipsec_event_listener.h
src/libipsec/ipsec_event_relay.c
src/libipsec/ipsec_event_relay.h
src/libipsec/ipsec_sa.c

index 3f937b118ace2290423a98ab1eb7c6581fc9ba6f..474672ca1bd134f4a382cf61b53e8396415b2dc2 100644 (file)
@@ -117,19 +117,20 @@ static job_requeue_t rekey_child(char *config)
        enumerator_t *enumerator, *children;
        ike_sa_t *ike_sa;
        child_sa_t *child_sa;
-       u_int32_t reqid = 0, spi = 0;
-       protocol_id_t proto = PROTO_ESP;
+       u_int32_t spi, proto;
+       host_t *dst = NULL;
 
        enumerator = charon->controller->create_ike_sa_enumerator(
                                                                                                        charon->controller, TRUE);
        while (enumerator->enumerate(enumerator, &ike_sa))
        {
                children = ike_sa->create_child_sa_enumerator(ike_sa);
-               while (children->enumerate(children, (void**)&child_sa))
+               while (children->enumerate(children, &child_sa))
                {
                        if (streq(config, child_sa->get_name(child_sa)))
                        {
-                               reqid = child_sa->get_reqid(child_sa);
+                               dst = ike_sa->get_my_host(ike_sa);
+                               dst = dst->clone(dst);
                                proto = child_sa->get_protocol(child_sa);
                                spi = child_sa->get_spi(child_sa, TRUE);
                                break;
@@ -138,11 +139,12 @@ static job_requeue_t rekey_child(char *config)
                children->destroy(children);
        }
        enumerator->destroy(enumerator);
-       if (reqid)
+       if (dst)
        {
                DBG1(DBG_CFG, "starting rekey of CHILD_SA '%s'", config);
                lib->processor->queue_job(lib->processor,
-                                               (job_t*)rekey_child_sa_job_create(reqid, proto, spi));
+                                               (job_t*)rekey_child_sa_job_create(proto, spi, dst));
+               dst->destroy(dst);
        }
        else
        {
index 65166077e6ee51fecdd9cdf67f4fa0638cbea285..a0aefaa4e25b2ed084687000094c1302d83f2969 100644 (file)
@@ -40,10 +40,10 @@ struct private_kernel_android_ipsec_t {
 /**
  * Callback registrered with libipsec.
  */
-void expire(u_int32_t reqid, u_int8_t protocol, u_int32_t spi, bool hard)
+static void expire(u_int8_t protocol, u_int32_t spi, host_t *dst, bool hard)
 {
-       hydra->kernel_interface->expire(hydra->kernel_interface, reqid, protocol,
-                                                                       spi, hard);
+       hydra->kernel_interface->expire(hydra->kernel_interface, protocol,
+                                                                       spi, dst, hard);
 }
 
 METHOD(kernel_ipsec_t, get_spi, status_t,
index 059124e35bdd34feb586d3d73f52cf224cdd4c05..a6656e7d5d968fcaaff2ba02994f3378ba9fcacf 100644 (file)
@@ -72,23 +72,23 @@ METHOD(kernel_listener_t, acquire, bool,
 }
 
 METHOD(kernel_listener_t, expire, bool,
-       private_kernel_handler_t *this, u_int32_t reqid, u_int8_t protocol,
-       u_int32_t spi, bool hard)
+       private_kernel_handler_t *this, u_int8_t protocol, u_int32_t spi,
+       host_t *dst, bool hard)
 {
        protocol_id_t proto = proto_ip2ike(protocol);
 
-       DBG1(DBG_KNL, "creating %s job for %N CHILD_SA with SPI %.8x and reqid {%u}",
-                hard ? "delete" : "rekey", protocol_id_names, proto, ntohl(spi), reqid);
+       DBG1(DBG_KNL, "creating %s job for CHILD_SA %N/0x%08x/%H",
+                hard ? "delete" : "rekey", protocol_id_names, proto, ntohl(spi), dst);
 
        if (hard)
        {
                lib->processor->queue_job(lib->processor,
-                               (job_t*)delete_child_sa_job_create(reqid, proto, spi, hard));
+                               (job_t*)delete_child_sa_job_create(proto, spi, dst, hard));
        }
        else
        {
                lib->processor->queue_job(lib->processor,
-                               (job_t*)rekey_child_sa_job_create(reqid, proto, spi));
+                               (job_t*)rekey_child_sa_job_create(proto, spi, dst));
        }
        return TRUE;
 }
index 362b327464ef069739589e6b390c97f2402aef17..e6c5d6a1df940b1a0ea9518328bbd34734563b48 100644 (file)
@@ -222,10 +222,10 @@ static inline bool policy_entry_equals(policy_entry_t *a,
 /**
  * Expiration callback
  */
-static void expire(u_int32_t reqid, u_int8_t protocol, u_int32_t spi, bool hard)
+static void expire(u_int8_t protocol, u_int32_t spi, host_t *dst, bool hard)
 {
-       hydra->kernel_interface->expire(hydra->kernel_interface, reqid, protocol,
-                                                                       spi, hard);
+       hydra->kernel_interface->expire(hydra->kernel_interface, protocol,
+                                                                       spi, dst, hard);
 }
 
 METHOD(kernel_ipsec_t, get_features, kernel_feature_t,
index 9fd6541a5cd9fe927771de7e1e8a65fc4c43cb86..86db9e64382a9151e635eabe85064f4e1465d2eb 100644 (file)
@@ -2032,9 +2032,8 @@ static void expire_data_destroy(expire_data_t *data)
 static job_requeue_t expire_job(expire_data_t *data)
 {
        private_kernel_wfp_ipsec_t *this = data->this;
-       u_int32_t reqid = 0;
        u_int8_t protocol;
-       entry_t *entry;
+       entry_t *entry = NULL;
        sa_entry_t key = {
                .spi = data->spi,
                .dst = data->dst,
@@ -2048,7 +2047,6 @@ static job_requeue_t expire_job(expire_data_t *data)
                if (entry)
                {
                        protocol = entry->isa.protocol;
-                       reqid = entry->reqid;
                        if (entry->osa.dst)
                        {
                                key.dst = entry->osa.dst;
@@ -2065,15 +2063,14 @@ static job_requeue_t expire_job(expire_data_t *data)
                if (entry)
                {
                        protocol = entry->isa.protocol;
-                       reqid = entry->reqid;
                }
                this->mutex->unlock(this->mutex);
        }
 
-       if (reqid)
+       if (entry)
        {
-               hydra->kernel_interface->expire(hydra->kernel_interface,
-                                                                               reqid, protocol, data->spi, data->hard);
+               hydra->kernel_interface->expire(hydra->kernel_interface, protocol,
+                                                                               data->spi, data->dst, data->hard);
        }
 
        return JOB_REQUEUE_NONE;
index 99d07f59364d2001b8752e2d591e09b40bc4a78c..0084fbf93fb1a0981c25f9dd4424434f3062effa 100644 (file)
@@ -432,13 +432,13 @@ METHOD(stroke_control_t, rekey, void,
                        while (children->enumerate(children, (void**)&child_sa))
                        {
                                if ((name && streq(name, child_sa->get_name(child_sa))) ||
-                                       (id && id == child_sa->get_reqid(child_sa)))
+                                       (id && id == child_sa->get_unique_id(child_sa)))
                                {
                                        lib->processor->queue_job(lib->processor,
                                                (job_t*)rekey_child_sa_job_create(
-                                                               child_sa->get_reqid(child_sa),
                                                                child_sa->get_protocol(child_sa),
-                                                               child_sa->get_spi(child_sa, TRUE)));
+                                                               child_sa->get_spi(child_sa, TRUE),
+                                                               ike_sa->get_my_host(ike_sa)));
                                        if (!all)
                                        {
                                                finished = TRUE;
index 9afbac02b00cc4f086110f086fc7610ac19abae4..0d85883be7fcd891651fab274f31abfc0735efa6 100644 (file)
@@ -30,11 +30,6 @@ struct private_delete_child_sa_job_t {
         */
        delete_child_sa_job_t public;
 
-       /**
-        * reqid of the CHILD_SA
-        */
-       u_int32_t reqid;
-
        /**
         * protocol of the CHILD_SA (ESP/AH)
         */
@@ -45,6 +40,11 @@ struct private_delete_child_sa_job_t {
         */
        u_int32_t spi;
 
+       /**
+        * SA destination address
+        */
+       host_t *dst;
+
        /**
         * Delete for an expired CHILD_SA
         */
@@ -54,6 +54,7 @@ struct private_delete_child_sa_job_t {
 METHOD(job_t, destroy, void,
        private_delete_child_sa_job_t *this)
 {
+       this->dst->destroy(this->dst);
        free(this);
 }
 
@@ -62,12 +63,12 @@ METHOD(job_t, execute, job_requeue_t,
 {
        ike_sa_t *ike_sa;
 
-       ike_sa = charon->ike_sa_manager->checkout_by_id(charon->ike_sa_manager,
-                                                                                                       this->reqid, TRUE);
+       ike_sa = charon->child_sa_manager->checkout(charon->child_sa_manager,
+                                                                       this->protocol, this->spi, this->dst, NULL);
        if (ike_sa == NULL)
        {
-               DBG1(DBG_JOB, "CHILD_SA with reqid %d not found for delete",
-                        this->reqid);
+               DBG1(DBG_JOB, "CHILD_SA %N/0x%08x/%H not found for delete",
+                        protocol_id_names, this->protocol, htonl(this->spi), this->dst);
        }
        else
        {
@@ -87,8 +88,8 @@ METHOD(job_t, get_priority, job_priority_t,
 /*
  * Described in header
  */
-delete_child_sa_job_t *delete_child_sa_job_create(u_int32_t reqid,
-                                                       protocol_id_t protocol, u_int32_t spi, bool expired)
+delete_child_sa_job_t *delete_child_sa_job_create(protocol_id_t protocol,
+                                                                       u_int32_t spi, host_t *dst, bool expired)
 {
        private_delete_child_sa_job_t *this;
 
@@ -100,12 +101,11 @@ delete_child_sa_job_t *delete_child_sa_job_create(u_int32_t reqid,
                                .destroy = _destroy,
                        },
                },
-               .reqid = reqid,
                .protocol = protocol,
                .spi = spi,
+               .dst = dst->clone(dst),
                .expired = expired,
        );
 
        return &this->public;
 }
-
index be6d578bcdb5ef0b82f0e3a7aa90854491845570..6fa53644cb3f005e15cfb26b1899102d38053cc9 100644 (file)
@@ -44,16 +44,13 @@ struct delete_child_sa_job_t {
 /**
  * Creates a job of type DELETE_CHILD_SA.
  *
- * The CHILD_SA is identified by its reqid, protocol (AH/ESP) and its
- * inbound SPI.
- *
- * @param reqid                reqid of the CHILD_SA, as used in kernel
  * @param protocol     protocol of the CHILD_SA
  * @param spi          security parameter index of the CHILD_SA
+ * @param dst          SA destination address
  * @param expired      TRUE if CHILD_SA already expired
  * @return                     delete_child_sa_job_t object
  */
-delete_child_sa_job_t *delete_child_sa_job_create(u_int32_t reqid,
-                                                       protocol_id_t protocol, u_int32_t spi, bool expired);
+delete_child_sa_job_t *delete_child_sa_job_create(protocol_id_t protocol,
+                                                                       u_int32_t spi, host_t *dst, bool expired);
 
 #endif /** DELETE_CHILD_SA_JOB_H_ @}*/
index 1bf8dc0cbb310c0e1e66d76726a32eee284896fa..8f17d39abc225f515ea89ba7419d60d6aa8fcf2a 100644 (file)
@@ -24,16 +24,12 @@ typedef struct private_rekey_child_sa_job_t private_rekey_child_sa_job_t;
  * Private data of an rekey_child_sa_job_t object.
  */
 struct private_rekey_child_sa_job_t {
+
        /**
         * Public rekey_child_sa_job_t interface.
         */
        rekey_child_sa_job_t public;
 
-       /**
-        * reqid of the child to rekey
-        */
-       u_int32_t reqid;
-
        /**
         * protocol of the CHILD_SA (ESP/AH)
         */
@@ -43,11 +39,17 @@ struct private_rekey_child_sa_job_t {
         * inbound SPI of the CHILD_SA
         */
        u_int32_t spi;
+
+       /**
+        * SA destination address
+        */
+       host_t *dst;
 };
 
 METHOD(job_t, destroy, void,
        private_rekey_child_sa_job_t *this)
 {
+       this->dst->destroy(this->dst);
        free(this);
 }
 
@@ -56,12 +58,12 @@ METHOD(job_t, execute, job_requeue_t,
 {
        ike_sa_t *ike_sa;
 
-       ike_sa = charon->ike_sa_manager->checkout_by_id(charon->ike_sa_manager,
-                                                                                                       this->reqid, TRUE);
+       ike_sa = charon->child_sa_manager->checkout(charon->child_sa_manager,
+                                                                       this->protocol, this->spi, this->dst, NULL);
        if (ike_sa == NULL)
        {
-               DBG2(DBG_JOB, "CHILD_SA with reqid %d not found for rekeying",
-                        this->reqid);
+               DBG1(DBG_JOB, "CHILD_SA %N/0x%08x/%H not found for rekey",
+                        protocol_id_names, this->protocol, htonl(this->spi), this->dst);
        }
        else
        {
@@ -80,9 +82,8 @@ METHOD(job_t, get_priority, job_priority_t,
 /*
  * Described in header
  */
-rekey_child_sa_job_t *rekey_child_sa_job_create(u_int32_t reqid,
-                                                                                               protocol_id_t protocol,
-                                                                                               u_int32_t spi)
+rekey_child_sa_job_t *rekey_child_sa_job_create(protocol_id_t protocol,
+                                                                                               u_int32_t spi, host_t *dst)
 {
        private_rekey_child_sa_job_t *this;
 
@@ -94,9 +95,9 @@ rekey_child_sa_job_t *rekey_child_sa_job_create(u_int32_t reqid,
                                .destroy = _destroy,
                        },
                },
-               .reqid = reqid,
                .protocol = protocol,
                .spi = spi,
+               .dst = dst->clone(dst),
        );
 
        return &this->public;
index fcbe65a06e6926612d7e612b842fcf85e8f7561b..364bb5ae7be4fc5afcdcc9fdd34de32c9d05b5a9 100644 (file)
@@ -43,15 +43,11 @@ struct rekey_child_sa_job_t {
 /**
  * Creates a job of type REKEY_CHILD_SA.
  *
- * The CHILD_SA is identified by its protocol (AH/ESP) and its
- * inbound SPI.
- *
- * @param reqid                reqid of the CHILD_SA to rekey
  * @param protocol     protocol of the CHILD_SA
  * @param spi          security parameter index of the CHILD_SA
+ * @param dst          SA destination address
  * @return                     rekey_child_sa_job_t object
  */
-rekey_child_sa_job_t *rekey_child_sa_job_create(u_int32_t reqid,
-                                                                                               protocol_id_t protocol,
-                                                                                               u_int32_t spi);
+rekey_child_sa_job_t *rekey_child_sa_job_create(protocol_id_t protocol,
+                                                                                               u_int32_t spi, host_t *dst);
 #endif /** REKEY_CHILD_SA_JOB_H_ @}*/
index 213155a294e1f6bb9bdf1f8045c43cdb066f5158..c806e19ca3fb912d2c5072ae1687410bc331fea5 100644 (file)
@@ -96,9 +96,9 @@ static void schedule_delayed_rekey(private_child_rekey_t *this)
 
        retry = RETRY_INTERVAL - (random() % RETRY_JITTER);
        job = (job_t*)rekey_child_sa_job_create(
-                                               this->child_sa->get_reqid(this->child_sa),
                                                this->child_sa->get_protocol(this->child_sa),
-                                               this->child_sa->get_spi(this->child_sa, TRUE));
+                                               this->child_sa->get_spi(this->child_sa, TRUE),
+                                               this->ike_sa->get_my_host(this->ike_sa));
        DBG1(DBG_IKE, "CHILD_SA rekeying failed, trying again in %d seconds", retry);
        this->child_sa->set_state(this->child_sa, CHILD_INSTALLED);
        lib->scheduler->schedule_job(lib->scheduler, job, retry);
index 28821fc15e726f937e09e56bf47cbc5ca2a02e61..b5ade37d17997fe1650bb70f269e85ffcb445899 100644 (file)
@@ -815,17 +815,18 @@ METHOD(kernel_interface_t, acquire, void,
 }
 
 METHOD(kernel_interface_t, expire, void,
-       private_kernel_interface_t *this, u_int32_t reqid, u_int8_t protocol,
-       u_int32_t spi, bool hard)
+       private_kernel_interface_t *this, u_int8_t protocol, u_int32_t spi,
+       host_t *dst, bool hard)
 {
        kernel_listener_t *listener;
        enumerator_t *enumerator;
+
        this->mutex->lock(this->mutex);
        enumerator = this->listeners->create_enumerator(this->listeners);
        while (enumerator->enumerate(enumerator, &listener))
        {
                if (listener->expire &&
-                       !listener->expire(listener, reqid, protocol, spi, hard))
+                       !listener->expire(listener, protocol, spi, dst, hard))
                {
                        this->listeners->remove_at(this->listeners, enumerator);
                }
index 9a86e78d613e293f22694a1401121d72c22bd640..2db53f504216924c379dfba25c2b569b6777bfe0 100644 (file)
@@ -559,13 +559,13 @@ struct kernel_interface_t {
        /**
         * Raise an expire event.
         *
-        * @param reqid                 reqid of the expired SA
         * @param protocol              protocol of the expired SA
         * @param spi                   spi of the expired SA
+        * @param dst                   destination address of expired SA
         * @param hard                  TRUE if it is a hard expire, FALSE otherwise
         */
-       void (*expire)(kernel_interface_t *this, u_int32_t reqid,
-                                  u_int8_t protocol, u_int32_t spi, bool hard);
+       void (*expire)(kernel_interface_t *this, u_int8_t protocol, u_int32_t spi,
+                                  host_t *dst, bool hard);
 
        /**
         * Raise a mapping event.
index 4382a43fd2224011befc4f2e6192eac0b6aceaf3..122453f721626251aebb3bb1bada4c14094e36ca 100644 (file)
@@ -49,14 +49,14 @@ struct kernel_listener_t {
        /**
         * Hook called if an exire event for an IPsec SA is received.
         *
-        * @param reqid                 reqid of the expired SA
         * @param protocol              protocol of the expired SA
         * @param spi                   spi of the expired SA
+        * @param dst                   destination address of expired SA
         * @param hard                  TRUE if it is a hard expire, FALSE otherwise
         * @return                              TRUE to remain registered, FALSE to unregister
         */
-       bool (*expire)(kernel_listener_t *this, u_int32_t reqid,
-                                  u_int8_t protocol, u_int32_t spi, bool hard);
+       bool (*expire)(kernel_listener_t *this, u_int8_t protocol, u_int32_t spi,
+                                  host_t *dst, bool hard);
 
        /**
         * Hook called if the NAT mappings of an IPsec SA changed.
index 31bb4f65697b14b6335e48db8c8543a802b077a7..f8077d83621a5a484c762802eebcd9fb2de75c9a 100644 (file)
@@ -870,25 +870,26 @@ static void process_expire(private_kernel_netlink_ipsec_t *this,
                                                   struct nlmsghdr *hdr)
 {
        struct xfrm_user_expire *expire;
-       u_int32_t spi, reqid;
+       u_int32_t spi;
        u_int8_t protocol;
+       host_t *dst;
 
        expire = NLMSG_DATA(hdr);
        protocol = expire->state.id.proto;
        spi = expire->state.id.spi;
-       reqid = expire->state.reqid;
 
        DBG2(DBG_KNL, "received a XFRM_MSG_EXPIRE");
 
-       if (protocol != IPPROTO_ESP && protocol != IPPROTO_AH)
+       if (protocol == IPPROTO_ESP || protocol == IPPROTO_AH)
        {
-               DBG2(DBG_KNL, "ignoring XFRM_MSG_EXPIRE for SA with SPI %.8x and "
-                                         "reqid {%u} which is not a CHILD_SA", ntohl(spi), reqid);
-               return;
+               dst = xfrm2host(expire->state.family, &expire->state.id.daddr, 0);
+               if (dst)
+               {
+                       hydra->kernel_interface->expire(hydra->kernel_interface, protocol,
+                                                                                       spi, dst, expire->hard != 0);
+                       dst->destroy(dst);
+               }
        }
-
-       hydra->kernel_interface->expire(hydra->kernel_interface, reqid, protocol,
-                                                                       spi, expire->hard != 0);
 }
 
 /**
index 348549bfa917c2c682a09e780648d10063badf04..9b846864e9c289adb07ecb98c6c5e0b8d3d5b910 100644 (file)
@@ -1296,7 +1296,8 @@ static void process_expire(private_kernel_pfkey_ipsec_t *this,
 {
        pfkey_msg_t response;
        u_int8_t protocol;
-       u_int32_t spi, reqid;
+       u_int32_t spi;
+       host_t *dst;
        bool hard;
 
        DBG2(DBG_KNL, "received an SADB_EXPIRE");
@@ -1309,18 +1310,18 @@ static void process_expire(private_kernel_pfkey_ipsec_t *this,
 
        protocol = satype2proto(msg->sadb_msg_satype);
        spi = response.sa->sadb_sa_spi;
-       reqid = response.x_sa2->sadb_x_sa2_reqid;
        hard = response.lft_hard != NULL;
 
-       if (protocol != IPPROTO_ESP && protocol != IPPROTO_AH)
+       if (protocol == IPPROTO_ESP || protocol == IPPROTO_AH)
        {
-               DBG2(DBG_KNL, "ignoring SADB_EXPIRE for SA with SPI %.8x and "
-                                         "reqid {%u} which is not a CHILD_SA", ntohl(spi), reqid);
-               return;
+               dst = host_create_from_sockaddr((sockaddr_t*)(response.dst + 1));
+               if (dst)
+               {
+                       hydra->kernel_interface->expire(hydra->kernel_interface, protocol,
+                                                                                       spi, dst, hard);
+                       dst->destroy(dst);
+               }
        }
-
-       hydra->kernel_interface->expire(hydra->kernel_interface, reqid, protocol,
-                                                                       spi, hard);
 }
 
 #ifdef SADB_X_MIGRATE
index c5c39b0f11350121f380887c91a11fb7ea6a7cff..f15f6fe5291cb6152cefd6b5a6fbe580f762219a 100644 (file)
@@ -35,14 +35,12 @@ struct ipsec_event_listener_t {
        /**
         * Called when the lifetime of an IPsec SA expired
         *
-        * @param reqid                 reqid of the expired SA
         * @param protocol              protocol of the expired SA
         * @param spi                   spi of the expired SA
+        * @param dst                   destination address of expired SA
         * @param hard                  TRUE if this is a hard expire, FALSE otherwise
         */
-       void (*expire)(u_int32_t reqid, u_int8_t protocol, u_int32_t spi,
-                                  bool hard);
-
+       void (*expire)(u_int8_t protocol, u_int32_t spi, host_t *dst, bool hard);
 };
 
 #endif /** IPSEC_EVENT_LISTENER_H_ @}*/
index c6b2a550d62e1b4c37ccf81e10d767f74bfe34ed..048063053a78d85adcea1553c322fa7cd5870e54 100644 (file)
@@ -65,23 +65,26 @@ typedef struct {
        } type;
 
        /**
-        * Reqid of the SA, if any
+        * Protocol of the SA
         */
-       u_int32_t reqid;
+       u_int8_t protocol;
 
        /**
         * SPI of the SA, if any
         */
        u_int32_t spi;
 
+       /**
+        * SA destination address
+        */
+       host_t *dst;
+
        /**
         * Additional data for specific event types
         */
        union {
 
                struct {
-                       /** Protocol of the SA */
-                       u_int8_t protocol;
                        /** TRUE in case of a hard expire */
                        bool hard;
                } expire;
@@ -90,6 +93,15 @@ typedef struct {
 
 } ipsec_event_t;
 
+/**
+ * Destroy IPsec event data
+ */
+static void ipsec_event_destroy(ipsec_event_t *event)
+{
+       event->dst->destroy(event->dst);
+       free(event);
+}
+
 /**
  * Dequeue events and relay them to listeners
  */
@@ -110,31 +122,31 @@ static job_requeue_t handle_events(private_ipsec_event_relay_t *this)
                        case IPSEC_EVENT_EXPIRE:
                                if (current->expire)
                                {
-                                       current->expire(event->reqid, event->data.expire.protocol,
-                                                                       event->spi, event->data.expire.hard);
+                                       current->expire(event->protocol, event->spi, event->dst,
+                                                                       event->data.expire.hard);
                                }
                                break;
                }
        }
        enumerator->destroy(enumerator);
        this->lock->unlock(this->lock);
-       free(event);
+       ipsec_event_destroy(event);
        return JOB_REQUEUE_DIRECT;
 }
 
 METHOD(ipsec_event_relay_t, expire, void,
-       private_ipsec_event_relay_t *this, u_int32_t reqid, u_int8_t protocol,
-       u_int32_t spi, bool hard)
+       private_ipsec_event_relay_t *this, u_int8_t protocol, u_int32_t spi,
+       host_t *dst, bool hard)
 {
        ipsec_event_t *event;
 
        INIT(event,
                .type = IPSEC_EVENT_EXPIRE,
-               .reqid = reqid,
+               .protocol = protocol,
                .spi = spi,
+               .dst = dst->clone(dst),
                .data = {
                        .expire = {
-                               .protocol = protocol,
                                .hard = hard,
                        },
                },
index c6935d54658972c83b8fce99b677f6053bd2d01d..1dddf121bbaa5fab21ca12a2e6cfd39f05df9e6a 100644 (file)
@@ -38,13 +38,13 @@ struct ipsec_event_relay_t {
        /**
         * Raise an expire event.
         *
-        * @param reqid                 reqid of the expired IPsec SA
         * @param protocol              protocol (e.g ESP) of the expired SA
         * @param spi                   SPI of the expired SA
+        * @param dst                   destination address of expired SA
         * @param hard                  TRUE for a hard expire, FALSE otherwise
         */
-       void (*expire)(ipsec_event_relay_t *this, u_int32_t reqid,
-                                  u_int8_t protocol, u_int32_t spi, bool hard);
+       void (*expire)(ipsec_event_relay_t *this, u_int8_t protocol, u_int32_t spi,
+                                  host_t *dst, bool hard);
 
        /**
         * Register a listener to events raised by this manager
index 3d0bbe169d58c715d1a8a4f65d5ee15fcc488bfa..ccbbb1b3cc2380b9750958006d5a4c574dec151d 100644 (file)
@@ -194,8 +194,8 @@ METHOD(ipsec_sa_t, expire, void,
                if (!this->hard_expired)
                {
                        this->hard_expired = TRUE;
-                       ipsec->events->expire(ipsec->events, this->reqid, this->protocol,
-                                                                 this->spi, TRUE);
+                       ipsec->events->expire(ipsec->events, this->protocol, this->spi,
+                                                                 this->dst, TRUE);
                }
        }
        else
@@ -203,8 +203,8 @@ METHOD(ipsec_sa_t, expire, void,
                if (!this->hard_expired && !this->soft_expired)
                {
                        this->soft_expired = TRUE;
-                       ipsec->events->expire(ipsec->events, this->reqid, this->protocol,
-                                                                 this->spi, FALSE);
+                       ipsec->events->expire(ipsec->events, this->protocol, this->spi,
+                                                                 this->dst, FALSE);
                }
        }
 }