/**
 * @file json.c
 * @author Radek Krejci <rkrejci@cesnet.cz>
 * @brief Generic JSON format parser for libyang
 *
 * Copyright (c) 2020 CESNET, z.s.p.o.
 *
 * This source code is licensed under BSD 3-Clause License (the "License").
 * You may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     https://opensource.org/licenses/BSD-3-Clause
 */

#include <assert.h>
#include <ctype.h>
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>

#include "common.h"
#include "json.h"
#include "parser_internal.h"

#define JSON_PUSH_STATUS_RET(CTX, STATUS) \
    LY_CHECK_ERR_RET(ly_set_add(&CTX->status, (void*)STATUS, LY_SET_OPT_USEASLIST) == -1, LOGMEM(CTX->ctx), LY_EMEM)

#define JSON_POP_STATUS_RET(CTX) \
    assert(CTX->status.count); CTX->status.count--;

const char *
lyjson_token2str(enum LYJSON_PARSER_STATUS status)
{
    switch (status) {
    case LYJSON_ERROR:
        return "error";
    case LYJSON_ROOT:
        return "document root";
    case LYJSON_FALSE:
        return "false";
    case LYJSON_TRUE:
        return "true";
    case LYJSON_NULL:
        return "null";
    case LYJSON_OBJECT:
        return "object";
    case LYJSON_OBJECT_CLOSED:
        return "object closed";
    case LYJSON_OBJECT_EMPTY:
        return "empty object";
    case LYJSON_ARRAY:
        return "array";
    case LYJSON_ARRAY_CLOSED:
        return "array closed";
    case LYJSON_ARRAY_EMPTY:
        return "empty array";
    case LYJSON_NUMBER:
        return "number";
    case LYJSON_STRING:
        return "string";
    case LYJSON_END:
        return "end of input";
    }

    return "";
}

static LY_ERR
skip_ws(struct lyjson_ctx *jsonctx)
{
    /* skip leading whitespaces */
    while (*jsonctx->in->current != '\0' && is_jsonws(*jsonctx->in->current)) {
        if (*jsonctx->in->current == 0x0a) { /* new line */
            jsonctx->line++;
        }
        ly_in_skip(jsonctx->in, 1);
    }
    if (*jsonctx->in->current == '\0') {
        JSON_PUSH_STATUS_RET(jsonctx, LYJSON_END);
    }

    return LY_SUCCESS;
}

/*
 * @brief Set value corresponding to the current context's status
 */
static void
lyjson_ctx_set_value(struct lyjson_ctx *jsonctx, const char *value, size_t value_len, uint8_t dynamic)
{
    assert(jsonctx);

    if (dynamic) {
        free((char *)jsonctx->value);
    }
    jsonctx->value = value;
    jsonctx->value_len = value_len;
    jsonctx->dynamic = dynamic;
}

static LY_ERR
lyjson_check_next(struct lyjson_ctx *jsonctx)
{
    if (jsonctx->status.count == 1) {
        /* top level value (JSON-text), ws expected */
        if (*jsonctx->in->current == '\0' || is_jsonws(*jsonctx->in->current)) {
            return LY_SUCCESS;
        }
    } else if (lyjson_ctx_status(jsonctx, 1) == LYJSON_OBJECT) {
        LY_CHECK_RET(skip_ws(jsonctx));
        if (*jsonctx->in->current == ',' || *jsonctx->in->current == '}') {
            return LY_SUCCESS;
        }
    } else if (lyjson_ctx_status(jsonctx, 1) == LYJSON_ARRAY) {
        LY_CHECK_RET(skip_ws(jsonctx));
        if (*jsonctx->in->current == ',' || *jsonctx->in->current == ']') {
            return LY_SUCCESS;
        }
    } else {
        LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LYVE_SYNTAX,
               "Unexpected character \"%c\" after JSON %s.", *jsonctx->in->current, lyjson_token2str(lyjson_ctx_status(jsonctx, 0)));
    }

    return LY_EVALID;
}

/**
 * Input is expected to start after the opening quotation-mark.
 * When succeeds, input is moved after the closing quotation-mark.
 */
static LY_ERR
lyjson_string_(struct lyjson_ctx *jsonctx)
{
#define BUFSIZE 24
#define BUFSIZE_STEP 128

    const char *in = jsonctx->in->current, *start;
    char *buf = NULL;
    size_t offset;   /* read offset in input buffer */
    size_t len;      /* length of the output string (write offset in output buffer) */
    size_t size = 0; /* size of the output buffer */
    size_t u;
    uint64_t start_line;

    assert(jsonctx);

    /* init */
    start = in;
    start_line = jsonctx->line;
    offset = len = 0;

    /* parse */
    while (in[offset]) {
        if (in[offset] == '\\') {
            /* escape sequence */
            size_t slash = offset;
            uint32_t value;
            uint8_t i = 1;

            if (!buf) {
                /* prepare output buffer */
                buf = malloc(BUFSIZE);
                LY_CHECK_ERR_RET(!buf, LOGMEM(jsonctx->ctx), LY_EMEM);
                size = BUFSIZE;
            }

            /* allocate enough for the offset and next character,
             * we will need 4 bytes at most since we support only the predefined
             * (one-char) entities and character references */
            if (len + offset + 4 >= size) {
                buf = ly_realloc(buf, size + BUFSIZE_STEP);
                LY_CHECK_ERR_RET(!buf, LOGMEM(jsonctx->ctx), LY_EMEM);
                size += BUFSIZE_STEP;
            }

            if (offset) {
                /* store what we have so far */
                memcpy(&buf[len], in, offset);
                len += offset;
                in += offset;
                offset = 0;
            }

            switch (in[++offset]) {
            case '"':
                /* quotation mark */
                value = 0x22;
                break;
            case '\\':
                /* reverse solidus */
                value = 0x5c;
                break;
            case '/':
                /* solidus */
                value = 0x2f;
                break;
            case 'b':
                /* backspace */
                value = 0x08;
                break;
            case 'f':
                /* form feed */
                value = 0x0c;
                break;
            case 'n':
                /* line feed */
                value = 0x0a;
                break;
            case 'r':
                /* carriage return */
                value = 0x0d;
                break;
            case 't':
                /* tab */
                value = 0x09;
                break;
            case 'u':
                /* Basic Multilingual Plane character \uXXXX */
                offset++;
                for (value = i = 0; i < 4; i++) {
                    if (isdigit(in[offset + i])) {
                        u = (in[offset + i] - '0');
                    } else if (in[offset + i] > 'F') {
                        u = 10 + (in[offset + i] - 'a');
                    } else {
                        u = 10 + (in[offset + i] - 'A');
                    }
                    value = (16 * value) + u;
                }
                break;
            default:
                /* invalid escape sequence */
                LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LYVE_SYNTAX,
                       "Invalid character escape sequence \\%c.", in[offset]);
                goto error;

            }

            offset += i;   /* add read escaped characters */
            LY_CHECK_ERR_GOTO(ly_pututf8(&buf[len], value, &u),
                              LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LYVE_SYNTAX,
                                     "Invalid character reference \"%.*s\" (0x%08x).", offset - slash, &in[slash], value),
                              error);
            len += u;      /* update number of bytes in buffer */
            in += offset;  /* move the input by the processed bytes stored in the buffer ... */
            offset = 0;    /* ... and reset the offset index for future moving data into buffer */

        } else if (in[offset] == '"') {
            /* end of string */
            if (buf) {
                /* realloc exact size string */
                buf = ly_realloc(buf, len + offset + 1);
                LY_CHECK_ERR_RET(!buf, LOGMEM(jsonctx->ctx), LY_EMEM);
                size = len + offset + 1;
                memcpy(&buf[len], in, offset);

                /* set terminating NULL byte */
                buf[len + offset] = '\0';
            }
            len += offset;
            ++offset;
            in += offset;
            goto success;
        } else {
            /* get it as UTF-8 character for check */
            const char *c = &in[offset];
            uint32_t code = 0;
            size_t code_len = 0;

            LY_CHECK_ERR_GOTO(ly_getutf8(&c, &code, &code_len),
                              LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_INCHAR, in[offset]), error);

            LY_CHECK_ERR_GOTO(!is_jsonstrchar(code),
                              LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LYVE_SYNTAX,
                                     "Invalid character in JSON string \"%.*s\" (0x%08x).", &in[offset] - start + code_len, start, code),
                              error);

            /* character is ok, continue */
            offset += code_len;
        }
    }

    /* EOF reached before endchar */
    LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_EOF);
    LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &start_line, LYVE_SYNTAX, "Missing quotation-mark at the end of a JSON string.");

