Add first pass at a memory validator
diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt
index 09dece8..87f9154 100644
--- a/test/CMakeLists.txt
+++ b/test/CMakeLists.txt
@@ -8,7 +8,7 @@
 
 set (CMAKE_RUNTIME_OUTPUT_DIRECTORY ${dist_dir}/test )
 
-add_executable ( cose_test test.c json.c encrypt.c )
+add_executable ( cose_test test.c json.c encrypt.c context.c )
 
 target_link_libraries (cose_test PRIVATE cose-c )
 
diff --git a/test/context.c b/test/context.c
new file mode 100644
index 0000000..04a7a8e
--- /dev/null
+++ b/test/context.c
@@ -0,0 +1,115 @@
+#include <stdlib.h>
+#include <stdio.h>
+#include <memory.h>
+#include <assert.h>
+
+#include <cn-cbor\cn-cbor.h>
+
+#include "context.h"
+
+typedef unsigned char byte;
+
+typedef struct {
+	cn_cbor_context context;
+	byte * pFirst;
+} MyContext;
+
+typedef struct _MyItem {
+	struct _MyItem *	pNext;
+	size_t		size;
+	byte        pad[4];
+	byte        data[4];
+} MyItem;
+
+
+bool CheckMemory(MyContext * pContext)
+{
+	MyItem * p;
+	int i;
+
+	//  Walk memory and check every block
+
+	for (p =  (MyItem *) pContext->pFirst; p != NULL; p = p->pNext) {
+		if (p->pad[0] == (byte) 0xab) {
+			//  Block has been freed
+			for (i = 0; i < p->size + 8; i++) {
+				if (p->pad[i] != (byte) 0xab) {
+					fprintf(stderr, "Freed block is modified");
+					assert(false);
+				}
+			}
+		}
+		else if (p->pad[0] == (byte) 0xef) {
+			for (i = 0; i < 4; i++) {
+				if ((p->pad[i] != (byte) 0xef) || (p->pad[i + 4 + p->size] != (byte) 0xef)) {
+					fprintf(stderr, "Curent block was overrun");
+					assert(false);
+				}
+			}
+		}
+		else {
+			fprintf(stderr, "Incorrect pad value");
+			assert(false);
+		}
+	}
+
+	return true;
+}
+
+void * MyCalloc(size_t count, size_t size, void * context)
+{
+	MyItem * pb = (MyItem *) malloc(sizeof(MyItem) + count*size);
+	MyContext * myContext = (MyContext *)context;
+
+	CheckMemory(myContext);
+
+	memset(pb, 0xef, sizeof(MyItem) + count*size);
+	memset(&pb->data, 0, count*size);
+
+	pb->pNext = (struct _MyItem *) myContext->pFirst;
+	myContext->pFirst = (byte *) pb;
+	pb->size = count*size;
+
+    return &pb->data;
+}
+
+void MyFree(void * ptr, void * context)
+{
+	MyItem * pb = (MyItem *) ((byte *) ptr - sizeof(MyItem) + 4);
+	MyContext * myContext = (MyContext *)context;
+
+	CheckMemory(myContext);
+
+	memset(&pb->pad, 0xab, pb->size + 8);
+}
+
+
+cn_cbor_context * CreateContext()
+{
+	MyContext * p = malloc(sizeof(MyContext));
+
+	p->context.calloc_func = MyCalloc;
+	p->context.free_func = MyFree;
+	p->context.context = p;
+	p->pFirst = NULL;
+
+	return &p->context;
+}
+
+void FreeContext(cn_cbor_context* pContext)
+{
+	MyContext * myContext = (MyContext *)pContext;
+	MyItem * pItem;
+	MyItem * pItem2;
+
+	CheckMemory(myContext);
+
+	for (pItem = (MyItem *) myContext->pFirst; pItem != NULL;  pItem = pItem2) {
+		pItem2 = pItem->pNext;
+		free(pItem);
+	}
+
+	free(myContext);
+
+	return;
+}
diff --git a/test/context.h b/test/context.h
new file mode 100644
index 0000000..5e9f1d2
--- /dev/null
+++ b/test/context.h
@@ -0,0 +1,4 @@
+
+extern cn_cbor_context * CreateContext();
+extern void FreeContext(cn_cbor_context * pContext);
+
diff --git a/test/encrypt.c b/test/encrypt.c
index cefb104..11e7af0 100644
--- a/test/encrypt.c
+++ b/test/encrypt.c
@@ -11,6 +11,7 @@
 
 #include "json.h"
 #include "test.h"
+#include "context.h"
 
 
 int ValidateEnveloped(const cn_cbor * pControl)
@@ -27,6 +28,8 @@
 	bool fFail = false;
 	bool fFailBody = false;
 
+        allocator = CreateContext();
+
 	pFail = cn_cbor_mapget_string(pControl, "fail");
 	if ((pFail != NULL) && (pFail->type == CN_CBOR_TRUE)) {
 		fFailBody = true;
@@ -79,6 +82,9 @@
 		else fFail = false;
 	}
 
+        FreeContext(allocator);
+        allocator = NULL;
+
 	if (fFail) CFails += 1;
 	return 0;
 }