You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@avro.apache.org by dc...@apache.org on 2011/09/25 22:47:42 UTC

svn commit: r1175570 [11/13] - in /avro/trunk: ./ lang/c/jansson/ lang/c/jansson/doc/ lang/c/jansson/doc/ext/ lang/c/jansson/src/ lang/c/jansson/test/ lang/c/jansson/test/bin/ lang/c/jansson/test/scripts/ lang/c/jansson/test/suites/ lang/c/jansson/test...

Added: avro/trunk/lang/c/jansson/test/suites/api/test_array.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_array.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_array.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_array.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,400 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <jansson.h>
+#include "util.h"
+
+static void test_misc(void)
+{
+    json_t *array, *five, *seven, *value;
+    int i;
+
+    array = json_array();
+    five = json_integer(5);
+    seven = json_integer(7);
+
+    if(!array)
+        fail("unable to create array");
+    if(!five || !seven)
+        fail("unable to create integer");
+
+    if(json_array_size(array) != 0)
+        fail("empty array has nonzero size");
+
+    if(!json_array_append(array, NULL))
+        fail("able to append NULL");
+
+    if(json_array_append(array, five))
+        fail("unable to append");
+
+    if(json_array_size(array) != 1)
+        fail("wrong array size");
+
+    value = json_array_get(array, 0);
+    if(!value)
+        fail("unable to get item");
+    if(value != five)
+        fail("got wrong value");
+
+    if(json_array_append(array, seven))
+        fail("unable to append value");
+
+    if(json_array_size(array) != 2)
+        fail("wrong array size");
+
+    value = json_array_get(array, 1);
+    if(!value)
+        fail("unable to get item");
+    if(value != seven)
+        fail("got wrong value");
+
+    if(json_array_set(array, 0, seven))
+        fail("unable to set value");
+
+    if(!json_array_set(array, 0, NULL))
+        fail("able to set NULL");
+
+    if(json_array_size(array) != 2)
+        fail("wrong array size");
+
+    value = json_array_get(array, 0);
+    if(!value)
+        fail("unable to get item");
+    if(value != seven)
+        fail("got wrong value");
+
+    if(json_array_get(array, 2) != NULL)
+        fail("able to get value out of bounds");
+
+    if(!json_array_set(array, 2, seven))
+        fail("able to set value out of bounds");
+
+    for(i = 2; i < 30; i++) {
+        if(json_array_append(array, seven))
+            fail("unable to append value");
+
+        if(json_array_size(array) != i + 1)
+            fail("wrong array size");
+    }
+
+    for(i = 0; i < 30; i++) {
+        value = json_array_get(array, i);
+        if(!value)
+            fail("unable to get item");
+        if(value != seven)
+            fail("got wrong value");
+    }
+
+    if(json_array_set_new(array, 15, json_integer(123)))
+        fail("unable to set new value");
+
+    value = json_array_get(array, 15);
+    if(!json_is_integer(value) || json_integer_value(value) != 123)
+        fail("json_array_set_new works incorrectly");
+
+    if(!json_array_set_new(array, 15, NULL))
+        fail("able to set_new NULL value");
+
+    if(json_array_append_new(array, json_integer(321)))
+        fail("unable to append new value");
+
+    value = json_array_get(array, json_array_size(array) - 1);
+    if(!json_is_integer(value) || json_integer_value(value) != 321)
+        fail("json_array_append_new works incorrectly");
+
+    if(!json_array_append_new(array, NULL))
+        fail("able to append_new NULL value");
+
+    json_decref(five);
+    json_decref(seven);
+    json_decref(array);
+}
+
+static void test_insert(void)
+{
+    json_t *array, *five, *seven, *eleven, *value;
+    int i;
+
+    array = json_array();
+    five = json_integer(5);
+    seven = json_integer(7);
+    eleven = json_integer(11);
+
+    if(!array)
+        fail("unable to create array");
+    if(!five || !seven || !eleven)
+        fail("unable to create integer");
+
+
+    if(!json_array_insert(array, 1, five))
+        fail("able to insert value out of bounds");
+
+
+    if(json_array_insert(array, 0, five))
+        fail("unable to insert value in an empty array");
+
+    if(json_array_get(array, 0) != five)
+        fail("json_array_insert works incorrectly");
+
+    if(json_array_size(array) != 1)
+        fail("array size is invalid after insertion");
+
+
+    if(json_array_insert(array, 1, seven))
+        fail("unable to insert value at the end of an array");
+
+    if(json_array_get(array, 0) != five)
+        fail("json_array_insert works incorrectly");
+
+    if(json_array_get(array, 1) != seven)
+        fail("json_array_insert works incorrectly");
+
+    if(json_array_size(array) != 2)
+        fail("array size is invalid after insertion");
+
+
+    if(json_array_insert(array, 1, eleven))
+        fail("unable to insert value in the middle of an array");
+
+    if(json_array_get(array, 0) != five)
+        fail("json_array_insert works incorrectly");
+
+    if(json_array_get(array, 1) != eleven)
+        fail("json_array_insert works incorrectly");
+
+    if(json_array_get(array, 2) != seven)
+        fail("json_array_insert works incorrectly");
+
+    if(json_array_size(array) != 3)
+        fail("array size is invalid after insertion");
+
+
+    if(json_array_insert_new(array, 2, json_integer(123)))
+        fail("unable to insert value in the middle of an array");
+
+    value = json_array_get(array, 2);
+    if(!json_is_integer(value) || json_integer_value(value) != 123)
+        fail("json_array_insert_new works incorrectly");
+
+    if(json_array_size(array) != 4)
+        fail("array size is invalid after insertion");
+
+
+    for(i = 0; i < 20; i++) {
+        if(json_array_insert(array, 0, seven))
+            fail("unable to insert value at the begining of an array");
+    }
+
+    for(i = 0; i < 20; i++) {
+        if(json_array_get(array, i) != seven)
+            fail("json_aray_insert works incorrectly");
+    }
+
+    if(json_array_size(array) != 24)
+        fail("array size is invalid after loop insertion");
+
+    json_decref(five);
+    json_decref(seven);
+    json_decref(eleven);
+    json_decref(array);
+}
+
+static void test_remove(void)
+{
+    json_t *array, *five, *seven;
+
+    array = json_array();
+    five = json_integer(5);
+    seven = json_integer(7);
+
+    if(!array)
+        fail("unable to create array");
+    if(!five)
+        fail("unable to create integer");
+    if(!seven)
+        fail("unable to create integer");
+
+
+    if(!json_array_remove(array, 0))
+        fail("able to remove an unexisting index");
+
+
+    if(json_array_append(array, five))
+        fail("unable to append");
+
+    if(!json_array_remove(array, 1))
+        fail("able to remove an unexisting index");
+
+    if(json_array_remove(array, 0))
+        fail("unable to remove");
+
+    if(json_array_size(array) != 0)
+        fail("array size is invalid after removing");
+
+
+    if(json_array_append(array, five) ||
+       json_array_append(array, seven) ||
+       json_array_append(array, five) ||
+       json_array_append(array, seven))
+        fail("unable to append");
+
+    if(json_array_remove(array, 2))
+        fail("unable to remove");
+
+    if(json_array_size(array) != 3)
+        fail("array size is invalid after removing");
+
+    if(json_array_get(array, 0) != five ||
+       json_array_get(array, 1) != seven ||
+       json_array_get(array, 2) != seven)
+        fail("remove works incorrectly");
+
+    json_decref(five);
+    json_decref(seven);
+    json_decref(array);
+}
+
+static void test_clear(void)
+{
+    json_t *array, *five, *seven;
+    int i;
+
+    array = json_array();
+    five = json_integer(5);
+    seven = json_integer(7);
+
+    if(!array)
+        fail("unable to create array");
+    if(!five || !seven)
+        fail("unable to create integer");
+
+    for(i = 0; i < 10; i++) {
+        if(json_array_append(array, five))
+            fail("unable to append");
+    }
+    for(i = 0; i < 10; i++) {
+        if(json_array_append(array, seven))
+            fail("unable to append");
+    }
+
+    if(json_array_size(array) != 20)
+        fail("array size is invalid after appending");
+
+    if(json_array_clear(array))
+        fail("unable to clear");
+
+    if(json_array_size(array) != 0)
+        fail("array size is invalid after clearing");
+
+    json_decref(five);
+    json_decref(seven);
+    json_decref(array);
+}
+
+static void test_extend(void)
+{
+    json_t *array1, *array2, *five, *seven;
+    int i;
+
+    array1 = json_array();
+    array2 = json_array();
+    five = json_integer(5);
+    seven = json_integer(7);
+
+    if(!array1 || !array2)
+        fail("unable to create array");
+    if(!five || !seven)
+        fail("unable to create integer");
+
+    for(i = 0; i < 10; i++) {
+        if(json_array_append(array1, five))
+            fail("unable to append");
+    }
+    for(i = 0; i < 10; i++) {
+        if(json_array_append(array2, seven))
+            fail("unable to append");
+    }
+
+    if(json_array_size(array1) != 10 || json_array_size(array2) != 10)
+        fail("array size is invalid after appending");
+
+    if(json_array_extend(array1, array2))
+        fail("unable to extend");
+
+    for(i = 0; i < 10; i++) {
+        if(json_array_get(array1, i) != five)
+            fail("invalid array contents after extending");
+    }
+    for(i = 10; i < 20; i++) {
+        if(json_array_get(array1, i) != seven)
+            fail("invalid array contents after extending");
+    }
+
+    json_decref(five);
+    json_decref(seven);
+    json_decref(array1);
+    json_decref(array2);
+}
+
+static void test_circular()
+{
+    json_t *array1, *array2;
+
+    /* the simple cases are checked */
+
+    array1 = json_array();
+    if(!array1)
+        fail("unable to create array");
+
+    if(json_array_append(array1, array1) == 0)
+        fail("able to append self");
+
+    if(json_array_insert(array1, 0, array1) == 0)
+        fail("able to insert self");
+
+    if(json_array_append_new(array1, json_true()))
+        fail("failed to append true");
+
+    if(json_array_set(array1, 0, array1) == 0)
+        fail("able to set self");
+
+    json_decref(array1);
+
+
+    /* create circular references */
+
+    array1 = json_array();
+    array2 = json_array();
+    if(!array1 || !array2)
+        fail("unable to create array");
+
+    if(json_array_append(array1, array2) ||
+       json_array_append(array2, array1))
+        fail("unable to append");
+
+    /* circularity is detected when dumping */
+    if(json_dumps(array1, 0) != NULL)
+        fail("able to dump circulars");
+
+    /* decref twice to deal with the circular references */
+    json_decref(array1);
+    json_decref(array2);
+    json_decref(array1);
+}
+
+
+int main()
+{
+    test_misc();
+    test_insert();
+    test_remove();
+    test_clear();
+    test_extend();
+    test_circular();
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_copy.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_copy.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_copy.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_copy.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,319 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <string.h>
+#include <jansson.h>
+#include "util.h"
+
+static void test_copy_simple(void)
+{
+    json_t *value, *copy;
+
+    if(json_copy(NULL))
+        fail("copying NULL doesn't return NULL");
+
+    /* true */
+    value = json_true();
+    copy = json_copy(value);
+    if(value != copy)
+        fail("copying true failed");
+    json_decref(value);
+    json_decref(copy);
+
+    /* false */
+    value = json_false();
+    copy = json_copy(value);
+    if(value != copy)
+        fail("copying false failed");
+    json_decref(value);
+    json_decref(copy);
+
+    /* null */
+    value = json_null();
+    copy = json_copy(value);
+    if(value != copy)
+        fail("copying null failed");
+    json_decref(value);
+    json_decref(copy);
+
+    /* string */
+    value = json_string("foo");
+    if(!value)
+        fail("unable to create a string");
+    copy = json_copy(value);
+    if(!copy)
+        fail("unable to copy a string");
+    if(copy == value)
+        fail("copying a string doesn't copy");
+    if(!json_equal(copy, value))
+        fail("copying a string produces an inequal copy");
+    if(value->refcount != 1 || copy->refcount != 1)
+        fail("invalid refcounts");
+    json_decref(value);
+    json_decref(copy);
+
+    /* integer */
+    value = json_integer(543);
+    if(!value)
+        fail("unable to create an integer");
+    copy = json_copy(value);
+    if(!copy)
+        fail("unable to copy an integer");
+    if(copy == value)
+        fail("copying an integer doesn't copy");
+    if(!json_equal(copy, value))
+        fail("copying an integer produces an inequal copy");
+    if(value->refcount != 1 || copy->refcount != 1)
+        fail("invalid refcounts");
+    json_decref(value);
+    json_decref(copy);
+
+    /* real */
+    value = json_real(123e9);
+    if(!value)
+        fail("unable to create a real");
+    copy = json_copy(value);
+    if(!copy)
+        fail("unable to copy a real");
+    if(copy == value)
+        fail("copying a real doesn't copy");
+    if(!json_equal(copy, value))
+        fail("copying a real produces an inequal copy");
+    if(value->refcount != 1 || copy->refcount != 1)
+        fail("invalid refcounts");
+    json_decref(value);
+    json_decref(copy);
+}
+
+static void test_deep_copy_simple(void)
+{
+    json_t *value, *copy;
+
+    if(json_deep_copy(NULL))
+        fail("deep copying NULL doesn't return NULL");
+
+    /* true */
+    value = json_true();
+    copy = json_deep_copy(value);
+    if(value != copy)
+        fail("deep copying true failed");
+    json_decref(value);
+    json_decref(copy);
+
+    /* false */
+    value = json_false();
+    copy = json_deep_copy(value);
+    if(value != copy)
+        fail("deep copying false failed");
+    json_decref(value);
+    json_decref(copy);
+
+    /* null */
+    value = json_null();
+    copy = json_deep_copy(value);
+    if(value != copy)
+        fail("deep copying null failed");
+    json_decref(value);
+    json_decref(copy);
+
+    /* string */
+    value = json_string("foo");
+    if(!value)
+        fail("unable to create a string");
+    copy = json_deep_copy(value);
+    if(!copy)
+        fail("unable to deep copy a string");
+    if(copy == value)
+        fail("deep copying a string doesn't copy");
+    if(!json_equal(copy, value))
+        fail("deep copying a string produces an inequal copy");
+    if(value->refcount != 1 || copy->refcount != 1)
+        fail("invalid refcounts");
+    json_decref(value);
+    json_decref(copy);
+
+    /* integer */
+    value = json_integer(543);
+    if(!value)
+        fail("unable to create an integer");
+    copy = json_deep_copy(value);
+    if(!copy)
+        fail("unable to deep copy an integer");
+    if(copy == value)
+        fail("deep copying an integer doesn't copy");
+    if(!json_equal(copy, value))
+        fail("deep copying an integer produces an inequal copy");
+    if(value->refcount != 1 || copy->refcount != 1)
+        fail("invalid refcounts");
+    json_decref(value);
+    json_decref(copy);
+
+    /* real */
+    value = json_real(123e9);
+    if(!value)
+        fail("unable to create a real");
+    copy = json_deep_copy(value);
+    if(!copy)
+        fail("unable to deep copy a real");
+    if(copy == value)
+        fail("deep copying a real doesn't copy");
+    if(!json_equal(copy, value))
+        fail("deep copying a real produces an inequal copy");
+    if(value->refcount != 1 || copy->refcount != 1)
+        fail("invalid refcounts");
+    json_decref(value);
+    json_decref(copy);
+}
+
+static void test_copy_array(void)
+{
+    const char *json_array_text = "[1, \"foo\", 3.141592, {\"foo\": \"bar\"}]";
+
+    json_t *array, *copy;
+    size_t i;
+
+    array = json_loads(json_array_text, 0, NULL);
+    if(!array)
+        fail("unable to parse an array");
+
+    copy = json_copy(array);
+    if(!copy)
+        fail("unable to copy an array");
+    if(copy == array)
+        fail("copying an array doesn't copy");
+    if(!json_equal(copy, array))
+        fail("copying an array produces an inequal copy");
+
+    for(i = 0; i < json_array_size(copy); i++)
+    {
+        if(json_array_get(array, i) != json_array_get(copy, i))
+            fail("copying an array modifies its elements");
+    }
+
+    json_decref(array);
+    json_decref(copy);
+}
+
+static void test_deep_copy_array(void)
+{
+    const char *json_array_text = "[1, \"foo\", 3.141592, {\"foo\": \"bar\"}]";
+
+    json_t *array, *copy;
+    size_t i;
+
+    array = json_loads(json_array_text, 0, NULL);
+    if(!array)
+        fail("unable to parse an array");
+
+    copy = json_deep_copy(array);
+    if(!copy)
+        fail("unable to deep copy an array");
+    if(copy == array)
+        fail("deep copying an array doesn't copy");
+    if(!json_equal(copy, array))
+        fail("deep copying an array produces an inequal copy");
+
+    for(i = 0; i < json_array_size(copy); i++)
+    {
+        if(json_array_get(array, i) == json_array_get(copy, i))
+            fail("deep copying an array doesn't copy its elements");
+    }
+
+    json_decref(array);
+    json_decref(copy);
+}
+
+static void test_copy_object(void)
+{
+    const char *json_object_text =
+        "{\"foo\": \"bar\", \"a\": 1, \"b\": 3.141592, \"c\": [1,2,3,4]}";
+
+    json_t *object, *copy;
+    void *iter;
+
+    object = json_loads(json_object_text, 0, NULL);
+    if(!object)
+        fail("unable to parse an object");
+
+    copy = json_copy(object);
+    if(!copy)
+        fail("unable to copy an object");
+    if(copy == object)
+        fail("copying an object doesn't copy");
+    if(!json_equal(copy, object))
+        fail("copying an object produces an inequal copy");
+
+    iter = json_object_iter(object);
+    while(iter)
+    {
+        const char *key;
+        json_t *value1, *value2;
+
+        key = json_object_iter_key(iter);
+        value1 = json_object_iter_value(iter);
+        value2 = json_object_get(copy, key);
+
+        if(value1 != value2)
+            fail("deep copying an object modifies its items");
+
+        iter = json_object_iter_next(object, iter);
+    }
+
+    json_decref(object);
+    json_decref(copy);
+}
+
+static void test_deep_copy_object(void)
+{
+    const char *json_object_text =
+        "{\"foo\": \"bar\", \"a\": 1, \"b\": 3.141592, \"c\": [1,2,3,4]}";
+
+    json_t *object, *copy;
+    void *iter;
+
+    object = json_loads(json_object_text, 0, NULL);
+    if(!object)
+        fail("unable to parse an object");
+
+    copy = json_deep_copy(object);
+    if(!copy)
+        fail("unable to deep copy an object");
+    if(copy == object)
+        fail("deep copying an object doesn't copy");
+    if(!json_equal(copy, object))
+        fail("deep copying an object produces an inequal copy");
+
+    iter = json_object_iter(object);
+    while(iter)
+    {
+        const char *key;
+        json_t *value1, *value2;
+
+        key = json_object_iter_key(iter);
+        value1 = json_object_iter_value(iter);
+        value2 = json_object_get(copy, key);
+
+        if(value1 == value2)
+            fail("deep copying an object doesn't copy its items");
+
+        iter = json_object_iter_next(object, iter);
+    }
+
+    json_decref(object);
+    json_decref(copy);
+}
+
+int main()
+{
+    test_copy_simple();
+    test_deep_copy_simple();
+    test_copy_array();
+    test_deep_copy_array();
+    test_copy_object();
+    test_deep_copy_object();
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_dump.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_dump.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_dump.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_dump.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,142 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <jansson.h>
+#include <string.h>
+#include "util.h"
+
+static void encode_twice()
+{
+    /* Encode an empty object/array, add an item, encode again */
+
+    json_t *json;
+    char *result;
+
+    json = json_object();
+    result = json_dumps(json, 0);
+    if(!result || strcmp(result, "{}"))
+      fail("json_dumps failed");
+    free(result);
+
+    json_object_set_new(json, "foo", json_integer(5));
+    result = json_dumps(json, 0);
+    if(!result || strcmp(result, "{\"foo\": 5}"))
+      fail("json_dumps failed");
+    free(result);
+
+    json_decref(json);
+
+    json = json_array();
+    result = json_dumps(json, 0);
+    if(!result || strcmp(result, "[]"))
+      fail("json_dumps failed");
+    free(result);
+
+    json_array_append_new(json, json_integer(5));
+    result = json_dumps(json, 0);
+    if(!result || strcmp(result, "[5]"))
+      fail("json_dumps failed");
+    free(result);
+
+    json_decref(json);
+}
+
+static void circular_references()
+{
+    /* Construct a JSON object/array with a circular reference:
+
+       object: {"a": {"b": {"c": <circular reference to $.a>}}}
+       array: [[[<circular reference to the $[0] array>]]]
+
+       Encode it, remove the circular reference and encode again.
+    */
+
+    json_t *json;
+    char *result;
+
+    json = json_object();
+    json_object_set_new(json, "a", json_object());
+    json_object_set_new(json_object_get(json, "a"), "b", json_object());
+    json_object_set(json_object_get(json_object_get(json, "a"), "b"), "c",
+                    json_object_get(json, "a"));
+
+    if(json_dumps(json, 0))
+        fail("json_dumps encoded a circular reference!");
+
+    json_object_del(json_object_get(json_object_get(json, "a"), "b"), "c");
+
+    result = json_dumps(json, 0);
+    if(!result || strcmp(result, "{\"a\": {\"b\": {}}}"))
+        fail("json_dumps failed!");
+    free(result);
+
+    json_decref(json);
+
+    json = json_array();
+    json_array_append_new(json, json_array());
+    json_array_append_new(json_array_get(json, 0), json_array());
+    json_array_append(json_array_get(json_array_get(json, 0), 0),
+                      json_array_get(json, 0));
+
+    if(json_dumps(json, 0))
+        fail("json_dumps encoded a circular reference!");
+
+    json_array_remove(json_array_get(json_array_get(json, 0), 0), 0);
+
+    result = json_dumps(json, 0);
+    if(!result || strcmp(result, "[[[]]]"))
+        fail("json_dumps failed!");
+    free(result);
+
+    json_decref(json);
+}
+
+static void encode_other_than_array_or_object()
+{
+    /* Encoding anything other than array or object should only
+     * succeed if the JSON_ENCODE_ANY flag is used */
+
+    json_t *json;
+    FILE *fp = NULL;
+    char *result;
+
+    json = json_string("foo");
+    if(json_dumps(json, 0) != NULL)
+        fail("json_dumps encoded a string!");
+    if(json_dumpf(json, fp, 0) == 0)
+        fail("json_dumpf encoded a string!");
+
+    result = json_dumps(json, JSON_ENCODE_ANY);
+    if(!result || strcmp(result, "\"foo\"") != 0)
+        fail("json_dumps failed to encode a string with JSON_ENCODE_ANY");
+
+    free(result);
+    json_decref(json);
+
+    json = json_integer(42);
+    if(json_dumps(json, 0) != NULL)
+        fail("json_dumps encoded an integer!");
+    if(json_dumpf(json, fp, 0) == 0)
+        fail("json_dumpf encoded an integer!");
+
+    result = json_dumps(json, JSON_ENCODE_ANY);
+    if(!result || strcmp(result, "42") != 0)
+        fail("json_dumps failed to encode an integer with JSON_ENCODE_ANY");
+
+    free(result);
+    json_decref(json);
+
+
+}
+
+int main()
+{
+    encode_twice();
+    circular_references();
+    encode_other_than_array_or_object();
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_equal.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_equal.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_equal.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_equal.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,190 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <jansson.h>
+#include "util.h"
+
+static void test_equal_simple()
+{
+    json_t *value1, *value2;
+
+    if(json_equal(NULL, NULL))
+        fail("json_equal fails for two NULLs");
+
+    value1 = json_true();
+    if(json_equal(value1, NULL) || json_equal(NULL, value1))
+        fail("json_equal fails for NULL");
+
+    /* this covers true, false and null as they are singletons */
+    if(!json_equal(value1, value1))
+        fail("identical objects are not equal");
+    json_decref(value1);
+
+    /* integer */
+    value1 = json_integer(1);
+    value2 = json_integer(1);
+    if(!value1 || !value2)
+        fail("unable to create integers");
+    if(!json_equal(value1, value2))
+        fail("json_equal fails for two equal integers");
+    json_decref(value2);
+
+    value2 = json_integer(2);
+    if(!value2)
+        fail("unable to create an integer");
+    if(json_equal(value1, value2))
+        fail("json_equal fails for two inequal integers");
+
+    json_decref(value1);
+    json_decref(value2);
+
+    /* real */
+    value1 = json_real(1.2);
+    value2 = json_real(1.2);
+    if(!value1 || !value2)
+        fail("unable to create reals");
+    if(!json_equal(value1, value2))
+        fail("json_equal fails for two equal reals");
+    json_decref(value2);
+
+    value2 = json_real(3.141592);
+    if(!value2)
+        fail("unable to create an real");
+    if(json_equal(value1, value2))
+        fail("json_equal fails for two inequal reals");
+
+    json_decref(value1);
+    json_decref(value2);
+
+    /* string */
+    value1 = json_string("foo");
+    value2 = json_string("foo");
+    if(!value1 || !value2)
+        fail("unable to create strings");
+    if(!json_equal(value1, value2))
+        fail("json_equal fails for two equal strings");
+    json_decref(value2);
+
+    value2 = json_string("bar");
+    if(!value2)
+        fail("unable to create an string");
+    if(json_equal(value1, value2))
+        fail("json_equal fails for two inequal strings");
+
+    json_decref(value1);
+    json_decref(value2);
+}
+
+static void test_equal_array()
+{
+    json_t *array1, *array2;
+
+    array1 = json_array();
+    array2 = json_array();
+    if(!array1 || !array2)
+        fail("unable to create arrays");
+
+    if(!json_equal(array1, array2))
+        fail("json_equal fails for two empty arrays");
+
+    json_array_append_new(array1, json_integer(1));
+    json_array_append_new(array2, json_integer(1));
+    json_array_append_new(array1, json_string("foo"));
+    json_array_append_new(array2, json_string("foo"));
+    json_array_append_new(array1, json_integer(2));
+    json_array_append_new(array2, json_integer(2));
+    if(!json_equal(array1, array2))
+        fail("json_equal fails for two equal arrays");
+
+    json_array_remove(array2, 2);
+    if(json_equal(array1, array2))
+        fail("json_equal fails for two inequal arrays");
+
+    json_array_append_new(array2, json_integer(3));
+    if(json_equal(array1, array2))
+        fail("json_equal fails for two inequal arrays");
+
+    json_decref(array1);
+    json_decref(array2);
+}
+
+static void test_equal_object()
+{
+    json_t *object1, *object2;
+
+    object1 = json_object();
+    object2 = json_object();
+    if(!object1 || !object2)
+        fail("unable to create objects");
+
+    if(!json_equal(object1, object2))
+        fail("json_equal fails for two empty objects");
+
+    json_object_set_new(object1, "a", json_integer(1));
+    json_object_set_new(object2, "a", json_integer(1));
+    json_object_set_new(object1, "b", json_string("foo"));
+    json_object_set_new(object2, "b", json_string("foo"));
+    json_object_set_new(object1, "c", json_integer(2));
+    json_object_set_new(object2, "c", json_integer(2));
+    if(!json_equal(object1, object2))
+        fail("json_equal fails for two equal objects");
+
+    json_object_del(object2, "c");
+    if(json_equal(object1, object2))
+        fail("json_equal fails for two inequal objects");
+
+    json_object_set_new(object2, "c", json_integer(3));
+    if(json_equal(object1, object2))
+        fail("json_equal fails for two inequal objects");
+
+    json_object_del(object2, "c");
+    json_object_set_new(object2, "d", json_integer(2));
+    if(json_equal(object1, object2))
+        fail("json_equal fails for two inequal objects");
+
+    json_decref(object1);
+    json_decref(object2);
+}
+
+static void test_equal_complex()
+{
+    json_t *value1, *value2;
+
+    const char *complex_json =
+"{"
+"    \"integer\": 1, "
+"    \"real\": 3.141592, "
+"    \"string\": \"foobar\", "
+"    \"true\": true, "
+"    \"object\": {"
+"        \"array-in-object\": [1,true,\"foo\",{}],"
+"        \"object-in-object\": {\"foo\": \"bar\"}"
+"    },"
+"    \"array\": [\"foo\", false, null, 1.234]"
+"}";
+
+    value1 = json_loads(complex_json, 0, NULL);
+    value2 = json_loads(complex_json, 0, NULL);
+    if(!value1 || !value2)
+        fail("unable to parse JSON");
+    if(!json_equal(value1, value2))
+        fail("json_equal fails for two inequal strings");
+
+    json_decref(value1);
+    json_decref(value2);
+
+    /* TODO: There's no negative test case here */
+}
+
+int main()
+{
+    test_equal_simple();
+    test_equal_array();
+    test_equal_object();
+    test_equal_complex();
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_load.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_load.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_load.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_load.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,60 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <jansson.h>
+#include <string.h>
+#include "util.h"
+
+static void file_not_found()
+{
+    json_t *json;
+    json_error_t error;
+
+    json = json_load_file("/path/to/nonexistent/file.json", 0, &error);
+    if(json)
+        fail("json_load_file returned non-NULL for a nonexistent file");
+    if(error.line != -1)
+        fail("json_load_file returned an invalid line number");
+    if(strcmp(error.text, "unable to open /path/to/nonexistent/file.json: No such file or directory") != 0)
+        fail("json_load_file returned an invalid error message");
+}
+
+static void reject_duplicates()
+{
+    json_error_t error;
+
+    if(json_loads("{\"foo\": 1, \"foo\": 2}", JSON_REJECT_DUPLICATES, &error))
+        fail("json_loads did not detect a duplicate key");
+    check_error("duplicate object key near '\"foo\"'", "<string>", 1, 16, 16);
+}
+
+static void disable_eof_check()
+{
+    json_error_t error;
+    json_t *json;
+
+    const char *text = "{\"foo\": 1} garbage";
+
+    if(json_loads(text, 0, &error))
+        fail("json_loads did not detect garbage after JSON text");
+    check_error("end of file expected near 'garbage'", "<string>", 1, 18, 18);
+
+    json = json_loads(text, JSON_DISABLE_EOF_CHECK, &error);
+    if(!json)
+        fail("json_loads failed with JSON_DISABLE_EOF_CHECK");
+
+    json_decref(json);
+}
+
+int main()
+{
+    file_not_found();
+    reject_duplicates();
+    disable_eof_check();
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_loadb.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_loadb.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_loadb.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_loadb.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <jansson.h>
+#include <string.h>
+#include "util.h"
+
+int main()
+{
+    json_t *json;
+    json_error_t error;
+    const char str[] = "[\"A\", {\"B\": \"C\"}, 1, 2, 3]garbage";
+    size_t len = strlen(str) - strlen("garbage");
+
+    json = json_loadb(str, len, 0, &error);
+    if(!json) {
+        fail("json_loadb failed on a valid JSON buffer");
+    }
+    json_decref(json);
+
+    json = json_loadb(str, len - 1, 0, &error);
+    if (json) {
+        json_decref(json);
+        fail("json_loadb should have failed on an incomplete buffer, but it didn't");
+    }
+    if(error.line != 1) {
+        fail("json_loadb returned an invalid line number on fail");
+    }
+    if(strcmp(error.text, "']' expected near end of file") != 0) {
+        fail("json_loadb returned an invalid error message for an unclosed top-level array");
+    }
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_memory_funcs.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_memory_funcs.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_memory_funcs.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_memory_funcs.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,84 @@
+#include <string.h>
+#include <jansson.h>
+
+#include "util.h"
+
+static int malloc_called = 0;
+static int free_called = 0;
+
+/* helper */
+static void create_and_free_complex_object()
+{
+    json_t *obj;
+
+    obj = json_pack("{s:i,s:n,s:b,s:b,s:{s:s},s:[i,i,i]",
+                    "foo", 42,
+                    "bar",
+                    "baz", 1,
+                    "qux", 0,
+                    "alice", "bar", "baz",
+                    "bob", 9, 8, 7);
+
+    json_decref(obj);
+}
+
+static void *my_malloc(size_t size)
+{
+    malloc_called += 1;
+    return malloc(size);
+}
+
+static void my_free(void *ptr)
+{
+    free_called += 1;
+    free(ptr);
+}
+
+static void test_simple()
+{
+    json_set_alloc_funcs(my_malloc, my_free);
+    create_and_free_complex_object();
+
+    if(malloc_called != 27 || free_called != 27)
+        fail("Custom allocation failed");
+}
+
+
+/*
+  Test the secure memory functions code given in the API reference
+  documentation, but by using plain memset instead of
+  guaranteed_memset().
+*/
+
+static void *secure_malloc(size_t size)
+{
+    /* Store the memory area size in the beginning of the block */
+    void *ptr = malloc(size + 8);
+    *((size_t *)ptr) = size;
+    return ptr + 8;
+}
+
+static void secure_free(void *ptr)
+{
+    size_t size;
+
+    ptr -= 8;
+    size = *((size_t *)ptr);
+
+    /*guaranteed_*/memset(ptr, 0, size);
+    free(ptr);
+}
+
+static void test_secure_funcs(void)
+{
+    json_set_alloc_funcs(secure_malloc, secure_free);
+    create_and_free_complex_object();
+}
+
+int main()
+{
+    test_simple();
+    test_secure_funcs();
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_number.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_number.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_number.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_number.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <jansson.h>
+#include "util.h"
+
+int main()
+{
+    json_t *integer, *real;
+    int i;
+    double d;
+
+    integer = json_integer(5);
+    real = json_real(100.1);
+
+    if(!integer)
+        fail("unable to create integer");
+    if(!real)
+        fail("unable to create real");
+
+    i = json_integer_value(integer);
+    if(i != 5)
+        fail("wrong integer value");
+
+    d = json_real_value(real);
+    if(d != 100.1)
+        fail("wrong real value");
+
+    d = json_number_value(integer);
+    if(d != 5.0)
+        fail("wrong number value");
+    d = json_number_value(real);
+    if(d != 100.1)
+        fail("wrong number value");
+
+    json_decref(integer);
+    json_decref(real);
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_object.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_object.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_object.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_object.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,451 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <jansson.h>
+#include <string.h>
+#include "util.h"
+
+static void test_clear()
+{
+    json_t *object, *ten;
+
+    object = json_object();
+    ten = json_integer(10);
+
+    if(!object)
+        fail("unable to create object");
+    if(!ten)
+        fail("unable to create integer");
+
+    if(json_object_set(object, "a", ten) ||
+       json_object_set(object, "b", ten) ||
+       json_object_set(object, "c", ten) ||
+       json_object_set(object, "d", ten) ||
+       json_object_set(object, "e", ten))
+        fail("unable to set value");
+
+    if(json_object_size(object) != 5)
+        fail("invalid size");
+
+    json_object_clear(object);
+
+    if(json_object_size(object) != 0)
+        fail("invalid size after clear");
+
+    json_decref(ten);
+    json_decref(object);
+}
+
+static void test_update()
+{
+    json_t *object, *other, *nine, *ten;
+
+    object = json_object();
+    other = json_object();
+
+    nine = json_integer(9);
+    ten = json_integer(10);
+
+    if(!object || !other)
+        fail("unable to create object");
+    if(!nine || !ten)
+        fail("unable to create integer");
+
+
+    /* update an empty object with an empty object */
+
+    if(json_object_update(object, other))
+        fail("unable to update an emtpy object with an empty object");
+
+    if(json_object_size(object) != 0)
+        fail("invalid size after update");
+
+    if(json_object_size(other) != 0)
+        fail("invalid size for updater after update");
+
+
+    /* update an empty object with a nonempty object */
+
+    if(json_object_set(other, "a", ten) ||
+       json_object_set(other, "b", ten) ||
+       json_object_set(other, "c", ten) ||
+       json_object_set(other, "d", ten) ||
+       json_object_set(other, "e", ten))
+        fail("unable to set value");
+
+    if(json_object_update(object, other))
+        fail("unable to update an empty object");
+
+    if(json_object_size(object) != 5)
+        fail("invalid size after update");
+
+    if(json_object_get(object, "a") != ten ||
+       json_object_get(object, "b") != ten ||
+       json_object_get(object, "c") != ten ||
+       json_object_get(object, "d") != ten ||
+       json_object_get(object, "e") != ten)
+        fail("update works incorrectly");
+
+
+    /* perform the same update again */
+
+    if(json_object_update(object, other))
+        fail("unable to update an empty object");
+
+    if(json_object_size(object) != 5)
+        fail("invalid size after update");
+
+    if(json_object_get(object, "a") != ten ||
+       json_object_get(object, "b") != ten ||
+       json_object_get(object, "c") != ten ||
+       json_object_get(object, "d") != ten ||
+       json_object_get(object, "e") != ten)
+        fail("update works incorrectly");
+
+
+    /* update a nonempty object with a nonempty object with both old
+       and new keys */
+
+    if(json_object_clear(other))
+        fail("clear failed");
+
+    if(json_object_set(other, "a", nine) ||
+       json_object_set(other, "b", nine) ||
+       json_object_set(other, "f", nine) ||
+       json_object_set(other, "g", nine) ||
+       json_object_set(other, "h", nine))
+        fail("unable to set value");
+
+    if(json_object_update(object, other))
+        fail("unable to update a nonempty object");
+
+    if(json_object_size(object) != 8)
+        fail("invalid size after update");
+
+    if(json_object_get(object, "a") != nine ||
+       json_object_get(object, "b") != nine ||
+       json_object_get(object, "f") != nine ||
+       json_object_get(object, "g") != nine ||
+       json_object_get(object, "h") != nine)
+        fail("update works incorrectly");
+
+    json_decref(nine);
+    json_decref(ten);
+    json_decref(other);
+    json_decref(object);
+}
+
+static void test_circular()
+{
+    json_t *object1, *object2;
+
+    object1 = json_object();
+    object2 = json_object();
+    if(!object1 || !object2)
+        fail("unable to create object");
+
+    /* the simple case is checked */
+    if(json_object_set(object1, "a", object1) == 0)
+        fail("able to set self");
+
+    /* create circular references */
+    if(json_object_set(object1, "a", object2) ||
+       json_object_set(object2, "a", object1))
+        fail("unable to set value");
+
+    /* circularity is detected when dumping */
+    if(json_dumps(object1, 0) != NULL)
+        fail("able to dump circulars");
+
+    /* decref twice to deal with the circular references */
+    json_decref(object1);
+    json_decref(object2);
+    json_decref(object1);
+}
+
+static void test_set_nocheck()
+{
+    json_t *object, *string;
+
+    object = json_object();
+    string = json_string("bar");
+
+    if(!object)
+        fail("unable to create object");
+    if(!string)
+        fail("unable to create string");
+
+    if(json_object_set_nocheck(object, "foo", string))
+        fail("json_object_set_nocheck failed");
+    if(json_object_get(object, "foo") != string)
+        fail("json_object_get after json_object_set_nocheck failed");
+
+    /* invalid UTF-8 in key */
+    if(json_object_set_nocheck(object, "a\xefz", string))
+        fail("json_object_set_nocheck failed for invalid UTF-8");
+    if(json_object_get(object, "a\xefz") != string)
+        fail("json_object_get after json_object_set_nocheck failed");
+
+    if(json_object_set_new_nocheck(object, "bax", json_integer(123)))
+        fail("json_object_set_new_nocheck failed");
+    if(json_integer_value(json_object_get(object, "bax")) != 123)
+        fail("json_object_get after json_object_set_new_nocheck failed");
+
+    /* invalid UTF-8 in key */
+    if(json_object_set_new_nocheck(object, "asdf\xfe", json_integer(321)))
+        fail("json_object_set_new_nocheck failed for invalid UTF-8");
+    if(json_integer_value(json_object_get(object, "asdf\xfe")) != 321)
+        fail("json_object_get after json_object_set_new_nocheck failed");
+
+    json_decref(string);
+    json_decref(object);
+}
+
+static void test_iterators()
+{
+    json_t *object, *foo, *bar, *baz;
+    void *iter;
+
+    if(json_object_iter(NULL))
+        fail("able to iterate over NULL");
+
+    if(json_object_iter_next(NULL, NULL))
+        fail("able to increment an iterator on a NULL object");
+
+    object = json_object();
+    foo = json_string("foo");
+    bar = json_string("bar");
+    baz = json_string("baz");
+    if(!object || !foo || !bar || !bar)
+        fail("unable to create values");
+
+    if(json_object_iter_next(object, NULL))
+        fail("able to increment a NULL iterator");
+
+    if(json_object_set(object, "a", foo) ||
+       json_object_set(object, "b", bar) ||
+       json_object_set(object, "c", baz))
+        fail("unable to populate object");
+
+    iter = json_object_iter(object);
+    if(!iter)
+        fail("unable to get iterator");
+    if(strcmp(json_object_iter_key(iter), "a"))
+        fail("iterating failed: wrong key");
+    if(json_object_iter_value(iter) != foo)
+        fail("iterating failed: wrong value");
+
+    iter = json_object_iter_next(object, iter);
+    if(!iter)
+        fail("unable to increment iterator");
+    if(strcmp(json_object_iter_key(iter), "b"))
+        fail("iterating failed: wrong key");
+    if(json_object_iter_value(iter) != bar)
+        fail("iterating failed: wrong value");
+
+    iter = json_object_iter_next(object, iter);
+    if(!iter)
+        fail("unable to increment iterator");
+    if(strcmp(json_object_iter_key(iter), "c"))
+        fail("iterating failed: wrong key");
+    if(json_object_iter_value(iter) != baz)
+        fail("iterating failed: wrong value");
+
+    if(json_object_iter_next(object, iter) != NULL)
+        fail("able to iterate over the end");
+
+    if(json_object_iter_at(object, "foo"))
+        fail("json_object_iter_at() succeeds for non-existent key");
+
+    iter = json_object_iter_at(object, "b");
+    if(!iter)
+        fail("json_object_iter_at() fails for an existing key");
+
+    if(strcmp(json_object_iter_key(iter), "b"))
+        fail("iterating failed: wrong key");
+    if(json_object_iter_value(iter) != bar)
+        fail("iterating failed: wrong value");
+
+    iter = json_object_iter_next(object, iter);
+    if(!iter)
+        fail("unable to increment iterator");
+    if(strcmp(json_object_iter_key(iter), "c"))
+        fail("iterating failed: wrong key");
+    if(json_object_iter_value(iter) != baz)
+        fail("iterating failed: wrong value");
+
+    if(json_object_iter_set(object, iter, bar))
+        fail("unable to set value at iterator");
+
+    if(strcmp(json_object_iter_key(iter), "c"))
+        fail("json_object_iter_key() fails after json_object_iter_set()");
+    if(json_object_iter_value(iter) != bar)
+        fail("json_object_iter_value() fails after json_object_iter_set()");
+    if(json_object_get(object, "c") != bar)
+        fail("json_object_get() fails after json_object_iter_set()");
+
+    json_decref(object);
+    json_decref(foo);
+    json_decref(bar);
+    json_decref(baz);
+}
+
+static void test_misc()
+{
+    json_t *object, *string, *other_string, *value;
+
+    object = json_object();
+    string = json_string("test");
+    other_string = json_string("other");
+
+    if(!object)
+        fail("unable to create object");
+    if(!string || !other_string)
+        fail("unable to create string");
+
+    if(json_object_get(object, "a"))
+        fail("value for nonexisting key");
+
+    if(json_object_set(object, "a", string))
+        fail("unable to set value");
+
+    if(!json_object_set(object, NULL, string))
+        fail("able to set NULL key");
+
+    if(!json_object_set(object, "a", NULL))
+        fail("able to set NULL value");
+
+    /* invalid UTF-8 in key */
+    if(!json_object_set(object, "a\xefz", string))
+        fail("able to set invalid unicode key");
+
+    value = json_object_get(object, "a");
+    if(!value)
+        fail("no value for existing key");
+    if(value != string)
+        fail("got different value than what was added");
+
+    /* "a", "lp" and "px" collide in a five-bucket hashtable */
+    if(json_object_set(object, "b", string) ||
+       json_object_set(object, "lp", string) ||
+       json_object_set(object, "px", string))
+        fail("unable to set value");
+
+    value = json_object_get(object, "a");
+    if(!value)
+        fail("no value for existing key");
+    if(value != string)
+        fail("got different value than what was added");
+
+    if(json_object_set(object, "a", other_string))
+        fail("unable to replace an existing key");
+
+    value = json_object_get(object, "a");
+    if(!value)
+        fail("no value for existing key");
+    if(value != other_string)
+        fail("got different value than what was set");
+
+    if(!json_object_del(object, "nonexisting"))
+        fail("able to delete a nonexisting key");
+
+    if(json_object_del(object, "px"))
+        fail("unable to delete an existing key");
+
+    if(json_object_del(object, "a"))
+        fail("unable to delete an existing key");
+
+    if(json_object_del(object, "lp"))
+        fail("unable to delete an existing key");
+
+
+    /* add many keys to initiate rehashing */
+
+    if(json_object_set(object, "a", string))
+        fail("unable to set value");
+
+    if(json_object_set(object, "lp", string))
+        fail("unable to set value");
+
+    if(json_object_set(object, "px", string))
+        fail("unable to set value");
+
+    if(json_object_set(object, "c", string))
+        fail("unable to set value");
+
+    if(json_object_set(object, "d", string))
+        fail("unable to set value");
+
+    if(json_object_set(object, "e", string))
+        fail("unable to set value");
+
+
+    if(json_object_set_new(object, "foo", json_integer(123)))
+        fail("unable to set new value");
+
+    value = json_object_get(object, "foo");
+    if(!json_is_integer(value) || json_integer_value(value) != 123)
+        fail("json_object_set_new works incorrectly");
+
+    if(!json_object_set_new(object, NULL, json_integer(432)))
+        fail("able to set_new NULL key");
+
+    if(!json_object_set_new(object, "foo", NULL))
+        fail("able to set_new NULL value");
+
+    json_decref(string);
+    json_decref(other_string);
+    json_decref(object);
+}
+
+static void test_preserve_order()
+{
+    json_t *object;
+    char *result;
+
+    const char *expected = "{\"foobar\": 1, \"bazquux\": 6, \"lorem ipsum\": 3, \"sit amet\": 5, \"helicopter\": 7}";
+
+    object = json_object();
+
+    json_object_set_new(object, "foobar", json_integer(1));
+    json_object_set_new(object, "bazquux", json_integer(2));
+    json_object_set_new(object, "lorem ipsum", json_integer(3));
+    json_object_set_new(object, "dolor", json_integer(4));
+    json_object_set_new(object, "sit amet", json_integer(5));
+
+    /* changing a value should preserve the order */
+    json_object_set_new(object, "bazquux", json_integer(6));
+
+    /* deletion shouldn't change the order of others */
+    json_object_del(object, "dolor");
+
+    /* add a new item just to make sure */
+    json_object_set_new(object, "helicopter", json_integer(7));
+
+    result = json_dumps(object, JSON_PRESERVE_ORDER);
+
+    if(strcmp(expected, result) != 0) {
+        fprintf(stderr, "%s != %s", expected, result);
+        fail("JSON_PRESERVE_ORDER doesn't work");
+    }
+
+    free(result);
+    json_decref(object);
+}
+
+int main()
+{
+    test_misc();
+    test_clear();
+    test_update();
+    test_circular();
+    test_set_nocheck();
+    test_iterators();
+    test_preserve_order();
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_pack.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_pack.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_pack.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_pack.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,232 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ * Copyright (c) 2010-2011 Graeme Smecher <gr...@mail.mcgill.ca>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <string.h>
+#include <jansson.h>
+#include <stdio.h>
+#include "util.h"
+
+int main()
+{
+    json_t *value;
+    int i;
+    json_error_t error;
+
+    /*
+     * Simple, valid json_pack cases
+     */
+
+    /* true */
+    value = json_pack("b", 1);
+    if(!json_is_true(value))
+        fail("json_pack boolean failed");
+    if(value->refcount != (ssize_t)-1)
+        fail("json_pack boolean refcount failed");
+    json_decref(value);
+
+    /* false */
+    value = json_pack("b", 0);
+    if(!json_is_false(value))
+        fail("json_pack boolean failed");
+    if(value->refcount != (ssize_t)-1)
+        fail("json_pack boolean refcount failed");
+    json_decref(value);
+
+    /* null */
+    value = json_pack("n");
+    if(!json_is_null(value))
+        fail("json_pack null failed");
+    if(value->refcount != (ssize_t)-1)
+        fail("json_pack null refcount failed");
+    json_decref(value);
+
+    /* integer */
+    value = json_pack("i", 1);
+    if(!json_is_integer(value) || json_integer_value(value) != 1)
+        fail("json_pack integer failed");
+    if(value->refcount != (ssize_t)1)
+        fail("json_pack integer refcount failed");
+    json_decref(value);
+
+    /* integer from json_int_t */
+    value = json_pack("I", (json_int_t)555555);
+    if(!json_is_integer(value) || json_integer_value(value) != 555555)
+        fail("json_pack json_int_t failed");
+    if(value->refcount != (ssize_t)1)
+        fail("json_pack integer refcount failed");
+    json_decref(value);
+
+    /* real */
+    value = json_pack("f", 1.0);
+    if(!json_is_real(value) || json_real_value(value) != 1.0)
+        fail("json_pack real failed");
+    if(value->refcount != (ssize_t)1)
+        fail("json_pack real refcount failed");
+    json_decref(value);
+
+    /* string */
+    value = json_pack("s", "test");
+    if(!json_is_string(value) || strcmp("test", json_string_value(value)))
+        fail("json_pack string failed");
+    if(value->refcount != (ssize_t)1)
+        fail("json_pack string refcount failed");
+    json_decref(value);
+
+    /* empty object */
+    value = json_pack("{}", 1.0);
+    if(!json_is_object(value) || json_object_size(value) != 0)
+        fail("json_pack empty object failed");
+    if(value->refcount != (ssize_t)1)
+        fail("json_pack empty object refcount failed");
+    json_decref(value);
+
+    /* empty list */
+    value = json_pack("[]", 1.0);
+    if(!json_is_array(value) || json_array_size(value) != 0)
+        fail("json_pack empty list failed");
+    if(value->refcount != (ssize_t)1)
+        fail("json_pack empty list failed");
+    json_decref(value);
+
+    /* non-incref'd object */
+    value = json_pack("o", json_integer(1));
+    if(!json_is_integer(value) || json_integer_value(value) != 1)
+        fail("json_pack object failed");
+    if(value->refcount != (ssize_t)1)
+        fail("json_pack integer refcount failed");
+    json_decref(value);
+
+    /* incref'd object */
+    value = json_pack("O", json_integer(1));
+    if(!json_is_integer(value) || json_integer_value(value) != 1)
+        fail("json_pack object failed");
+    if(value->refcount != (ssize_t)2)
+        fail("json_pack integer refcount failed");
+    json_decref(value);
+    json_decref(value);
+
+    /* simple object */
+    value = json_pack("{s:[]}", "foo");
+    if(!json_is_object(value) || json_object_size(value) != 1)
+        fail("json_pack array failed");
+    if(!json_is_array(json_object_get(value, "foo")))
+        fail("json_pack array failed");
+    if(json_object_get(value, "foo")->refcount != (ssize_t)1)
+        fail("json_pack object refcount failed");
+    json_decref(value);
+
+    /* simple array */
+    value = json_pack("[i,i,i]", 0, 1, 2);
+    if(!json_is_array(value) || json_array_size(value) != 3)
+        fail("json_pack object failed");
+    for(i=0; i<3; i++)
+    {
+        if(!json_is_integer(json_array_get(value, i)) ||
+           json_integer_value(json_array_get(value, i)) != i)
+
+            fail("json_pack integer array failed");
+    }
+    json_decref(value);
+
+    /* Whitespace; regular string */
+    value = json_pack(" s ", "test");
+    if(!json_is_string(value) || strcmp("test", json_string_value(value)))
+        fail("json_pack string (with whitespace) failed");
+    json_decref(value);
+
+    /* Whitespace; empty array */
+    value = json_pack("[ ]");
+    if(!json_is_array(value) || json_array_size(value) != 0)
+        fail("json_pack empty array (with whitespace) failed");
+    json_decref(value);
+
+    /* Whitespace; array */
+    value = json_pack("[ i , i,  i ] ", 1, 2, 3);
+    if(!json_is_array(value) || json_array_size(value) != 3)
+        fail("json_pack array (with whitespace) failed");
+    json_decref(value);
+
+    /*
+     * Invalid cases
+     */
+
+    /* newline in format string */
+    if(json_pack_ex(&error, 0, "{\n\n1"))
+        fail("json_pack failed to catch invalid format '1'");
+    check_error("Expected format 's', got '1'", "<format>", 3, 1, 4);
+
+    /* mismatched open/close array/object */
+    if(json_pack_ex(&error, 0, "[}"))
+        fail("json_pack failed to catch mismatched '}'");
+    check_error("Unexpected format character '}'", "<format>", 1, 2, 2);
+
+    if(json_pack_ex(&error, 0, "{]"))
+        fail("json_pack failed to catch mismatched ']'");
+    check_error("Expected format 's', got ']'", "<format>", 1, 2, 2);
+
+    /* missing close array */
+    if(json_pack_ex(&error, 0, "["))
+        fail("json_pack failed to catch missing ']'");
+    check_error("Unexpected end of format string", "<format>", 1, 2, 2);
+
+    /* missing close object */
+    if(json_pack_ex(&error, 0, "{"))
+        fail("json_pack failed to catch missing '}'");
+    check_error("Unexpected end of format string", "<format>", 1, 2, 2);
+
+    /* garbage after format string */
+    if(json_pack_ex(&error, 0, "[i]a", 42))
+        fail("json_pack failed to catch garbage after format string");
+    check_error("Garbage after format string", "<format>", 1, 4, 4);
+
+    if(json_pack_ex(&error, 0, "ia", 42))
+        fail("json_pack failed to catch garbage after format string");
+    check_error("Garbage after format string", "<format>", 1, 2, 2);
+
+    /* NULL string */
+    if(json_pack_ex(&error, 0, "s", NULL))
+        fail("json_pack failed to catch null argument string");
+    check_error("NULL string argument", "<args>", 1, 1, 1);
+
+    /* NULL format */
+    if(json_pack_ex(&error, 0, NULL))
+        fail("json_pack failed to catch NULL format string");
+    check_error("NULL or empty format string", "<format>", -1, -1, 0);
+
+    /* NULL key */
+    if(json_pack_ex(&error, 0, "{s:i}", NULL, 1))
+        fail("json_pack failed to catch NULL key");
+    check_error("NULL object key", "<args>", 1, 2, 2);
+
+    /* More complicated checks for row/columns */
+    if(json_pack_ex(&error, 0, "{ {}: s }", "foo"))
+        fail("json_pack failed to catch object as key");
+    check_error("Expected format 's', got '{'", "<format>", 1, 3, 3);
+
+    /* Complex object */
+    if(json_pack_ex(&error, 0, "{ s: {},  s:[ii{} }", "foo", "bar", 12, 13))
+        fail("json_pack failed to catch missing ]");
+    check_error("Unexpected format character '}'", "<format>", 1, 19, 19);
+
+    /* Complex array */
+    if(json_pack_ex(&error, 0, "[[[[[   [[[[[  [[[[ }]]]] ]]]] ]]]]]"))
+        fail("json_pack failed to catch extra }");
+    check_error("Unexpected format character '}'", "<format>", 1, 21, 21);
+
+    /* Invalid UTF-8 in object key */
+    if(json_pack_ex(&error, 0, "{s:i}", "\xff\xff", 42))
+        fail("json_pack failed to catch invalid UTF-8 in an object key");
+    check_error("Invalid UTF-8 in object key", "<args>", 1, 2, 2);
+
+    /* Invalid UTF-8 in a string */
+    if(json_pack_ex(&error, 0, "{s:s}", "foo", "\xff\xff"))
+        fail("json_pack failed to catch invalid UTF-8 in a string");
+    check_error("Invalid UTF-8 string", "<args>", 1, 4, 4);
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_simple.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_simple.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_simple.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_simple.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,185 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <string.h>
+#include <jansson.h>
+#include "util.h"
+
+/* Call the simple functions not covered by other tests of the public API */
+int main()
+{
+    json_t *value;
+
+    value = json_integer(1);
+    if(json_typeof(value) != JSON_INTEGER)
+        fail("json_typeof failed");
+
+    if(json_is_object(value))
+        fail("json_is_object failed");
+
+    if(json_is_array(value))
+        fail("json_is_array failed");
+
+    if(json_is_string(value))
+        fail("json_is_string failed");
+
+    if(!json_is_integer(value))
+        fail("json_is_integer failed");
+
+    if(json_is_real(value))
+        fail("json_is_real failed");
+
+    if(!json_is_number(value))
+        fail("json_is_number failed");
+
+    if(json_is_true(value))
+        fail("json_is_true failed");
+
+    if(json_is_false(value))
+        fail("json_is_false failed");
+
+    if(json_is_boolean(value))
+        fail("json_is_boolean failed");
+
+    if(json_is_null(value))
+        fail("json_is_null failed");
+
+    json_decref(value);
+
+
+    value = json_string("foo");
+    if(!value)
+        fail("json_string failed");
+    if(strcmp(json_string_value(value), "foo"))
+        fail("invalid string value");
+
+    if(json_string_set(value, "bar"))
+        fail("json_string_set failed");
+    if(strcmp(json_string_value(value), "bar"))
+        fail("invalid string value");
+
+    json_decref(value);
+
+    value = json_string(NULL);
+    if(value)
+        fail("json_string(NULL) failed");
+
+    /* invalid UTF-8  */
+    value = json_string("a\xefz");
+    if(value)
+        fail("json_string(<invalid utf-8>) failed");
+
+    value = json_string_nocheck("foo");
+    if(!value)
+        fail("json_string_nocheck failed");
+    if(strcmp(json_string_value(value), "foo"))
+        fail("invalid string value");
+
+    if(json_string_set_nocheck(value, "bar"))
+        fail("json_string_set_nocheck failed");
+    if(strcmp(json_string_value(value), "bar"))
+        fail("invalid string value");
+
+    json_decref(value);
+
+    /* invalid UTF-8 */
+    value = json_string_nocheck("qu\xff");
+    if(!value)
+        fail("json_string_nocheck failed");
+    if(strcmp(json_string_value(value), "qu\xff"))
+        fail("invalid string value");
+
+    if(json_string_set_nocheck(value, "\xfd\xfe\xff"))
+        fail("json_string_set_nocheck failed");
+    if(strcmp(json_string_value(value), "\xfd\xfe\xff"))
+        fail("invalid string value");
+
+    json_decref(value);
+
+
+    value = json_integer(123);
+    if(!value)
+        fail("json_integer failed");
+    if(json_integer_value(value) != 123)
+        fail("invalid integer value");
+    if(json_number_value(value) != 123.0)
+        fail("invalid number value");
+
+    if(json_integer_set(value, 321))
+        fail("json_integer_set failed");
+    if(json_integer_value(value) != 321)
+        fail("invalid integer value");
+    if(json_number_value(value) != 321.0)
+        fail("invalid number value");
+
+    json_decref(value);
+
+    value = json_real(123.123);
+    if(!value)
+        fail("json_real failed");
+    if(json_real_value(value) != 123.123)
+        fail("invalid integer value");
+    if(json_number_value(value) != 123.123)
+        fail("invalid number value");
+
+    if(json_real_set(value, 321.321))
+        fail("json_real_set failed");
+    if(json_real_value(value) != 321.321)
+        fail("invalid real value");
+    if(json_number_value(value) != 321.321)
+        fail("invalid number value");
+
+    json_decref(value);
+
+    value = json_true();
+    if(!value)
+        fail("json_true failed");
+    json_decref(value);
+
+    value = json_false();
+    if(!value)
+        fail("json_false failed");
+    json_decref(value);
+
+    value = json_null();
+    if(!value)
+        fail("json_null failed");
+    json_decref(value);
+
+    /* Test reference counting on singletons (true, false, null) */
+    value = json_true();
+    if(value->refcount != (size_t)-1)
+      fail("refcounting true works incorrectly");
+    json_decref(value);
+    if(value->refcount != (size_t)-1)
+      fail("refcounting true works incorrectly");
+    json_incref(value);
+    if(value->refcount != (size_t)-1)
+      fail("refcounting true works incorrectly");
+
+    value = json_false();
+    if(value->refcount != (size_t)-1)
+      fail("refcounting false works incorrectly");
+    json_decref(value);
+    if(value->refcount != (size_t)-1)
+      fail("refcounting false works incorrectly");
+    json_incref(value);
+    if(value->refcount != (size_t)-1)
+      fail("refcounting false works incorrectly");
+
+    value = json_null();
+    if(value->refcount != (size_t)-1)
+      fail("refcounting null works incorrectly");
+    json_decref(value);
+    if(value->refcount != (size_t)-1)
+      fail("refcounting null works incorrectly");
+    json_incref(value);
+    if(value->refcount != (size_t)-1)
+      fail("refcounting null works incorrectly");
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/test_unpack.c
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/test_unpack.c?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/test_unpack.c (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/test_unpack.c Sun Sep 25 20:47:26 2011
@@ -0,0 +1,341 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ * Copyright (c) 2010-2011 Graeme Smecher <gr...@mail.mcgill.ca>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#include <string.h>
+#include <jansson.h>
+#include <stdio.h>
+#include "util.h"
+
+int main()
+{
+    json_t *j, *j2;
+    int i1, i2, i3;
+    json_int_t I1;
+    int rv;
+    double f;
+    char *s;
+
+    json_error_t error;
+
+    /*
+     * Simple, valid json_pack cases
+     */
+
+    /* true */
+    rv = json_unpack(json_true(), "b", &i1);
+    if(rv || !i1)
+        fail("json_unpack boolean failed");
+
+    /* false */
+    rv = json_unpack(json_false(), "b", &i1);
+    if(rv || i1)
+        fail("json_unpack boolean failed");
+
+    /* null */
+    if(json_unpack(json_null(), "n"))
+        fail("json_unpack null failed");
+
+    /* integer */
+    j = json_integer(42);
+    rv = json_unpack(j, "i", &i1);
+    if(rv || i1 != 42)
+        fail("json_unpack integer failed");
+    json_decref(j);
+
+    /* json_int_t */
+    j = json_integer(5555555);
+    rv = json_unpack(j, "I", &I1);
+    if(rv || I1 != 5555555)
+        fail("json_unpack json_int_t failed");
+    json_decref(j);
+
+    /* real */
+    j = json_real(1.7);
+    rv = json_unpack(j, "f", &f);
+    if(rv || f != 1.7)
+        fail("json_unpack real failed");
+    json_decref(j);
+
+    /* number */
+    j = json_integer(12345);
+    rv = json_unpack(j, "F", &f);
+    if(rv || f != 12345.0)
+        fail("json_unpack (real or) integer failed");
+    json_decref(j);
+
+    j = json_real(1.7);
+    rv = json_unpack(j, "F", &f);
+    if(rv || f != 1.7)
+        fail("json_unpack real (or integer) failed");
+    json_decref(j);
+
+    /* string */
+    j = json_string("foo");
+    rv = json_unpack(j, "s", &s);
+    if(rv || strcmp(s, "foo"))
+        fail("json_unpack string failed");
+    json_decref(j);
+
+    /* empty object */
+    j = json_object();
+    if(json_unpack(j, "{}"))
+        fail("json_unpack empty object failed");
+    json_decref(j);
+
+    /* empty list */
+    j = json_array();
+    if(json_unpack(j, "[]"))
+        fail("json_unpack empty list failed");
+    json_decref(j);
+
+    /* non-incref'd object */
+    j = json_object();
+    rv = json_unpack(j, "o", &j2);
+    if(j2 != j || j->refcount != 1)
+        fail("json_unpack object failed");
+    json_decref(j);
+
+    /* incref'd object */
+    j = json_object();
+    rv = json_unpack(j, "O", &j2);
+    if(j2 != j || j->refcount != 2)
+        fail("json_unpack object failed");
+    json_decref(j);
+    json_decref(j);
+
+    /* simple object */
+    j = json_pack("{s:i}", "foo", 42);
+    rv = json_unpack(j, "{s:i}", "foo", &i1);
+    if(rv || i1 != 42)
+        fail("json_unpack simple object failed");
+    json_decref(j);
+
+    /* simple array */
+    j = json_pack("[iii]", 1, 2, 3);
+    rv = json_unpack(j, "[i,i,i]", &i1, &i2, &i3);
+    if(rv || i1 != 1 || i2 != 2 || i3 != 3)
+        fail("json_unpack simple array failed");
+    json_decref(j);
+
+    /* object with many items & strict checking */
+    j = json_pack("{s:i, s:i, s:i}", "a", 1, "b", 2, "c", 3);
+    rv = json_unpack(j, "{s:i, s:i, s:i}", "a", &i1, "b", &i2, "c", &i3);
+    if(rv || i1 != 1 || i2 != 2 || i3 != 3)
+        fail("json_unpack object with many items failed");
+    json_decref(j);
+
+    /*
+     * Invalid cases
+     */
+
+    j = json_integer(42);
+    if(!json_unpack_ex(j, &error, 0, "z"))
+        fail("json_unpack succeeded with invalid format character");
+    check_error("Unexpected format character 'z'", "<format>", 1, 1, 1);
+
+    if(!json_unpack_ex(NULL, &error, 0, "[i]"))
+        fail("json_unpack succeeded with NULL root");
+    check_error("NULL root value", "<root>", -1, -1, 0);
+    json_decref(j);
+
+    /* mismatched open/close array/object */
+    j = json_pack("[]");
+    if(!json_unpack_ex(j, &error, 0, "[}"))
+        fail("json_unpack failed to catch mismatched ']'");
+    check_error("Unexpected format character '}'", "<format>", 1, 2, 2);
+    json_decref(j);
+
+    j = json_pack("{}");
+    if(!json_unpack_ex(j, &error, 0, "{]"))
+        fail("json_unpack failed to catch mismatched '}'");
+    check_error("Expected format 's', got ']'", "<format>", 1, 2, 2);
+    json_decref(j);
+
+    /* missing close array */
+    j = json_pack("[]");
+    if(!json_unpack_ex(j, &error, 0, "["))
+        fail("json_unpack failed to catch missing ']'");
+    check_error("Unexpected end of format string", "<format>", 1, 2, 2);
+    json_decref(j);
+
+    /* missing close object */
+    j = json_pack("{}");
+    if(!json_unpack_ex(j, &error, 0, "{"))
+        fail("json_unpack failed to catch missing '}'");
+    check_error("Unexpected end of format string", "<format>", 1, 2, 2);
+    json_decref(j);
+
+    /* garbage after format string */
+    j = json_pack("[i]", 42);
+    if(!json_unpack_ex(j, &error, 0, "[i]a", &i1))
+        fail("json_unpack failed to catch garbage after format string");
+    check_error("Garbage after format string", "<format>", 1, 4, 4);
+    json_decref(j);
+
+    j = json_integer(12345);
+    if(!json_unpack_ex(j, &error, 0, "ia", &i1))
+        fail("json_unpack failed to catch garbage after format string");
+    check_error("Garbage after format string", "<format>", 1, 2, 2);
+    json_decref(j);
+
+    /* NULL format string */
+    j = json_pack("[]");
+    if(!json_unpack_ex(j, &error, 0, NULL))
+        fail("json_unpack failed to catch null format string");
+    check_error("NULL or empty format string", "<format>", -1, -1, 0);
+    json_decref(j);
+
+    /* NULL string pointer */
+    j = json_string("foobie");
+    if(!json_unpack_ex(j, &error, 0, "s", NULL))
+        fail("json_unpack failed to catch null string pointer");
+    check_error("NULL string argument", "<args>", 1, 1, 1);
+    json_decref(j);
+
+    /* invalid types */
+    j = json_integer(42);
+    j2 = json_string("foo");
+    if(!json_unpack_ex(j, &error, 0, "s"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected string, got integer", "<validation>", 1, 1, 1);
+
+    if(!json_unpack_ex(j, &error, 0, "n"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected null, got integer", "<validation>", 1, 1, 1);
+
+    if(!json_unpack_ex(j, &error, 0, "b"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected true or false, got integer", "<validation>", 1, 1, 1);
+
+    if(!json_unpack_ex(j2, &error, 0, "i"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected integer, got string", "<validation>", 1, 1, 1);
+
+    if(!json_unpack_ex(j2, &error, 0, "I"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected integer, got string", "<validation>", 1, 1, 1);
+
+    if(!json_unpack_ex(j, &error, 0, "f"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected real, got integer", "<validation>", 1, 1, 1);
+
+    if(!json_unpack_ex(j2, &error, 0, "F"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected real or integer, got string", "<validation>", 1, 1, 1);
+
+    if(!json_unpack_ex(j, &error, 0, "[i]"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected array, got integer", "<validation>", 1, 1, 1);
+
+    if(!json_unpack_ex(j, &error, 0, "{si}", "foo"))
+        fail("json_unpack failed to catch invalid type");
+    check_error("Expected object, got integer", "<validation>", 1, 1, 1);
+
+    json_decref(j);
+    json_decref(j2);
+
+    /* Array index out of range */
+    j = json_pack("[i]", 1);
+    if(!json_unpack_ex(j, &error, 0, "[ii]", &i1, &i2))
+        fail("json_unpack failed to catch index out of array bounds");
+    check_error("Array index 1 out of range", "<validation>", 1, 3, 3);
+    json_decref(j);
+
+    /* NULL object key */
+    j = json_pack("{si}", "foo", 42);
+    if(!json_unpack_ex(j, &error, 0, "{si}", NULL, &i1))
+        fail("json_unpack failed to catch null string pointer");
+    check_error("NULL object key", "<args>", 1, 2, 2);
+    json_decref(j);
+
+    /* Object key not found */
+    j = json_pack("{si}", "foo", 42);
+    if(!json_unpack_ex(j, &error, 0, "{si}", "baz", &i1))
+        fail("json_unpack failed to catch null string pointer");
+    check_error("Object item not found: baz", "<validation>", 1, 3, 3);
+    json_decref(j);
+
+    /*
+     * Strict validation
+     */
+
+    j = json_pack("[iii]", 1, 2, 3);
+    rv = json_unpack(j, "[iii!]", &i1, &i2, &i3);
+    if(rv || i1 != 1 || i2 != 2 || i3 != 3)
+        fail("json_unpack array with strict validation failed");
+    json_decref(j);
+
+    j = json_pack("[iii]", 1, 2, 3);
+    if(!json_unpack_ex(j, &error, 0, "[ii!]", &i1, &i2))
+        fail("json_unpack array with strict validation failed");
+    check_error("1 array item(s) left unpacked", "<validation>", 1, 5, 5);
+    json_decref(j);
+
+    /* Like above, but with JSON_STRICT instead of '!' format */
+    j = json_pack("[iii]", 1, 2, 3);
+    if(!json_unpack_ex(j, &error, JSON_STRICT, "[ii]", &i1, &i2))
+        fail("json_unpack array with strict validation failed");
+    check_error("1 array item(s) left unpacked", "<validation>", 1, 4, 4);
+    json_decref(j);
+
+    j = json_pack("{s:s, s:i}", "foo", "bar", "baz", 42);
+    rv = json_unpack(j, "{sssi!}", "foo", &s, "baz", &i1);
+    if(rv || strcmp(s, "bar") != 0 || i1 != 42)
+        fail("json_unpack object with strict validation failed");
+    json_decref(j);
+
+    /* Unpack the same item twice */
+    j = json_pack("{s:s, s:i}", "foo", "bar", "baz", 42);
+    if(!json_unpack_ex(j, &error, 0, "{s:s,s:s!}", "foo", &s, "foo", &s))
+        fail("json_unpack object with strict validation failed");
+    check_error("1 object item(s) left unpacked", "<validation>", 1, 10, 10);
+    json_decref(j);
+
+    j = json_pack("[i,{s:i,s:n},[i,i]]", 1, "foo", 2, "bar", 3, 4);
+    if(json_unpack_ex(j, NULL, JSON_STRICT | JSON_VALIDATE_ONLY,
+                      "[i{sisn}[ii]]", "foo", "bar"))
+        fail("json_unpack complex value with strict validation failed");
+    json_decref(j);
+
+    /* ! and * must be last */
+    j = json_pack("[ii]", 1, 2);
+    if(!json_unpack_ex(j, &error, 0, "[i!i]", &i1, &i2))
+        fail("json_unpack failed to catch ! in the middle of an array");
+    check_error("Expected ']' after '!', got 'i'", "<format>", 1, 4, 4);
+
+    if(!json_unpack_ex(j, &error, 0, "[i*i]", &i1, &i2))
+        fail("json_unpack failed to catch * in the middle of an array");
+    check_error("Expected ']' after '*', got 'i'", "<format>", 1, 4, 4);
+    json_decref(j);
+
+    j = json_pack("{sssi}", "foo", "bar", "baz", 42);
+    if(!json_unpack_ex(j, &error, 0, "{ss!si}", "foo", &s, "baz", &i1))
+        fail("json_unpack failed to catch ! in the middle of an object");
+    check_error("Expected '}' after '!', got 's'", "<format>", 1, 5, 5);
+
+    if(!json_unpack_ex(j, &error, 0, "{ss*si}", "foo", &s, "baz", &i1))
+        fail("json_unpack failed to catch ! in the middle of an object");
+    check_error("Expected '}' after '*', got 's'", "<format>", 1, 5, 5);
+    json_decref(j);
+
+    /* Error in nested object */
+    j = json_pack("{s{snsn}}", "foo", "bar", "baz");
+    if(!json_unpack_ex(j, &error, 0, "{s{sn!}}", "foo", "bar"))
+        fail("json_unpack nested object with strict validation failed");
+    check_error("1 object item(s) left unpacked", "<validation>", 1, 7, 7);
+    json_decref(j);
+
+    /* Error in nested array */
+    j = json_pack("[[ii]]", 1, 2);
+    if(!json_unpack_ex(j, &error, 0, "[[i!]]", &i1))
+        fail("json_unpack nested array with strict validation failed");
+    check_error("1 array item(s) left unpacked", "<validation>", 1, 5, 5);
+    json_decref(j);
+
+    return 0;
+}

Added: avro/trunk/lang/c/jansson/test/suites/api/util.h
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/api/util.h?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/api/util.h (added)
+++ avro/trunk/lang/c/jansson/test/suites/api/util.h Sun Sep 25 20:47:26 2011
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2009-2011 Petri Lehtinen <pe...@digip.org>
+ *
+ * Jansson is free software; you can redistribute it and/or modify
+ * it under the terms of the MIT license. See LICENSE for details.
+ */
+
+#ifndef UTIL_H
+#define UTIL_H
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <jansson.h>
+
+#define failhdr fprintf(stderr, "%s:%s:%d: ", __FILE__, __FUNCTION__, __LINE__)
+
+#define fail(msg)                                                \
+    do {                                                         \
+        failhdr;                                                 \
+        fprintf(stderr, "%s\n", msg);                            \
+        exit(1);                                                 \
+    } while(0)
+
+/* Assumes json_error_t error */
+#define check_error(text_, source_, line_, column_, position_)          \
+    do {                                                                \
+        if(strcmp(error.text, text_) != 0) {                            \
+            failhdr;                                                    \
+            fprintf(stderr, "text: \"%s\" != \"%s\"\n", error.text, text_); \
+            exit(1);                                                    \
+        }                                                               \
+        if(strcmp(error.source, source_) != 0) {                        \
+            failhdr;                                                    \
+                                                                        \
+            fprintf(stderr, "source: \"%s\" != \"%s\"\n", error.source, source_); \
+            exit(1);                                                    \
+        }                                                               \
+        if(error.line != line_) {                                       \
+            failhdr;                                                    \
+            fprintf(stderr, "line: %d != %d\n", error.line, line_);     \
+            exit(1);                                                    \
+        }                                                               \
+        if(error.column != column_) {                                   \
+            failhdr;                                                    \
+            fprintf(stderr, "column: %d != %d\n", error.column, column_); \
+            exit(1);                                                    \
+        }                                                               \
+        if(error.position != position_) {                               \
+            failhdr;                                                    \
+            fprintf(stderr, "position: %d != %d\n", error.position, position_); \
+            exit(1);                                                    \
+        }                                                               \
+    } while(0)
+
+#endif

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/encoded-surrogate-half/error
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/encoded-surrogate-half/error?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/encoded-surrogate-half/error (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/encoded-surrogate-half/error Sun Sep 25 20:47:26 2011
@@ -0,0 +1,2 @@
+1 2 2
+unable to decode byte 0xed near '"'

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/encoded-surrogate-half/input
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/encoded-surrogate-half/input?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/encoded-surrogate-half/input (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/encoded-surrogate-half/input Sun Sep 25 20:47:26 2011
@@ -0,0 +1 @@
+["í¢« <-- encoded surrogate half"]

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-after-backslash/error
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-after-backslash/error?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-after-backslash/error (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-after-backslash/error Sun Sep 25 20:47:26 2011
@@ -0,0 +1,2 @@
+1 3 3
+unable to decode byte 0xe5 near '"\'

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-after-backslash/input
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-after-backslash/input?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-after-backslash/input (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-after-backslash/input Sun Sep 25 20:47:26 2011
@@ -0,0 +1 @@
+["\å"]

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-array/error
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-array/error?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-array/error (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-array/error Sun Sep 25 20:47:26 2011
@@ -0,0 +1,2 @@
+1 1 1
+unable to decode byte 0xe5

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-array/input
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-array/input?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-array/input (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-array/input Sun Sep 25 20:47:26 2011
@@ -0,0 +1 @@
+[å]

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-bigger-int/error
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-bigger-int/error?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-bigger-int/error (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-bigger-int/error Sun Sep 25 20:47:26 2011
@@ -0,0 +1,2 @@
+1 4 4
+unable to decode byte 0xe5 near '123'

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-bigger-int/input
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-bigger-int/input?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-bigger-int/input (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-bigger-int/input Sun Sep 25 20:47:26 2011
@@ -0,0 +1 @@
+[123å]

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-escape/error
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-escape/error?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-escape/error (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-escape/error Sun Sep 25 20:47:26 2011
@@ -0,0 +1,2 @@
+1 4 4
+unable to decode byte 0xe5 near '"\u'

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-escape/input
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-escape/input?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-escape/input (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-escape/input Sun Sep 25 20:47:26 2011
@@ -0,0 +1 @@
+["\uå"]

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-exponent/error
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-exponent/error?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-exponent/error (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-exponent/error Sun Sep 25 20:47:26 2011
@@ -0,0 +1,2 @@
+1 4 4
+unable to decode byte 0xe5 near '1e1'

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-exponent/input
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-exponent/input?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-exponent/input (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-exponent/input Sun Sep 25 20:47:26 2011
@@ -0,0 +1 @@
+[1e1å]

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-identifier/error
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-identifier/error?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-identifier/error (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-identifier/error Sun Sep 25 20:47:26 2011
@@ -0,0 +1,2 @@
+1 2 2
+unable to decode byte 0xe5 near 'a'

Added: avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-identifier/input
URL: http://svn.apache.org/viewvc/avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-identifier/input?rev=1175570&view=auto
==============================================================================
--- avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-identifier/input (added)
+++ avro/trunk/lang/c/jansson/test/suites/invalid-unicode/invalid-utf-8-in-identifier/input Sun Sep 25 20:47:26 2011
@@ -0,0 +1 @@
+[aå]