88 lines
3.0 KiB
C
88 lines
3.0 KiB
C
/* This Source Code Form is subject to the terms of the Mozilla Public
|
|
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
|
|
|
#include "toml_internal.h"
|
|
|
|
Result(void) toml_parse_table(TomlParser* self, TomlTable* target_table)
|
|
{
|
|
Deferral(1);
|
|
|
|
i32 is_array = false;
|
|
TomlTable* real_table = target_table;
|
|
TomlArray* key_path = TomlArray_new();
|
|
Defer(TomlArray_free(key_path));
|
|
|
|
if (self->ptr < self->end &&* self->ptr == '[') {
|
|
is_array = true;
|
|
toml_move_next(self);
|
|
}
|
|
|
|
while (1) {
|
|
if (*self->ptr == ' ' ||* self->ptr == '\t') {
|
|
do {
|
|
toml_move_next(self);
|
|
} while (*self->ptr <* self->end && (*self->ptr == ' ' ||* self->ptr == '\t'));
|
|
} else if (*self->ptr == ']') {
|
|
if (is_array) {
|
|
if (self->ptr + 2 <= self->end && strncmp(self->ptr, "]]", 2) == 0) {
|
|
toml_next_n(self, 2);
|
|
break;
|
|
}
|
|
} else {
|
|
toml_move_next(self);
|
|
break;
|
|
}
|
|
} else {
|
|
str key_part;
|
|
if (isalnum(*self->ptr) ||* self->ptr == '_') {
|
|
try_void(toml_parse_bare_key(self, &key_part));
|
|
} else if (*self->ptr == '\"') {
|
|
toml_move_next(self);
|
|
try_void(toml_parse_basic_string(self, &key_part));
|
|
} else if (*self->ptr == '\'') {
|
|
toml_move_next(self);
|
|
try_void(toml_parse_literal_string(self, &key_part));
|
|
} else {
|
|
Return RESULT_ERROR_CODE_FMT(TLIBTOML, TLIBTOML_ERR_SYNTAX,
|
|
"%s:%d:%d: unexpected token",
|
|
self->filename, self->lineno, self->colno);
|
|
}
|
|
|
|
TomlValue key_part_value = TomlValue_move_str(key_part);
|
|
TomlArray_append(key_path, key_part_value);
|
|
|
|
while (self->ptr < self->end &&
|
|
(*self->ptr == ' ' ||* self->ptr == '\t')) {
|
|
toml_move_next(self);
|
|
}
|
|
|
|
if (self->ptr < self->end &&* self->ptr == '.') {
|
|
toml_move_next(self);
|
|
}
|
|
}
|
|
}
|
|
|
|
if (key_path->len == 0) {
|
|
Return RESULT_ERROR_CODE_FMT(TLIBTOML, TLIBTOML_ERR_SYNTAX,
|
|
"%s:%d:%d: empty table name",
|
|
self->filename, self->lineno, self->colno);
|
|
}
|
|
|
|
while (self->ptr < self->end &&
|
|
(*self->ptr == ' ' ||* self->ptr == '\t' ||* self->ptr == '\r')) {
|
|
toml_move_next(self);
|
|
}
|
|
|
|
if (self->ptr < self->end &&* self->ptr != '\n') {
|
|
Return RESULT_ERROR_CODE_FMT(TLIBTOML, TLIBTOML_ERR_SYNTAX,
|
|
"%s:%d:%d: new line expected",
|
|
self->filename, self->lineno, self->colno);
|
|
}
|
|
|
|
try(real_table, p, toml_walk_table_path(self, target_table, key_path, is_array, true));
|
|
try_void(toml_parse_key_value(self, real_table));
|
|
|
|
Return RESULT_VOID;
|
|
}
|