mirror of
https://github.com/warmcat/libwebsockets.git
synced 2025-03-30 00:00:16 +01:00
lejp: object indexes
This adds an optional feature LEJP_FLAG_FEAT_OBJECT_INDEXES that changes lejp to treat { } items as indexable in ctx->i[] / ctx->ipos, since they also can take commas. This may break existing uses so it requires the default-off feature flag to enable it. The flags context field is zeroed by lejp_construct(), so any flags should be set on ctx->flags after alling that. There's also a flag LEJP_FLAG_LATEST available as an alias to enable any desirable but not-backwards-compatible behaviour, including this. Add the info to the README and adapt the unit test to do it both with and without the FEAT_OBJECT_INDEXES flag.
This commit is contained in:
parent
9734cadf11
commit
c935df1e7e
4 changed files with 188 additions and 60 deletions
|
@ -24,6 +24,21 @@ The features are:
|
||||||
- collates utf-8 text payloads into a 250-byte chunk buffer in the json parser
|
- collates utf-8 text payloads into a 250-byte chunk buffer in the json parser
|
||||||
context object for ease of access
|
context object for ease of access
|
||||||
|
|
||||||
|
## LEJP Context initialization
|
||||||
|
|
||||||
|
lejp doesn't allocate at all, you define a `struct lejp_ctx` usually on the
|
||||||
|
stack somewhere, and call `lejp_construct()` to initialize it.
|
||||||
|
|
||||||
|
To minimize surprises as lejp evolves, there is now a `flags` member of the
|
||||||
|
ctx, which defaults to zero for compatibility with older versions. After
|
||||||
|
the `lejp_construct()` call, you can set `ctx.flags` to indicate you want
|
||||||
|
newer options
|
||||||
|
|
||||||
|
|lejp flags|Meaning|
|
||||||
|
|---|---|
|
||||||
|
|LEJP_FLAG_FEAT_OBJECT_INDEXES|Provide indexes for { x, y, x } lists same as for arrays|
|
||||||
|
|LEJP_FLAG_LATEST|Alias indicating you want the "best" current options, even if incompatible with old behaviours|
|
||||||
|
|
||||||
## Type handling
|
## Type handling
|
||||||
|
|
||||||
LEJP leaves all numbers in text form, they are signalled in different callbacks
|
LEJP leaves all numbers in text form, they are signalled in different callbacks
|
||||||
|
@ -87,6 +102,20 @@ or the match index from your path array starting from 1 for the first entry.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## Details of object and array indexes
|
||||||
|
|
||||||
|
LEJP maintains a "stack" of index counters, each element represents one level
|
||||||
|
in the current hierarchy that may have a list or array of objects in it.
|
||||||
|
The amount of levels currently is held in `ctx->ipos`, and `ctx->i[]` holds
|
||||||
|
`uint16_t` index counts for each level.
|
||||||
|
|
||||||
|
By querying these, you can understand at which element index in a hierarchy of
|
||||||
|
arrays in the JSON you are at, unambiguously.
|
||||||
|
|
||||||
|
By default that is done for each `[]` array level, if you set `ctx.flags` with
|
||||||
|
`LEJP_FLAG_FEAT_OBJECT_INDEXES` option, it is also done for each `{}` object
|
||||||
|
level, which can also take comma-separated lists that need index tracking.
|
||||||
|
|
||||||
## Comparison with LECP (CBOR parser)
|
## Comparison with LECP (CBOR parser)
|
||||||
|
|
||||||
LECP is based on the same principles as LEJP and shares most of the callbacks.
|
LECP is based on the same principles as LEJP and shares most of the callbacks.
|
||||||
|
|
|
@ -245,6 +245,10 @@ struct lejp_ctx {
|
||||||
/* short */
|
/* short */
|
||||||
|
|
||||||
uint16_t uni;
|
uint16_t uni;
|
||||||
|
#define LEJP_FLAG_FEAT_OBJECT_INDEXES (1 << 0)
|
||||||
|
#define LEJP_FLAG_LATEST \
|
||||||
|
(LEJP_FLAG_FEAT_OBJECT_INDEXES)
|
||||||
|
uint16_t flags;
|
||||||
|
|
||||||
/* char */
|
/* char */
|
||||||
|
|
||||||
|
|
|
@ -82,6 +82,7 @@ lejp_construct(struct lejp_ctx *ctx,
|
||||||
ctx->path[0] = '\0';
|
ctx->path[0] = '\0';
|
||||||
ctx->user = user;
|
ctx->user = user;
|
||||||
ctx->line = 1;
|
ctx->line = 1;
|
||||||
|
ctx->flags = 0; /* user may set after construction */
|
||||||
|
|
||||||
ctx->pst_sp = 0;
|
ctx->pst_sp = 0;
|
||||||
ctx->pst[0].callback = callback;
|
ctx->pst[0].callback = callback;
|
||||||
|
@ -287,6 +288,17 @@ lejp_parse(struct lejp_ctx *ctx, const unsigned char *json, int len)
|
||||||
ret = LEJP_REJECT_IDLE_NO_BRACE;
|
ret = LEJP_REJECT_IDLE_NO_BRACE;
|
||||||
goto reject;
|
goto reject;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (ctx->flags & LEJP_FLAG_FEAT_OBJECT_INDEXES) {
|
||||||
|
/* since insides of {} can have ',', we should
|
||||||
|
* add an index level so we can count them
|
||||||
|
*/
|
||||||
|
ctx->i[ctx->ipos++] = 0;
|
||||||
|
if (ctx->ipos > LWS_ARRAY_SIZE(ctx->i)) {
|
||||||
|
ret = LEJP_REJECT_MP_DELIM_ISTACK;
|
||||||
|
goto reject;
|
||||||
|
}
|
||||||
|
}
|
||||||
if (ctx->pst[ctx->pst_sp].callback(ctx,
|
if (ctx->pst[ctx->pst_sp].callback(ctx,
|
||||||
LEJPCB_OBJECT_START))
|
LEJPCB_OBJECT_START))
|
||||||
goto reject_callback;
|
goto reject_callback;
|
||||||
|
@ -458,6 +470,16 @@ lejp_parse(struct lejp_ctx *ctx, const unsigned char *json, int len)
|
||||||
ctx->st[ctx->sp].s = LEJP_MP_COMMA_OR_END;
|
ctx->st[ctx->sp].s = LEJP_MP_COMMA_OR_END;
|
||||||
c = LEJP_MEMBERS;
|
c = LEJP_MEMBERS;
|
||||||
lejp_check_path_match(ctx);
|
lejp_check_path_match(ctx);
|
||||||
|
if (ctx->flags & LEJP_FLAG_FEAT_OBJECT_INDEXES) {
|
||||||
|
/* since insides of {} can have ',', we should
|
||||||
|
* add an index level so we can count them
|
||||||
|
*/
|
||||||
|
ctx->i[ctx->ipos++] = 0;
|
||||||
|
if (ctx->ipos > LWS_ARRAY_SIZE(ctx->i)) {
|
||||||
|
ret = LEJP_REJECT_MP_DELIM_ISTACK;
|
||||||
|
goto reject;
|
||||||
|
}
|
||||||
|
}
|
||||||
if (ctx->pst[ctx->pst_sp].callback(ctx,
|
if (ctx->pst[ctx->pst_sp].callback(ctx,
|
||||||
LEJPCB_OBJECT_START))
|
LEJPCB_OBJECT_START))
|
||||||
goto reject_callback;
|
goto reject_callback;
|
||||||
|
@ -499,7 +521,9 @@ lejp_parse(struct lejp_ctx *ctx, const unsigned char *json, int len)
|
||||||
ctx->pst[ctx->pst_sp].ppos = (unsigned char)
|
ctx->pst[ctx->pst_sp].ppos = (unsigned char)
|
||||||
ctx->st[ctx->sp - 1].p;
|
ctx->st[ctx->sp - 1].p;
|
||||||
ctx->ipos = (unsigned char)ctx->st[ctx->sp - 1].i;
|
ctx->ipos = (unsigned char)ctx->st[ctx->sp - 1].i;
|
||||||
}
|
} else
|
||||||
|
if (ctx->flags & LEJP_FLAG_FEAT_OBJECT_INDEXES)
|
||||||
|
ctx->ipos--;
|
||||||
ctx->path[ctx->pst[ctx->pst_sp].ppos] = '\0';
|
ctx->path[ctx->pst[ctx->pst_sp].ppos] = '\0';
|
||||||
if (ctx->path_match &&
|
if (ctx->path_match &&
|
||||||
ctx->pst[ctx->pst_sp].ppos <= ctx->path_match_len)
|
ctx->pst[ctx->pst_sp].ppos <= ctx->path_match_len)
|
||||||
|
@ -643,6 +667,11 @@ lejp_parse(struct lejp_ctx *ctx, const unsigned char *json, int len)
|
||||||
if (c == ',') {
|
if (c == ',') {
|
||||||
/* increment this stack level's index */
|
/* increment this stack level's index */
|
||||||
ctx->st[ctx->sp].s = LEJP_M_P;
|
ctx->st[ctx->sp].s = LEJP_M_P;
|
||||||
|
|
||||||
|
if (ctx->flags & LEJP_FLAG_FEAT_OBJECT_INDEXES)
|
||||||
|
if (ctx->ipos)
|
||||||
|
ctx->i[ctx->ipos - 1]++;
|
||||||
|
|
||||||
if (!ctx->sp) {
|
if (!ctx->sp) {
|
||||||
ctx->pst[ctx->pst_sp].ppos = 0;
|
ctx->pst[ctx->pst_sp].ppos = 0;
|
||||||
/*
|
/*
|
||||||
|
@ -662,11 +691,15 @@ lejp_parse(struct lejp_ctx *ctx, const unsigned char *json, int len)
|
||||||
*/
|
*/
|
||||||
ctx->path_match = 0;
|
ctx->path_match = 0;
|
||||||
|
|
||||||
|
lejp_check_path_match(ctx);
|
||||||
|
|
||||||
if (ctx->st[ctx->sp - 1].s != LEJP_MP_ARRAY_END)
|
if (ctx->st[ctx->sp - 1].s != LEJP_MP_ARRAY_END)
|
||||||
break;
|
break;
|
||||||
/* top level is definitely an array... */
|
/* top level is definitely an array... */
|
||||||
if (ctx->ipos)
|
if (!(ctx->flags & LEJP_FLAG_FEAT_OBJECT_INDEXES))
|
||||||
ctx->i[ctx->ipos - 1]++;
|
if (ctx->ipos)
|
||||||
|
ctx->i[ctx->ipos - 1]++;
|
||||||
|
|
||||||
ctx->st[ctx->sp].s = LEJP_MP_VALUE;
|
ctx->st[ctx->sp].s = LEJP_MP_VALUE;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -687,7 +720,10 @@ lejp_parse(struct lejp_ctx *ctx, const unsigned char *json, int len)
|
||||||
ctx->pst[ctx->pst_sp].ppos = (unsigned char)
|
ctx->pst[ctx->pst_sp].ppos = (unsigned char)
|
||||||
ctx->st[ctx->sp - 1].p;
|
ctx->st[ctx->sp - 1].p;
|
||||||
ctx->ipos = (unsigned char)ctx->st[ctx->sp - 1].i;
|
ctx->ipos = (unsigned char)ctx->st[ctx->sp - 1].i;
|
||||||
}
|
} else
|
||||||
|
if (ctx->flags & LEJP_FLAG_FEAT_OBJECT_INDEXES)
|
||||||
|
ctx->ipos--;
|
||||||
|
|
||||||
ctx->path[ctx->pst[ctx->pst_sp].ppos] = '\0';
|
ctx->path[ctx->pst[ctx->pst_sp].ppos] = '\0';
|
||||||
if (ctx->path_match &&
|
if (ctx->path_match &&
|
||||||
ctx->pst[ctx->pst_sp].ppos <= ctx->path_match_len)
|
ctx->pst[ctx->pst_sp].ppos <= ctx->path_match_len)
|
||||||
|
@ -731,8 +767,11 @@ pop_level:
|
||||||
if (ctx->sp) {
|
if (ctx->sp) {
|
||||||
ctx->pst[ctx->pst_sp].ppos = (unsigned char)ctx->st[ctx->sp].p;
|
ctx->pst[ctx->pst_sp].ppos = (unsigned char)ctx->st[ctx->sp].p;
|
||||||
ctx->ipos = (unsigned char)ctx->st[ctx->sp].i;
|
ctx->ipos = (unsigned char)ctx->st[ctx->sp].i;
|
||||||
}
|
} else
|
||||||
|
if (ctx->flags & LEJP_FLAG_FEAT_OBJECT_INDEXES)
|
||||||
|
ctx->ipos--;
|
||||||
ctx->path[ctx->pst[ctx->pst_sp].ppos] = '\0';
|
ctx->path[ctx->pst[ctx->pst_sp].ppos] = '\0';
|
||||||
|
|
||||||
if (ctx->path_match &&
|
if (ctx->path_match &&
|
||||||
ctx->pst[ctx->pst_sp].ppos <= ctx->path_match_len)
|
ctx->pst[ctx->pst_sp].ppos <= ctx->path_match_len)
|
||||||
/*
|
/*
|
||||||
|
@ -761,13 +800,14 @@ array_end:
|
||||||
ctx->pst[ctx->pst_sp].ppos = (unsigned char)
|
ctx->pst[ctx->pst_sp].ppos = (unsigned char)
|
||||||
ctx->st[ctx->sp - 1].p;
|
ctx->st[ctx->sp - 1].p;
|
||||||
ctx->path[ctx->pst[ctx->pst_sp].ppos] = '\0';
|
ctx->path[ctx->pst[ctx->pst_sp].ppos] = '\0';
|
||||||
|
lejp_check_path_match(ctx);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if (c != ']') {
|
if (c != ']') {
|
||||||
ret = LEJP_REJECT_MP_ARRAY_END_MISSING;
|
ret = LEJP_REJECT_MP_ARRAY_END_MISSING;
|
||||||
goto reject;
|
goto reject;
|
||||||
}
|
}
|
||||||
|
lejp_check_path_match(ctx);
|
||||||
ctx->st[ctx->sp].s = LEJP_MP_COMMA_OR_END;
|
ctx->st[ctx->sp].s = LEJP_MP_COMMA_OR_END;
|
||||||
ctx->pst[ctx->pst_sp].callback(ctx, LEJPCB_ARRAY_END);
|
ctx->pst[ctx->pst_sp].callback(ctx, LEJPCB_ARRAY_END);
|
||||||
if (defer) {
|
if (defer) {
|
||||||
|
|
|
@ -132,6 +132,11 @@ static const char * const json_tests[] = {
|
||||||
"{" /* test 11: array of arrays */
|
"{" /* test 11: array of arrays */
|
||||||
"\"array1\": [[\"a\", \"b\", \"b1\"], [\"c\", \"d\", \"d1\"]],"
|
"\"array1\": [[\"a\", \"b\", \"b1\"], [\"c\", \"d\", \"d1\"]],"
|
||||||
"\"array2\": [[\"e\", \"f\", \"f1\"], [\"g\", \"h\", \"h1\"]]"
|
"\"array2\": [[\"e\", \"f\", \"f1\"], [\"g\", \"h\", \"h1\"]]"
|
||||||
|
"}",
|
||||||
|
|
||||||
|
"{" /* test 12: test 11 but done with LEJP_FLAG_FEAT_OBJECT_INDEXES */
|
||||||
|
"\"array1\": [[\"a\", \"b\", \"b1\"], [\"c\", \"d\", \"d1\"]],"
|
||||||
|
"\"array2\": [[\"e\", \"f\", \"f1\"], [\"g\", \"h\", \"h1\"]]"
|
||||||
"}"
|
"}"
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -350,69 +355,118 @@ struct lejp_results {
|
||||||
{ 2, 0, 0, { 0 }, "", "123" },
|
{ 2, 0, 0, { 0 }, "", "123" },
|
||||||
{ 16, 0, 0, { 0 }, "", "123" },
|
{ 16, 0, 0, { 0 }, "", "123" },
|
||||||
{ 5, 0, 0, { 0 }, "array1", "123" },
|
{ 5, 0, 0, { 0 }, "array1", "123" },
|
||||||
{ 14, 0, 0, { 0 }, "array1[]", "123" },
|
{ 14, 0, 2, { 0 }, "array1[]", "123" },
|
||||||
{ 14, 1, 0, { 0, }, "array1[][]", "123" },
|
{ 14, 1, 1, { 0, }, "array1[][]", "123" },
|
||||||
{ 11, 2, 0, { 0, 0, }, "array1[][]", "" },
|
{ 11, 2, 1, { 0, 0, }, "array1[][]", "" },
|
||||||
{ 77, 2, 0, { 0, 0, }, "array1[][]", "a" },
|
{ 77, 2, 1, { 0, 0, }, "array1[][]", "a" },
|
||||||
{ 11, 2, 0, { 0, 1, }, "array1[][]", "" },
|
{ 11, 2, 1, { 0, 1, }, "array1[][]", "" },
|
||||||
{ 77, 2, 0, { 0, 1, }, "array1[][]", "b" },
|
{ 77, 2, 1, { 0, 1, }, "array1[][]", "b" },
|
||||||
{ 11, 2, 0, { 0, 2, }, "array1[][]", "" },
|
{ 11, 2, 1, { 0, 2, }, "array1[][]", "" },
|
||||||
{ 77, 2, 0, { 0, 2, }, "array1[][]", "b1" },
|
{ 77, 2, 1, { 0, 2, }, "array1[][]", "b1" },
|
||||||
{ 15, 1, 0, { 0, }, "array1[]", "b1" },
|
{ 15, 1, 2, { 0, }, "array1[]", "b1" },
|
||||||
{ 14, 1, 0, { 1, }, "array1[][]", "b1" },
|
{ 14, 1, 1, { 1, }, "array1[][]", "b1" },
|
||||||
{ 11, 2, 0, { 1, 0, }, "array1[][]", "" },
|
{ 11, 2, 1, { 1, 0, }, "array1[][]", "" },
|
||||||
{ 77, 2, 0, { 1, 0, }, "array1[][]", "c" },
|
{ 77, 2, 1, { 1, 0, }, "array1[][]", "c" },
|
||||||
{ 11, 2, 0, { 1, 1, }, "array1[][]", "" },
|
{ 11, 2, 1, { 1, 1, }, "array1[][]", "" },
|
||||||
{ 77, 2, 0, { 1, 1, }, "array1[][]", "d" },
|
{ 77, 2, 1, { 1, 1, }, "array1[][]", "d" },
|
||||||
{ 11, 2, 0, { 1, 2, }, "array1[][]", "" },
|
{ 11, 2, 1, { 1, 2, }, "array1[][]", "" },
|
||||||
{ 77, 2, 0, { 1, 2, }, "array1[][]", "d1" },
|
{ 77, 2, 1, { 1, 2, }, "array1[][]", "d1" },
|
||||||
{ 15, 1, 0, { 1, }, "array1[]", "d1" },
|
{ 15, 1, 2, { 1, }, "array1[]", "d1" },
|
||||||
{ 15, 1, 0, { 1, }, "array1[]", "d1" },
|
{ 15, 1, 2, { 1, }, "array1[]", "d1" },
|
||||||
{ 5, 1, 0, { 1, }, "array2", "d1" },
|
{ 5, 1, 0, { 1, }, "array2", "d1" },
|
||||||
{ 14, 1, 0, { 1, }, "array2[]", "d1" },
|
{ 14, 1, 2, { 1, }, "array2[]", "d1" },
|
||||||
{ 14, 2, 0, { 1, 0, }, "array2[][]", "d1" },
|
{ 14, 2, 1, { 1, 0, }, "array2[][]", "d1" },
|
||||||
{ 11, 3, 0, { 1, 0, 0, }, "array2[][]", "" },
|
{ 11, 3, 1, { 1, 0, 0, }, "array2[][]", "" },
|
||||||
{ 77, 3, 0, { 1, 0, 0, }, "array2[][]", "e" },
|
{ 77, 3, 1, { 1, 0, 0, }, "array2[][]", "e" },
|
||||||
{ 11, 3, 0, { 1, 0, 1, }, "array2[][]", "" },
|
{ 11, 3, 1, { 1, 0, 1, }, "array2[][]", "" },
|
||||||
{ 77, 3, 0, { 1, 0, 1, }, "array2[][]", "f" },
|
{ 77, 3, 1, { 1, 0, 1, }, "array2[][]", "f" },
|
||||||
{ 11, 3, 0, { 1, 0, 2, }, "array2[][]", "" },
|
{ 11, 3, 1, { 1, 0, 2, }, "array2[][]", "" },
|
||||||
{ 77, 3, 0, { 1, 0, 2, }, "array2[][]", "f1" },
|
{ 77, 3, 1, { 1, 0, 2, }, "array2[][]", "f1" },
|
||||||
{ 15, 2, 0, { 1, 0, }, "array2[]", "f1" },
|
{ 15, 2, 2, { 1, 0, }, "array2[]", "f1" },
|
||||||
{ 14, 2, 0, { 1, 1, }, "array2[][]", "f1" },
|
{ 14, 2, 1, { 1, 1, }, "array2[][]", "f1" },
|
||||||
{ 11, 3, 0, { 1, 1, 0, }, "array2[][]", "" },
|
{ 11, 3, 1, { 1, 1, 0, }, "array2[][]", "" },
|
||||||
{ 77, 3, 0, { 1, 1, 0, }, "array2[][]", "g" },
|
{ 77, 3, 1, { 1, 1, 0, }, "array2[][]", "g" },
|
||||||
{ 11, 3, 0, { 1, 1, 1, }, "array2[][]", "" },
|
{ 11, 3, 1, { 1, 1, 1, }, "array2[][]", "" },
|
||||||
{ 77, 3, 0, { 1, 1, 1, }, "array2[][]", "h" },
|
{ 77, 3, 1, { 1, 1, 1, }, "array2[][]", "h" },
|
||||||
{ 11, 3, 0, { 1, 1, 2, }, "array2[][]", "" },
|
{ 11, 3, 1, { 1, 1, 2, }, "array2[][]", "" },
|
||||||
{ 77, 3, 0, { 1, 1, 2, }, "array2[][]", "h1" },
|
{ 77, 3, 1, { 1, 1, 2, }, "array2[][]", "h1" },
|
||||||
{ 15, 2, 0, { 1, 1, }, "array2[]", "h1" },
|
{ 15, 2, 2, { 1, 1, }, "array2[]", "h1" },
|
||||||
{ 15, 2, 0, { 1, 1, }, "array2[]", "h1" },
|
{ 15, 2, 2, { 1, 1, }, "array2[]", "h1" },
|
||||||
{ 17, 2, 0, { 1, 1, }, "array2[]", "h1" },
|
{ 17, 2, 0, { 1, 1, }, "array2[]", "h1" },
|
||||||
{ 3, 2, 0, { 1, 1, }, "array2[]", "h1" },
|
{ 3, 2, 0, { 1, 1, }, "array2[]", "h1" },
|
||||||
|
}, r12[] = { /* test 11 but done with LEJP_FLAG_FEAT_OBJECT_INDEXES */
|
||||||
|
{ 0, 0, 0, { 0 }, "", "h1" },
|
||||||
|
{ 2, 0, 0, { 0 }, "", "h1" },
|
||||||
|
{ 16, 1, 0, { 0, }, "", "h1" },
|
||||||
|
{ 5, 1, 0, { 0, }, "array1", "h1" },
|
||||||
|
{ 14, 1, 2, { 0, }, "array1[]", "h1" },
|
||||||
|
{ 14, 2, 1, { 0, 0, }, "array1[][]", "h1" },
|
||||||
|
{ 11, 3, 1, { 0, 0, 0, }, "array1[][]", "" },
|
||||||
|
{ 77, 3, 1, { 0, 0, 0, }, "array1[][]", "a" },
|
||||||
|
{ 11, 3, 1, { 0, 0, 1, }, "array1[][]", "" },
|
||||||
|
{ 77, 3, 1, { 0, 0, 1, }, "array1[][]", "b" },
|
||||||
|
{ 11, 3, 1, { 0, 0, 2, }, "array1[][]", "" },
|
||||||
|
{ 77, 3, 1, { 0, 0, 2, }, "array1[][]", "b1" },
|
||||||
|
{ 15, 2, 2, { 0, 0, }, "array1[]", "b1" },
|
||||||
|
{ 14, 2, 1, { 0, 1, }, "array1[][]", "b1" },
|
||||||
|
{ 11, 3, 1, { 0, 1, 0, }, "array1[][]", "" },
|
||||||
|
{ 77, 3, 1, { 0, 1, 0, }, "array1[][]", "c" },
|
||||||
|
{ 11, 3, 1, { 0, 1, 1, }, "array1[][]", "" },
|
||||||
|
{ 77, 3, 1, { 0, 1, 1, }, "array1[][]", "d" },
|
||||||
|
{ 11, 3, 1, { 0, 1, 2, }, "array1[][]", "" },
|
||||||
|
{ 77, 3, 1, { 0, 1, 2, }, "array1[][]", "d1" },
|
||||||
|
{ 15, 2, 2, { 0, 1, }, "array1[]", "d1" },
|
||||||
|
{ 15, 1, 2, { 0, 1, }, "array1[]", "d1" },
|
||||||
|
{ 5, 1, 0, { 1, }, "array2", "d1" },
|
||||||
|
{ 14, 1, 2, { 1, }, "array2[]", "d1" },
|
||||||
|
{ 14, 2, 1, { 1, 0, }, "array2[][]", "d1" },
|
||||||
|
{ 11, 3, 1, { 1, 0, 0, }, "array2[][]", "" },
|
||||||
|
{ 77, 3, 1, { 1, 0, 0, }, "array2[][]", "e" },
|
||||||
|
{ 11, 3, 1, { 1, 0, 1, }, "array2[][]", "" },
|
||||||
|
{ 77, 3, 1, { 1, 0, 1, }, "array2[][]", "f" },
|
||||||
|
{ 11, 3, 1, { 1, 0, 2, }, "array2[][]", "" },
|
||||||
|
{ 77, 3, 1, { 1, 0, 2, }, "array2[][]", "f1" },
|
||||||
|
{ 15, 2, 2, { 1, 0, }, "array2[]", "f1" },
|
||||||
|
{ 14, 2, 1, { 1, 1, }, "array2[][]", "f1" },
|
||||||
|
{ 11, 3, 1, { 1, 1, 0, }, "array2[][]", "" },
|
||||||
|
{ 77, 3, 1, { 1, 1, 0, }, "array2[][]", "g" },
|
||||||
|
{ 11, 3, 1, { 1, 1, 1, }, "array2[][]", "" },
|
||||||
|
{ 77, 3, 1, { 1, 1, 1, }, "array2[][]", "h" },
|
||||||
|
{ 11, 3, 1, { 1, 1, 2, }, "array2[][]", "" },
|
||||||
|
{ 77, 3, 1, { 1, 1, 2, }, "array2[][]", "h1" },
|
||||||
|
{ 15, 2, 2, { 1, 1, }, "array2[]", "h1" },
|
||||||
|
{ 15, 1, 2, { 1, }, "array2[]", "h1" },
|
||||||
|
{ 17, 1, 0, { 1, }, "array2[]", "h1" },
|
||||||
|
{ 3, 1, 0, { 1, }, "array2[]", "h1" },
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static const char * const tok[] = {
|
||||||
|
"something",
|
||||||
|
}, * const tok_test11[] = { /* matches for test 11, 12 */
|
||||||
|
"*[][]",
|
||||||
|
"*[]",
|
||||||
|
};
|
||||||
|
|
||||||
struct lejp_results_pkg {
|
struct lejp_results_pkg {
|
||||||
const struct lejp_results *r;
|
const struct lejp_results *r;
|
||||||
size_t len;
|
size_t len;
|
||||||
|
const char * const *tokens;
|
||||||
|
size_t tokens_len;
|
||||||
|
uint16_t ctx_flags;
|
||||||
} rpkg[] = {
|
} rpkg[] = {
|
||||||
{ r1, LWS_ARRAY_SIZE(r1) },
|
{ r1, LWS_ARRAY_SIZE(r1), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r2, LWS_ARRAY_SIZE(r2) },
|
{ r2, LWS_ARRAY_SIZE(r2), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r3, LWS_ARRAY_SIZE(r3) },
|
{ r3, LWS_ARRAY_SIZE(r3), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r4, LWS_ARRAY_SIZE(r4) },
|
{ r4, LWS_ARRAY_SIZE(r4), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r5, LWS_ARRAY_SIZE(r5) },
|
{ r5, LWS_ARRAY_SIZE(r5), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r6, LWS_ARRAY_SIZE(r6) },
|
{ r6, LWS_ARRAY_SIZE(r6), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r7, LWS_ARRAY_SIZE(r7) },
|
{ r7, LWS_ARRAY_SIZE(r7), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r8, LWS_ARRAY_SIZE(r8) },
|
{ r8, LWS_ARRAY_SIZE(r8), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r9, LWS_ARRAY_SIZE(r9) },
|
{ r9, LWS_ARRAY_SIZE(r9), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r10, LWS_ARRAY_SIZE(r10) },
|
{ r10, LWS_ARRAY_SIZE(r10), tok, LWS_ARRAY_SIZE(tok), 0 },
|
||||||
{ r11, LWS_ARRAY_SIZE(r11) },
|
{ r11, LWS_ARRAY_SIZE(r11), tok_test11, LWS_ARRAY_SIZE(tok_test11), 0 },
|
||||||
};
|
{ r12, LWS_ARRAY_SIZE(r12), tok_test11, LWS_ARRAY_SIZE(tok_test11),
|
||||||
|
LEJP_FLAG_FEAT_OBJECT_INDEXES },
|
||||||
|
|
||||||
static const char * const tok[] = {
|
|
||||||
"something",
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -491,7 +545,8 @@ int main(int argc, const char **argv)
|
||||||
lwsl_user("%s: ++++++++++++++++ test %d\n", __func__, m + 1);
|
lwsl_user("%s: ++++++++++++++++ test %d\n", __func__, m + 1);
|
||||||
step = 0;
|
step = 0;
|
||||||
|
|
||||||
lejp_construct(&ctx, test_cb, NULL, tok, LWS_ARRAY_SIZE(tok));
|
lejp_construct(&ctx, test_cb, NULL, rpkg[m].tokens, (uint8_t)rpkg[m].tokens_len);
|
||||||
|
ctx.flags = rpkg[m].ctx_flags;
|
||||||
|
|
||||||
lwsl_hexdump_info(json_tests[m], strlen(json_tests[m]));
|
lwsl_hexdump_info(json_tests[m], strlen(json_tests[m]));
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue