2 * Copyright (c) 2015, Vsevolod Stakhov
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
13 * THIS SOFTWARE IS PROVIDED BY AUTHOR ''AS IS'' AND ANY
14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
15 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
16 * DISCLAIMED. IN NO EVENT SHALL AUTHOR BE LIABLE FOR ANY
17 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
18 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
19 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
20 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
21 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
22 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 #include "ucl_internal.h"
35 #elif defined(HAVE_SYS_ENDIAN_H)
36 #include <sys/endian.h>
37 #elif defined(HAVE_MACHINE_ENDIAN_H)
38 #include <machine/endian.h>
41 #if !defined(__LITTLE_ENDIAN__) && !defined(__BIG_ENDIAN__)
42 #if __BYTE_ORDER == __LITTLE_ENDIAN
43 #define __LITTLE_ENDIAN__
44 #elif __BYTE_ORDER == __BIG_ENDIAN
45 #define __BIG_ENDIAN__
47 #define __LITTLE_ENDIAN__
51 #define SWAP_LE_BE16(val) ((uint16_t) ( \
52 (uint16_t) ((uint16_t) (val) >> 8) | \
53 (uint16_t) ((uint16_t) (val) << 8)))
55 #if defined(__clang__) || (defined(__GNUC__) && __GNUC__ >= 4 && defined (__GNUC_MINOR__) && __GNUC_MINOR__ >= 3)
56 # define SWAP_LE_BE32(val) ((uint32_t)__builtin_bswap32 ((uint32_t)(val)))
57 # define SWAP_LE_BE64(val) ((uint64_t)__builtin_bswap64 ((uint64_t)(val)))
59 #define SWAP_LE_BE32(val) ((uint32_t)( \
60 (((uint32_t)(val) & (uint32_t)0x000000ffU) << 24) | \
61 (((uint32_t)(val) & (uint32_t)0x0000ff00U) << 8) | \
62 (((uint32_t)(val) & (uint32_t)0x00ff0000U) >> 8) | \
63 (((uint32_t)(val) & (uint32_t)0xff000000U) >> 24)))
65 #define SWAP_LE_BE64(val) ((uint64_t)( \
67 (uint64_t)(0x00000000000000ffULL)) << 56) | \
69 (uint64_t)(0x000000000000ff00ULL)) << 40) | \
71 (uint64_t)(0x0000000000ff0000ULL)) << 24) | \
73 (uint64_t) (0x00000000ff000000ULL)) << 8) | \
75 (uint64_t)(0x000000ff00000000ULL)) >> 8) | \
77 (uint64_t)(0x0000ff0000000000ULL)) >> 24) | \
79 (uint64_t)(0x00ff000000000000ULL)) >> 40) | \
81 (uint64_t)(0xff00000000000000ULL)) >> 56)))
84 #ifdef __LITTLE_ENDIAN__
85 #define TO_BE16 SWAP_LE_BE16
86 #define TO_BE32 SWAP_LE_BE32
87 #define TO_BE64 SWAP_LE_BE64
88 #define FROM_BE16 SWAP_LE_BE16
89 #define FROM_BE32 SWAP_LE_BE32
90 #define FROM_BE64 SWAP_LE_BE64
92 #define TO_BE16(val) (uint16_t)(val)
93 #define TO_BE32(val) (uint32_t)(val)
94 #define TO_BE64(val) (uint64_t)(val)
95 #define FROM_BE16(val) (uint16_t)(val)
96 #define FROM_BE32(val) (uint32_t)(val)
97 #define FROM_BE64(val) (uint64_t)(val)
101 ucl_emitter_print_int_msgpack (struct ucl_emitter_context *ctx, int64_t val)
103 const struct ucl_emitter_functions *func = ctx->func;
104 unsigned char buf[sizeof(uint64_t) + 1];
105 const unsigned char mask_positive = 0x7f, mask_negative = 0xe0,
106 uint8_ch = 0xcc, uint16_ch = 0xcd, uint32_ch = 0xce, uint64_ch = 0xcf,
107 int8_ch = 0xd0, int16_ch = 0xd1, int32_ch = 0xd2, int64_ch = 0xd3;
112 /* Fixed num 7 bits */
114 buf[0] = mask_positive & val;
116 else if (val <= UINT8_MAX) {
121 else if (val <= UINT16_MAX) {
122 uint16_t v = TO_BE16 (val);
126 memcpy (&buf[1], &v, sizeof (v));
128 else if (val <= UINT32_MAX) {
129 uint32_t v = TO_BE32 (val);
133 memcpy (&buf[1], &v, sizeof (v));
136 uint64_t v = TO_BE64 (val);
140 memcpy (&buf[1], &v, sizeof (v));
146 uval = ((val ^ (val >> 63)) - (val >> 63));
148 if (val > -(1 << 5)) {
150 buf[0] = (mask_negative | uval) & 0xff;
152 else if (uval <= INT8_MAX) {
153 uint8_t v = (uint8_t)val;
158 else if (uval <= INT16_MAX) {
159 uint16_t v = TO_BE16 (val);
163 memcpy (&buf[1], &v, sizeof (v));
165 else if (uval <= INT32_MAX) {
166 uint32_t v = TO_BE32 (val);
170 memcpy (&buf[1], &v, sizeof (v));
173 uint64_t v = TO_BE64 (val);
177 memcpy (&buf[1], &v, sizeof (v));
181 func->ucl_emitter_append_len (buf, len, func->ud);
185 ucl_emitter_print_double_msgpack (struct ucl_emitter_context *ctx, double val)
187 const struct ucl_emitter_functions *func = ctx->func;
192 const unsigned char dbl_ch = 0xcb;
193 unsigned char buf[sizeof(double) + 1];
195 /* Convert to big endian */
200 memcpy (&buf[1], &u.d, sizeof (double));
201 func->ucl_emitter_append_len (buf, sizeof (buf), func->ud);
205 ucl_emitter_print_bool_msgpack (struct ucl_emitter_context *ctx, bool val)
207 const struct ucl_emitter_functions *func = ctx->func;
208 const unsigned char true_ch = 0xc3, false_ch = 0xc2;
210 func->ucl_emitter_append_character (val ? true_ch : false_ch, 1, func->ud);
214 ucl_emitter_print_string_msgpack (struct ucl_emitter_context *ctx,
215 const char *s, size_t len)
217 const struct ucl_emitter_functions *func = ctx->func;
218 const unsigned char fix_mask = 0xA0, l8_ch = 0xd9, l16_ch = 0xda, l32_ch = 0xdb;
219 unsigned char buf[5];
224 buf[0] = (len | fix_mask) & 0xff;
226 else if (len <= 0xff) {
231 else if (len <= 0xffff) {
232 uint16_t bl = TO_BE16 (len);
236 memcpy (&buf[1], &bl, sizeof (bl));
239 uint32_t bl = TO_BE32 (len);
243 memcpy (&buf[1], &bl, sizeof (bl));
246 func->ucl_emitter_append_len (buf, blen, func->ud);
247 func->ucl_emitter_append_len (s, len, func->ud);
251 ucl_emitter_print_binary_string_msgpack (struct ucl_emitter_context *ctx,
252 const char *s, size_t len)
254 const struct ucl_emitter_functions *func = ctx->func;
255 const unsigned char l8_ch = 0xc4, l16_ch = 0xc5, l32_ch = 0xc6;
256 unsigned char buf[5];
264 else if (len <= 0xffff) {
265 uint16_t bl = TO_BE16 (len);
269 memcpy (&buf[1], &bl, sizeof (bl));
272 uint32_t bl = TO_BE32 (len);
276 memcpy (&buf[1], &bl, sizeof (bl));
279 func->ucl_emitter_append_len (buf, blen, func->ud);
280 func->ucl_emitter_append_len (s, len, func->ud);
284 ucl_emitter_print_null_msgpack (struct ucl_emitter_context *ctx)
286 const struct ucl_emitter_functions *func = ctx->func;
287 const unsigned char nil = 0xc0;
289 func->ucl_emitter_append_character (nil, 1, func->ud);
293 ucl_emitter_print_key_msgpack (bool print_key, struct ucl_emitter_context *ctx,
294 const ucl_object_t *obj)
297 ucl_emitter_print_string_msgpack (ctx, obj->key, obj->keylen);
302 ucl_emitter_print_array_msgpack (struct ucl_emitter_context *ctx, size_t len)
304 const struct ucl_emitter_functions *func = ctx->func;
305 const unsigned char fix_mask = 0x90, l16_ch = 0xdc, l32_ch = 0xdd;
306 unsigned char buf[5];
311 buf[0] = (len | fix_mask) & 0xff;
313 else if (len <= 0xffff) {
314 uint16_t bl = TO_BE16 (len);
318 memcpy (&buf[1], &bl, sizeof (bl));
321 uint32_t bl = TO_BE32 (len);
325 memcpy (&buf[1], &bl, sizeof (bl));
328 func->ucl_emitter_append_len (buf, blen, func->ud);
332 ucl_emitter_print_object_msgpack (struct ucl_emitter_context *ctx, size_t len)
334 const struct ucl_emitter_functions *func = ctx->func;
335 const unsigned char fix_mask = 0x80, l16_ch = 0xde, l32_ch = 0xdf;
336 unsigned char buf[5];
341 buf[0] = (len | fix_mask) & 0xff;
343 else if (len <= 0xffff) {
344 uint16_t bl = TO_BE16 (len);
348 memcpy (&buf[1], &bl, sizeof (bl));
351 uint32_t bl = TO_BE32 (len);
355 memcpy (&buf[1], &bl, sizeof (bl));
358 func->ucl_emitter_append_len (buf, blen, func->ud);
362 enum ucl_msgpack_format {
363 msgpack_positive_fixint = 0,
398 msgpack_negative_fixint,
402 typedef ssize_t (*ucl_msgpack_parse_function)(struct ucl_parser *parser,
403 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
404 const unsigned char *pos, size_t remain);
406 static ssize_t ucl_msgpack_parse_map (struct ucl_parser *parser,
407 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
408 const unsigned char *pos, size_t remain);
409 static ssize_t ucl_msgpack_parse_array (struct ucl_parser *parser,
410 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
411 const unsigned char *pos, size_t remain);
412 static ssize_t ucl_msgpack_parse_string (struct ucl_parser *parser,
413 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
414 const unsigned char *pos, size_t remain);
415 static ssize_t ucl_msgpack_parse_int (struct ucl_parser *parser,
416 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
417 const unsigned char *pos, size_t remain);
418 static ssize_t ucl_msgpack_parse_float (struct ucl_parser *parser,
419 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
420 const unsigned char *pos, size_t remain);
421 static ssize_t ucl_msgpack_parse_bool (struct ucl_parser *parser,
422 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
423 const unsigned char *pos, size_t remain);
424 static ssize_t ucl_msgpack_parse_null (struct ucl_parser *parser,
425 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
426 const unsigned char *pos, size_t remain);
427 static ssize_t ucl_msgpack_parse_ignore (struct ucl_parser *parser,
428 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
429 const unsigned char *pos, size_t remain);
431 #define MSGPACK_FLAG_FIXED (1 << 0)
432 #define MSGPACK_FLAG_CONTAINER (1 << 1)
433 #define MSGPACK_FLAG_TYPEVALUE (1 << 2)
434 #define MSGPACK_FLAG_EXT (1 << 3)
435 #define MSGPACK_FLAG_ASSOC (1 << 4)
436 #define MSGPACK_FLAG_KEY (1 << 5)
437 #define MSGPACK_CONTAINER_BIT (1ULL << 62)
440 * Search tree packed in array
442 struct ucl_msgpack_parser {
443 uint8_t prefix; /* Prefix byte */
444 uint8_t prefixlen; /* Length of prefix in bits */
445 uint8_t fmt; /* The desired format */
446 uint8_t len; /* Length of the object
448 or length of value in case
450 uint8_t flags; /* Flags of the specified type */
451 ucl_msgpack_parse_function func; /* Parser function */
458 MSGPACK_FLAG_FIXED|MSGPACK_FLAG_KEY,
459 ucl_msgpack_parse_string
464 msgpack_positive_fixint,
466 MSGPACK_FLAG_FIXED|MSGPACK_FLAG_TYPEVALUE,
467 ucl_msgpack_parse_int
472 msgpack_negative_fixint,
474 MSGPACK_FLAG_FIXED|MSGPACK_FLAG_TYPEVALUE,
475 ucl_msgpack_parse_int
482 MSGPACK_FLAG_FIXED|MSGPACK_FLAG_CONTAINER|MSGPACK_FLAG_ASSOC,
483 ucl_msgpack_parse_map
490 MSGPACK_FLAG_FIXED|MSGPACK_FLAG_CONTAINER,
491 ucl_msgpack_parse_array
499 ucl_msgpack_parse_string
507 ucl_msgpack_parse_string
515 ucl_msgpack_parse_int
523 ucl_msgpack_parse_int
531 ucl_msgpack_parse_int
539 ucl_msgpack_parse_int
547 ucl_msgpack_parse_float
555 ucl_msgpack_parse_float
562 MSGPACK_FLAG_FIXED | MSGPACK_FLAG_TYPEVALUE,
563 ucl_msgpack_parse_bool
570 MSGPACK_FLAG_FIXED | MSGPACK_FLAG_TYPEVALUE,
571 ucl_msgpack_parse_bool
579 ucl_msgpack_parse_int
587 ucl_msgpack_parse_int
595 ucl_msgpack_parse_int
603 ucl_msgpack_parse_int
610 MSGPACK_FLAG_FIXED | MSGPACK_FLAG_TYPEVALUE,
611 ucl_msgpack_parse_null
619 ucl_msgpack_parse_string
627 ucl_msgpack_parse_string
635 ucl_msgpack_parse_string
643 ucl_msgpack_parse_string
650 MSGPACK_FLAG_CONTAINER,
651 ucl_msgpack_parse_array
658 MSGPACK_FLAG_CONTAINER,
659 ucl_msgpack_parse_array
666 MSGPACK_FLAG_CONTAINER|MSGPACK_FLAG_ASSOC,
667 ucl_msgpack_parse_map
674 MSGPACK_FLAG_CONTAINER|MSGPACK_FLAG_ASSOC,
675 ucl_msgpack_parse_map
683 ucl_msgpack_parse_ignore
691 ucl_msgpack_parse_ignore
699 ucl_msgpack_parse_ignore
706 MSGPACK_FLAG_FIXED | MSGPACK_FLAG_EXT,
707 ucl_msgpack_parse_ignore
714 MSGPACK_FLAG_FIXED | MSGPACK_FLAG_EXT,
715 ucl_msgpack_parse_ignore
722 MSGPACK_FLAG_FIXED | MSGPACK_FLAG_EXT,
723 ucl_msgpack_parse_ignore
730 MSGPACK_FLAG_FIXED | MSGPACK_FLAG_EXT,
731 ucl_msgpack_parse_ignore
738 MSGPACK_FLAG_FIXED | MSGPACK_FLAG_EXT,
739 ucl_msgpack_parse_ignore
743 #undef MSGPACK_DEBUG_PARSER
745 static inline struct ucl_msgpack_parser *
746 ucl_msgpack_get_parser_from_type (unsigned char t)
748 unsigned int i, shift, mask;
750 for (i = 0; i < sizeof (parsers) / sizeof (parsers[0]); i ++) {
751 shift = CHAR_BIT - parsers[i].prefixlen;
752 mask = parsers[i].prefix >> shift;
754 if (mask == (((unsigned int)t) >> shift)) {
762 static inline struct ucl_stack *
763 ucl_msgpack_get_container (struct ucl_parser *parser,
764 struct ucl_msgpack_parser *obj_parser, uint64_t len)
766 struct ucl_stack *stack;
768 assert (obj_parser != NULL);
770 if (obj_parser->flags & MSGPACK_FLAG_CONTAINER) {
771 assert ((len & MSGPACK_CONTAINER_BIT) == 0);
773 * Insert new container to the stack
775 if (parser->stack == NULL) {
776 parser->stack = calloc (1, sizeof (struct ucl_stack));
778 if (parser->stack == NULL) {
779 ucl_create_err (&parser->err, "no memory");
784 stack = calloc (1, sizeof (struct ucl_stack));
787 ucl_create_err (&parser->err, "no memory");
791 stack->next = parser->stack;
792 parser->stack = stack;
795 parser->stack->level = len | MSGPACK_CONTAINER_BIT;
797 #ifdef MSGPACK_DEBUG_PARSER
798 stack = parser->stack;
800 fprintf(stderr, "+");
804 fprintf(stderr, "%s -> %d\n", obj_parser->flags & MSGPACK_FLAG_ASSOC ? "object" : "array", (int)len);
809 * Get the current stack top
812 return parser->stack;
815 ucl_create_err (&parser->err, "bad top level object for msgpack");
820 return parser->stack;
824 ucl_msgpack_is_container_finished (struct ucl_stack *container)
828 assert (container != NULL);
830 if (container->level & MSGPACK_CONTAINER_BIT) {
831 level = container->level & ~MSGPACK_CONTAINER_BIT;
842 ucl_msgpack_insert_object (struct ucl_parser *parser,
843 const unsigned char *key,
844 size_t keylen, ucl_object_t *obj)
847 struct ucl_stack *container;
849 container = parser->stack;
850 assert (container != NULL);
851 assert (container->level > 0);
852 assert (obj != NULL);
853 assert (container->obj != NULL);
855 if (container->obj->type == UCL_ARRAY) {
856 ucl_array_append (container->obj, obj);
858 else if (container->obj->type == UCL_OBJECT) {
859 if (key == NULL || keylen == 0) {
860 ucl_create_err (&parser->err, "cannot insert object with no key");
865 obj->keylen = keylen;
867 if (!(parser->flags & UCL_PARSER_ZEROCOPY)) {
868 ucl_copy_key_trash (obj);
871 ucl_parser_process_object_element (parser, obj);
874 ucl_create_err (&parser->err, "bad container type");
878 if (container->level & MSGPACK_CONTAINER_BIT) {
879 level = container->level & ~MSGPACK_CONTAINER_BIT;
880 container->level = (level - 1) | MSGPACK_CONTAINER_BIT;
886 static struct ucl_stack *
887 ucl_msgpack_get_next_container (struct ucl_parser *parser)
889 struct ucl_stack *cur = NULL;
898 if (cur->level & MSGPACK_CONTAINER_BIT) {
899 level = cur->level & ~MSGPACK_CONTAINER_BIT;
902 /* We need to switch to the previous container */
903 parser->stack = cur->next;
904 parser->cur_obj = cur->obj;
907 #ifdef MSGPACK_DEBUG_PARSER
910 fprintf(stderr, "-");
913 fprintf(stderr, "-%s -> %d\n", parser->cur_obj->type == UCL_OBJECT ? "object" : "array", (int)parser->cur_obj->len);
916 return ucl_msgpack_get_next_container (parser);
921 * For UCL containers we don't know length, so we just insert the whole
922 * message pack blob into the top level container
925 assert (cur->obj != NULL);
930 #define CONSUME_RET do { \
935 assert (remain >= 0); \
938 ucl_create_err (&parser->err, \
939 "cannot parse type %d of len %u", \
940 (int)obj_parser->fmt, \
946 #define GET_NEXT_STATE do { \
947 container = ucl_msgpack_get_next_container (parser); \
948 if (container == NULL) { \
949 ucl_create_err (&parser->err, \
950 "empty container"); \
953 next_state = container->obj->type == UCL_OBJECT ? \
954 read_assoc_key : read_array_value; \
958 ucl_msgpack_consume (struct ucl_parser *parser)
960 const unsigned char *p, *end, *key = NULL;
961 struct ucl_stack *container;
962 enum e_msgpack_parser_state {
972 } state = read_type, next_state = error_state;
973 struct ucl_msgpack_parser *obj_parser = NULL;
975 ssize_t ret, remain, keylen = 0;
976 #ifdef MSGPACK_DEBUG_PARSER
978 enum e_msgpack_parser_state hist[256];
981 p = parser->chunks->begin;
982 remain = parser->chunks->remain;
987 #ifdef MSGPACK_DEBUG_PARSER
988 hist[i++ % 256] = state;
992 obj_parser = ucl_msgpack_get_parser_from_type (*p);
994 if (obj_parser == NULL) {
995 ucl_create_err (&parser->err, "unknown msgpack format: %x",
1000 /* Now check length sanity */
1001 if (obj_parser->flags & MSGPACK_FLAG_FIXED) {
1002 if (obj_parser->len == 0) {
1003 /* We have an embedded size */
1004 len = *p & ~obj_parser->prefix;
1007 if (remain < obj_parser->len) {
1008 ucl_create_err (&parser->err, "not enough data remain to "
1009 "read object's length: %u remain, %u needed",
1010 (unsigned)remain, obj_parser->len);
1015 len = obj_parser->len;
1018 if (!(obj_parser->flags & MSGPACK_FLAG_TYPEVALUE)) {
1019 /* We must pass value as the second byte */
1026 /* Len is irrelevant now */
1031 /* Length is not embedded */
1032 if (remain < obj_parser->len) {
1033 ucl_create_err (&parser->err, "not enough data remain to "
1034 "read object's length: %u remain, %u needed",
1035 (unsigned)remain, obj_parser->len);
1043 switch (obj_parser->len) {
1048 len = FROM_BE16 (*(uint16_t *)p);
1051 len = FROM_BE32 (*(uint32_t *)p);
1054 len = FROM_BE64 (*(uint64_t *)p);
1061 p += obj_parser->len;
1062 remain -= obj_parser->len;
1065 if (obj_parser->flags & MSGPACK_FLAG_ASSOC) {
1066 /* We have just read the new associative map */
1067 state = start_assoc;
1069 else if (obj_parser->flags & MSGPACK_FLAG_CONTAINER){
1070 state = start_array;
1078 parser->cur_obj = ucl_object_new_full (UCL_OBJECT,
1079 parser->chunks->priority);
1080 /* Insert to the previous level container */
1081 if (parser->stack && !ucl_msgpack_insert_object (parser,
1082 key, keylen, parser->cur_obj)) {
1085 /* Get new container */
1086 container = ucl_msgpack_get_container (parser, obj_parser, len);
1088 if (container == NULL) {
1092 ret = obj_parser->func (parser, container, len, obj_parser->fmt,
1100 next_state = read_assoc_key;
1104 state = finish_assoc_value;
1109 parser->cur_obj = ucl_object_new_full (UCL_ARRAY,
1110 parser->chunks->priority);
1111 /* Insert to the previous level container */
1112 if (parser->stack && !ucl_msgpack_insert_object (parser,
1113 key, keylen, parser->cur_obj)) {
1116 /* Get new container */
1117 container = ucl_msgpack_get_container (parser, obj_parser, len);
1119 if (container == NULL) {
1123 ret = obj_parser->func (parser, container, len, obj_parser->fmt,
1129 next_state = read_array_value;
1133 state = finish_array_value;
1137 case read_array_value:
1139 * p is now at the value start, len now contains length read and
1140 * obj_parser contains the corresponding specific parser
1142 container = parser->stack;
1144 if (container == NULL) {
1148 ret = obj_parser->func (parser, container, len, obj_parser->fmt,
1153 /* Insert value to the container and check if we have finished array */
1154 if (!ucl_msgpack_insert_object (parser, NULL, 0,
1159 if (ucl_msgpack_is_container_finished (container)) {
1160 state = finish_array_value;
1163 /* Read more elements */
1165 next_state = read_array_value;
1170 case read_assoc_key:
1172 * Keys must have string type for ucl msgpack
1174 if (!(obj_parser->flags & MSGPACK_FLAG_KEY)) {
1175 ucl_create_err (&parser->err, "bad type for key: %u, expected "
1176 "string", (unsigned)obj_parser->fmt);
1184 if (keylen > remain || keylen == 0) {
1185 ucl_create_err (&parser->err, "too long or empty key");
1193 next_state = read_assoc_value;
1196 case read_assoc_value:
1198 * p is now at the value start, len now contains length read and
1199 * obj_parser contains the corresponding specific parser
1201 container = parser->stack;
1203 if (container == NULL) {
1207 ret = obj_parser->func (parser, container, len, obj_parser->fmt,
1211 assert (key != NULL && keylen > 0);
1213 if (!ucl_msgpack_insert_object (parser, key, keylen,
1221 if (ucl_msgpack_is_container_finished (container)) {
1222 state = finish_assoc_value;
1225 /* Read more elements */
1227 next_state = read_assoc_key;
1231 case finish_array_value:
1232 case finish_assoc_value:
1238 ucl_create_err (&parser->err, "invalid state machine state");
1244 /* Check the finishing state */
1248 /* Empty container at the end */
1250 ucl_create_err (&parser->err, "invalid non-empty container at the end");
1255 parser->cur_obj = ucl_object_new_full (
1256 state == start_array ? UCL_ARRAY : UCL_OBJECT,
1257 parser->chunks->priority);
1258 /* Insert to the previous level container */
1259 if (!ucl_msgpack_insert_object (parser,
1260 key, keylen, parser->cur_obj)) {
1263 /* Get new container */
1264 container = ucl_msgpack_get_container (parser, obj_parser, len);
1266 if (container == NULL) {
1270 ret = obj_parser->func (parser, container, len, obj_parser->fmt,
1274 case read_array_value:
1275 case read_assoc_value:
1277 ucl_create_err (&parser->err, "unfinished value at the end");
1282 container = parser->stack;
1284 if (container == NULL) {
1288 ret = obj_parser->func (parser, container, len, obj_parser->fmt,
1293 /* Insert value to the container and check if we have finished array */
1294 if (!ucl_msgpack_insert_object (parser, NULL, 0,
1299 case finish_array_value:
1300 case finish_assoc_value:
1302 /* Valid finishing state */
1305 /* Invalid finishing state */
1306 ucl_create_err (&parser->err, "invalid state machine finishing state: %d",
1312 /* Rewind to the top level container */
1313 ucl_msgpack_get_next_container (parser);
1314 assert (parser->stack == NULL ||
1315 (parser->stack->level & MSGPACK_CONTAINER_BIT) == 0);
1321 ucl_parse_msgpack (struct ucl_parser *parser)
1323 ucl_object_t *container = NULL;
1324 const unsigned char *p;
1327 assert (parser != NULL);
1328 assert (parser->chunks != NULL);
1329 assert (parser->chunks->begin != NULL);
1330 assert (parser->chunks->remain != 0);
1332 p = parser->chunks->begin;
1334 if (parser->stack) {
1335 container = parser->stack->obj;
1339 * When we start parsing message pack chunk, we must ensure that we
1340 * have either a valid container or the top object inside message pack is
1343 if (container == NULL) {
1344 if ((*p & 0x80) != 0x80 && !(*p >= 0xdc && *p <= 0xdf)) {
1345 ucl_create_err (&parser->err, "bad top level object for msgpack");
1350 ret = ucl_msgpack_consume (parser);
1352 if (ret && parser->top_obj == NULL) {
1353 parser->top_obj = parser->cur_obj;
1360 ucl_msgpack_parse_map (struct ucl_parser *parser,
1361 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
1362 const unsigned char *pos, size_t remain)
1364 container->obj = parser->cur_obj;
1370 ucl_msgpack_parse_array (struct ucl_parser *parser,
1371 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
1372 const unsigned char *pos, size_t remain)
1374 container->obj = parser->cur_obj;
1380 ucl_msgpack_parse_string (struct ucl_parser *parser,
1381 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
1382 const unsigned char *pos, size_t remain)
1390 obj = ucl_object_new_full (UCL_STRING, parser->chunks->priority);
1391 obj->value.sv = pos;
1394 if (fmt >= msgpack_bin8 && fmt <= msgpack_bin32) {
1395 obj->flags |= UCL_OBJECT_BINARY;
1398 if (!(parser->flags & UCL_PARSER_ZEROCOPY)) {
1399 if (obj->flags & UCL_OBJECT_BINARY) {
1400 obj->trash_stack[UCL_TRASH_VALUE] = malloc (len);
1402 if (obj->trash_stack[UCL_TRASH_VALUE] != NULL) {
1403 memcpy (obj->trash_stack[UCL_TRASH_VALUE], pos, len);
1407 ucl_copy_value_trash (obj);
1411 parser->cur_obj = obj;
1417 ucl_msgpack_parse_int (struct ucl_parser *parser,
1418 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
1419 const unsigned char *pos, size_t remain)
1435 obj = ucl_object_new_full (UCL_INT, parser->chunks->priority);
1438 case msgpack_positive_fixint:
1439 obj->value.iv = (*pos & 0x7f);
1442 case msgpack_negative_fixint:
1443 obj->value.iv = - (*pos & 0x1f);
1447 obj->value.iv = (unsigned char)*pos;
1451 memcpy (&iv8, pos, sizeof (iv8));
1452 obj->value.iv = iv8;
1456 memcpy (&iv16, pos, sizeof (iv16));
1457 iv16 = FROM_BE16 (iv16);
1458 obj->value.iv = iv16;
1461 case msgpack_uint16:
1462 memcpy (&uiv16, pos, sizeof (uiv16));
1463 uiv16 = FROM_BE16 (uiv16);
1464 obj->value.iv = uiv16;
1468 memcpy (&iv32, pos, sizeof (iv32));
1469 iv32 = FROM_BE32 (iv32);
1470 obj->value.iv = iv32;
1473 case msgpack_uint32:
1474 memcpy(&uiv32, pos, sizeof(uiv32));
1475 uiv32 = FROM_BE32(uiv32);
1476 obj->value.iv = uiv32;
1480 memcpy (&iv64, pos, sizeof (iv64));
1481 iv64 = FROM_BE64 (iv64);
1482 obj->value.iv = iv64;
1485 case msgpack_uint64:
1486 memcpy(&uiv64, pos, sizeof(uiv64));
1487 uiv64 = FROM_BE64(uiv64);
1488 obj->value.iv = uiv64;
1496 parser->cur_obj = obj;
1502 ucl_msgpack_parse_float (struct ucl_parser *parser,
1503 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
1504 const unsigned char *pos, size_t remain)
1517 obj = ucl_object_new_full (UCL_FLOAT, parser->chunks->priority);
1520 case msgpack_float32:
1521 memcpy(&d.i, pos, sizeof(d.i));
1522 d.i = FROM_BE32(d.i);
1523 /* XXX: can be slow */
1524 obj->value.dv = d.f;
1527 case msgpack_float64:
1528 memcpy(&uiv64, pos, sizeof(uiv64));
1529 uiv64 = FROM_BE64(uiv64);
1530 obj->value.iv = uiv64;
1538 parser->cur_obj = obj;
1544 ucl_msgpack_parse_bool (struct ucl_parser *parser,
1545 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
1546 const unsigned char *pos, size_t remain)
1554 obj = ucl_object_new_full (UCL_BOOLEAN, parser->chunks->priority);
1558 obj->value.iv = true;
1561 obj->value.iv = false;
1568 parser->cur_obj = obj;
1574 ucl_msgpack_parse_null (struct ucl_parser *parser,
1575 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
1576 const unsigned char *pos, size_t remain)
1584 obj = ucl_object_new_full (UCL_NULL, parser->chunks->priority);
1585 parser->cur_obj = obj;
1591 ucl_msgpack_parse_ignore (struct ucl_parser *parser,
1592 struct ucl_stack *container, size_t len, enum ucl_msgpack_format fmt,
1593 const unsigned char *pos, size_t remain)
1600 case msgpack_fixext1:
1603 case msgpack_fixext2:
1606 case msgpack_fixext4:
1609 case msgpack_fixext8:
1612 case msgpack_fixext16:
1621 ucl_create_err (&parser->err, "bad type: %x", (unsigned)fmt);