]> granicus.if.org Git - json-c/commitdiff
update json_object_new_string_len, json_escape_str (internal). Writer handles \x00...
authorJehiah Czebotar <jehiah@gmail.com>
Fri, 14 Jan 2011 17:23:06 +0000 (17:23 +0000)
committerJehiah Czebotar <jehiah@gmail.com>
Fri, 14 Jan 2011 17:23:06 +0000 (17:23 +0000)
Added parse_null test. This does not change anything with how the parser handles \u0000 or null characters

This commit is addapted from one by Adomas Paltanavičius <adomas@leanholding.com>

git-svn-id: http://svn.metaparadigm.com/svn/json-c/trunk@63 327403b1-1117-474d-bef2-5cb71233fd97

Makefile.am
json_object.c
json_object.h
json_object_private.h
test_null.c [new file with mode: 0644]
test_null.expected [new file with mode: 0644]
test_null.test [new file with mode: 0644]

index dc920f896e10eec10f8087554c61bb5f770a9362..dc8b34859f5306b98828329d500ccfc379f6e921 100644 (file)
@@ -32,7 +32,7 @@ libjson_la_SOURCES = \
        linkhash.c \
        printbuf.c
 
-check_PROGRAMS = test1 test2 test4 test_parse_int64
+check_PROGRAMS = test1 test2 test4 test_parse_int64 test_null
 
 test1_SOURCES = test1.c
 test1_LDADD = $(lib_LTLIBRARIES)
@@ -46,7 +46,10 @@ test4_LDADD = $(lib_LTLIBRARIES)
 test_parse_int64_SOURCES = test_parse_int64.c
 test_parse_int64_LDADD = $(lib_LTLIBRARIES)
 
-TESTS = test1.test test2.test test4.test parse_int64.test
+test_null_SOURCES = test_null.c
+test_null_LDADD = $(lib_LTLIBRARIES)
+
+TESTS = test1.test test2.test test4.test parse_int64.test test_null.test
 EXTRA_DIST += $(TESTS)
 testsubdir=testSubDir
 TESTS_ENVIRONMENT       = top_builddir=$(top_builddir)
index 2b6dad4b7dffd38ea5855fdb220ceae0d6a9de35..8f1a67e574e628ca441c932a8f61265ce8052387 100644 (file)
@@ -83,15 +83,13 @@ static void json_object_fini(void) {
 
 /* string escaping */
 
-static int json_escape_str(struct printbuf *pb, char *str)
+static int json_escape_str(struct printbuf *pb, char *str, int len)
 {
   int pos = 0, start_offset = 0;
   unsigned char c;
-  do {
+  while (len--) {
     c = str[pos];
     switch(c) {
-    case '\0':
-      break;
     case '\b':
     case '\n':
     case '\r':
@@ -120,7 +118,7 @@ static int json_escape_str(struct printbuf *pb, char *str)
        start_offset = ++pos;
       } else pos++;
     }
-  } while(c);
+  }
   if(pos - start_offset > 0)
     printbuf_memappend(pb, str + start_offset, pos - start_offset);
   return 0;
@@ -218,7 +216,7 @@ static int json_object_object_to_json_string(struct json_object* jso,
        json_object_object_foreachC(jso, iter) {
                        if(i) sprintbuf(pb, ",");
                        sprintbuf(pb, " \"");
-                       json_escape_str(pb, iter.key);
+                       json_escape_str(pb, iter.key, strlen(iter.key));
                        sprintbuf(pb, "\": ");
                        if(iter.val == NULL) sprintbuf(pb, "null");
                        else iter.val->_to_json_string(iter.val, pb);
@@ -309,7 +307,7 @@ boolean json_object_get_boolean(struct json_object *jso)
   case json_type_double:
     return (jso->o.c_double != 0);
   case json_type_string:
-    return (strlen(jso->o.c_string) != 0);
+    return (jso->o.c_string.len != 0);
   default:
     return FALSE;
   }
@@ -346,7 +344,7 @@ int32_t json_object_get_int(struct json_object *jso)
         * Parse strings into 64-bit numbers, then use the
         * 64-to-32-bit number handling below.
         */
-       if (json_parse_int64(jso->o.c_string, &cint64) != 0)
+       if (json_parse_int64(jso->o.c_string.str, &cint64) != 0)
                return 0; /* whoops, it didn't work. */
        o_type = json_type_int;
   }
@@ -391,7 +389,7 @@ int64_t json_object_get_int64(struct json_object *jso)
   case json_type_boolean:
     return jso->o.c_boolean;
   case json_type_string:
-       if (json_parse_int64(jso->o.c_string, &cint) == 0) return cint;
+       if (json_parse_int64(jso->o.c_string.str, &cint) == 0) return cint;
   default:
     return 0;
   }
@@ -428,7 +426,7 @@ double json_object_get_double(struct json_object *jso)
   case json_type_boolean:
     return jso->o.c_boolean;
   case json_type_string:
-    if(sscanf(jso->o.c_string, "%lf", &cdouble) == 1) return cdouble;
+    if(sscanf(jso->o.c_string.str, "%lf", &cdouble) == 1) return cdouble;
   default:
     return 0.0;
   }
