Add a full native JSON parser to Kore.

Mostly compliant, ignores \uXXXX in strings for now.

New API functions:

void kore_json_init(struct kore_json *json, const u_int8_t *data, size_t len);
  - Prepares JSON data for parsing.

int kore_json_parse(struct kore_json *json)
  - Parses the JSON data prepared via kore_json_init. Returns KORE_RESULT_ERROR
    if parsing failed or KORE_RESULT_OK if it succeeded.

struct kore_json_item *kore_json_get(struct kore_json *json, const char *path,
                                     int type);
  - Try to find the object matching a given search patch and type.

  eg, given a JSON structure of:
    {
      "reasons": {
        "strings": [
          "first reason",
          "second"
        ]
      }
    }

  one can obtain the second element in the reasons.strings array via:

    item = kore_json_get(json, "reasons/strings[0]", KORE_JSON_TYPE_STRING);

  Returns NULL if the item was not found or a type mismatch was hit,
  otherwise will return the item of that type.

  The kore_json_item data structure has a data member that contains the
  relevant bits depending on the type:

    KORE_JSON_TYPE_ARRAY, KORE_JSON_TYPE_OBJECT:
      the data.items member is valid.

    KORE_JSON_TYPE_STRING:
      the data.string member is valid.

    KORE_JSON_TYPE_NUMBER:
      the data.number member is valid.

    KORE_JSON_TYPE_LITERAL:
      the data.literal member is valid.

void kore_json_cleanup(struct kore_json *json);
  - Cleanup any resources

const char *kore_json_strerror(struct kore_json *json);
  - Return pointer to human readable error string.
This commit is contained in:
Joris Vink 2019-10-20 23:22:11 +02:00
parent 7da7141c21
commit 06fa452c96
2 changed files with 79 additions and 2 deletions

View File

@ -15,8 +15,8 @@ PLATFORM=platform.h
VERSION=src/version.c
S_SRC= src/kore.c src/buf.c src/config.c src/connection.c \
src/domain.c src/filemap.c src/fileref.c src/mem.c src/msg.c \
src/module.c src/net.c src/pool.c src/runtime.c src/timer.c \
src/domain.c src/filemap.c src/fileref.c src/json.c src/mem.c \
src/msg.c src/module.c src/net.c src/pool.c src/runtime.c src/timer.c \
src/utils.c src/worker.c src/keymgr.c $(VERSION)
FEATURES=

View File

@ -464,6 +464,76 @@ struct kore_buf {
size_t offset;
};
#define KORE_JSON_TYPE_OBJECT 1
#define KORE_JSON_TYPE_ARRAY 2
#define KORE_JSON_TYPE_STRING 3
#define KORE_JSON_TYPE_NUMBER 4
#define KORE_JSON_TYPE_LITERAL 5
#define KORE_JSON_FALSE 0
#define KORE_JSON_TRUE 1
#define KORE_JSON_NULL 2
#define KORE_JSON_DEPTH_MAX 10
#define KORE_JSON_ERR_NONE 0
#define KORE_JSON_ERR_INVALID_OBJECT 1
#define KORE_JSON_ERR_INVALID_ARRAY 2
#define KORE_JSON_ERR_INVALID_STRING 3
#define KORE_JSON_ERR_INVALID_NUMBER 4
#define KORE_JSON_ERR_INVALID_LITERAL 5
#define KORE_JSON_ERR_DEPTH 6
#define KORE_JSON_ERR_EOF 7
#define KORE_JSON_ERR_INVALID_JSON 8
#define KORE_JSON_ERR_INVALID_SEARCH 9
#define KORE_JSON_ERR_NOT_FOUND 10
#define KORE_JSON_ERR_TYPE_MISMATCH 11
#define KORE_JSON_ERR_LAST KORE_JSON_ERR_TYPE_MISMATCH
#define kore_json_object(j, p) \
kore_json_get(j, p, KORE_JSON_TYPE_OBJECT)
#define kore_json_array(j, p) \
kore_json_get(j, p, KORE_JSON_TYPE_ARRAY)
#define kore_json_string(j, p) \
kore_json_get(j, p, KORE_JSON_TYPE_STRING)
#define kore_json_number(j, p) \
kore_json_get(j, p, KORE_JSON_TYPE_NUMBER)
#define kore_json_literal(j, p) \
kore_json_get(j, p, KORE_JSON_TYPE_LITERAL)
struct kore_json {
const u_int8_t *data;
int depth;
int error;
size_t length;
size_t offset;
struct kore_buf tmpbuf;
struct kore_json_item *root;
};
struct kore_json_item {
int type;
char *name;
struct kore_json_item *parent;
union {
TAILQ_HEAD(, kore_json_item) items;
char *string;
double number;
int literal;
} data;
int (*parse)(struct kore_json *,
struct kore_json_item *);
TAILQ_ENTRY(kore_json_item) list;
};
struct kore_pool_region {
void *start;
size_t length;
@ -874,6 +944,13 @@ void kore_buf_appendv(struct kore_buf *, const char *, va_list);
void kore_buf_replace_string(struct kore_buf *,
const char *, const void *, size_t);
int kore_json_parse(struct kore_json *);
void kore_json_cleanup(struct kore_json *);
void kore_json_init(struct kore_json *, const u_int8_t *, size_t);
const char *kore_json_strerror(struct kore_json *);
struct kore_json_item *kore_json_get(struct kore_json *, const char *, int);
void kore_keymgr_run(void);
void kore_keymgr_cleanup(int);