error:
    free(buf);
    return LY_EVALID;

success:
    ly_in_skip(jsonctx->in, in - jsonctx->in->current);
    if (buf) {
        lyjson_ctx_set_value(jsonctx, buf, len, 1);
    } else {
        lyjson_ctx_set_value(jsonctx, start, len, 0);
    }

    return LY_SUCCESS;

#undef BUFSIZE
#undef BUFSIZE_STEP
}

/*
 *
 * Wrapper around lyjson_string_() adding LYJSON_STRING status into context to allow using lyjson_string_() for parsing object's name.
 */
static LY_ERR
lyjson_string(struct lyjson_ctx *jsonctx)
{
    LY_CHECK_RET(lyjson_string_(jsonctx));

    JSON_PUSH_STATUS_RET(jsonctx, LYJSON_STRING);
    LY_CHECK_RET(lyjson_check_next(jsonctx));

    return LY_SUCCESS;
}

static LY_ERR
lyjson_number(struct lyjson_ctx *jsonctx)
{
    size_t offset = 0, exponent = 0;
    const char *in = jsonctx->in->current;
    uint8_t minus = 0;

    if (in[offset] == '-') {
        ++offset;
        minus = 1;
    }

    if (in[offset] == '0') {
        ++offset;
    } else if (isdigit(in[offset])) {
        ++offset;
        while (isdigit(in[offset])) {
            ++offset;
        }
    } else {
invalid_character:
        if (in[offset]) {
            LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LYVE_SYNTAX, "Invalid character in JSON Number value (\"%c\").", in[offset]);
        } else {
            LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_EOF);
        }
        return LY_EVALID;
    }

    if (in[offset] == '.') {
        ++offset;
        if (!isdigit(in[offset])) {
            goto invalid_character;
        }
        while (isdigit(in[offset])) {
            ++offset;
        }
    }

    if ((in[offset] == 'e') || (in[offset] == 'E')) {
        exponent = offset++;
        if ((in[offset] == '+') || (in[offset] == '-')) {
            ++offset;
        }
        if (!isdigit(in[offset])) {
            goto invalid_character;
        }
        while (isdigit(in[offset])) {
            ++offset;
        }
    }

    if (exponent) {
        /* convert JSON number with exponent into the representation used by YANG */
        long int  e_val;
        char *ptr, *dec_point, *num;
        const char *e_ptr = &in[exponent + 1];
        size_t num_len, i;
        int64_t dp_position; /* final position of the deciaml point */

        errno = 0;
        e_val = strtol(e_ptr, &ptr, 10);
        if (errno) {
            LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LYVE_SEMANTICS,
                   "Exponent out-of-bounds in a JSON Number value (%.*s).", offset - minus - (e_ptr - in), e_ptr);
            return LY_EVALID;
        }

        dec_point = ly_strnchr(in, '.', exponent);
        if (!dec_point) {
            /* value is integer, we are just ... */
            if (e_val >= 0) {
                /* adding zeros at the end */
                num_len = exponent + e_val;
                dp_position = num_len; /* decimal point is behind the actual value */
            } else if ((size_t)labs(e_val) < exponent) {
                /* adding decimal point between the integer's digits */
                num_len = exponent + 1;
                dp_position = exponent + e_val;
            } else {
                /* adding decimal point before the integer with adding leading zero(s) */
                num_len = labs(e_val) + 2;
                dp_position = exponent + e_val;
            }
            dp_position -= minus;
        } else {
            /* value is decimal, we are moving the decimal point */
            dp_position = dec_point - in + e_val - minus;
            if (dp_position > (ssize_t)exponent) {
                /* moving decimal point after the decimal value make the integer result */
                num_len = dp_position;
            } else if (dp_position < 0) {
                /* moving decimal point before the decimal value requires additional zero(s)
                 * (decimal point is already count in exponent value) */
                num_len = exponent + labs(dp_position) + 1;
            } else {
                /* moving decimal point just inside the decimal value does not make any change in length */
                num_len = exponent;
            }
        }

        /* allocate buffer for the result (add terminating NULL-byte */
        num = malloc(num_len + 1);
        LY_CHECK_ERR_RET(!num, LOGMEM(jsonctx->ctx), LY_EMEM);

        /* compose the resulting vlaue */
        i = 0;
        if (minus) {
            num[i++] = '-';
        }
        /* add leading zeros */
        if (dp_position <= 0) {
            num[i++] = '0';
            num[i++] = '.';
            for ( ; dp_position; dp_position++) {
                num[i++] = '0';
            }
        }
        /* copy the value */
        uint8_t dp_placed;
        size_t j;
        for (dp_placed = dp_position ? 0 : 1, j = minus; j < exponent; j++) {
            if (in[j] == '.') {
                continue;
            }
            if (!dp_placed) {
                if (!dp_position) {
                    num[i++] = '.';
                    dp_placed = 1;
                } else {
                    dp_position--;
                    if (in[j] == '0') {
                        num_len--;
                        continue;
                    }
                }
            }

            num[i++] = in[j];
        }
        /* trailing zeros */
        while (dp_position--) {
            num[i++] = '0';
        }
        /* terminating NULL byte */
        num[i] = '\0';

        /* store the modified number */
        lyjson_ctx_set_value(jsonctx, num, num_len, 1);
    } else {
        /* store the number */
        lyjson_ctx_set_value(jsonctx, jsonctx->in->current, offset, 0);
    }
    ly_in_skip(jsonctx->in, offset);

    JSON_PUSH_STATUS_RET(jsonctx, LYJSON_NUMBER);
    LY_CHECK_RET(lyjson_check_next(jsonctx));

    return LY_SUCCESS;
}

static LY_ERR
lyjson_object_name(struct lyjson_ctx *jsonctx)
{
    if (*jsonctx->in->current != '"') {
        LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_INSTREXP, LY_VCODE_INSTREXP_len(jsonctx->in->current),
               jsonctx->in->current, "a JSON object's member");
        return LY_EVALID;
    }
    ly_in_skip(jsonctx->in, 1);

    LY_CHECK_RET(lyjson_string_(jsonctx));
    LY_CHECK_RET(skip_ws(jsonctx));
    LY_CHECK_ERR_RET(
            *jsonctx->in->current != ':',
            LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_INSTREXP,
                   LY_VCODE_INSTREXP_len(jsonctx->in->current), jsonctx->in->current, "a JSON object's name-separator ':'"),
            LY_EVALID);
    ly_in_skip(jsonctx->in, 1);
    LY_CHECK_RET(skip_ws(jsonctx));

    return LY_SUCCESS;
}

static LY_ERR
lyjson_object(struct lyjson_ctx *jsonctx)
{
    LY_CHECK_RET(skip_ws(jsonctx));

    if (*jsonctx->in->current == '}') {
        /* empty object */
        ly_in_skip(jsonctx->in, 1);
        lyjson_ctx_set_value(jsonctx, NULL, 0, 0);
        JSON_PUSH_STATUS_RET(jsonctx, LYJSON_OBJECT_EMPTY);
        return LY_SUCCESS;
    }

    LY_CHECK_RET(lyjson_object_name(jsonctx));

    /* output data are set by lyjson_string_() */
    JSON_PUSH_STATUS_RET(jsonctx, LYJSON_OBJECT);

    return LY_SUCCESS;
}

/*
 * @brief Process JSON array envelope
 *
 *
 *
 * @param[in] jsonctx JSON parser context
 * @return LY_SUCCESS or LY_EMEM
 */
static LY_ERR
lyjson_array(struct lyjson_ctx *jsonctx)
{
    LY_CHECK_RET(skip_ws(jsonctx));

    if (*jsonctx->in->current == ']') {
        /* empty array */
        ly_in_skip(jsonctx->in, 1);
        JSON_PUSH_STATUS_RET(jsonctx, LYJSON_ARRAY_EMPTY);
    } else {
        JSON_PUSH_STATUS_RET(jsonctx, LYJSON_ARRAY);
    }

    /* erase previous values, array has no value on its own */
    lyjson_ctx_set_value(jsonctx, NULL, 0, 0);

    return LY_SUCCESS;
}

