farp: Only cache IPv4 traffic selectors
authorTobias Brunner <tobias@strongswan.org>
Tue, 26 Nov 2019 16:55:47 +0000 (17:55 +0100)
committerTobias Brunner <tobias@strongswan.org>
Fri, 6 Dec 2019 08:58:29 +0000 (09:58 +0100)
Since ARP is IPv4 only there is no point caching IPv6 traffic
selectors/CHILD_SAs.

src/libcharon/plugins/farp/farp_listener.c

index 28ced54..377dda3 100644 (file)
@@ -1,4 +1,7 @@
 /*
+ * Copyright (C) 2019 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
  * Copyright (C) 2010 Martin Willi
  * Copyright (C) 2010 revosec AG
  *
@@ -53,6 +56,18 @@ typedef struct {
        uint32_t reqid;
 } entry_t;
 
+/**
+ * Destroy a cache entry
+ */
+static void destroy_entry(entry_t *this)
+{
+       this->local->destroy_offset(this->local,
+                                                               offsetof(traffic_selector_t, destroy));
+       this->remote->destroy_offset(this->remote,
+                                                                offsetof(traffic_selector_t, destroy));
+       free(this);
+}
+
 METHOD(listener_t, child_updown, bool,
        private_farp_listener_t *this, ike_sa_t *ike_sa, child_sa_t *child_sa,
        bool up)
@@ -69,20 +84,35 @@ METHOD(listener_t, child_updown, bool,
                        .reqid = child_sa->get_reqid(child_sa),
                );
 
-               enumerator = child_sa->create_ts_enumerator(child_sa, TRUE);
+               enumerator = child_sa->create_ts_enumerator(child_sa, FALSE);
                while (enumerator->enumerate(enumerator, &ts))
                {
-                       entry->local->insert_last(entry->local, ts->clone(ts));
+                       if (ts->get_type(ts) != TS_IPV4_ADDR_RANGE)
+                       {
+                               continue;
+                       }
+                       entry->remote->insert_last(entry->remote, ts->clone(ts));
                }
                enumerator->destroy(enumerator);
 
-               enumerator = child_sa->create_ts_enumerator(child_sa, FALSE);
+               enumerator = child_sa->create_ts_enumerator(child_sa, TRUE);
                while (enumerator->enumerate(enumerator, &ts))
                {
-                       entry->remote->insert_last(entry->remote, ts->clone(ts));
+                       if (ts->get_type(ts) != TS_IPV4_ADDR_RANGE)
+                       {
+                               continue;
+                       }
+                       entry->local->insert_last(entry->local, ts->clone(ts));
                }
                enumerator->destroy(enumerator);
 
+               if (!entry->remote->get_count(entry->remote) ||
+                       !entry->local->get_count(entry->local))
+               {
+                       destroy_entry(entry);
+                       return TRUE;
+               }
+
                this->lock->write_lock(this->lock);
                this->entries->insert_last(this->entries, entry);
                this->lock->unlock(this->lock);
@@ -96,11 +126,7 @@ METHOD(listener_t, child_updown, bool,
                        if (entry->reqid == child_sa->get_reqid(child_sa))
                        {
                                this->entries->remove_at(this->entries, enumerator);
-                               entry->local->destroy_offset(entry->local,
-                                                                               offsetof(traffic_selector_t, destroy));
-                               entry->remote->destroy_offset(entry->remote,
-                                                                               offsetof(traffic_selector_t, destroy));
-                               free(entry);
+                               destroy_entry(entry);
                                break;
                        }
                }