feat: working subtables

This commit is contained in:
3lswear
2022-01-23 13:50:12 +03:00
parent 3b2469b130
commit d9b66c8795
4 changed files with 90 additions and 26 deletions

View File

@@ -16,16 +16,18 @@ namespace config
TOMLMap *root; //root of TOML tree TOMLMap *root; //root of TOML tree
/* toml_node *current; //node currently being parsed */ /* toml_node *current; //node currently being parsed */
Tokenizer tokenizer; Tokenizer tokenizer;
static std::vector<std::string> split_name(std::string name); static std::vector<std::string> split_name(std::string name);
static void put_to_subtable(TOMLMap *root, static void put_to_subtable(TOMLMap *root,
std::vector<std::string> full_name, std::vector<std::string> full_name,
toml_node *map_node); toml_node *map_node, toml_node::e_type type);
public: public:
TOMLParser(const std::string filename); TOMLParser(const std::string filename);
TOMLMap *parse(void); TOMLMap *parse(void);
toml_node *parseMap(void); toml_node *parseMap(void);
void processMap(void);
void parseMapArray(void); void parseMapArray(void);

View File

@@ -26,8 +26,7 @@ namespace config
NIL, NIL,
OPEN_BRACKET, OPEN_BRACKET,
CLOSE_BRACKET, CLOSE_BRACKET,
MAP_OPEN, MAP_DECL,
MAP_CLOSE,
MAPARRAY_DECL MAPARRAY_DECL
}; };

View File

@@ -28,6 +28,37 @@ namespace config
TOMLParser::TOMLParser(const std::string filename) : tokenizer(filename) TOMLParser::TOMLParser(const std::string filename) : tokenizer(filename)
{}; {};
void TOMLParser::processMap(void)
{
std::cerr << "Processing map" << std::endl;
toml_node *map_node;
s_token current;
try { current = tokenizer.getToken(); }
catch (std::logic_error e)
{
std::cerr << e.what() << std::endl;
return;
}
if (current.type == MAP_DECL)
{
if (tokenizer.getToken().type != NEWLINE)
throw std::logic_error("no newline after MAP_DECL");
map_node = parseMap();
}
else
throw std::logic_error("unexpected token in processMap");
std::cout << current.value << std::endl;
std::vector<std::string> full_name;
full_name = split_name(current.value);
put_to_subtable(root, full_name, map_node, toml_node::MAP);
}
toml_node *TOMLParser::parseMap(void) toml_node *TOMLParser::parseMap(void)
{ {
std::cerr << "Parsing map" << std::endl; std::cerr << "Parsing map" << std::endl;
@@ -51,9 +82,11 @@ namespace config
tokenizer.set_last(NEWLINE); tokenizer.set_last(NEWLINE);
break; break;
} }
else if (nextToken.type == OPEN_BRACKET) else if (nextToken.type == MAP_DECL)
{ {
tokenizer.rollBackToken();
tokenizer.set_last(NEWLINE);
break;
} }
std::string key = nextToken.value; std::string key = nextToken.value;
std::cerr << key << std::endl; std::cerr << key << std::endl;
@@ -139,15 +172,13 @@ namespace config
else else
throw std::logic_error("unexpected token in parseMapArray"); throw std::logic_error("unexpected token in parseMapArray");
TOMLMap::iterator it;
std::cout << current.value << std::endl; std::cout << current.value << std::endl;
std::string name = current.value;
std::vector<std::string> full_name; std::vector<std::string> full_name;
full_name = split_name(name); full_name = split_name(current.value);
/* throw std::logic_error("tha end"); */ put_to_subtable(root, full_name, map_node, toml_node::MAPARRAY);
put_to_subtable(root, full_name, map_node);
} }
@@ -294,6 +325,17 @@ namespace config
tokenizer.rollBackToken(); tokenizer.rollBackToken();
parseMapArray(); parseMapArray();
} }
else if (current.type == MAP_DECL)
{
std::cerr << "MAP_DECL value: " << current.value << std::endl;
tokenizer.set_last(NEWLINE);
tokenizer.rollBackToken();
/* if (tokenizer.getToken().type != NEWLINE) */
/* throw std::logic_error("no newline after MAP_DECL"); */
/* (*mapObject)[nextToken.value] = parseMap(); */
processMap();
continue;
}
else else
{ {
std::string key = current.value; std::string key = current.value;
@@ -378,7 +420,7 @@ namespace config
void TOMLParser::put_to_subtable(TOMLMap *root, void TOMLParser::put_to_subtable(TOMLMap *root,
std::vector<std::string> full_name, std::vector<std::string> full_name,
toml_node *map_node) toml_node *map_node, toml_node::e_type type)
{ {
std::vector<std::string>::iterator subname = full_name.begin(); std::vector<std::string>::iterator subname = full_name.begin();
toml_node *maparr_node; toml_node *maparr_node;
@@ -391,16 +433,28 @@ namespace config
if (subname + 1 == full_name.end()) if (subname + 1 == full_name.end())
{ {
it = local_root->find(*subname); it = local_root->find(*subname);
if (it == local_root->end()) if (type == toml_node::MAPARRAY)
{ {
maparr_node = new toml_node; if (it == local_root->end())
TOMLMapArray *map_array = new TOMLMapArray; {
map_array->push_back(map_node->getMap()); maparr_node = new toml_node;
maparr_node->setMapArray(map_array); TOMLMapArray *map_array = new TOMLMapArray;
(*local_root)[*subname] = maparr_node; map_array->push_back(map_node->getMap());
maparr_node->setMapArray(map_array);
(*local_root)[*subname] = maparr_node;
}
else
(it->second)->getMapArray()->push_back(map_node->getMap());
}
else if (type == toml_node::MAP)
{
if (it == local_root->end())
{
(*local_root)[*subname] = map_node;
}
else
throw std::logic_error("map already in subtable!");
} }
else
(it->second)->getMapArray()->push_back(map_node->getMap());
break; break;
} }
else else
@@ -419,9 +473,7 @@ namespace config
} }
/* subname found in local_root */ /* subname found in local_root */
else else
{
local_root = *((it->second)->getMapArray()->end() - 1); local_root = *((it->second)->getMapArray()->end() - 1);
}
} }
++subname; ++subname;

View File

@@ -88,9 +88,9 @@ namespace config
file.get(c); file.get(c);
} }
} }
else if (c == '[') else if (c == '[' && firstToken())
{ {
std::streampos prev_pos = file.tellg(); /* std::streampos prev_pos = file.tellg(); */
file.get(c); file.get(c);
if (c == '[') if (c == '[')
{ {
@@ -108,10 +108,21 @@ namespace config
} }
else else
{ {
token.type = OPEN_BRACKET; token.type = MAP_DECL;
file.seekg(prev_pos); token.value += c;
file.get(c);
while (c != ']')
{
token.value += c;
file.get(c);
}
if (c != ']')
throw std::logic_error("malformed MAP_DECL");
} }
}
else if (c == '[')
{
token.type = OPEN_BRACKET;
} }
else if (c == ']') else if (c == ']')
token.type = CLOSE_BRACKET; token.type = CLOSE_BRACKET;