summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSøren Sandmann Pedersen <sandmann@daimi.au.dk>2009-04-17 22:34:03 -0400
committerSøren Sandmann Pedersen <sandmann@daimi.au.dk>2009-04-17 22:34:03 -0400
commit7b2ba6dfce48c9aa7df7c5e096bc74bd023b2efc (patch)
tree1a446e52f82fb12ca140fabcdadd828feb6829bd
parent1de63e9dc588e4e95657563638ea5cb8b19cdaf0 (diff)
Add prefixes to arrays
-rw-r--r--Makefile.am6
-rw-r--r--array.c29
-rw-r--r--libnul.h1
-rw-r--r--prefix-test.c40
4 files changed, 68 insertions, 8 deletions
diff --git a/Makefile.am b/Makefile.am
index 530e464..485385a 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -25,13 +25,17 @@ libnul_la_LIBADD = @DEP_LIBS@ libffi/libffi_convenience.la
libnul_la_LDFLAGS = -no-undefined
-noinst_PROGRAMS = example dbw-example
+noinst_PROGRAMS = example dbw-example prefix-test
+
example_SOURCES = example.c
example_LDADD = $(top_builddir)/libnul.la
dbw_example_SOURCES = dbw-example.c
dbw_example_LDADD = $(top_builddir)/libnul.la
+prefix_test_SOURCES = prefix-test.c
+prefix_test_LDADD = $(top_builddir)/libnul.la
+
pkgconfigdir = $(libdir)/pkgconfig
pkgconfig_DATA = libnul.pc
diff --git a/array.c b/array.c
index d436414..f8e9b82 100644
--- a/array.c
+++ b/array.c
@@ -39,6 +39,7 @@ struct array_t
gssize n_elements; /* Number of elements in use, not including
* the nul terminator
*/
+ gssize n_prefix_bytes; /* Number of data bytes used for the application prefix */
align_t data[1];
};
@@ -65,7 +66,10 @@ array_free (void *data, const int *magic)
static void
nul_terminate (array_t *array)
{
- char *end = (char *)array->data + array->n_elements * array->element_size;
+ char *end = (char *)array->data;
+
+ end += array->n_prefix_bytes;
+ end += array->n_elements * array->element_size;
memset (end, 0, array->element_size);
}
@@ -78,6 +82,7 @@ realloc_array (array_t *array, int n_elements)
/* FIXME: overflow? */
n_bytes = NUL_STRUCT_OFFSET (array_t, data);
n_bytes += (n_elements + 1) * array->element_size;
+ n_bytes += array->n_prefix_bytes;
if (n_bytes > array->n_bytes)
{
@@ -97,12 +102,13 @@ realloc_array (array_t *array, int n_elements)
}
static void *
-array_new (int element_size, const int *magic)
+array_new (int element_size, const int *magic, int n_prefix_bytes)
{
array_t *array = g_new (array_t, 1);
array->magic = magic;
array->element_size = element_size;
+ array->n_prefix_bytes = n_prefix_bytes;
array->n_bytes = sizeof (array_t);
array->n_elements = 0;
@@ -117,13 +123,16 @@ array_delete_head (void *data, const int *magic, gssize n_elements)
array_t *array = get_array (data, magic);
int n_bytes = n_elements * array->element_size;
int n_total = array->n_elements * array->element_size;
+ char *first;
if (n_elements < 0 || n_elements > array->n_elements)
n_bytes = n_total;
/* FIXME: this should be done in constant time */
+
+ first = (char *)array->data + array->n_prefix_bytes;
- memmove (array->data, (char *)array->data + n_bytes, n_total - n_bytes);
+ memmove (first, first + n_bytes, n_total - n_bytes);
array->n_elements -= n_elements;
@@ -158,7 +167,7 @@ array_append_undefined (void *data,
nul_terminate (array);
if (tail)
- *tail = (char *)array->data + array->element_size * (array->n_elements - n_elements);
+ *tail = (char *)array->data + array->n_prefix_bytes + array->element_size * (array->n_elements - n_elements);
return array->data;
}
@@ -205,7 +214,13 @@ static const int arr_t_magic;
nul_ptr_t
nul_array_new (int element_size)
{
- return array_new (element_size, &arr_t_magic);
+ return array_new (element_size, &arr_t_magic, 0);
+}
+
+nul_ptr_t
+nul_array_new_prefix (int element_size, int prefix_size)
+{
+ return array_new (element_size, &arr_t_magic, prefix_size);
}
nul_ptr_t
@@ -256,7 +271,7 @@ static const int parr_t_magic;
void **
nul_ptr_array_new (void)
{
- return array_new (sizeof (void *), &parr_t_magic);
+ return array_new (sizeof (void *), &parr_t_magic, 0);
}
void **
@@ -285,7 +300,7 @@ static const int string_t_magic;
nul_string_t *
nul_string_new (void)
{
- return array_new (sizeof (char), &string_t_magic);
+ return array_new (sizeof (char), &string_t_magic, 0);
}
void
diff --git a/libnul.h b/libnul.h
index f22acf7..3bf4106 100644
--- a/libnul.h
+++ b/libnul.h
@@ -53,6 +53,7 @@ typedef void * const nul_const_ptr_t;
* Generic arrays
*/
nul_ptr_t nul_array_new (int element_size) NUL_UR;
+nul_ptr_t nul_array_new_prefix (int element_size, int prefix_size); NUL_UR;
nul_ptr_t nul_array_append (nul_ptr_t array, nul_ptr_t element) NUL_UR;
gsize nul_array_len (nul_ptr_t array);
void nul_array_free (nul_ptr_t array);
diff --git a/prefix-test.c b/prefix-test.c
new file mode 100644
index 0000000..5c44562
--- /dev/null
+++ b/prefix-test.c
@@ -0,0 +1,40 @@
+#include <stdio.h>
+#include <libnul.h>
+
+typedef struct
+{
+ int a;
+ int b;
+ char *x;
+
+ int data[1];
+
+} prefixed_t;
+
+
+int
+main (void)
+{
+ int i;
+ prefixed_t *prefixed = nul_array_new_prefix (
+ sizeof (int), NUL_STRUCT_OFFSET (prefixed_t, data));
+
+ prefixed->a = 0xaaaaaaaa;
+ prefixed->b = 0xbbbbbbbb;
+ prefixed->x = "HI!";
+
+ i = 0;
+ prefixed = nul_array_append (prefixed, &i); i++;
+ prefixed = nul_array_append (prefixed, &i); i++;
+ prefixed = nul_array_append (prefixed, &i); i++;
+ prefixed = nul_array_append (prefixed, &i); i++;
+ prefixed = nul_array_append (prefixed, &i); i++;
+ prefixed = nul_array_append (prefixed, &i); i++;
+
+ for (i = 0; i < nul_array_len (prefixed); ++i)
+ {
+ printf ("%d\n", prefixed->data[i]);
+ }
+
+ return 0;
+}