static LY_ERR
lyjson_value(struct lyjson_ctx *jsonctx)
{
    if (jsonctx->status.count && lyjson_ctx_status(jsonctx, 0) == LYJSON_END) {
        return LY_SUCCESS;
    }

    if (*jsonctx->in->current == 'f' && !strncmp(jsonctx->in->current, "false", 5)) {
        /* false */
        lyjson_ctx_set_value(jsonctx, jsonctx->in->current, 5, 0);
        ly_in_skip(jsonctx->in, 5);
        JSON_PUSH_STATUS_RET(jsonctx, LYJSON_FALSE);
        LY_CHECK_RET(lyjson_check_next(jsonctx));

    } else if (*jsonctx->in->current == 't' && !strncmp(jsonctx->in->current, "true", 4)) {
        /* true */
        lyjson_ctx_set_value(jsonctx, jsonctx->in->current, 4, 0);
        ly_in_skip(jsonctx->in, 4);
        JSON_PUSH_STATUS_RET(jsonctx, LYJSON_TRUE);
        LY_CHECK_RET(lyjson_check_next(jsonctx));

    } else if (*jsonctx->in->current == 'n' && !strncmp(jsonctx->in->current, "null", 4)) {
        /* none */
        lyjson_ctx_set_value(jsonctx, jsonctx->in->current, 0, 0);
        ly_in_skip(jsonctx->in, 4);
        JSON_PUSH_STATUS_RET(jsonctx, LYJSON_NULL);
        LY_CHECK_RET(lyjson_check_next(jsonctx));

    } else if (*jsonctx->in->current == '"') {
        /* string */
        ly_in_skip(jsonctx->in, 1);
        LY_CHECK_RET(lyjson_string(jsonctx));

    } else if (*jsonctx->in->current == '[') {
        /* array */
        ly_in_skip(jsonctx->in, 1);
        LY_CHECK_RET(lyjson_array(jsonctx));

    } else if (*jsonctx->in->current == '{') {
        /* object */
        ly_in_skip(jsonctx->in, 1);
        LY_CHECK_RET(lyjson_object(jsonctx));

    } else if (*jsonctx->in->current == '-' || (*jsonctx->in->current >= '0' && *jsonctx->in->current <= '9')) {
        /* number */
        LY_CHECK_RET(lyjson_number(jsonctx));

    } else {
        /* unexpected value */
        LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_INSTREXP, LY_VCODE_INSTREXP_len(jsonctx->in->current),
               jsonctx->in->current, "a JSON value");
        return LY_EVALID;
    }

    return LY_SUCCESS;
}

LY_ERR
lyjson_ctx_new(const struct ly_ctx *ctx, struct ly_in *in, struct lyjson_ctx **jsonctx_p)
{
    LY_ERR ret = LY_SUCCESS;
    struct lyjson_ctx *jsonctx;

    assert(ctx);
    assert(in);
    assert(jsonctx_p);

    /* new context */
    jsonctx = calloc(1, sizeof *jsonctx);
    LY_CHECK_ERR_RET(!jsonctx, LOGMEM(ctx), LY_EMEM);
    jsonctx->ctx = ctx;
    jsonctx->line = 1;
    jsonctx->in = in;

    /* parse JSON value, if any */
    LY_CHECK_GOTO(ret = skip_ws(jsonctx), cleanup);
    if (lyjson_ctx_status(jsonctx, 0) == LYJSON_END) {
        /* empty data input */
        goto cleanup;
    }

    ret = lyjson_value(jsonctx);

    if (jsonctx->status.count > 1 && lyjson_ctx_status(jsonctx, 0) == LYJSON_END) {
        LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_EOF);
        ret = LY_EVALID;
    }

cleanup:
    if (ret) {
        lyjson_ctx_free(jsonctx);
    } else {
        *jsonctx_p = jsonctx;
    }
    return ret;
}

void
lyjson_ctx_backup(struct lyjson_ctx *jsonctx)
{
    if (jsonctx->backup.dynamic) {
        free((char *)jsonctx->backup.value);
    }
    jsonctx->backup.status = lyjson_ctx_status(jsonctx, 0);
    jsonctx->backup.status_count = jsonctx->status.count;
    jsonctx->backup.value = jsonctx->value;
    jsonctx->backup.value_len = jsonctx->value_len;
    jsonctx->backup.input = jsonctx->in->current;
    jsonctx->backup.dynamic = jsonctx->dynamic;
    jsonctx->dynamic = 0;
}

