Permalink
Browse files

latest from upstream

  • Loading branch information...
2 parents 5dfed29 + cc61a3f commit 85921ef75155de7d86bfa7bc0fa0d81d9fc95a04 @brianmario committed Apr 27, 2011
Showing with 3,803 additions and 1,549 deletions.
  1. +20 −32 CMakeLists.txt
  2. +13 −29 COPYING
  3. +43 −10 ChangeLog
  4. +9 −3 README
  5. +14 −29 configure
  6. +23 −0 example/CMakeLists.txt
  7. +7 −0 example/README.md
  8. +69 −0 example/parse_config.c
  9. +101 −0 example/sample.config
  10. +23 −0 perf/CMakeLists.txt
  11. +1,418 −0 perf/documents.c
  12. +28 −0 perf/documents.h
  13. +134 −0 perf/perftest.c
  14. +13 −29 reformatter/CMakeLists.txt
  15. +62 −87 reformatter/json_reformat.c
  16. +15 −31 src/CMakeLists.txt
  17. +2 −2 src/YAJL.dxy
  18. +19 −33 src/api/yajl_common.h
  19. +62 −73 src/api/yajl_gen.h
  20. +107 −77 src/api/yajl_parse.h
  21. +177 −0 src/api/yajl_tree.h
  22. +14 −177 src/yajl
  23. +58 −59 src/yajl.c
  24. +16 −32 src/yajl_alloc.c
  25. +14 −30 src/yajl_alloc.h
  26. +21 −37 src/yajl_buf.c
  27. +17 −33 src/yajl_buf.h
  28. +20 −36 src/yajl_bytestack.h
  29. +78 −46 src/yajl_encode.c
  30. +19 −35 src/yajl_encode.h
  31. +109 −78 src/yajl_gen.c
  32. +102 −87 src/yajl_lex.c
  33. +20 −38 src/yajl_lex.h
  34. +142 −100 src/yajl_parser.c
  35. +31 −35 src/yajl_parser.h
  36. +501 −0 src/yajl_tree.c
  37. +13 −29 test/CMakeLists.txt
  38. 0 test/cases/ac_difficult_json_c_test_case_with_comments.json
  39. 0 test/cases/ac_difficult_json_c_test_case_with_comments.json.gold
  40. 0 test/cases/ac_simple_with_comments.json
  41. +9 −0 test/cases/ac_simple_with_comments.json.gold
  42. 0 test/cases/ag_false_then_garbage.json
  43. 0 test/cases/ag_false_then_garbage.json.gold
  44. 0 test/cases/ag_null_then_garbage.json
  45. 0 test/cases/ag_null_then_garbage.json.gold
  46. 0 test/cases/ag_true_then_garbage.json
  47. 0 test/cases/ag_true_then_garbage.json.gold
  48. +1 −0 test/cases/am_eof.json
  49. +4 −0 test/cases/am_eof.json.gold
  50. +1 −0 test/cases/am_integers.json
  51. +3 −0 test/cases/am_integers.json.gold
  52. +3 −0 test/cases/am_multiple.json
  53. +5 −0 test/cases/am_multiple.json.gold
  54. +7 −0 test/cases/am_stuff.json
  55. +14 −0 test/cases/am_stuff.json.gold
  56. 0 test/cases/ap_array_open.json
  57. 0 test/cases/ap_array_open.json.gold
  58. +1 −0 test/cases/ap_eof_str.json
  59. 0 test/cases/ap_eof_str.json.gold
  60. 0 test/cases/ap_map_open.json
  61. 0 test/cases/ap_map_open.json.gold
  62. +1 −0 test/cases/ap_partial_ok.json
  63. +2 −0 test/cases/{array_open.json.gold → ap_partial_ok.json.gold}
  64. +0 −1 test/cases/array_open.json
  65. +1 −0 test/cases/bignums.json
  66. +5 −0 test/cases/bignums.json.gold
  67. +0 −11 test/cases/dc_simple_with_comments.json
  68. +0 −5 test/cases/dc_simple_with_comments.json.gold
  69. +0 −1 test/cases/difficult_json_c_test_case_with_comments.json
  70. +0 −36 test/cases/difficult_json_c_test_case_with_comments.json.gold
  71. +1 −0 test/cases/doubles_in_array.json
  72. +8 −0 test/cases/doubles_in_array.json.gold
  73. +0 −1 test/cases/false_then_garbage.json
  74. +0 −2 test/cases/false_then_garbage.json.gold
  75. 0 test/cases/fg_false_then_garbage.json
  76. +3 −0 test/cases/fg_false_then_garbage.json.gold
  77. +1 −0 test/cases/fg_issue_7.json
  78. +3 −0 test/cases/fg_issue_7.json.gold
  79. 0 test/cases/fg_null_then_garbage.json
  80. +3 −0 test/cases/fg_null_then_garbage.json.gold
  81. +1 −0 test/cases/fg_true_then_garbage.json
  82. +3 −0 test/cases/fg_true_then_garbage.json.gold
  83. +1 −0 test/cases/high_overflow.json
  84. +2 −0 test/cases/high_overflow.json.gold
  85. +1 −0 test/cases/low_overflow.json
  86. +2 −0 test/cases/low_overflow.json.gold
  87. +0 −1 test/cases/map_open.json
  88. +0 −2 test/cases/map_open.json.gold
  89. +3 −0 test/cases/multiple.json
  90. +4 −0 test/cases/multiple.json.gold
  91. +1 −0 test/cases/np_partial_bad.json
  92. +5 −0 test/cases/np_partial_bad.json.gold
  93. +0 −1 test/cases/null_then_garbage.json
  94. +0 −2 test/cases/null_then_garbage.json.gold
  95. +1 −5 test/cases/simple_with_comments.json.gold
  96. +0 −1 test/cases/true_then_garbage.json
  97. +0 −2 test/cases/true_then_garbage.json.gold
  98. +1 −0 test/cases/zerobyte.json
  99. 0 test/cases/zerobyte.json.gold
  100. +43 −21 test/run_tests.sh
  101. +67 −77 test/yajl_test.c
  102. +13 −29 verify/CMakeLists.txt
  103. +45 −64 verify/json_verify.c