@@ -441,14 +439,14 @@ static int json_object_string_to_json_string(struct json_object* jso,
                                             struct printbuf *pb)
 {
   sprintbuf(pb, "\"");
-  json_escape_str(pb, jso->o.c_string);
+  json_escape_str(pb, jso->o.c_string.str, jso->o.c_string.len);
   sprintbuf(pb, "\"");
   return 0;
 }
 
 static void json_object_string_delete(struct json_object* jso)
 {
-  free(jso->o.c_string);
+  free(jso->o.c_string.str);
   json_object_generic_delete(jso);
 }
 
@@ -458,7 +456,8 @@ struct json_object* json_object_new_string(const char *s)
   if(!jso) return NULL;
   jso->_delete = &json_object_string_delete;
   jso->_to_json_string = &json_object_string_to_json_string;
-  jso->o.c_string = strdup(s);
+  jso->o.c_string.str = strdup(s);
+  jso->o.c_string.len = strlen(s);
   return jso;
 }
 
@@ -468,7 +467,9 @@ struct json_object* json_object_new_string_len(const char *s, int len)
   if(!jso) return NULL;
   jso->_delete = &json_object_string_delete;
   jso->_to_json_string = &json_object_string_to_json_string;
-  jso->o.c_string = strndup(s, len);
+  jso->o.c_string.str = malloc(len);
+  memcpy(jso->o.c_string.str, (void *)s, len);
+  jso->o.c_string.len = len;
   return jso;
 }
 
@@ -477,12 +478,22 @@ const char* json_object_get_string(struct json_object *jso)
   if(!jso) return NULL;
   switch(jso->o_type) {
   case json_type_string:
-    return jso->o.c_string;
+    return jso->o.c_string.str;
   default:
     return json_object_to_json_string(jso);
   }
 }
 
+int json_object_get_string_len(struct json_object *jso)  {
+  if(!jso) return 0;
+  switch(jso->o_type) {
+  case json_type_string:
+    return jso->o.c_string.len;
+  default:
+    return 0;
+  }
+}
+
 
 /* json_object_array */
 
index 9a44c6ef7e60a44be02830e8ea85357bd6b9179f..d8fdc29d090181f2f107885651c9dc82e8dfc4cb 100644 (file)
@@ -337,6 +337,16 @@ extern struct json_object* json_object_new_string_len(const char *s, int len);
  */
 extern const char* json_object_get_string(struct json_object *obj);
 
+/** Get the string length of a json_object
+ *
+ * If the passed object is not of type json_type_string then zero
+ * will be returned.
+ *
+ * @param obj the json_object instance
+ * @returns int
+ */
+extern int json_object_get_string_len(struct json_object *obj);
+
 #ifdef __cplusplus
 }
 #endif
index 04f510ad374796e0be0f3ee8304c56b8ac480150..c7f604bf4b015a4297f72a82511c51e4f877b4a4 100644 (file)
@@ -33,7 +33,10 @@ struct json_object
     int64_t c_int64;
     struct lh_table *c_object;
     struct array_list *c_array;
-    char *c_string;
+    struct {
+        char *str;
+        int len;
+    } c_string;
   } o;
 };
 
diff --git a/test_null.c b/test_null.c
new file mode 100644 (file)
index 0000000..73729b8
--- /dev/null
@@ -0,0 +1,35 @@
+/*
+* Tests if binary strings are supported.
+*/
+
+#include <stdio.h>
+#include <string.h>
+#include "config.h"
+
+#include "json_inttypes.h"
+#include "json_object.h"
+
+int main() {
+    // this test has a space after the null character. check that it's still included
+    const char *input = " \0 ";
+    const char *expected = "\" \\u0000 \"";
+    struct json_object *string = json_object_new_string_len(input, 3);
+    const char *json = json_object_to_json_string(string);
+
+    int strings_match =  !strcmp( expected, json);
+    int retval = 0;
+    if (strings_match) {
+        printf("JSON write result is correct: %s\n", json);
+        printf("PASS\n");
+    } else {
+        printf("JSON write result doesn't match expected string\n");
+        printf("expected string: ");
+        printf("%s\n", expected);
+        printf("parsed string:   ");
+        printf("%s\n", json);
+        printf("FAIL\n");
+        retval=1;
+    }
+    json_object_put(string);
+    return retval;
+}
diff --git a/test_null.expected b/test_null.expected
new file mode 100644 (file)
index 0000000..fd7b479
--- /dev/null
@@ -0,0 +1,2 @@
+JSON write result is correct: " \u0000 "
+PASS
diff --git a/test_null.test b/test_null.test
new file mode 100644 (file)
index 0000000..469ec64
--- /dev/null
@@ -0,0 +1,12 @@
+#!/bin/sh
+
+# Common definitions
+if test -z "$srcdir"; then
+    srcdir="${0%/*}"
+    test "$srcdir" = "$0" && srcdir=.
+    test -z "$srcdir" && srcdir=.
+fi
+. "$srcdir/test-defs.sh"
+
+run_output_test test_null
+exit $?