bug fix. The depth counter of the parser was incremented at the start of a value but never decremented
This commit is contained in:
+41
-32
@@ -1421,43 +1421,16 @@ static xj_value *parse_object(context_t *ctx)
|
|||||||
return xj_value_object__nocheck(head, count, ctx->alloc, ctx->error);
|
return xj_value_object__nocheck(head, count, ctx->alloc, ctx->error);
|
||||||
}
|
}
|
||||||
|
|
||||||
static xj_value *parse_value(context_t *ctx)
|
static xj_value *parse_bool_or_null(context_t *ctx)
|
||||||
{
|
{
|
||||||
if(ctx->i == ctx->len)
|
|
||||||
{
|
|
||||||
xj_report(ctx->error, "String ended where a value was expected");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
ctx->depth += 1;
|
|
||||||
if(ctx->depth == XJ_MAX_DEPTH)
|
|
||||||
{
|
|
||||||
xj_preport(ctx->error, ctx->str, ctx->i, "Maximum depth reached");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
assert(!isspace(ctx->str[ctx->i]));
|
|
||||||
|
|
||||||
char c = ctx->str[ctx->i];
|
|
||||||
|
|
||||||
if(c == '"')
|
|
||||||
return parse_string(ctx, 0);
|
|
||||||
|
|
||||||
if(isdigit(c) || c == '-')
|
|
||||||
return parse_number(ctx);
|
|
||||||
|
|
||||||
if(c == '[')
|
|
||||||
return parse_array(ctx);
|
|
||||||
|
|
||||||
if(c == '{')
|
|
||||||
return parse_object(ctx);
|
|
||||||
|
|
||||||
static const char kword_null [] = "null";
|
static const char kword_null [] = "null";
|
||||||
static const char kword_true [] = "true";
|
static const char kword_true [] = "true";
|
||||||
static const char kword_false[] = "false";
|
static const char kword_false[] = "false";
|
||||||
const char *kword;
|
const char *kword;
|
||||||
int kwlen;
|
int kwlen;
|
||||||
|
|
||||||
|
char c = ctx->str[ctx->i];
|
||||||
|
|
||||||
if(c == 'n')
|
if(c == 'n')
|
||||||
{
|
{
|
||||||
kword = kword_null;
|
kword = kword_null;
|
||||||
@@ -1497,17 +1470,53 @@ static xj_value *parse_value(context_t *ctx)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
{
|
// Get to the character that made the comparison fail
|
||||||
int p = 0;
|
int p = 0;
|
||||||
while(kword[p] == ctx->str[ctx->i+p])
|
while(kword[p] == ctx->str[ctx->i+p])
|
||||||
p += 1;
|
p += 1;
|
||||||
ctx->i += p;
|
ctx->i += p;
|
||||||
|
|
||||||
|
xj_preport(ctx->error, ctx->str, ctx->i,
|
||||||
|
"Bad character '%c'", ctx->str[ctx->i]);
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
xj_preport(ctx->error, ctx->str, ctx->i, "Bad character '%c'", ctx->str[ctx->i]);
|
static xj_value *parse_value(context_t *ctx)
|
||||||
|
{
|
||||||
|
if(ctx->i == ctx->len)
|
||||||
|
{
|
||||||
|
xj_report(ctx->error, "String ended where a value was expected");
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(ctx->depth+1 == XJ_MAX_DEPTH)
|
||||||
|
{
|
||||||
|
xj_preport(ctx->error, ctx->str, ctx->i, "Maximum depth reached");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
ctx->depth += 1;
|
||||||
|
|
||||||
|
assert(!isspace(ctx->str[ctx->i]));
|
||||||
|
|
||||||
|
xj_value *res;
|
||||||
|
|
||||||
|
char c = ctx->str[ctx->i];
|
||||||
|
|
||||||
|
if(c == '"')
|
||||||
|
res = parse_string(ctx, 0);
|
||||||
|
else if(isdigit(c) || c == '-')
|
||||||
|
res = parse_number(ctx);
|
||||||
|
else if(c == '[')
|
||||||
|
res = parse_array(ctx);
|
||||||
|
else if(c == '{')
|
||||||
|
res = parse_object(ctx);
|
||||||
|
else
|
||||||
|
res = parse_bool_or_null(ctx);
|
||||||
|
|
||||||
|
ctx->depth -= 1;
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
/* Symbol:
|
/* Symbol:
|
||||||
* xj_decode
|
* xj_decode
|
||||||
*
|
*
|
||||||
|
|||||||
Reference in New Issue
Block a user