View
52 CMakeLists.txt
@@ -1,50 +1,35 @@
-# Copyright 2010, Lloyd Hilaiel.
-#
-# Redistribution and use in source and binary forms, with or without
-# modification, are permitted provided that the following conditions are
-# met:
-#
-# 1. Redistributions of source code must retain the above copyright
-# notice, this list of conditions and the following disclaimer.
-#
-# 2. Redistributions in binary form must reproduce the above copyright
-# notice, this list of conditions and the following disclaimer in
-# the documentation and/or other materials provided with the
-# distribution.
-#
-# 3. Neither the name of Lloyd Hilaiel nor the names of its
-# contributors may be used to endorse or promote products derived
-# from this software without specific prior written permission.
-#
-# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
-# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
-# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
-# DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
-# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
-# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
-# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
-# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
-# STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
-# IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
-# POSSIBILITY OF SUCH DAMAGE.
+# Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+#
+# Permission to use, copy, modify, and/or distribute this software for any
+# purpose with or without fee is hereby granted, provided that the above
+# copyright notice and this permission notice appear in all copies.
+#
+# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
CMAKE_MINIMUM_REQUIRED(VERSION 2.6)
PROJECT(YetAnotherJSONParser C)
-SET (YAJL_MAJOR 1)
+SET (YAJL_MAJOR 2)
SET (YAJL_MINOR 0)
-SET (YAJL_MICRO 11)
+SET (YAJL_MICRO 1)
SET (YAJL_DIST_NAME "yajl-${YAJL_MAJOR}.${YAJL_MINOR}.${YAJL_MICRO}")
IF (NOT CMAKE_BUILD_TYPE)
SET(CMAKE_BUILD_TYPE "Release")
ENDIF (NOT CMAKE_BUILD_TYPE)
-SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS}")
IF (WIN32)
+ SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /W4")
ADD_DEFINITIONS(-DWIN32)
SET(linkFlags "/PDB:NONE /INCREMENTAL:NO /OPT:NOREF /OPT:NOICF")
SET(CMAKE_EXE_LINKER_FLAGS "${linkFlags}"
@@ -62,6 +47,7 @@ IF (WIN32)
SET(CMAKE_C_FLAGS_DEBUG "/D DEBUG /Od /Z7")
SET(CMAKE_C_FLAGS_RELEASE "/D NDEBUG /O2")
ELSE (WIN32)
+ SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall")
IF(CMAKE_COMPILER_IS_GNUCC)
INCLUDE(CheckCCompilerFlag)
CHECK_C_COMPILER_FLAG(-fvisibility=hidden HAVE_GCC_VISIBILITY)
@@ -81,6 +67,8 @@ ADD_SUBDIRECTORY(src)
ADD_SUBDIRECTORY(test)
ADD_SUBDIRECTORY(reformatter)
ADD_SUBDIRECTORY(verify)
+ADD_SUBDIRECTORY(example)
+ADD_SUBDIRECTORY(perf)
INCLUDE(YAJLDoc.cmake)
View
42 COPYING
@@ -1,29 +1,13 @@
-Copyright 2010, Lloyd Hilaiel.
-
-Redistribution and use in source and binary forms, with or without
-modification, are permitted provided that the following conditions are
-met:
-
- 1. Redistributions of source code must retain the above copyright
- notice, this list of conditions and the following disclaimer.
-
- 2. Redistributions in binary form must reproduce the above copyright
- notice, this list of conditions and the following disclaimer in
- the documentation and/or other materials provided with the
- distribution.
-
- 3. Neither the name of Lloyd Hilaiel nor the names of its
- contributors may be used to endorse or promote products derived
- from this software without specific prior written permission.
-
-THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
-IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
-WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
-DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
-INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
-(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
-SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
-HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
-STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
-IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
-POSSIBILITY OF SUCH DAMAGE.
+Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+
+Permission to use, copy, modify, and/or distribute this software for any
+purpose with or without fee is hereby granted, provided that the above
+copyright notice and this permission notice appear in all copies.
+
+THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
View
53 ChangeLog
@@ -1,6 +1,39 @@
+2.0.0
+ * lth YAJL is now ISC licensed: http://en.wikipedia.org/wiki/ISC_license
+ * lth 20-35% (osx and linux respectively) parsing performance
+ improvement attained by tweaking string scanning (idea: @michaelrhanson).
+ * Florian Forster & lth - yajl_tree interface introduced as a higher level
+ interface to the parser (eats JSON, poops a memory representation)
+ * lth require a C99 compiler
+ * lth integers are now represented with long long (64bit+) on all platforms.
+ * lth size_t now used throughout to represent buffer lengths, so you can
+ safely manage buffers greater than 4GB.
+ * gno semantic improvements to yajl's API regarding partial value parsing and
+ trailing garbage
+ * lth new configuration mechanism for yajl, see yajl_config() and
+ yajl_gen_config()
+ * gno more allocation checking in more places
+ * gno remove usage of strtol, replace with custom implementation that cares
+ not about your locale.
+ * lth yajl_parse_complete renamed to yajl_complete_parse.
+ * lth add a switch to validate utf8 strings as they are generated.
+ * lth tests are a lot quieter in their output.
+ * lth addition of a little in tree performance benchmark, `perftest` in
+ perf/perftest.c
+
+1.0.12
+ * Conrad Irwin - Parse null bytes correctly
+ * Mirek Rusin - fix LLVM warnings
+ * gno - Don't generate numbers for keys. closes #13
+ * lth - various win32 fixes, including build documentation improvements
+ * John Stamp - Don't export private symbols.
+ * John Stamp - Install yajl_version.h, not the template.
+ * John Stamp - Don't use -fPIC for static lib. Cmake will automatically add it for the shared.
+ * lth 0 fix paths embedded in dylib upon installation on osx. closes #11
+
1.0.11
* lth remove -Wno-missing-field-initializers for greater gcc compat (3.4.6)
-
+
1.0.10
* Brian Maher - yajl is now buildable without a c++ compiler present
* Brian Maher - fix header installation on OSX with cmake 2.8.0 installed
@@ -35,15 +68,15 @@
* jstamp support for combining short options in tools
* jstamp exit properly on errors from tools
* octo test success no longer depends on integer size
- * max fix configure --prefix
-
+ * max fix configure --prefix
+
1.0.5
* lth several performance improvements related to function
inlinin'
1.0.4
* lth fix broken utf8 validation for three & four byte represenations.
- thanks to http://github.com/brianmario and
+ thanks to http://github.com/brianmario and
http://github.com/technoweenie
1.0.3
@@ -53,7 +86,7 @@
1.0.2
* lth update doxygen documentation with new sample code, passing NULL
for allocation functions added in 1.0.0
-
+
1.0.1
* lth resolve crash in json_reformatter due to incorrectly ordered
parameters.
@@ -71,7 +104,7 @@
* tjw cleanup of code for symmetry and ease of reading
* lth integration of patches from Robert Varga which cleanup
compilation warnings on 64 bit linux
-
+
0.4.0
* lth buffer overflow bug in yajl_gen_double s/%lf/%g/ - thanks to
Eric Bergstrome
@@ -85,7 +118,7 @@
* lth fix handling of special characters hex 0F and 1F in yajl_encode
(thanks to Robert Geiger)
* lth allow leading zeros in exponents (thanks to Hatem Nassrat)
-
+
0.3.0
* lth doxygen documentation (html & man) generated as part of the
build
@@ -105,15 +138,15 @@
0.2.2
* lth on windows build debug with C7 symbols and no pdb files.
-
+
0.2.1
* fix yajl_reformat and yajl_verify to work on arbitrarily sized
inputs.
* fix win32 build break, clean up all errors and warnings.
* fix optimized build flags.
-
+
0.2.0
* optionally support comments in input text
-
+
0.1.0
* Initial release
View
12 README
@@ -1,3 +1,8 @@
+**********************************************************************
+ This is YAJL 2, for the legacy version of YAJL. see
+ https://github.com/lloyd/yajl/tree/1.x
+**********************************************************************
+
Welcome to Yet Another JSON Library (YAJL)
## Why does the world need another C library for parsing JSON?
@@ -21,9 +26,10 @@ of the more important aspects of YAJL.
## YAJL is Free.
-BSD licensing means you can use it in open source and commercial products
-alike. My request beyond the licensing is that if you find bugs drop
-me a email, or better yet, fork me on git and fix it!
+Permissive licensing means you can use it in open source and
+commercial products alike without any fees. My request beyond the
+licensing is that if you find bugs drop me a email, or better yet,
+fork and fix.
Porting YAJL should be trivial, the implementation is ANSI C. If you
port to new systems I'd love to hear of it and integrate your patches.
View
43 configure
@@ -1,33 +1,18 @@
#!/usr/bin/env ruby
-# Copyright 2010, Lloyd Hilaiel.
-#
-# Redistribution and use in source and binary forms, with or without
-# modification, are permitted provided that the following conditions are
-# met:
-#
-# 1. Redistributions of source code must retain the above copyright
-# notice, this list of conditions and the following disclaimer.
-#
-# 2. Redistributions in binary form must reproduce the above copyright
-# notice, this list of conditions and the following disclaimer in
-# the documentation and/or other materials provided with the
-# distribution.
-#
-# 3. Neither the name of Lloyd Hilaiel nor the names of its
-# contributors may be used to endorse or promote products derived
-# from this software without specific prior written permission.
-#
-# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
-# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
-# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
-# DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
-# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
-# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
-# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
-# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
-# STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
-# IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
-# POSSIBILITY OF SUCH DAMAGE.
+#
+# Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+#
+# Permission to use, copy, modify, and/or distribute this software for any
+# purpose with or without fee is hereby granted, provided that the above
+# copyright notice and this permission notice appear in all copies.
+#
+# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
require 'fileutils'
require 'optparse'
View
23 example/CMakeLists.txt
@@ -0,0 +1,23 @@
+# Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+#
+# Permission to use, copy, modify, and/or distribute this software for any
+# purpose with or without fee is hereby granted, provided that the above
+# copyright notice and this permission notice appear in all copies.
+#
+# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+
+SET (SRCS parse_config.c)
+
+# use the library we build, duh.
+INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/include)
+LINK_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/lib)
+
+ADD_EXECUTABLE(parse_config ${SRCS})
+
+TARGET_LINK_LIBRARIES(parse_config yajl_s)
View
7 example/README.md
@@ -0,0 +1,7 @@
+This directory holds an example of how one might use yajl in the
+simplest possible way, to do something like parse and extract values
+from a configuration file.
+
+Note that use of the yajl_tree.h utility is completely optional, and
+yajl_parse.h offers a lower level stream parsing API that is more
+efficient and flexible at the cost of some complexity.
View
69 example/parse_config.c
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <stdio.h>
+#include <string.h>
+
+#include "yajl/yajl_tree.h"
+
+static unsigned char fileData[65536];
+
+int
+main(void)
+{
+ size_t rd;
+ yajl_val node;
+ char errbuf[1024];
+
+ /* null plug buffers */
+ fileData[0] = errbuf[0] = 0;
+
+ /* read the entire config file */
+ rd = fread((void *) fileData, 1, sizeof(fileData) - 1, stdin);
+
+ /* file read error handling */
+ if (rd == 0 && !feof(stdin)) {
+ fprintf(stderr, "error encountered on file read\n");
+ return 1;
+ } else if (rd >= sizeof(fileData) - 1) {
+ fprintf(stderr, "config file too big\n");
+ return 1;
+ }
+
+ /* we have the whole config file in memory. let's parse it ... */
+ node = yajl_tree_parse((const char *) fileData, errbuf, sizeof(errbuf));
+
+ /* parse error handling */
+ if (node == NULL) {
+ fprintf(stderr, "parse_error: ");
+ if (strlen(errbuf)) fprintf(stderr, " %s", errbuf);
+ else fprintf(stderr, "unknown error");
+ fprintf(stderr, "\n");
+ return 1;
+ }
+
+ /* ... and extract a nested value from the config file */
+ {
+ const char * path[] = { "Logging", "timeFormat", (const char *) 0 };
+ yajl_val v = yajl_tree_get(node, path, yajl_t_string);
+ if (v) printf("%s/%s: %s\n", path[0], path[1], YAJL_GET_STRING(v));
+ else printf("no such node: %s/%s\n", path[0], path[1]);
+ }
+
+ yajl_tree_free(node);
+
+ return 0;
+}
View
101 example/sample.config
@@ -0,0 +1,101 @@
+/*
+ * The configuration file for Yahoo! BrowserPlus, included in the YAJL
+ * tree as a sample configuration file for parsing.
+ *
+ * This is the configuration file for BrowserPlus
+ */
+
+{
+ // The type of build this is, which is accessible to JavaScript via
+ // BrowserPlus.getPlatformInfo();
+ // Different build types should only differ in signatures accepted
+ // (BrowserPlus.crt) and configured distribution servers.
+ "BuildType": "ephemeral",
+
+ // the base url for the "primary" distribution server. This server will
+ // be the single source of truth for Permissions, and will used to
+ // attain services
+ "DistServer": "http://browserplus.yahoo.com",
+
+ // An array of "secondary" distribution servers, which will be checked
+ // in order for services if the primary server has no components
+ // available which match an issued require statement.
+ "SecondaryDistServers": [
+ "http://first.fictional.server",
+ "http://second.fictional.server"
+ ],
+
+ // Logging Setup
+ "Logging" :
+ {
+ // Log level. Values: "debug"|"info"|"warn"|"error"|"fatal"|"off"
+ "level": "BP_LOG_LEVEL",
+
+ // Destination. Values: "file"|"console"|"win32"
+ "dest": "BP_LOG_DEST",
+
+ // Log message layout. Values: "standard"|"source"|"raw"
+ "layout": "standard",
+
+ // Time format. Values: "utc"|"local"|"msec"
+ "timeFormat": "utc",
+
+ // File size in KB which will trigger a rollover
+ "fileRolloverKB": 2048,
+
+ // Whether to send file logging from each service to a distinct file.
+ // Values: "combined"|"separate"
+ "serviceLogMode": "combined"
+ },
+
+ // Daemon setup
+ // Syntax: "Options": "option1 option2 etc"
+ // -fg run in foreground, log to console
+ "Options":"",
+
+ // Auto-shutdown daemon if idle for this time. Use 0 for no auto-shutdown.
+ "MaxIdleSecs": 5,
+
+ // At the end of each BrowserPlus session a small web request is made
+ // to yahoo to indicate that BrowserPlus was used. This report includes
+ // * information about the browser being used
+ // * an "installation id", which is a unique token that's generated
+ // the first time BrowserPlus runs.
+ //
+ // By design, there is *no information* in this request that gives
+ // Yahoo! information about:
+ // a) the site that the user is visiting (see, "url": false)
+ // b) who the user is (the installation token cannot be tracked to a
+ // specific user).
+ //
+ // This information is primarily captured to help Yahoo! understand
+ // adoption and usage of the BrowserPlus platform.
+ "UsageReporting":
+ {
+ "enabled": true,
+ "url": false,
+ "id": true
+ },
+
+ // "Breakpoints" is an array of strings holding named breakpoints.
+ // Platform code checks for specific entries at certain key points, and if
+ // a matching entry is found here a DebugBreak will be performed.
+ // For developers with Visual Studio installed, the DebugBreak will cause an
+ // opportunity to perform just-in-time attachment of an existing or new
+ // debugger instance.
+ // The currently-defined breakpoints are listed below:
+ // runServiceProcess - A DebugBreak is performed in the service
+ // "harness" just prior to service load.
+ // ax.FinalConstruct - A DebugBreak is performed at entry to
+ // FinalConstruct of the ActiveX plugin.
+ // PluginInit - Very early in the NPAPI plugin initialization.
+ // A wonderful spot to stop and set more
+ // breakpoints.
+ //"Breakpoints": ["runServiceProcess"],
+
+ // How often we check for service updates. We guarantee at least this
+ // much time will pass between checks, though the true time may be
+ // much more if sites which use browserplus are not visited.
+ // The time is in seconds.
+ "ServiceUpdatePollPeriod": 86400
+}
View
23 perf/CMakeLists.txt
@@ -0,0 +1,23 @@
+# Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+#
+# Permission to use, copy, modify, and/or distribute this software for any
+# purpose with or without fee is hereby granted, provided that the above
+# copyright notice and this permission notice appear in all copies.
+#
+# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+
+SET (SRCS perftest.c documents.c documents.h)
+
+# use the library we build, duh.
+INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/include)
+LINK_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/lib)
+
+ADD_EXECUTABLE(perftest ${SRCS})
+
+TARGET_LINK_LIBRARIES(perftest yajl_s)
View
1,418 perf/documents.c
1,418 additions, 0 deletions not shown because the diff is too large. Please use a local Git client to view these changes.
View
28 perf/documents.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#ifndef __DOCUMENTS_H__
+#define __DOCUMENTS_H__
+
+/* a header that provides access to several json documents broken into chunks of
+ * less than 4k, cause C99 says that's what we should do and YAJL likes streams */
+
+extern const char ** g_documents[];
+int num_docs(void);
+const char ** get_doc(int i);
+unsigned int doc_size(int i);
+
+#endif
View
134 perf/perftest.c
@@ -0,0 +1,134 @@
+/*
+ * Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <yajl/yajl_parse.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "documents.h"
+
+/* a platform specific defn' of a function to get a high res time in a
+ * portable format */
+#ifndef WIN32
+#include <sys/time.h>
+static double mygettime(void) {
+ struct timeval now;
+ gettimeofday(&now, NULL);
+ return now.tv_sec + (now.tv_usec / 1000000.0);
+}
+#else
+#define _WIN32 1
+#include <windows.h>
+static double mygettime(void) {
+ long long tval;
+ FILETIME ft;
+ GetSystemTimeAsFileTime(&ft);
+ tval = ft.dwHighDateTime;
+ tval <<=32;
+ tval |= ft.dwLowDateTime;
+ return tval / 10000000.00;
+}
+#endif
+
+#define PARSE_TIME_SECS 3
+
+static int
+run(int validate_utf8)
+{
+ long long times = 0;
+ double starttime;
+
+ starttime = mygettime();
+
+ /* allocate a parser */
+ for (;;) {
+ int i;
+ {
+ double now = mygettime();
+ if (now - starttime >= PARSE_TIME_SECS) break;
+ }
+
+ for (i = 0; i < 100; i++) {
+ yajl_handle hand = yajl_alloc(NULL, NULL, NULL);
+ yajl_status stat;
+ const char ** d;
+
+ yajl_config(hand, yajl_dont_validate_strings, validate_utf8 ? 0 : 1);
+
+ for (d = get_doc(times % num_docs()); *d; d++) {
+ stat = yajl_parse(hand, (unsigned char *) *d, strlen(*d));
+ if (stat != yajl_status_ok) break;
+ }
+
+ stat = yajl_complete_parse(hand);
+
+ if (stat != yajl_status_ok) {
+ unsigned char * str =
+ yajl_get_error(hand, 1,
+ (unsigned char *) *d,
+ (*d ? strlen(*d) : 0));
+ fprintf(stderr, "%s", (const char *) str);
+ yajl_free_error(hand, str);
+ return 1;
+ }
+ yajl_free(hand);
+ times++;
+ }
+ }
+
+ /* parsed doc 'times' times */
+ {
+ double throughput;
+ double now;
+ const char * all_units[] = { "B/s", "KB/s", "MB/s", (char *) 0 };
+ const char ** units = all_units;
+ int i, avg_doc_size = 0;
+
+ now = mygettime();
+
+ for (i = 0; i < num_docs(); i++) avg_doc_size += doc_size(i);
+ avg_doc_size /= num_docs();
+
+ throughput = (times * avg_doc_size) / (now - starttime);
+
+ while (*(units + 1) && throughput > 1024) {
+ throughput /= 1024;
+ units++;
+ }
+
+ printf("Parsing speed: %g %s\n", throughput, *units);
+ }
+
+ return 0;
+}
+
+int
+main(void)
+{
+ int rv = 0;
+
+ printf("-- speed tests determine parsing throughput given %d different sample documents --\n",
+ num_docs());
+
+ printf("With UTF8 validation:\n");
+ rv = run(1);
+ if (rv != 0) return rv;
+ printf("Without UTF8 validation:\n");
+ rv = run(0);
+ return rv;
+}
+
View
42 reformatter/CMakeLists.txt
@@ -1,32 +1,16 @@
-# Copyright 2010, Lloyd Hilaiel.
-#
-# Redistribution and use in source and binary forms, with or without
-# modification, are permitted provided that the following conditions are
-# met:
-#
-# 1. Redistributions of source code must retain the above copyright
-# notice, this list of conditions and the following disclaimer.
-#
-# 2. Redistributions in binary form must reproduce the above copyright
-# notice, this list of conditions and the following disclaimer in
-# the documentation and/or other materials provided with the
-# distribution.
-#
-# 3. Neither the name of Lloyd Hilaiel nor the names of its
-# contributors may be used to endorse or promote products derived
-# from this software without specific prior written permission.
-#
-# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
-# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
-# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
-# DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
-# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
-# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
-# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
-# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
-# STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
-# IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
-# POSSIBILITY OF SUCH DAMAGE.
+# Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+#
+# Permission to use, copy, modify, and/or distribute this software for any
+# purpose with or without fee is hereby granted, provided that the above
+# copyright notice and this permission notice appear in all copies.
+#
+# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
# set up a paths
SET (binDir ${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/bin)
View
149 reformatter/json_reformat.c
@@ -1,34 +1,18 @@
/*
- * Copyright 2010, Lloyd Hilaiel.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. Neither the name of Lloyd Hilaiel nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
- * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
- * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
- * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
- * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
- * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
+ * Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
#include <yajl/yajl_parse.h>
#include <yajl/yajl_gen.h>
@@ -40,67 +24,58 @@
static int reformat_null(void * ctx)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_null(g);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_null(g);
}
static int reformat_boolean(void * ctx, int boolean)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_bool(g, boolean);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_bool(g, boolean);
}
-static int reformat_number(void * ctx, const char * s, unsigned int l)
+static int reformat_number(void * ctx, const char * s, size_t l)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_number(g, s, l);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_number(g, s, l);
}
static int reformat_string(void * ctx, const unsigned char * stringVal,
- unsigned int stringLen)
+ size_t stringLen)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_string(g, stringVal, stringLen);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_string(g, stringVal, stringLen);
}
static int reformat_map_key(void * ctx, const unsigned char * stringVal,
- unsigned int stringLen)
+ size_t stringLen)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_string(g, stringVal, stringLen);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_string(g, stringVal, stringLen);
}
static int reformat_start_map(void * ctx)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_map_open(g);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_map_open(g);
}
static int reformat_end_map(void * ctx)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_map_close(g);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_map_close(g);
}
static int reformat_start_array(void * ctx)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_array_open(g);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_array_open(g);
}
static int reformat_end_array(void * ctx)
{
yajl_gen g = (yajl_gen) ctx;
- yajl_gen_array_close(g);
- return 1;
+ return yajl_gen_status_ok == yajl_gen_array_close(g);
}
static yajl_callbacks callbacks = {
@@ -135,28 +110,35 @@ main(int argc, char ** argv)
yajl_handle hand;
static unsigned char fileData[65536];
/* generator config */
- yajl_gen_config conf = { 1, " " };
- yajl_gen g;
+ yajl_gen g;
yajl_status stat;
size_t rd;
- /* allow comments */
- yajl_parser_config cfg = { 1, 1 };
- int retval = 0, done = 0;
+ int retval = 0;
+ int a = 1;
+
+ g = yajl_gen_alloc(NULL);
+ yajl_gen_config(g, yajl_gen_beautify, 1);
+ yajl_gen_config(g, yajl_gen_validate_utf8, 1);
+
+ /* ok. open file. let's read and parse */
+ hand = yajl_alloc(&callbacks, NULL, (void *) g);
+ /* and let's allow comments by default */
+ yajl_config(hand, yajl_allow_comments, 1);
/* check arguments.*/
- int a = 1;
while ((a < argc) && (argv[a][0] == '-') && (strlen(argv[a]) > 1)) {
unsigned int i;
for ( i=1; i < strlen(argv[a]); i++) {
switch (argv[a][i]) {
case 'm':
- conf.beautify = 0;
+ yajl_gen_config(g, yajl_gen_beautify, 0);
break;
case 'u':
- cfg.checkUTF8 = 0;
+ yajl_config(hand, yajl_dont_validate_strings, 1);
break;
default:
- fprintf(stderr, "unrecognized option: '%c'\n\n", argv[a][i]);
+ fprintf(stderr, "unrecognized option: '%c'\n\n",
+ argv[a][i]);
usage(argv[0]);
}
}
@@ -165,51 +147,44 @@ main(int argc, char ** argv)
if (a < argc) {
usage(argv[0]);
}
-
- g = yajl_gen_alloc(&conf, NULL);
- /* ok. open file. let's read and parse */
- hand = yajl_alloc(&callbacks, &cfg, NULL, (void *) g);
-
- while (!done) {
+
+ for (;;) {
rd = fread((void *) fileData, 1, sizeof(fileData) - 1, stdin);
-
+
if (rd == 0) {
if (!feof(stdin)) {
fprintf(stderr, "error on file read.\n");
retval = 1;
- break;
}
- done = 1;
+ break;
}
fileData[rd] = 0;
-
- if (done)
- /* parse any remaining buffered data */
- stat = yajl_parse_complete(hand);
- else
- /* read file data, pass to parser */
- stat = yajl_parse(hand, fileData, rd);
-
- if (stat != yajl_status_ok &&
- stat != yajl_status_insufficient_data)
+
+ stat = yajl_parse(hand, fileData, rd);
+
+ if (stat != yajl_status_ok) break;
+
{
- unsigned char * str = yajl_get_error(hand, 1, fileData, rd);
- fprintf(stderr, "%s", (const char *) str);
- yajl_free_error(hand, str);
- retval = 1;
- break;
- } else {
const unsigned char * buf;
- unsigned int len;
+ size_t len;
yajl_gen_get_buf(g, &buf, &len);
fwrite(buf, 1, len, stdout);
yajl_gen_clear(g);
}
}
+ stat = yajl_complete_parse(hand);
+
+ if (stat != yajl_status_ok) {
+ unsigned char * str = yajl_get_error(hand, 1, fileData, rd);
+ fprintf(stderr, "%s", (const char *) str);
+ yajl_free_error(hand, str);
+ retval = 1;
+ }
+
yajl_gen_free(g);
yajl_free(hand);
-
+
return retval;
}
View
46 src/CMakeLists.txt
@@ -1,39 +1,23 @@
-# Copyright 2010, Lloyd Hilaiel.
-#
-# Redistribution and use in source and binary forms, with or without
-# modification, are permitted provided that the following conditions are
-# met:
-#
-# 1. Redistributions of source code must retain the above copyright
-# notice, this list of conditions and the following disclaimer.
-#
-# 2. Redistributions in binary form must reproduce the above copyright
-# notice, this list of conditions and the following disclaimer in
-# the documentation and/or other materials provided with the
-# distribution.
-#
-# 3. Neither the name of Lloyd Hilaiel nor the names of its
-# contributors may be used to endorse or promote products derived
-# from this software without specific prior written permission.
-#
-# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
-# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
-# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
-# DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
-# INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
-# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
-# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
-# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
-# STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
-# IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
-# POSSIBILITY OF SUCH DAMAGE.
+# Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+#
+# Permission to use, copy, modify, and/or distribute this software for any
+# purpose with or without fee is hereby granted, provided that the above
+# copyright notice and this permission notice appear in all copies.
+#
+# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
SET (SRCS yajl.c yajl_lex.c yajl_parser.c yajl_buf.c
yajl_encode.c yajl_gen.c yajl_alloc.c
- yajl_version.c
+ yajl_tree.c yajl_version.c
)
SET (HDRS yajl_parser.h yajl_lex.h yajl_buf.h yajl_encode.h yajl_alloc.h)
-SET (PUB_HDRS api/yajl_parse.h api/yajl_gen.h api/yajl_common.h)
+SET (PUB_HDRS api/yajl_parse.h api/yajl_gen.h api/yajl_common.h api/yajl_tree.h)
# useful when fixing lexer bugs.
#ADD_DEFINITIONS(-DYAJL_LEXER_DEBUG)
View
4 src/YAJL.dxy
@@ -151,7 +151,7 @@ MULTILINE_CPP_IS_BRIEF = NO
# If set to NO, the detailed description appears after the member
# documentation.
-DETAILS_AT_TOP = YES
+# DETAILS_AT_TOP = YES
# If the INHERIT_DOCS tag is set to YES (the default) then an undocumented
# member inherits the documentation from any documented member that it
@@ -518,7 +518,7 @@ EXCLUDE_SYMBOLS =
# directories that contain example code fragments that are included (see
# the \include command).
-EXAMPLE_PATH =
+EXAMPLE_PATH = ..
# If the value of the EXAMPLE_PATH tag contains directories, you can use the
# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp
View
52 src/api/yajl_common.h
@@ -1,38 +1,24 @@
/*
- * Copyright 2010, Lloyd Hilaiel.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. Neither the name of Lloyd Hilaiel nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
- * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
- * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
- * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
- * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
- * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
+ * Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
#ifndef __YAJL_COMMON_H__
#define __YAJL_COMMON_H__
+#include <stddef.h>
+
#ifdef __cplusplus
extern "C" {
#endif
@@ -58,14 +44,14 @@ extern "C" {
/** pointer to a malloc function, supporting client overriding memory
* allocation routines */
-typedef void * (*yajl_malloc_func)(void *ctx, unsigned int sz);
+typedef void * (*yajl_malloc_func)(void *ctx, size_t sz);
/** pointer to a free function, supporting client overriding memory
* allocation routines */
typedef void (*yajl_free_func)(void *ctx, void * ptr);
/** pointer to a realloc function which can resize an allocation. */
-typedef void * (*yajl_realloc_func)(void *ctx, void * ptr, unsigned int sz);
+typedef void * (*yajl_realloc_func)(void *ctx, void * ptr, size_t sz);
/** A structure which can be passed to yajl_*_alloc routines to allow the
* client to specify memory allocation functions to be used. */
@@ -84,6 +70,6 @@ typedef struct
#ifdef __cplusplus
}
-#endif
+#endif
#endif
View
135 src/api/yajl_gen.h
@@ -1,34 +1,18 @@
/*
- * Copyright 2010, Lloyd Hilaiel.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. Neither the name of Lloyd Hilaiel nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
- * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
- * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
- * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
- * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
- * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
+ * Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
/**
* \file yajl_gen.h
@@ -40,6 +24,8 @@
#ifndef __YAJL_GEN_H__
#define __YAJL_GEN_H__
+#include <stddef.h>
+
#ifdef __cplusplus
extern "C" {
#endif
@@ -63,7 +49,11 @@ extern "C" {
yajl_gen_invalid_number,
/** A print callback was passed in, so there is no internal
* buffer to get from */
- yajl_gen_no_buf
+ yajl_gen_no_buf,
+ /** returned from yajl_gen_string() when the yajl_gen_validate_utf8
+ * option is enabled and an invalid was passed by client code.
+ */
+ yajl_gen_invalid_string
} yajl_gen_status;
/** an opaque handle to a generator */
@@ -72,71 +62,70 @@ extern "C" {
/** a callback used for "printing" the results. */
typedef void (*yajl_print_t)(void * ctx,
const char * str,
- unsigned int len);
+ size_t len);
- /** configuration structure for the generator */
- typedef struct {
+ /** configuration parameters for the parser, these may be passed to
+ * yajl_gen_config() along with option specific argument(s). In general,
+ * all configuration parameters default to *off*. */
+ typedef enum {
/** generate indented (beautiful) output */
- unsigned int beautify;
- /** an opportunity to define an indent string. such as \\t or
- * some number of spaces. default is four spaces ' '. This
- * member is only relevant when beautify is true */
- const char * indentString;
- /** escape the '/' character */
- unsigned int htmlSafe;
- } yajl_gen_config;
+ yajl_gen_beautify = 0x01,
+ /**
+ * Set an indent string which is used when yajl_gen_beautify
+ * is enabled. Maybe something like \\t or some number of
+ * spaces. The default is four spaces ' '.
+ */
+ yajl_gen_indent_string = 0x02,
+ /**
+ * Set a function and context argument that should be used to
+ * output generated json. the function should conform to the
+ * yajl_print_t prototype while the context argument is a
+ * void * of your choosing.
+ *
+ * example:
+ * yajl_gen_config(g, yajl_gen_print_callback, myFunc, myVoidPtr);
+ */
+ yajl_gen_print_callback = 0x04,
+ /**
+ * Normally the generator does not validate that strings you
+ * pass to it via yajl_gen_string() are valid UTF8. Enabling
+ * this option will cause it to do so.
+ */
+ yajl_gen_validate_utf8 = 0x08
+ } yajl_gen_option;
- /** allocate a generator handle
- * \param config a pointer to a structure containing parameters which
- * configure the behavior of the json generator
- * \param allocFuncs an optional pointer to a structure which allows
- * the client to overide the memory allocation
- * used by yajl. May be NULL, in which case
- * malloc/free/realloc will be used.
- *
- * \returns an allocated handle on success, NULL on failure (bad params)
+ /** allow the modification of generator options subsequent to handle
+ * allocation (via yajl_alloc)
+ * \returns zero in case of errors, non-zero otherwise
*/
- YAJL_API yajl_gen yajl_gen_alloc(const yajl_gen_config * config,
- const yajl_alloc_funcs * allocFuncs);
-
- /** allocate a generator handle that will print to the specified
- * callback rather than storing the results in an internal buffer.
- * \param callback a pointer to a printer function. May be NULL
- * in which case, the results will be store in an
- * internal buffer.
- * \param config a pointer to a structure containing parameters
- * which configure the behavior of the json
- * generator.
+ YAJL_API int yajl_gen_config(yajl_gen g, yajl_gen_option opt, ...);
+
+ /** allocate a generator handle
* \param allocFuncs an optional pointer to a structure which allows
* the client to overide the memory allocation
* used by yajl. May be NULL, in which case
* malloc/free/realloc will be used.
- * \param ctx a context pointer that will be passed to the
- * printer callback.
*
* \returns an allocated handle on success, NULL on failure (bad params)
*/
- YAJL_API yajl_gen yajl_gen_alloc2(const yajl_print_t callback,
- const yajl_gen_config * config,
- const yajl_alloc_funcs * allocFuncs,
- void * ctx);
+ YAJL_API yajl_gen yajl_gen_alloc(const yajl_alloc_funcs * allocFuncs);
/** free a generator handle */
YAJL_API void yajl_gen_free(yajl_gen handle);
- YAJL_API yajl_gen_status yajl_gen_integer(yajl_gen hand, long int number);
+ YAJL_API yajl_gen_status yajl_gen_integer(yajl_gen hand, long long int number);
/** generate a floating point number. number may not be infinity or
* NaN, as these have no representation in JSON. In these cases the
* generator will return 'yajl_gen_invalid_number' */
YAJL_API yajl_gen_status yajl_gen_double(yajl_gen hand, double number);
YAJL_API yajl_gen_status yajl_gen_number(yajl_gen hand,
const char * num,
- unsigned int len);
+ size_t len);
YAJL_API yajl_gen_status yajl_gen_string(yajl_gen hand,
const unsigned char * str,
- unsigned int len);
+ size_t len);
YAJL_API yajl_gen_status yajl_gen_null(yajl_gen hand);
- YAJL_API yajl_gen_status yajl_gen_bool(yajl_gen hand, int boolean);
+ YAJL_API yajl_gen_status yajl_gen_bool(yajl_gen hand, int boolean);
YAJL_API yajl_gen_status yajl_gen_map_open(yajl_gen hand);
YAJL_API yajl_gen_status yajl_gen_map_close(yajl_gen hand);
YAJL_API yajl_gen_status yajl_gen_array_open(yajl_gen hand);
@@ -147,7 +136,7 @@ extern "C" {
* buffer. This allows stream generation. */
YAJL_API yajl_gen_status yajl_gen_get_buf(yajl_gen hand,
const unsigned char ** buf,
- unsigned int * len);
+ size_t * len);
/** clear yajl's output buffer, but maintain all internal generation
* state. This function will not "reset" the generator state, and is
View
184 src/api/yajl_parse.h
@@ -1,58 +1,40 @@
/*
- * Copyright 2010, Lloyd Hilaiel.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. Neither the name of Lloyd Hilaiel nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
- * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
- * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
- * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
- * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
- * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
+ * Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
/**
* \file yajl_parse.h
- * Interface to YAJL's JSON parsing facilities.
+ * Interface to YAJL's JSON stream parsing facilities.
*/
#include <yajl/yajl_common.h>
#ifndef __YAJL_PARSE_H__
#define __YAJL_PARSE_H__
+#include <stddef.h>
+
#ifdef __cplusplus
extern "C" {
-#endif
+#endif
/** error codes returned from this interface */
typedef enum {
/** no error was encountered */
yajl_status_ok,
/** a client callback returned zero, stopping the parse */
yajl_status_client_canceled,
- /** The parse cannot yet complete because more json input text
- * is required, call yajl_parse with the next buffer of input text.
- * (pertinent only when stream parsing) */
- yajl_status_insufficient_data,
/** An error occured during the parse. Call yajl_get_error for
* more information about the encountered error */
yajl_status_error
@@ -75,67 +57,115 @@ extern "C" {
* continue. If zero, the parse will be canceled and
* yajl_status_client_canceled will be returned from the parse.
*
- * Note about handling of numbers:
- * yajl will only convert numbers that can be represented in a double
- * or a long int. All other numbers will be passed to the client
- * in string form using the yajl_number callback. Furthermore, if
- * yajl_number is not NULL, it will always be used to return numbers,
- * that is yajl_integer and yajl_double will be ignored. If
- * yajl_number is NULL but one of yajl_integer or yajl_double are
- * defined, parsing of a number larger than is representable
- * in a double or long int will result in a parse error.
+ * \attention {
+ * A note about the handling of numbers:
+ *
+ * yajl will only convert numbers that can be represented in a
+ * double or a 64 bit (long long) int. All other numbers will
+ * be passed to the client in string form using the yajl_number
+ * callback. Furthermore, if yajl_number is not NULL, it will
+ * always be used to return numbers, that is yajl_integer and
+ * yajl_double will be ignored. If yajl_number is NULL but one
+ * of yajl_integer or yajl_double are defined, parsing of a
+ * number larger than is representable in a double or 64 bit
+ * integer will result in a parse error.
+ * }
*/
typedef struct {
int (* yajl_null)(void * ctx);
int (* yajl_boolean)(void * ctx, int boolVal);
- int (* yajl_integer)(void * ctx, long integerVal);
+ int (* yajl_integer)(void * ctx, long long integerVal);
int (* yajl_double)(void * ctx, double doubleVal);
/** A callback which passes the string representation of the number
* back to the client. Will be used for all numbers when present */
int (* yajl_number)(void * ctx, const char * numberVal,
- unsigned int numberLen);
+ size_t numberLen);
/** strings are returned as pointers into the JSON text when,
* possible, as a result, they are _not_ null padded */
int (* yajl_string)(void * ctx, const unsigned char * stringVal,
- unsigned int stringLen);
+ size_t stringLen);
int (* yajl_start_map)(void * ctx);
int (* yajl_map_key)(void * ctx, const unsigned char * key,
- unsigned int stringLen);
- int (* yajl_end_map)(void * ctx);
+ size_t stringLen);
+ int (* yajl_end_map)(void * ctx);
int (* yajl_start_array)(void * ctx);
- int (* yajl_end_array)(void * ctx);
+ int (* yajl_end_array)(void * ctx);
} yajl_callbacks;
-
- /** configuration structure for the generator */
- typedef struct {
- /** if nonzero, javascript style comments will be allowed in
- * the json input, both slash star and slash slash */
- unsigned int allowComments;
- /** if nonzero, invalid UTF8 strings will cause a parse
- * error */
- unsigned int checkUTF8;
- } yajl_parser_config;
/** allocate a parser handle
* \param callbacks a yajl callbacks structure specifying the
* functions to call when different JSON entities
* are encountered in the input text. May be NULL,
* which is only useful for validation.
- * \param config configuration parameters for the parse.
+ * \param afs memory allocation functions, may be NULL for to use
+ * C runtime library routines (malloc and friends)
* \param ctx a context pointer that will be passed to callbacks.
*/
YAJL_API yajl_handle yajl_alloc(const yajl_callbacks * callbacks,
- const yajl_parser_config * config,
- const yajl_alloc_funcs * allocFuncs,
+ yajl_alloc_funcs * afs,
void * ctx);
-
- /** allow resetting of the lexer without the need to realloc a new parser */
- void yajl_reset_parser(yajl_handle hand);
- /** free a parser handle */
+
+ /** configuration parameters for the parser, these may be passed to
+ * yajl_config() along with option specific argument(s). In general,
+ * all configuration parameters default to *off*. */
+ typedef enum {
+ /** Ignore javascript style comments present in
+ * JSON input. Non-standard, but rather fun
+ * arguments: toggled off with integer zero, on otherwise.
+ *
+ * example:
+ * yajl_config(h, yajl_allow_comments, 1); // turn comment support on
+ */
+ yajl_allow_comments = 0x01,
+ /**
+ * When set the parser will verify that all strings in JSON input are
+ * valid UTF8 and will emit a parse error if this is not so. When set,
+ * this option makes parsing slightly more expensive (~7% depending
+ * on processor and compiler in use)
+ *
+ * example:
+ * yajl_config(h, yajl_dont_validate_strings, 1); // disable utf8 checking
+ */
+ yajl_dont_validate_strings = 0x02,
+ /**
+ * By default, upon calls to yajl_complete_parse(), yajl will
+ * ensure the entire input text was consumed and will raise an error
+ * otherwise. Enabling this flag will cause yajl to disable this
+ * check. This can be useful when parsing json out of a that contains more
+ * than a single JSON document.
+ */
+ yajl_allow_trailing_garbage = 0x04,
+ /**
+ * Allow multiple values to be parsed by a single handle. The
+ * entire text must be valid JSON, and values can be seperated
+ * by any kind of whitespace. This flag will change the
+ * behavior of the parser, and cause it continue parsing after
+ * a value is parsed, rather than transitioning into a
+ * complete state. This option can be useful when parsing multiple
+ * values from an input stream.
+ */
+ yajl_allow_multiple_values = 0x08,
+ /**
+ * When yajl_complete_parse() is called the parser will
+ * check that the top level value was completely consumed. I.E.,
+ * if called whilst in the middle of parsing a value
+ * yajl will enter an error state (premature EOF). Setting this
+ * flag suppresses that check and the corresponding error.
+ */
+ yajl_allow_partial_values = 0x10
+ } yajl_option;
+
+ /** allow the modification of parser options subsequent to handle
+ * allocation (via yajl_alloc)
+ * \returns zero in case of errors, non-zero otherwise
+ */
+ YAJL_API int yajl_config(yajl_handle h, yajl_option opt, ...);
+
+ /** free a parser handle */
YAJL_API void yajl_free(yajl_handle handle);
/** Parse some json!
@@ -145,7 +175,7 @@ extern "C" {
*/
YAJL_API yajl_status yajl_parse(yajl_handle hand,
const unsigned char * jsonText,
- unsigned int jsonTextLength);
+ size_t jsonTextLength);
/** Parse any remaining buffered json.
* Since yajl is a stream-based parser, without an explicit end of
@@ -156,8 +186,8 @@ extern "C" {
*
* \param hand - a handle to the json parser allocated with yajl_alloc
*/
- YAJL_API yajl_status yajl_parse_complete(yajl_handle hand);
-
+ YAJL_API yajl_status yajl_complete_parse(yajl_handle hand);
+
/** get an error string describing the state of the
* parse.
*
@@ -166,31 +196,31 @@ extern "C" {
* the specific char.
*
* \returns A dynamically allocated string will be returned which should
- * be freed with yajl_free_error
+ * be freed with yajl_free_error
*/
YAJL_API unsigned char * yajl_get_error(yajl_handle hand, int verbose,
const unsigned char * jsonText,
- unsigned int jsonTextLength);
+ size_t jsonTextLength);
/**
* get the amount of data consumed from the last chunk passed to YAJL.
*
* In the case of a successful parse this can help you understand if
* the entire buffer was consumed (which will allow you to handle
- * "junk at end of input".
- *
+ * "junk at end of input").
+ *
* In the event an error is encountered during parsing, this function
* affords the client a way to get the offset into the most recent
* chunk where the error occured. 0 will be returned if no error
* was encountered.
*/
- YAJL_API unsigned int yajl_get_bytes_consumed(yajl_handle hand);
+ YAJL_API size_t yajl_get_bytes_consumed(yajl_handle hand);
/** free an error returned from yajl_get_error */
YAJL_API void yajl_free_error(yajl_handle hand, unsigned char * str);
#ifdef __cplusplus
}
-#endif
+#endif
#endif
View
177 src/api/yajl_tree.h
@@ -0,0 +1,177 @@
+/*
+ * Copyright (c) 2010-2011 Florian Forster <ff at octo.it>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/**
+ * \file yajl_tree.h
+ *
+ * Parses JSON data and returns the data in tree form.
+ *
+ * \author Florian Forster
+ * \date August 2010
+ *
+ * This interface makes quick parsing and extraction of
+ * smallish JSON docs trivial:
+ *
+ * \include example/parse_config.c
+ */
+
+#ifndef YAJL_TREE_H
+#define YAJL_TREE_H 1
+
+#include <yajl/yajl_common.h>
+
+/** possible data types that a yajl_val_s can hold */
+typedef enum {
+ yajl_t_string = 1,
+ yajl_t_number = 2,
+ yajl_t_object = 3,
+ yajl_t_array = 4,
+ yajl_t_true = 5,
+ yajl_t_false = 6,
+ yajl_t_null = 7,
+ /** The any type isn't valid for yajl_val_s.type, but can be
+ * used as an argument to routines like yajl_tree_get().
+ */
+ yajl_t_any = 8
+} yajl_type;
+
+#define YAJL_NUMBER_INT_VALID 0x01
+#define YAJL_NUMBER_DOUBLE_VALID 0x02
+
+/** A pointer to a node in the parse tree */
+typedef struct yajl_val_s * yajl_val;
+
+/**
+ * A JSON value representation capable of holding one of the seven
+ * types above. For "string", "number", "object", and "array"
+ * additional data is available in the union. The "YAJL_IS_*"
+ * and "YAJL_GET_*" macros below allow type checking and convenient
+ * value extraction.
+ */
+struct yajl_val_s
+{
+ /** Type of the value contained. Use the "YAJL_IS_*" macors to check for a
+ * specific type. */
+ yajl_type type;
+ /** Type-specific data. You may use the "YAJL_GET_*" macros to access these
+ * members. */
+ union
+ {
+ char * string;
+ struct {
+ long long i; /*< integer value, if representable. */
+ double d; /*< double value, if representable. */
+ /** Signals whether the \em i and \em d members are
+ * valid. See \c YAJL_NUMBER_INT_VALID and
+ * \c YAJL_NUMBER_DOUBLE_VALID. */
+ char *r; /*< unparsed number in string form. */
+ unsigned int flags;
+ } number;
+ struct {
+ const char **keys; /*< Array of keys */
+ yajl_val *values; /*< Array of values. */
+ size_t len; /*< Number of key-value-pairs. */
+ } object;
+ struct {
+ yajl_val *values; /*< Array of elements. */
+ size_t len; /*< Number of elements. */
+ } array;
+ } u;
+};
+
+/**
+ * Parse a string.
+ *
+ * Parses an null-terminated string containing JSON data and returns a pointer
+ * to the top-level value (root of the parse tree).
+ *
+ * \param input Pointer to a null-terminated utf8 string containing
+ * JSON data.
+ * \param error_buffer Pointer to a buffer in which an error message will
+ * be stored if \em yajl_tree_parse fails, or
+ * \c NULL. The buffer will be initialized before
+ * parsing, so its content will be destroyed even if
+ * \em yajl_tree_parse succeeds.
+ * \param error_buffer_size Size of the memory area pointed to by
+ * \em error_buffer_size. If \em error_buffer_size is
+ * \c NULL, this argument is ignored.
+ *
+ * \returns Pointer to the top-level value or \c NULL on error. The memory
+ * pointed to must be freed using \em yajl_tree_free. In case of an error, a
+ * null terminated message describing the error in more detail is stored in
+ * \em error_buffer if it is not \c NULL.
+ */
+YAJL_API yajl_val yajl_tree_parse (const char *input,
+ char *error_buffer, size_t error_buffer_size);
+
+/**
+ * Free a parse tree returned by "yajl_tree_parse".
+ *
+ * \param v Pointer to a JSON value returned by "yajl_tree_parse". Passing NULL
+ * is valid and results in a no-op.
+ */
+YAJL_API void yajl_tree_free (yajl_val v);
+
+/**
+ * Access a nested value inside a tree.
+ *
+ * \param parent the node under which you'd like to extract values.
+ * \param path A null terminated array of strings, each the name of an object key
+ * \param type the yajl_type of the object you seek, or yajl_t_any if any will do.
+ *
+ * \returns a pointer to the found value, or NULL if we came up empty.
+ *
+ * Future Ideas: it'd be nice to move path to a string and implement support for
+ * a teeny tiny micro language here, so you can extract array elements, do things
+ * like .first and .last, even .length. Inspiration from JSONPath and css selectors?
+ * No it wouldn't be fast, but that's not what this API is about.
+ */
+YAJL_API yajl_val yajl_tree_get(yajl_val parent, const char ** path, yajl_type type);
+
+/* Various convenience macros to check the type of a `yajl_val` */
+#define YAJL_IS_STRING(v) (((v) != NULL) && ((v)->type == yajl_t_string))
+#define YAJL_IS_NUMBER(v) (((v) != NULL) && ((v)->type == yajl_t_number))
+#define YAJL_IS_INTEGER(v) (YAJL_IS_NUMBER(v) && ((v)->u.flags & YAJL_NUMBER_INT_VALID))
+#define YAJL_IS_DOUBLE(v) (YAJL_IS_NUMBER(v) && ((v)->u.flags & YAJL_NUMBER_DOUBLE_VALID))
+#define YAJL_IS_OBJECT(v) (((v) != NULL) && ((v)->type == yajl_t_object))
+#define YAJL_IS_ARRAY(v) (((v) != NULL) && ((v)->type == yajl_t_array ))
+#define YAJL_IS_TRUE(v) (((v) != NULL) && ((v)->type == yajl_t_true ))
+#define YAJL_IS_FALSE(v) (((v) != NULL) && ((v)->type == yajl_t_false ))
+#define YAJL_IS_NULL(v) (((v) != NULL) && ((v)->type == yajl_t_null ))
+
+/** Given a yajl_val_string return a ptr to the bare string it contains,
+ * or NULL if the value is not a string. */
+#define YAJL_GET_STRING(v) (YAJL_IS_STRING(v) ? (v)->u.string : NULL)
+
+/** Get the string representation of a number. You should check type first,
+ * perhaps using YAJL_IS_NUMBER */
+#define YAJL_GET_NUMBER(v) ((v)->u.number.r)
+
+/** Get the double representation of a number. You should check type first,
+ * perhaps using YAJL_IS_DOUBLE */
+#define YAJL_GET_DOUBLE(v) ((v)->u.number.d)
+
+/** Get the 64bit (long long) integer representation of a number. You should
+ * check type first, perhaps using YAJL_IS_INTEGER */
+#define YAJL_GET_INTEGER(v) ((v)->u.number.i)
+
+/** Get a pointer to a yajl_val_object or NULL if the value is not an object. */
+#define YAJL_GET_OBJECT(v) (YAJL_IS_OBJECT(v) ? &(v)->u.object : NULL)
+
+/** Get a pointer to a yajl_val_array or NULL if the value is not an object. */
+#define YAJL_GET_ARRAY(v) (YAJL_IS_ARRAY(v) ? &(v)->u.array : NULL)
+
+#endif /* YAJL_TREE_H */
View
191 src/yajl
@@ -1,11 +1,16 @@
+/**
+\example reformatter/json_reformat.c
+\example example/parse_config.c
+*/
+
/*!
- \mainpage Yet Another JSON Library (YAJL)
+ \mainpage Yet Another JSON Library (YAJL)
\author Lloyd Hilaiel
- \date 2010
+ \date 2007-2011
Yet Another JSON Library (YAJL) is a small event-driven (SAX-style)
JSON parser written in ANSI C, and a small validating JSON
-generator. YAJL is released under the BSD license.
+generator. YAJL is released under the permissive ISC license.
\section features Features
@@ -15,182 +20,14 @@ generator. YAJL is released under the BSD license.
-# tiny
-# event driven
-# support for generating "beautified" JSON
+ -# includes
+It also includes a small simplified tree interface for
+simplified parsing and extraction of data from smallish JSON documents.
\section usage Usage
-The following code sample is a complete JSON "reformating" program. It
-demonstrates how to perform stream parsing and generation.
-
-\code
-#include <yajl/yajl_parse.h>
-#include <yajl/yajl_gen.h>
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-static int reformat_null(void * ctx)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_null(g);
- return 1;
-}
-
-static int reformat_boolean(void * ctx, int boolean)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_bool(g, boolean);
- return 1;
-}
-
-static int reformat_number(void * ctx, const char * s, unsigned int l)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_number(g, s, l);
- return 1;
-}
-
-static int reformat_string(void * ctx, const unsigned char * stringVal,
- unsigned int stringLen)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_string(g, stringVal, stringLen);
- return 1;
-}
-
-static int reformat_map_key(void * ctx, const unsigned char * stringVal,
- unsigned int stringLen)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_string(g, stringVal, stringLen);
- return 1;
-}
-
-static int reformat_start_map(void * ctx)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_map_open(g);
- return 1;
-}
-
-
-static int reformat_end_map(void * ctx)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_map_close(g);
- return 1;
-}
-
-static int reformat_start_array(void * ctx)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_array_open(g);
- return 1;
-}
-
-static int reformat_end_array(void * ctx)
-{
- yajl_gen g = (yajl_gen) ctx;
- yajl_gen_array_close(g);
- return 1;
-}
-
-static yajl_callbacks callbacks = {
- reformat_null,
- reformat_boolean,
- NULL,
- NULL,
- reformat_number,
- reformat_string,
- reformat_start_map,
- reformat_map_key,
- reformat_end_map,
- reformat_start_array,
- reformat_end_array
-};
-
-static void
-usage(const char * progname)
-{
- fprintf(stderr, "usage: %s <filename>\n"
- " -m minimize json rather than beautify (default)\n"
- " -u allow invalid UTF8 inside strings during parsing\n",
- progname);
- exit(1);
-
-}
-
-int
-main(int argc, char ** argv)
-{
- yajl_handle hand;
- static unsigned char fileData[65536];
- /* generator config */
- yajl_gen_config conf = { 1, " " };
- yajl_gen g;
- yajl_status stat;
- size_t rd;
- /* allow comments */
- yajl_parser_config cfg = { 1, 1 };
- int done = 0;
-
- /* check arguments. We expect exactly one! */
- if (argc == 2) {
- if (!strcmp("-m", argv[1])) {
- conf.beautify = 0;
-
- } else if (!strcmp("-u", argv[1])) {
- cfg.checkUTF8 = 0;
- } else {
- usage(argv[0]);
- }
- } else if (argc != 1) {
- usage(argv[0]);
- }
-
- g = yajl_gen_alloc(&conf, NULL);
-
- /* ok. open file. let's read and parse */
- hand = yajl_alloc(&callbacks, &cfg, NULL, (void *) g);
-
- while (!done) {
- rd = fread((void *) fileData, 1, sizeof(fileData) - 1, stdin);
-
- if (rd == 0) {
- if (!feof(stdin)) {
- fprintf(stderr, "error on file read.\n");
- break;
- }
- done = 1;
- }
- fileData[rd] = 0;
-
- if (done)
- /* parse any remaining buffered data */
- stat = yajl_parse_complete(hand);
- else
- /* read file data, pass to parser */
- stat = yajl_parse(hand, fileData, rd);
-
- if (stat != yajl_status_ok &&
- stat != yajl_status_insufficient_data)
- {
- unsigned char * str = yajl_get_error(hand, 1, fileData, rd);
- fprintf(stderr, (const char *) str);
- yajl_free_error(hand, str);
- } else {
- const unsigned char * buf;
- unsigned int len;
- yajl_gen_get_buf(g, &buf, &len);
- fwrite(buf, 1, len, stdout);
- yajl_gen_clear(g);
- }
- }
+See <a href="reformatter_2json_reformat_8c-example.html">json_reformat.c</a> for a complete example of stream based parsing
+and generation of JSON. See <a href="example_2parse_config_8c-example.html">parse_config.c</a> for an example of the
+simplified tree interface.
- yajl_gen_free(g);
- yajl_free(hand);
-
- return 0;
-}
-\endcode
*/
View
117 src/yajl.c
@@ -1,34 +1,18 @@
/*
- * Copyright 2010, Lloyd Hilaiel.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. Neither the name of Lloyd Hilaiel nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
- * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
- * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
- * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
- * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
- * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
+ * Copyright (c) 2007-2011, Lloyd Hilaiel <lloyd@hilaiel.com>
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
#include "api/yajl_parse.h"
#include "yajl_lex.h"
@@ -37,6 +21,7 @@
#include <stdlib.h>
#include <string.h>
+#include <stdarg.h>
#include <assert.h>
const char *
@@ -50,9 +35,6 @@ yajl_status_to_string(yajl_status stat)
case yajl_status_client_canceled:
statStr = "client canceled parse";
break;
- case yajl_status_insufficient_data:
- statStr = "eof was met before the parse could complete";
- break;
case yajl_status_error:
statStr = "parse error";
break;
@@ -62,12 +44,9 @@ yajl_status_to_string(yajl_status stat)
yajl_handle
yajl_alloc(const yajl_callbacks * callbacks,
- const yajl_parser_config * config,
- const yajl_alloc_funcs * afs,
+ yajl_alloc_funcs * afs,
void * ctx)
{
- unsigned int allowComments = 0;
- unsigned int validateUTF8 = 0;
yajl_handle hand = NULL;
yajl_alloc_funcs afsBuffer;
@@ -87,66 +66,86 @@ yajl_alloc(const yajl_callbacks * callbacks,
/* copy in pointers to allocation routines */
memcpy((void *) &(hand->alloc), (void *) afs, sizeof(yajl_alloc_funcs));
- if (config != NULL) {
- allowComments = config->allowComments;
- validateUTF8 = config->checkUTF8;
- }
-
hand->callbacks = callbacks;
hand->ctx = ctx;
- hand->lexer = yajl_lex_alloc(&(hand->alloc), allowComments, validateUTF8);
+ hand->lexer = NULL;
hand->bytesConsumed = 0;
hand->decodeBuf = yajl_buf_alloc(&(hand->alloc));
+ hand->flags = 0;
yajl_bs_init(hand->stateStack, &(hand->alloc));
-
yajl_bs_push(hand->stateStack, yajl_state_start);
return hand;
}
-void
-yajl_reset_parser(yajl_handle hand) {
- hand->lexer = yajl_lex_realloc(hand->lexer);
+int
+yajl_config(yajl_handle h, yajl_option opt, ...)
+{
+ int rv = 1;
+ va_list ap;
+ va_start(ap, opt);
+
+ switch(opt) {
+ case yajl_allow_comments:
+ case yajl_dont_validate_strings:
+ case yajl_allow_trailing_garbage:
+ case yajl_allow_multiple_values:
+ case yajl_allow_partial_values:
+ if (va_arg(ap, int)) h->flags |= opt;
+ else h->flags &= ~opt;
+ break;
+ default:
+ rv = 0;
+ }
+ va_end(ap);
+
+ return rv;