Do not return value in a void func
[yaz-moved-to-github.git] / src / json.c
index a2d4f1d..91cb4e4 100644 (file)
@@ -1,5 +1,5 @@
 /* This file is part of the YAZ toolkit.
- * Copyright (C) 1995-2009 Index Data
+ * Copyright (C) 1995-2010 Index Data
  * See the file LICENSE for details.
  */
 
@@ -134,7 +134,7 @@ static int json_one_char(const char **p, char *out)
         case 'b':
             *out = '\b'; break;
         case 'f':
-            *out = '\b'; break;
+            *out = '\f'; break;
         case 'n':
             *out = '\n'; break;
         case 'r':
@@ -420,7 +420,7 @@ struct json_node *json_parser_parse(json_parser_t p, const char *json_str)
     p->buf = json_str;
     p->cp = p->buf;
 
-    n = json_parse_object(p);
+    n = json_parse_value(p);
     if (!n)
         return 0;
     c = look_ch(p);
@@ -433,7 +433,8 @@ struct json_node *json_parser_parse(json_parser_t p, const char *json_str)
     return n;
 }
 
-struct json_node *json_parse(const char *json_str, const char **errmsg)
+struct json_node *json_parse2(const char *json_str, const char **errmsg,
+                              size_t *pos)
 {
     json_parser_t p = json_parser_create();
     struct json_node *n = 0;
@@ -447,11 +448,58 @@ struct json_node *json_parse(const char *json_str, const char **errmsg)
         n = json_parser_parse(p, json_str);
         if (!n && errmsg)
             *errmsg = json_parser_get_errmsg(p);
+        if (pos)
+            *pos = json_parser_get_position(p);
         json_parser_destroy(p);
     }
     return n;
 }
 
+struct json_node *json_parse(const char *json_str, const char **errmsg)
+{
+    return json_parse2(json_str, errmsg, 0);
+}
+
+static void wrbuf_json_write(WRBUF b, const char *cp, size_t sz)
+{
+    size_t i;
+    for (i = 0; i < sz; i++)
+    {
+        if (cp[i] > 0 && cp[i] < 32)
+        {
+            wrbuf_putc(b, '\\');
+            switch (cp[i])
+            {
+            case '\b': wrbuf_putc(b, 'b'); break;
+            case '\f': wrbuf_putc(b, 'f'); break;
+            case '\n': wrbuf_putc(b, 'n'); break;
+            case '\r': wrbuf_putc(b, 'r'); break;
+            case '\t': wrbuf_putc(b, 't'); break;
+            default:
+                wrbuf_printf(b, "u%04x", cp[i]);
+            }
+        }
+        else if (cp[i] == '"')
+        {
+            wrbuf_putc(b, '\\'); wrbuf_putc(b, '"');
+        }
+        else if (cp[i] == '\\')
+        {
+            wrbuf_putc(b, '\\'); wrbuf_putc(b, '\\');
+        }
+        else
+        {   /* leave encoding as raw UTF-8 */
+            wrbuf_putc(b, cp[i]);
+        }
+    }       
+        
+}
+
+void wrbuf_json_puts(WRBUF b, const char *str)
+{
+    wrbuf_json_write(b, str, strlen(str));
+}
+
 void json_write_wrbuf(struct json_node *node, WRBUF result)
 {
     switch (node->type)
@@ -483,7 +531,7 @@ void json_write_wrbuf(struct json_node *node, WRBUF result)
         break;
     case json_node_string:
         wrbuf_puts(result, "\"");
-        wrbuf_puts(result, node->u.string);
+        wrbuf_json_puts(result, node->u.string);
         wrbuf_puts(result, "\"");
         break;
     case json_node_number:
@@ -586,6 +634,11 @@ const char *json_parser_get_errmsg(json_parser_t p)
     return p->err_msg;
 }
 
+size_t json_parser_get_position(json_parser_t p)
+{
+    return p->cp - p->buf;
+}
+
 /*
  * Local variables:
  * c-basic-offset: 4