void
lyjson_ctx_restore(struct lyjson_ctx *jsonctx)
{
    if (jsonctx->dynamic) {
        free((char *)jsonctx->value);
    }
    jsonctx->status.count = jsonctx->backup.status_count;
    jsonctx->status.objs[jsonctx->backup.status_count - 1] = (void *)jsonctx->backup.status;
    jsonctx->value = jsonctx->backup.value;
    jsonctx->value_len = jsonctx->backup.value_len;
    jsonctx->in->current = jsonctx->backup.input;
    jsonctx->dynamic = jsonctx->backup.dynamic;
    jsonctx->backup.dynamic = 0;
}

LY_ERR
lyjson_ctx_next(struct lyjson_ctx *jsonctx, enum LYJSON_PARSER_STATUS *status)
{
    LY_ERR ret = LY_SUCCESS;
    uint8_t toplevel = 0;
    enum LYJSON_PARSER_STATUS prev;

    assert(jsonctx);

    prev = lyjson_ctx_status(jsonctx, 0);

    if (prev == LYJSON_OBJECT || prev == LYJSON_ARRAY) {
        /* get value for the object's member OR the first value in the array */
        ret = lyjson_value(jsonctx);
        goto result;
    } else {
        /* the previous token is closed and should be completely processed */
        JSON_POP_STATUS_RET(jsonctx);
        prev = lyjson_ctx_status(jsonctx, 0);
    }

    if (!jsonctx->status.count) {
        /* we are done with the top level value */
        toplevel = 1;
    }
    LY_CHECK_RET(skip_ws(jsonctx));
    if (toplevel && !jsonctx->status.count) {
        /* EOF expected, but there are some data after the top level token */
        LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LYVE_SYNTAX,
               "Expecting end-of-input, but some data follows the top level JSON value.");
        return LY_EVALID;
    }

    if (toplevel) {
        /* we are done */
        return LY_SUCCESS;
    }

    /* continue with the next token */
    assert(prev == LYJSON_OBJECT || prev == LYJSON_ARRAY);

    if (*jsonctx->in->current == ',') {
        /* sibling item in the ... */
        ly_in_skip(jsonctx->in, 1);
        LY_CHECK_RET(skip_ws(jsonctx));

        if (prev == LYJSON_OBJECT) {
            /* ... object - get another object's member */
            ret = lyjson_object_name(jsonctx);
        } else { /* LYJSON_ARRAY */
            /* ... array - get another complete value */
            ret = lyjson_value(jsonctx);
        }
    } else if ((prev == LYJSON_OBJECT && *jsonctx->in->current == '}') || (prev == LYJSON_ARRAY && *jsonctx->in->current == ']')) {
        ly_in_skip(jsonctx->in, 1);
        JSON_POP_STATUS_RET(jsonctx);
        JSON_PUSH_STATUS_RET(jsonctx, prev + 1);
    } else {
        /* unexpected value */
        LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_INSTREXP, LY_VCODE_INSTREXP_len(jsonctx->in->current),
               jsonctx->in->current, prev == LYJSON_ARRAY ? "another JSON value in array" : "another JSON object's member");
        return LY_EVALID;
    }

result:
    if (ret == LY_SUCCESS && jsonctx->status.count > 1 && lyjson_ctx_status(jsonctx, 0) == LYJSON_END) {
        LOGVAL(jsonctx->ctx, LY_VLOG_LINE, &jsonctx->line, LY_VCODE_EOF);
        ret = LY_EVALID;
    }

    if (ret == LY_SUCCESS && status) {
        *status = lyjson_ctx_status(jsonctx, 0);
    }

    return ret;
}

enum LYJSON_PARSER_STATUS
lyjson_ctx_status(struct lyjson_ctx *jsonctx, uint32_t index)
{
    assert(jsonctx);

    if (jsonctx->status.count < index) {
        return LYJSON_ERROR;
    } else if (jsonctx->status.count == index) {
        return LYJSON_ROOT;
    } else {
        return (enum LYJSON_PARSER_STATUS)jsonctx->status.objs[jsonctx->status.count - (index + 1)];
    }
}

void
lyjson_ctx_free(struct lyjson_ctx *jsonctx)
{
    if (!jsonctx) {
        return;
    }

    if (jsonctx->dynamic) {
        free((char *)jsonctx->value);
    }
    if (jsonctx->backup.dynamic) {
        free((char *)jsonctx->backup.value);
    }

    ly_set_erase(&jsonctx->status, NULL);

    free(jsonctx);
}
