diff options
author | Martin Willi <martin@revosec.ch> | 2015-03-31 17:25:05 +0200 |
---|---|---|
committer | Martin Willi <martin@revosec.ch> | 2015-04-15 13:44:40 +0200 |
commit | f206bb74449f46c0558993f2b779ffa096fb32f2 (patch) | |
tree | 9b7a2e4058621aea4dd3184d78c47a39f6520bf1 /src/libstrongswan/utils/utils.c | |
parent | edab6c658c7d0c2d21877bf7aaad218c4b1c8167 (diff) | |
download | strongswan-f206bb74449f46c0558993f2b779ffa096fb32f2.tar.bz2 strongswan-f206bb74449f46c0558993f2b779ffa096fb32f2.tar.xz |
utils: Add malloc/free wrappers returning aligned data
While we could use posix_memalign(3), that is not fully portable. Further, it
might be difficult on some platforms to properly catch it in leak-detective,
which results in invalid free()s when releasing such memory.
We instead use a simple wrapper, which allocates larger data, and saves the
padding size in the allocated header. This requires that memory is released
using a dedicated function.
To reduce the risk of invalid free() when working on corrupted data, we fill up
all the padding with the padding length, and verify it during free_align().
Diffstat (limited to 'src/libstrongswan/utils/utils.c')
-rw-r--r-- | src/libstrongswan/utils/utils.c | 44 |
1 files changed, 44 insertions, 0 deletions
diff --git a/src/libstrongswan/utils/utils.c b/src/libstrongswan/utils/utils.c index 3d5e3dfc9..119c6563a 100644 --- a/src/libstrongswan/utils/utils.c +++ b/src/libstrongswan/utils/utils.c @@ -61,6 +61,50 @@ ENUM(status_names, SUCCESS, NEED_MORE, /** * Described in header. */ +void* malloc_align(size_t size, u_int8_t align) +{ + u_int8_t pad; + void *ptr; + + if (align == 0) + { + align = 1; + } + ptr = malloc(align + sizeof(pad) + size); + if (!ptr) + { + return NULL; + } + /* store padding length just before data, down to the allocation boundary + * to do some verification during free_align() */ + pad = align - ((uintptr_t)ptr % align); + memset(ptr, pad, pad); + return ptr + pad; +} + +/** + * Described in header. + */ +void free_align(void *ptr) +{ + u_int8_t pad, *pos; + + pos = ptr - 1; + /* verify padding to check any corruption */ + for (pad = *pos; (void*)pos >= ptr - pad; pos--) + { + if (*pos != pad) + { + DBG1(DBG_LIB, "!!!! invalid free_align() !!!!"); + return; + } + } + free(ptr - pad); +} + +/** + * Described in header. + */ void memxor(u_int8_t dst[], u_int8_t src[], size_t n) { int m, i; |