[PATCH 1/2] NVTable: allow huge LogMessage data
Balazs Scheidler
bazsi at balabit.hu
Tue Jan 31 18:14:44 CET 2012
This patch converts NVTable to use 32 bit offsets/sizes in order to allow
maximum 4GB log records, each value holding maximum 4GB data. The NVTable
structure is still artificially limited to 256MB in size.
Signed-off-by: Peter Eisenlohr <peter.eisenlohr at inform-software.com>
Signed-off-by: Balazs Scheidler <bazsi at balabit.hu>
---
lib/logmsg.h | 9 +++-
lib/nvtable.c | 114 +++++++++++++++++++++++---------------------
lib/nvtable.h | 68 ++++++++++++++-------------
tests/unit/test_nvtable.c | 8 ++--
4 files changed, 107 insertions(+), 92 deletions(-)
diff --git a/lib/logmsg.h b/lib/logmsg.h
index 418b884..926a50c 100644
--- a/lib/logmsg.h
+++ b/lib/logmsg.h
@@ -62,6 +62,13 @@ enum
LM_V_MSGID,
LM_V_SOURCE,
LM_V_LEGACY_MSGHDR,
+
+ /* NOTE: this is used as the number of "statically" allocated elements in
+ * an NVTable. NVTable may impose restrictions on this value (for
+ * instance had to be an even number earlier). So be sure to validate
+ * whether LM_V_MAX would fit NVTable if you add further enums here.
+ */
+
LM_V_MAX,
};
@@ -203,7 +210,7 @@ log_msg_get_value(LogMessage *self, NVHandle handle, gssize *value_len)
flags = nv_registry_get_handle_flags(logmsg_registry, handle);
if ((flags & LM_VF_MACRO) == 0)
- return __nv_table_get_value(self->payload, handle, NV_TABLE_BOUND_NUM_STATIC(LM_V_MAX), value_len);
+ return __nv_table_get_value(self->payload, handle, LM_V_MAX, value_len);
else
return log_msg_get_macro_value(self, flags >> 8, value_len);
}
diff --git a/lib/nvtable.c b/lib/nvtable.c
index adf4693..e86b6c3 100644
--- a/lib/nvtable.c
+++ b/lib/nvtable.c
@@ -147,34 +147,35 @@ nv_registry_free(NVRegistry *self)
/* clonable LogMessage support with shared data pointers */
-#define NV_TABLE_DYNVALUE_HANDLE(x) ((x) >> 16)
-#define NV_TABLE_DYNVALUE_OFS(x) ((x) & 0xFFFF)
+#define NV_TABLE_DYNVALUE_HANDLE(x) ((x).handle)
+#define NV_TABLE_DYNVALUE_OFS(x) ((x).ofs)
static inline gchar *
nv_table_get_bottom(NVTable *self)
{
- return nv_table_get_top(self) - (self->used << NV_TABLE_SCALE);
+ return nv_table_get_top(self) - self->used;
}
static inline gchar *
nv_table_get_ofs_table_top(NVTable *self)
{
- return (gchar *) &self->data[self->num_static_entries * sizeof(self->static_entries[0]) + self->num_dyn_entries * sizeof(guint32)];
+ return (gchar *) &self->data[self->num_static_entries * sizeof(self->static_entries[0]) +
+ self->num_dyn_entries * sizeof(NVDynValue)];
}
static inline NVEntry *
-nv_table_get_entry_at_ofs(NVTable *self, guint16 ofs)
+nv_table_get_entry_at_ofs(NVTable *self, guint32 ofs)
{
if (!ofs)
return NULL;
- return (NVEntry *) (nv_table_get_top(self) - (ofs << NV_TABLE_SCALE));
+ return (NVEntry *) (nv_table_get_top(self) - ofs);
}
-static inline guint32 *
+static inline NVDynValue *
nv_table_get_dyn_entries(NVTable *self)
{
- return (guint32 *) &self->static_entries[self->num_static_entries];
+ return (NVDynValue *) &self->static_entries[self->num_static_entries];
}
static inline gboolean
@@ -195,9 +196,9 @@ nv_table_alloc_value(NVTable *self, gsize alloc_size)
/* alloc error, NVTable should be realloced */
if (!nv_table_alloc_check(self, alloc_size))
return NULL;
- self->used += alloc_size >> NV_TABLE_SCALE;
- entry = (NVEntry *) (nv_table_get_top(self) - (self->used << NV_TABLE_SCALE));
- entry->alloc_len = alloc_size >> NV_TABLE_SCALE;
+ self->used += alloc_size;
+ entry = (NVEntry *) (nv_table_get_top(self) - (self->used));
+ entry->alloc_len = alloc_size;
entry->indirect = FALSE;
entry->referenced = FALSE;
return entry;
@@ -211,8 +212,11 @@ nv_table_resolve_indirect(NVTable *self, NVEntry *entry, gssize *length)
gssize referenced_length;
referenced_value = nv_table_get_value(self, entry->vindirect.handle, &referenced_length);
- if (entry->vindirect.ofs > referenced_length)
+ if (entry->vindirect.ofs > referenced_length) {
+ if (length)
+ *length = 0;
return null_string;
+ }
/* here we assume that indirect references are only looked up with
* non-zero terminated strings properly handled, thus the caller has
@@ -228,7 +232,7 @@ nv_table_resolve_entry(NVTable *self, NVEntry *entry, gssize *length)
if (!entry->indirect)
{
if (length)
- *length = entry->vdirect.value_len_lo + (entry->vdirect.value_len_hi << 16);
+ *length = entry->vdirect.value_len;
return entry->vdirect.data + entry->name_len + 1;
}
else
@@ -236,11 +240,11 @@ nv_table_resolve_entry(NVTable *self, NVEntry *entry, gssize *length)
}
NVEntry *
-nv_table_get_entry_slow(NVTable *self, NVHandle handle, guint32 **dyn_slot)
+nv_table_get_entry_slow(NVTable *self, NVHandle handle, NVDynValue **dyn_slot)
{
- guint16 ofs;
+ guint32 ofs;
gint l, h, m;
- guint32 *dyn_entries = nv_table_get_dyn_entries(self);
+ NVDynValue *dyn_entries = nv_table_get_dyn_entries(self);
guint32 mv;
if (!self->num_dyn_entries)
@@ -274,16 +278,17 @@ nv_table_get_entry_slow(NVTable *self, NVHandle handle, guint32 **dyn_slot)
}
}
- return nv_table_get_entry_at_ofs(self, ofs);
+ NVEntry *entry = nv_table_get_entry_at_ofs(self, ofs);
+ return entry;
}
static gboolean
-nv_table_reserve_table_entry(NVTable *self, NVHandle handle, guint32 **dyn_slot)
+nv_table_reserve_table_entry(NVTable *self, NVHandle handle, NVDynValue **dyn_slot)
{
if (G_UNLIKELY(!(*dyn_slot) && handle > self->num_static_entries))
{
/* this is a dynamic value */
- guint32 *dyn_entries = nv_table_get_dyn_entries(self);;
+ NVDynValue *dyn_entries = nv_table_get_dyn_entries(self);;
gint l, h, m, ndx;
gboolean found = FALSE;
@@ -329,7 +334,8 @@ nv_table_reserve_table_entry(NVTable *self, NVHandle handle, guint32 **dyn_slot)
/* we set ofs to zero here, which means that the NVEntry won't
be found even if the slot is present in dyn_entries */
- **dyn_slot = (handle << 16) + 0;
+ (**dyn_slot).handle = handle;
+ (**dyn_slot).ofs = 0;
if (!found)
self->num_dyn_entries++;
}
@@ -337,7 +343,7 @@ nv_table_reserve_table_entry(NVTable *self, NVHandle handle, guint32 **dyn_slot)
}
static inline void
-nv_table_set_table_entry(NVTable *self, NVHandle handle, guint16 ofs, guint32 *dyn_slot)
+nv_table_set_table_entry(NVTable *self, NVHandle handle, guint32 ofs, NVDynValue *dyn_slot)
{
if (G_LIKELY(handle <= self->num_static_entries))
{
@@ -347,7 +353,8 @@ nv_table_set_table_entry(NVTable *self, NVHandle handle, guint16 ofs, guint32 *d
else
{
/* this is a dynamic value */
- *dyn_slot = (handle << 16) + ofs;
+ (*dyn_slot).handle = handle;
+ (*dyn_slot).ofs = ofs;
}
}
@@ -379,11 +386,11 @@ gboolean
nv_table_add_value(NVTable *self, NVHandle handle, const gchar *name, gsize name_len, const gchar *value, gsize value_len, gboolean *new_entry)
{
NVEntry *entry;
- guint16 ofs;
- guint32 *dyn_slot;
+ guint32 ofs;
+ NVDynValue *dyn_slot;
- if (value_len > 255 * 1024)
- value_len = 255 * 1024;
+ if (value_len > NV_TABLE_MAX_BYTES)
+ value_len = NV_TABLE_MAX_BYTES;
if (new_entry)
*new_entry = FALSE;
entry = nv_table_get_entry(self, handle, &dyn_slot);
@@ -407,7 +414,7 @@ nv_table_add_value(NVTable *self, NVHandle handle, const gchar *name, gsize name
return FALSE;
}
}
- if (G_UNLIKELY(entry && (((guint) entry->alloc_len << NV_TABLE_SCALE)) >= value_len + NV_ENTRY_DIRECT_HDR + name_len + 2))
+ if (G_UNLIKELY(entry && (((guint) entry->alloc_len)) >= value_len + NV_ENTRY_DIRECT_HDR + name_len + 2))
{
gchar *dst;
/* this value already exists and the new value fits in the old space */
@@ -415,8 +422,7 @@ nv_table_add_value(NVTable *self, NVHandle handle, const gchar *name, gsize name
{
dst = entry->vdirect.data + entry->name_len + 1;
- entry->vdirect.value_len_lo = value_len & 0xFFFF;
- entry->vdirect.value_len_hi = (value_len >> 16);
+ entry->vdirect.value_len = value_len;
memcpy(dst, value, value_len);
dst[value_len] = 0;
}
@@ -424,8 +430,7 @@ nv_table_add_value(NVTable *self, NVHandle handle, const gchar *name, gsize name
{
/* this was an indirect entry, convert it */
entry->indirect = 0;
- entry->vdirect.value_len_lo = value_len & 0xFFFF;
- entry->vdirect.value_len_hi = (value_len >> 16);
+ entry->vdirect.value_len = value_len;
entry->name_len = name_len;
memcpy(entry->vdirect.data, name, name_len + 1);
memcpy(entry->vdirect.data + name_len + 1, value, value_len);
@@ -446,9 +451,8 @@ nv_table_add_value(NVTable *self, NVHandle handle, const gchar *name, gsize name
return FALSE;
}
- ofs = (nv_table_get_top(self) - (gchar *) entry) >> NV_TABLE_SCALE;
- entry->vdirect.value_len_lo = value_len & 0xFFFF;
- entry->vdirect.value_len_hi = value_len >> 16;
+ ofs = (nv_table_get_top(self) - (gchar *) entry);
+ entry->vdirect.value_len = value_len;
if (handle >= self->num_static_entries)
{
/* we only store the name for non-builtin values */
@@ -465,11 +469,11 @@ nv_table_add_value(NVTable *self, NVHandle handle, const gchar *name, gsize name
}
gboolean
-nv_table_add_value_indirect(NVTable *self, NVHandle handle, const gchar *name, gsize name_len, NVHandle ref_handle, guint8 type, guint16 rofs, guint16 rlen, gboolean *new_entry)
+nv_table_add_value_indirect(NVTable *self, NVHandle handle, const gchar *name, gsize name_len, NVHandle ref_handle, guint8 type, guint32 rofs, guint32 rlen, gboolean *new_entry)
{
NVEntry *entry, *ref_entry;
- guint32 *dyn_slot;
- guint16 ofs;
+ NVDynValue *dyn_slot;
+ guint32 ofs;
if (new_entry)
*new_entry = FALSE;
@@ -513,7 +517,7 @@ nv_table_add_value_indirect(NVTable *self, NVHandle handle, const gchar *name, g
if (!nv_table_foreach_entry(self, nv_table_make_direct, data))
return FALSE;
}
- if (entry && (((guint) entry->alloc_len << NV_TABLE_SCALE) >= NV_ENTRY_INDIRECT_HDR + name_len + 1))
+ if (entry && (((guint) entry->alloc_len) >= NV_ENTRY_INDIRECT_HDR + name_len + 1))
{
/* this value already exists and the new reference fits in the old space */
ref_entry->referenced = TRUE;
@@ -548,7 +552,7 @@ nv_table_add_value_indirect(NVTable *self, NVHandle handle, const gchar *name, g
return FALSE;
}
- ofs = (nv_table_get_top(self) - (gchar *) entry) >> NV_TABLE_SCALE;
+ ofs = (nv_table_get_top(self) - (gchar *) entry);
entry->vindirect.handle = ref_handle;
entry->vindirect.ofs = rofs;
entry->vindirect.len = rlen;
@@ -564,6 +568,7 @@ nv_table_add_value_indirect(NVTable *self, NVHandle handle, const gchar *name, g
entry->name_len = 0;
nv_table_set_table_entry(self, handle, ofs, dyn_slot);
+
return TRUE;
}
@@ -592,7 +597,7 @@ nv_table_foreach(NVTable *self, NVRegistry *registry, NVTableForeachFunc func, g
gboolean
nv_table_foreach_entry(NVTable *self, NVTableForeachEntryFunc func, gpointer user_data)
{
- guint32 *dyn_entries;
+ NVDynValue *dyn_entries;
NVEntry *entry;
gint i;
@@ -633,11 +638,11 @@ nv_table_clear(NVTable *self)
void
nv_table_init(NVTable *self, gsize alloc_length, gint num_static_entries)
{
- g_assert(alloc_length <= NVTABLE_MAX_BYTES);
- self->size = alloc_length >> NV_TABLE_SCALE;
+ g_assert(alloc_length <= NV_TABLE_MAX_BYTES);
+ self->size = alloc_length;
self->used = 0;
self->num_dyn_entries = 0;
- self->num_static_entries = NV_TABLE_BOUND_NUM_STATIC(num_static_entries);
+ self->num_static_entries = num_static_entries;
self->ref_cnt = 1;
self->borrowed = FALSE;
memset(&self->static_entries[0], 0, self->num_static_entries * sizeof(self->static_entries[0]));
@@ -677,33 +682,33 @@ nv_table_realloc(NVTable *self, NVTable **new)
/* double the size of the current allocation */
new_size = ((gsize) self->size) << 1;
- if (new_size > NVTABLE_MAX_SIZE)
- new_size = NVTABLE_MAX_SIZE;
+ if (new_size > NV_TABLE_MAX_BYTES)
+ new_size = NV_TABLE_MAX_BYTES;
if (new_size == old_size)
return FALSE;
if (self->ref_cnt == 1 && !self->borrowed)
{
- *new = self = g_realloc(self, new_size << NV_TABLE_SCALE);
+ *new = self = g_realloc(self, new_size);
self->size = new_size;
/* move the downwards growing region to the end of the new buffer */
memmove(NV_TABLE_ADDR(self, self->size - self->used),
NV_TABLE_ADDR(self, old_size - self->used),
- self->used << NV_TABLE_SCALE);
+ self->used);
}
else
{
- *new = g_malloc(new_size << NV_TABLE_SCALE);
+ *new = g_malloc(new_size);
/* we only copy the header first */
- memcpy(*new, self, sizeof(NVTable) + self->num_static_entries * sizeof(self->static_entries[0]) + self->num_dyn_entries * sizeof(guint32));
+ memcpy(*new, self, sizeof(NVTable) + self->num_static_entries * sizeof(self->static_entries[0]) + self->num_dyn_entries * sizeof(NVDynValue));
(*new)->ref_cnt = 1;
(*new)->borrowed = FALSE;
memmove(NV_TABLE_ADDR((*new), (*new)->size - (*new)->used),
NV_TABLE_ADDR(self, old_size - self->used),
- self->used << NV_TABLE_SCALE);
+ self->used);
nv_table_unref(self);
}
@@ -742,16 +747,17 @@ nv_table_clone(NVTable *self, gint additional_space)
if (nv_table_get_bottom(self) - nv_table_get_ofs_table_top(self) < additional_space)
new_size = self->size;
else
- new_size = self->size + (NV_TABLE_BOUND(additional_space) >> NV_TABLE_SCALE);
+ new_size = self->size + (NV_TABLE_BOUND(additional_space));
- new = g_malloc(new_size << NV_TABLE_SCALE);
- memcpy(new, self, sizeof(NVTable) + self->num_static_entries * sizeof(self->static_entries[0]) + self->num_dyn_entries * sizeof(guint32));
+ new = g_malloc(new_size);
+ memcpy(new, self, sizeof(NVTable) + self->num_static_entries * sizeof(self->static_entries[0]) + self->num_dyn_entries * sizeof(NVDynValue));
new->size = new_size;
new->ref_cnt = 1;
new->borrowed = FALSE;
memcpy(NV_TABLE_ADDR(new, new->size - new->used),
NV_TABLE_ADDR(self, self->size - self->used),
- self->used << NV_TABLE_SCALE);
+ self->used);
+
return new;
}
diff --git a/lib/nvtable.h b/lib/nvtable.h
index 60366f3..621e7d0 100644
--- a/lib/nvtable.h
+++ b/lib/nvtable.h
@@ -29,12 +29,19 @@
typedef struct _NVTable NVTable;
typedef struct _NVRegistry NVRegistry;
+typedef struct _NVDynValue NVDynValue;
typedef struct _NVEntry NVEntry;
-typedef guint16 NVHandle;
+typedef guint32 NVHandle;
typedef struct _NVHandleDesc NVHandleDesc;
typedef gboolean (*NVTableForeachFunc)(NVHandle handle, const gchar *name, const gchar *value, gssize value_len, gpointer user_data);
typedef gboolean (*NVTableForeachEntryFunc)(NVHandle handle, NVEntry *entry, gpointer user_data);
+struct _NVDynValue
+{
+ NVHandle handle;
+ guint32 ofs;
+};
+
struct _NVHandleDesc
{
gchar *name;
@@ -89,11 +96,6 @@ nv_registry_get_handle_name(NVRegistry *self, NVHandle handle, gssize *length)
return stored->name;
}
-/* size related values are stored in guint16 divided by 4 */
-#define NVTABLE_MAX_BYTES (65535 * 4)
-/* the maximum value for the size member */
-#define NVTABLE_MAX_SIZE (65535)
-
/*
* Contains a name-value pair.
*/
@@ -102,21 +104,20 @@ struct _NVEntry
/* negative offset, counting from string table top, e.g. start of the string is at @top + ofs */
guint8 indirect:1, referenced:1;
guint8 name_len;
- guint16 alloc_len;
+ guint32 alloc_len;
union
{
struct
{
- guint16 value_len_lo;
- guint8 value_len_hi;
+ guint32 value_len;
/* variable data, first the name of this entry, then the value, both are NUL terminated */
gchar data[0];
} vdirect;
struct
{
NVHandle handle;
- guint16 ofs;
- guint16 len;
+ guint32 ofs;
+ guint32 len;
guint8 type;
gchar name[0];
} vindirect;
@@ -151,15 +152,15 @@ nv_entry_get_name(NVEntry *self)
* Name value area:
* - the name-value area grows down (e.g. lower addresses) from the end of the struct
* - name-value pairs are referenced by the offset counting down from the end of the struct
- * - all NV pairs are positioned at 4 bytes boundary, thus we can index 256k with 16 bits (65536 << 2)
+ * - all NV pairs are positioned at 4 bytes boundary, so 32 bit variables in NVEntry
+ * can be accessed in an aligned manner
*
* Static value offsets:
- * - a fixed size of guint16 array, containing 16 bit offsets for statically allocated entries
+ * - a fixed size of guint32 array, containing 32 bit offsets for statically allocated entries
* - the handles for static values have a low value and they match the index in this array
*
* Dynamic values:
- * - a dynamically sized guint32 array, the two high order bytes specify the global ID of the given value,
- * - the low order 16 bits is the offset in this payload where
+ * - a dynamically sized NVDynEntry array (contains ID + offset)
* - dynamic values are sorted by the global ID
*
* Memory allocation
@@ -183,8 +184,8 @@ nv_entry_get_name(NVEntry *self)
struct _NVTable
{
/* byte order indication, etc. */
- guint16 size;
- guint16 used;
+ guint32 size;
+ guint32 used;
guint16 num_dyn_entries;
guint8 num_static_entries;
guint8 ref_cnt:7,
@@ -194,20 +195,21 @@ struct _NVTable
union
{
guint32 __dummy_for_alignment;
- guint16 static_entries[0];
+ guint32 static_entries[0];
gchar data[0];
};
};
-#define NV_TABLE_SCALE 2
#define NV_TABLE_BOUND(x) (((x) + 0x3) & ~0x3)
-#define NV_TABLE_ADDR(self, x) ((gchar *) ((self)) + ((x) << NV_TABLE_SCALE))
-#define NV_TABLE_ESTIMATE(value_num, string_sum) ((value_num) * (sizeof(guint16) + sizeof(LogMessageStringTableEntry) + string_sum)
-#define NV_TABLE_BOUND_NUM_STATIC(x) ((x) & ~1)
+#define NV_TABLE_ADDR(self, x) ((gchar *) ((self)) + ((gssize)(x)))
+
+/* 256MB, this is an artificial limit, but must be less than MAX_GUINT32 as
+ * we want to compare a guint32 to this variable without overflow. */
+#define NV_TABLE_MAX_BYTES (256*1024*1024)
gboolean nv_table_add_value(NVTable *self, NVHandle handle, const gchar *name, gsize name_len, const gchar *value, gsize value_len, gboolean *new_entry);
-gboolean nv_table_add_value_indirect(NVTable *self, NVHandle handle, const gchar *name, gsize name_len, NVHandle ref_handle, guint8 type, guint16 ofs, guint16 len, gboolean *new_entry);
+gboolean nv_table_add_value_indirect(NVTable *self, NVHandle handle, const gchar *name, gsize name_len, NVHandle ref_handle, guint8 type, guint32 ofs, guint32 len, gboolean *new_entry);
gboolean nv_table_foreach(NVTable *self, NVRegistry *registry, NVTableForeachFunc func, gpointer user_data);
gboolean nv_table_foreach_entry(NVTable *self, NVTableForeachEntryFunc func, gpointer user_data);
@@ -226,11 +228,11 @@ nv_table_get_alloc_size(gint num_static_entries, gint num_dyn_values, gint init_
NVTable *self G_GNUC_UNUSED = NULL;
gsize size;
- size = NV_TABLE_BOUND(init_length) + NV_TABLE_BOUND(sizeof(NVTable) + num_static_entries * sizeof(self->static_entries[0]) + num_dyn_values * sizeof(guint32));
+ size = NV_TABLE_BOUND(init_length) + NV_TABLE_BOUND(sizeof(NVTable) + num_static_entries * sizeof(self->static_entries[0]) + num_dyn_values * sizeof(NVDynValue));
if (size < 128)
return 128;
- if (size > NVTABLE_MAX_BYTES)
- size = NVTABLE_MAX_BYTES;
+ if (size > NV_TABLE_MAX_BYTES)
+ size = NV_TABLE_MAX_BYTES;
return size;
}
@@ -241,14 +243,14 @@ nv_table_get_top(NVTable *self)
}
/* private declarations for inline functions */
-NVEntry *nv_table_get_entry_slow(NVTable *self, NVHandle handle, guint32 **dyn_slot);
+NVEntry *nv_table_get_entry_slow(NVTable *self, NVHandle handle, NVDynValue **dyn_slot);
const gchar *nv_table_resolve_indirect(NVTable *self, NVEntry *entry, gssize *len);
static inline NVEntry *
-__nv_table_get_entry(NVTable *self, NVHandle handle, guint16 num_static_entries, guint32 **dyn_slot)
+__nv_table_get_entry(NVTable *self, NVHandle handle, guint16 num_static_entries, NVDynValue **dyn_slot)
{
- guint16 ofs;
+ guint32 ofs;
if (G_UNLIKELY(!handle))
{
@@ -262,7 +264,7 @@ __nv_table_get_entry(NVTable *self, NVHandle handle, guint16 num_static_entries,
*dyn_slot = NULL;
if (G_UNLIKELY(!ofs))
return NULL;
- return (NVEntry *) (nv_table_get_top(self) - (ofs << NV_TABLE_SCALE));
+ return (NVEntry *) (nv_table_get_top(self) - ofs);
}
else
{
@@ -271,7 +273,7 @@ __nv_table_get_entry(NVTable *self, NVHandle handle, guint16 num_static_entries,
}
static inline NVEntry *
-nv_table_get_entry(NVTable *self, NVHandle handle, guint32 **dyn_slot)
+nv_table_get_entry(NVTable *self, NVHandle handle, NVDynValue **dyn_slot)
{
return __nv_table_get_entry(self, handle, self->num_static_entries, dyn_slot);
}
@@ -280,7 +282,7 @@ static inline const gchar *
__nv_table_get_value(NVTable *self, NVHandle handle, guint16 num_static_entries, gssize *length)
{
NVEntry *entry;
- guint32 *dyn_slot;
+ NVDynValue *dyn_slot;
entry = nv_table_get_entry(self, handle, &dyn_slot);
if (G_UNLIKELY(!entry))
@@ -293,7 +295,7 @@ __nv_table_get_value(NVTable *self, NVHandle handle, guint16 num_static_entries,
if (!entry->indirect)
{
if (length)
- *length = entry->vdirect.value_len_lo + (entry->vdirect.value_len_hi << 16);
+ *length = entry->vdirect.value_len;
return entry->vdirect.data + entry->name_len + 1;
}
return nv_table_resolve_indirect(self, entry, length);
diff --git a/tests/unit/test_nvtable.c b/tests/unit/test_nvtable.c
index 9f17cf7..3bfa009 100644
--- a/tests/unit/test_nvtable.c
+++ b/tests/unit/test_nvtable.c
@@ -365,7 +365,7 @@ test_nvtable_indirect()
/* NOTE: the sizing of the NVTable can easily be broken, it is sized
to make it possible to store one direct entry */
- tab = nv_table_new(STATIC_VALUES, 0, 138);
+ tab = nv_table_new(STATIC_VALUES, 0, 138+3); // direct: +3
success = nv_table_add_value(tab, STATIC_HANDLE, STATIC_NAME, 4, value, 128, NULL);
TEST_ASSERT(success == TRUE);
@@ -437,7 +437,7 @@ test_nvtable_indirect()
/* the new entry will not fit to the space allocated to the old and neither to the NVTable */
/* setup code: add static and a dynamic-direct entry */
- tab = nv_table_new(STATIC_VALUES, 1, 154);
+ tab = nv_table_new(STATIC_VALUES, 1, 154+3+4); // direct: +3, indirect: +4
success = nv_table_add_value(tab, STATIC_HANDLE, STATIC_NAME, 4, value, 128, NULL);
TEST_ASSERT(success == TRUE);
success = nv_table_add_value(tab, handle, name, strlen(name), value, 1, NULL);
@@ -535,7 +535,7 @@ test_nvtable_indirect()
/* one that is too large */
- tab = nv_table_new(STATIC_VALUES, STATIC_VALUES, 256);
+ tab = nv_table_new(STATIC_VALUES, 4, 256);
success = nv_table_add_value(tab, STATIC_HANDLE, STATIC_NAME, 4, value, 128, NULL);
TEST_ASSERT(success == TRUE);
success = nv_table_add_value_indirect(tab, DYN_HANDLE, DYN_NAME, strlen(DYN_NAME), STATIC_HANDLE, 0, 1, 126, NULL);
@@ -600,7 +600,7 @@ test_nvtable_indirect()
/* one that is too large */
- tab = nv_table_new(STATIC_VALUES, STATIC_VALUES, 256);
+ tab = nv_table_new(STATIC_VALUES, 4, 256);
success = nv_table_add_value(tab, STATIC_HANDLE, STATIC_NAME, 4, value, 128, NULL);
TEST_ASSERT(success == TRUE);
success = nv_table_add_value_indirect(tab, DYN_HANDLE, DYN_NAME, strlen(DYN_NAME), STATIC_HANDLE, 0, 1, 126, NULL);
--
1.7.2.5
--------------080206030106010302040206
Content-Type: text/plain;
name="0002-syslog-source-make-buffer-dynamically-allocated.patch"
Content-Transfer-Encoding: 7bit
Content-Disposition: attachment;
filename*0="0002-syslog-source-make-buffer-dynamically-allocated.patch"
More information about the syslog-ng
mailing list