summaryrefslogtreecommitdiff
path: root/src/libhydra/attributes/mem_pool.c
diff options
context:
space:
mode:
authorYves-Alexis Perez <corsac@debian.org>2013-04-26 14:57:47 +0200
committerYves-Alexis Perez <corsac@debian.org>2013-04-26 14:57:47 +0200
commit10e5fb2b9b2f27c83b3e5a1d048b158d5cf42a43 (patch)
treebf1d05a2e37dbd1911b86fcc026fbe49b0239c71 /src/libhydra/attributes/mem_pool.c
parent7585facf05d927eb6df3929ce09ed5e60d905437 (diff)
downloadvyos-strongswan-10e5fb2b9b2f27c83b3e5a1d048b158d5cf42a43.tar.gz
vyos-strongswan-10e5fb2b9b2f27c83b3e5a1d048b158d5cf42a43.zip
Imported Upstream version 5.0.3
Diffstat (limited to 'src/libhydra/attributes/mem_pool.c')
-rw-r--r--src/libhydra/attributes/mem_pool.c55
1 files changed, 50 insertions, 5 deletions
diff --git a/src/libhydra/attributes/mem_pool.c b/src/libhydra/attributes/mem_pool.c
index af53e10de..c82b1d02f 100644
--- a/src/libhydra/attributes/mem_pool.c
+++ b/src/libhydra/attributes/mem_pool.c
@@ -21,7 +21,7 @@
#include <collections/linked_list.h>
#include <threading/mutex.h>
-#define POOL_LIMIT (sizeof(uintptr_t)*8)
+#define POOL_LIMIT (sizeof(u_int)*8 - 1)
typedef struct private_mem_pool_t private_mem_pool_t;
@@ -513,12 +513,11 @@ METHOD(mem_pool_t, destroy, void,
}
/**
- * Described in header
+ * Generic constructor
*/
-mem_pool_t *mem_pool_create(char *name, host_t *base, int bits)
+static private_mem_pool_t *create_generic(char *name)
{
private_mem_pool_t *this;
- int addr_bits;
INIT(this,
.public = {
@@ -538,6 +537,18 @@ mem_pool_t *mem_pool_create(char *name, host_t *base, int bits)
.mutex = mutex_create(MUTEX_TYPE_DEFAULT),
);
+ return this;
+}
+
+/**
+ * Described in header
+ */
+mem_pool_t *mem_pool_create(char *name, host_t *base, int bits)
+{
+ private_mem_pool_t *this;
+ int addr_bits;
+
+ this = create_generic(name);
if (base)
{
addr_bits = base->get_family(base) == AF_INET ? 32 : 128;
@@ -550,7 +561,7 @@ mem_pool_t *mem_pool_create(char *name, host_t *base, int bits)
DBG1(DBG_CFG, "virtual IP pool too large, limiting to %H/%d",
base, addr_bits - bits);
}
- this->size = 1 << (bits);
+ this->size = 1 << bits;
if (this->size > 2)
{ /* do not use first and last addresses of a block */
@@ -563,3 +574,37 @@ mem_pool_t *mem_pool_create(char *name, host_t *base, int bits)
return &this->public;
}
+/**
+ * Described in header
+ */
+mem_pool_t *mem_pool_create_range(char *name, host_t *from, host_t *to)
+{
+ private_mem_pool_t *this;
+ chunk_t fromaddr, toaddr;
+ u_int32_t diff;
+
+ fromaddr = from->get_address(from);
+ toaddr = to->get_address(to);
+
+ if (from->get_family(from) != to->get_family(to) ||
+ fromaddr.len != toaddr.len || fromaddr.len < sizeof(diff) ||
+ memcmp(fromaddr.ptr, toaddr.ptr, toaddr.len) > 0)
+ {
+ DBG1(DBG_CFG, "invalid IP address range: %H-%H", from, to);
+ return NULL;
+ }
+ if (fromaddr.len > sizeof(diff) &&
+ !chunk_equals(chunk_create(fromaddr.ptr, fromaddr.len - sizeof(diff)),
+ chunk_create(toaddr.ptr, toaddr.len - sizeof(diff))))
+ {
+ DBG1(DBG_CFG, "IP address range too large: %H-%H", from, to);
+ return NULL;
+ }
+ this = create_generic(name);
+ this->base = from->clone(from);
+ diff = untoh32(toaddr.ptr + toaddr.len - sizeof(diff)) -
+ untoh32(fromaddr.ptr + fromaddr.len - sizeof(diff));
+ this->size = diff + 1;
+
+ return &this->public;
+}