# HG changeset patch # User Roger Pau Monne <roger.pau@entel.upc.edu> # Date 1324374796 -3600 # Node ID f4ff3ce53fd2286def61e22222154e3c0a408667 # Parent f72b99fccfca694674259cc1c03c526a827b67ec libxl: add support for yajl 2.x This patch adds support for yajl versions 2.x, while retaining 1.x compatibility. This patch adds quite a lot of #ifdefs all over the json code, so I''m open to suggestions if there''s a better way to handle this. Tested with yajl 2.0.3 and 1.0.12. Signed-off-by: Roger Pau Monne <roger.pau@entel.upc.edu> diff -r f72b99fccfca -r f4ff3ce53fd2 tools/check/check_yajl_devel --- a/tools/check/check_yajl_devel Tue Dec 20 08:31:40 2011 +0100 +++ b/tools/check/check_yajl_devel Tue Dec 20 10:53:16 2011 +0100 @@ -5,4 +5,5 @@ has_header yajl/yajl_parse.h || fail "can''t find yajl/yajl_parse.h" has_header yajl/yajl_gen.h || fail "can''t find yajl/yajl_gen.h" +has_header yajl/yajl_version.h || fail "can''t find yajl/yajl_version.h" has_lib libyajl.so || fail "can''t find libyajl.so" diff -r f72b99fccfca -r f4ff3ce53fd2 tools/check/check_yajl_lib --- a/tools/check/check_yajl_lib Tue Dec 20 08:31:40 2011 +0100 +++ b/tools/check/check_yajl_lib Tue Dec 20 10:53:16 2011 +0100 @@ -3,4 +3,4 @@ . ./funcs.sh -has_lib libyajl.so.1 || fail "can''t find libyajl.so.1 version 1" +has_lib libyajl.so.1 || has_lib libyajl.so.2 || fail "can''t find libyajl.so.1 version 1 or libyajl.so.2 version 2" diff -r f72b99fccfca -r f4ff3ce53fd2 tools/libxl/libxl_json.c --- a/tools/libxl/libxl_json.c Tue Dec 20 08:31:40 2011 +0100 +++ b/tools/libxl/libxl_json.c Tue Dec 20 10:53:16 2011 +0100 @@ -519,7 +519,11 @@ static bool is_decimal(const char *s, un return false; } +#ifdef HAVE_YAJL_V2 +static int json_callback_number(void *opaque, const char *s, size_t len) +#else static int json_callback_number(void *opaque, const char *s, unsigned int len) +#endif { libxl__yajl_ctx *ctx = opaque; libxl__json_object *obj = NULL; @@ -575,8 +579,13 @@ out: return 1; } +#ifdef HAVE_YAJL_V2 +static int json_callback_string(void *opaque, const unsigned char *str, + size_t len) +#else static int json_callback_string(void *opaque, const unsigned char *str, unsigned int len) +#endif { libxl__yajl_ctx *ctx = opaque; char *t = NULL; @@ -608,8 +617,13 @@ static int json_callback_string(void *op return 1; } +#ifdef HAVE_YAJL_V2 +static int json_callback_map_key(void *opaque, const unsigned char *str, + size_t len) +#else static int json_callback_map_key(void *opaque, const unsigned char *str, unsigned int len) +#endif { libxl__yajl_ctx *ctx = opaque; char *t = NULL; @@ -772,17 +786,26 @@ libxl__json_object *libxl__json_parse(li DEBUG_GEN_ALLOC(&yajl_ctx); if (yajl_ctx.hand == NULL) { +#ifdef HAVE_YAJL_V2 + yajl_ctx.hand = yajl_alloc(&callbacks, NULL, &yajl_ctx); +#else yajl_parser_config cfg = { .allowComments = 1, .checkUTF8 = 1, }; yajl_ctx.hand = yajl_alloc(&callbacks, &cfg, NULL, &yajl_ctx); +#endif } status = yajl_parse(yajl_ctx.hand, (const unsigned char *)s, strlen(s)); if (status != yajl_status_ok) goto out; + +#ifdef HAVE_YAJL_V2 + status = yajl_complete_parse(yajl_ctx.hand); +#else + status = yajl_parse_complete(yajl_ctx.hand); +#endif - status = yajl_parse_complete(yajl_ctx.hand); if (status != yajl_status_ok) goto out; @@ -834,14 +857,25 @@ static const char *yajl_gen_status_to_st char *libxl__object_to_json(libxl_ctx *ctx, const char *type, libxl__gen_json_callback gen, void *p) { +#ifndef HAVE_YAJL_V2 yajl_gen_config conf = { 1, " " }; +#endif const unsigned char *buf; char *ret = NULL; +#ifdef HAVE_YAJL_V2 + size_t len = 0; +#else unsigned int len = 0; +#endif yajl_gen_status s; yajl_gen hand; +#ifdef HAVE_YAJL_V2 + hand = yajl_gen_alloc(NULL); +#else hand = yajl_gen_alloc(&conf, NULL); +#endif + if (!hand) return NULL; diff -r f72b99fccfca -r f4ff3ce53fd2 tools/libxl/libxl_json.h --- a/tools/libxl/libxl_json.h Tue Dec 20 08:31:40 2011 +0100 +++ b/tools/libxl/libxl_json.h Tue Dec 20 10:53:16 2011 +0100 @@ -16,8 +16,14 @@ #define LIBXL_JSON_H #include <yajl/yajl_gen.h> +#include <yajl/yajl_version.h> #include <_libxl_types_json.h> #include <_libxl_types_internal_json.h> +/* YAJL version check */ +#if defined(YAJL_MAJOR) && (YAJL_MAJOR > 1) +# define HAVE_YAJL_V2 1 +#endif + #endif /* LIBXL_JSON_H */ diff -r f72b99fccfca -r f4ff3ce53fd2 tools/libxl/libxl_qmp.c --- a/tools/libxl/libxl_qmp.c Tue Dec 20 08:31:40 2011 +0100 +++ b/tools/libxl/libxl_qmp.c Tue Dec 20 10:53:16 2011 +0100 @@ -453,15 +453,26 @@ static char *qmp_send_prepare(libxl__gc qmp_callback_t callback, void *opaque, qmp_request_context *context) { +#ifndef HAVE_YAJL_V2 yajl_gen_config conf = { 0, NULL }; +#endif const unsigned char *buf = NULL; char *ret = NULL; +#ifdef HAVE_YAJL_V2 + size_t len = 0; +#else unsigned int len = 0; +#endif yajl_gen_status s; yajl_gen hand; callback_id_pair *elm = NULL; +#ifdef HAVE_YAJL_V2 + hand = yajl_gen_alloc(NULL); +#else hand = yajl_gen_alloc(&conf, NULL); +#endif + if (!hand) { return NULL; }
On Tue, 2011-12-20 at 09:53 +0000, Roger Pau Monne wrote:> iff -r f72b99fccfca -r f4ff3ce53fd2 tools/check/check_yajl_lib > --- a/tools/check/check_yajl_lib Tue Dec 20 08:31:40 2011 +0100 > +++ b/tools/check/check_yajl_lib Tue Dec 20 10:53:16 2011 +0100 > @@ -3,4 +3,4 @@ > > . ./funcs.sh > > -has_lib libyajl.so.1 || fail "can''t find libyajl.so.1 version 1" > +has_lib libyajl.so.1 || has_lib libyajl.so.2 || fail "can''t find > libyajl.so.1 version 1 or libyajl.so.2 version 2"The purpose of specifically checking for .so.1 was to avoid trying to use v2. Since you''ve fixed this you can just make it check for libyajl.so.> diff -r f72b99fccfca -r f4ff3ce53fd2 tools/libxl/libxl_json.h > --- a/tools/libxl/libxl_json.h Tue Dec 20 08:31:40 2011 +0100 > +++ b/tools/libxl/libxl_json.h Tue Dec 20 10:53:16 2011 +0100 > @@ -16,8 +16,14 @@ > #define LIBXL_JSON_H > > #include <yajl/yajl_gen.h> > +#include <yajl/yajl_version.h>Sadly this isn''t in the version of libyajl in Debian Stable which is 1.0.8-1. :-( Ian.
2011/12/22 Ian Campbell <Ian.Campbell@citrix.com>:> On Tue, 2011-12-20 at 09:53 +0000, Roger Pau Monne wrote: >> iff -r f72b99fccfca -r f4ff3ce53fd2 tools/check/check_yajl_lib >> --- a/tools/check/check_yajl_lib Tue Dec 20 08:31:40 2011 +0100 >> +++ b/tools/check/check_yajl_lib Tue Dec 20 10:53:16 2011 +0100 >> @@ -3,4 +3,4 @@ >> >> . ./funcs.sh >> >> -has_lib libyajl.so.1 || fail "can't find libyajl.so.1 version 1" >> +has_lib libyajl.so.1 || has_lib libyajl.so.2 || fail "can't find >> libyajl.so.1 version 1 or libyajl.so.2 version 2" > > The purpose of specifically checking for .so.1 was to avoid trying to > use v2. Since you've fixed this you can just make it check for > libyajl.so. > > >> diff -r f72b99fccfca -r f4ff3ce53fd2 tools/libxl/libxl_json.h >> --- a/tools/libxl/libxl_json.h Tue Dec 20 08:31:40 2011 +0100 >> +++ b/tools/libxl/libxl_json.h Tue Dec 20 10:53:16 2011 +0100 >> @@ -16,8 +16,14 @@ >> #define LIBXL_JSON_H >> >> #include <yajl/yajl_gen.h> >> +#include <yajl/yajl_version.h> > > Sadly this isn't in the version of libyajl in Debian Stable which is > 1.0.8-1. :-(This is what I was afraid of, older versions of yajl doesn't have yajl_version.h. So now I will have to check if yajl_version.h is present to include it. Will try to put an updated patch today. _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Roger Pau Monne writes ("[Xen-devel] [PATCH] libxl: add support for yajl 2.x"):> This patch adds support for yajl versions 2.x, while retaining 1.x > compatibility. This patch adds quite a lot of #ifdefs all over the > json code, so I''m open to suggestions if there''s a better way to > handle this.I have some suggestions. The basic idea would be to try to put all of the ifdefs in one place in libxl_json.h.> +#ifdef HAVE_YAJL_V2 > +static int json_callback_number(void *opaque, const char *s, size_t len) > +#else > static int json_callback_number(void *opaque, const char *s, unsigned int len) > +#endifSo how about: /* libxl_json.h */ #ifdef HAVE_YAJL_V2 typedef size_t libxl_yajl_length; ... #else typedef unsigned int libxl_yajl_length; ... #endif /* libxl_json.c */ static int json_callback_number(void *opaque, const char *s, libxl_yajl_length len) { ...> +#ifdef HAVE_YAJL_V2 > + yajl_ctx.hand = yajl_alloc(&callbacks, NULL, &yajl_ctx); > +#else > yajl_parser_config cfg = { > .allowComments = 1, > .checkUTF8 = 1, > }; > yajl_ctx.hand = yajl_alloc(&callbacks, &cfg, NULL, &yajl_ctx); > +#endif...> status = yajl_parse(yajl_ctx.hand, (const unsigned char *)s, strlen(s)); > if (status != yajl_status_ok) > goto out; > +/* libxl_json.h */ #ifdef HAVE_YAJL_V2 ... static inline int libxl_yajl_alloc(...) { return yajl_alloc .... } ... #else ... static inline int libxl_yajl_alloc(...) { [version with cfg] } #define yajl_complete_parse yajl_parse_complete ... #endif etc. Ian.
2012/1/3 Ian Jackson <Ian.Jackson@eu.citrix.com>:> Roger Pau Monne writes ("[Xen-devel] [PATCH] libxl: add support for yajl 2.x"): >> This patch adds support for yajl versions 2.x, while retaining 1.x >> compatibility. This patch adds quite a lot of #ifdefs all over the >> json code, so I'm open to suggestions if there's a better way to >> handle this. > > I have some suggestions. The basic idea would be to try to put all of > the ifdefs in one place in libxl_json.h. > >> +#ifdef HAVE_YAJL_V2 >> +static int json_callback_number(void *opaque, const char *s, size_t len) >> +#else >> static int json_callback_number(void *opaque, const char *s, unsigned int len) >> +#endif > > So how about: > > /* libxl_json.h */ > > #ifdef HAVE_YAJL_V2 > typedef size_t libxl_yajl_length; > ... > #else > typedef unsigned int libxl_yajl_length; > ... > #endif > > > /* libxl_json.c */ > > static int json_callback_number(void *opaque, const char *s, > libxl_yajl_length len) { > ... > >> +#ifdef HAVE_YAJL_V2 >> + yajl_ctx.hand = yajl_alloc(&callbacks, NULL, &yajl_ctx); >> +#else >> yajl_parser_config cfg = { >> .allowComments = 1, >> .checkUTF8 = 1, >> }; >> yajl_ctx.hand = yajl_alloc(&callbacks, &cfg, NULL, &yajl_ctx); >> +#endif > ... >> status = yajl_parse(yajl_ctx.hand, (const unsigned char *)s, strlen(s)); >> if (status != yajl_status_ok) >> goto out; >> + > > /* libxl_json.h */ > > #ifdef HAVE_YAJL_V2 > ... > static inline int libxl_yajl_alloc(...) { return yajl_alloc .... } > ... > #else > ... > static inline int libxl_yajl_alloc(...) { [version with cfg] } > #define yajl_complete_parse yajl_parse_complete > ... > #endif > > etc.I haven't really though of this anymore, but this seems much more appropriate and less intrusive. _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel