|
|
@@ -62,13 +62,136 @@ static void expecteq( |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
static void lexeq(BXVariables &vars, const char *str, std::initializer_list<BXParser::Token> list) { |
|
|
|
INFO("Source: " << str); |
|
|
|
bufio::ISStream stream(str); |
|
|
|
BXParser parser(stream); |
|
|
|
parser.readToken(vars); |
|
|
|
|
|
|
|
size_t i = 1; |
|
|
|
for (auto &expected: list) { |
|
|
|
BXParser::Token tok = parser.readToken(vars); |
|
|
|
if (tok.kind != expected.kind) { |
|
|
|
INFO("Expected: " << (int)expected.kind); |
|
|
|
INFO("Actual: " << (int)tok.kind); |
|
|
|
FAIL("Token " << i << " doesn't match"); |
|
|
|
} |
|
|
|
|
|
|
|
if (tok.str != expected.str) { |
|
|
|
INFO("Expected: '" << expected.str << '\''); |
|
|
|
INFO("Actual: '" << tok.str << '\''); |
|
|
|
FAIL("Token " << i << "'s string doesn't match"); |
|
|
|
} |
|
|
|
|
|
|
|
if (tok.kind == BXParser::TokenKind::E_O_F) { |
|
|
|
return; |
|
|
|
} |
|
|
|
|
|
|
|
i += 1; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
static void lexeq(const char *str, std::initializer_list<BXParser::Token> list) { |
|
|
|
BXVariables vars; |
|
|
|
lexeq(vars, str, list); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser lex", "[BXParser][lex]") { |
|
|
|
lexeq("hello world", { |
|
|
|
{ BXParser::TokenKind::STRING, "hello" }, |
|
|
|
{ BXParser::TokenKind::STRING, "world" }, |
|
|
|
{ BXParser::TokenKind::E_O_F }, |
|
|
|
}); |
|
|
|
|
|
|
|
lexeq("hello := what's up", { |
|
|
|
{ BXParser::TokenKind::STRING, "hello" }, |
|
|
|
{ BXParser::TokenKind::COLON_EQUALS }, |
|
|
|
{ BXParser::TokenKind::STRING, "what's" }, |
|
|
|
{ BXParser::TokenKind::STRING, "up" }, |
|
|
|
{ BXParser::TokenKind::E_O_F }, |
|
|
|
}); |
|
|
|
|
|
|
|
lexeq("\t\t \t, := += =+\n\n\r\nhello", { |
|
|
|
{ BXParser::TokenKind::INDENTATION }, |
|
|
|
{ BXParser::TokenKind::COMMA }, |
|
|
|
{ BXParser::TokenKind::COLON_EQUALS }, |
|
|
|
{ BXParser::TokenKind::PLUS_EQUALS }, |
|
|
|
{ BXParser::TokenKind::EQUALS_PLUS }, |
|
|
|
{ BXParser::TokenKind::NEWLINE }, |
|
|
|
{ BXParser::TokenKind::STRING, "hello" }, |
|
|
|
{ BXParser::TokenKind::E_O_F }, |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser lex string interpolation", "[BXParser][lex]") { |
|
|
|
BXVariables vars = { |
|
|
|
{ "foo", { "hello"} }, |
|
|
|
}; |
|
|
|
|
|
|
|
lexeq(vars, "hey \"$foo\" lol", { |
|
|
|
{ BXParser::TokenKind::STRING, "hey" }, |
|
|
|
{ BXParser::TokenKind::STRING, "hello" }, |
|
|
|
{ BXParser::TokenKind::STRING, "lol" }, |
|
|
|
}); |
|
|
|
|
|
|
|
lexeq(vars, "hey \"no$foo\" lol", { |
|
|
|
{ BXParser::TokenKind::STRING, "hey" }, |
|
|
|
{ BXParser::TokenKind::STRING, "nohello" }, |
|
|
|
{ BXParser::TokenKind::STRING, "lol" }, |
|
|
|
}); |
|
|
|
|
|
|
|
lexeq(vars, "hey \"Xx${foo}xX\" lol", { |
|
|
|
{ BXParser::TokenKind::STRING, "hey" }, |
|
|
|
{ BXParser::TokenKind::STRING, "XxhelloxX" }, |
|
|
|
{ BXParser::TokenKind::STRING, "lol" }, |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser lex string interpolation without quotes", "[BXParser][lex]") { |
|
|
|
BXVariables vars = { |
|
|
|
{ "foo", { "hello"} }, |
|
|
|
}; |
|
|
|
|
|
|
|
lexeq(vars, "hey Xx$foo lol", { |
|
|
|
{ BXParser::TokenKind::STRING, "hey" }, |
|
|
|
{ BXParser::TokenKind::STRING, "Xxhello" }, |
|
|
|
{ BXParser::TokenKind::STRING, "lol" }, |
|
|
|
}); |
|
|
|
|
|
|
|
lexeq(vars, "hey Xx${ foo }xX lol", { |
|
|
|
{ BXParser::TokenKind::STRING, "hey" }, |
|
|
|
{ BXParser::TokenKind::STRING, "XxhelloxX" }, |
|
|
|
{ BXParser::TokenKind::STRING, "lol" }, |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser lex array expansion", "[BXParser][lex]") { |
|
|
|
lexeq("hey $foo lol", { |
|
|
|
{ BXParser::TokenKind::STRING, "hey" }, |
|
|
|
{ BXParser::TokenKind::EXPANSION, "foo" }, |
|
|
|
{ BXParser::TokenKind::STRING, "lol" }, |
|
|
|
}); |
|
|
|
|
|
|
|
lexeq("hey ${foo} lol", { |
|
|
|
{ BXParser::TokenKind::STRING, "hey" }, |
|
|
|
{ BXParser::TokenKind::EXPANSION, "foo" }, |
|
|
|
{ BXParser::TokenKind::STRING, "lol" }, |
|
|
|
}); |
|
|
|
|
|
|
|
lexeq("hey ${ \tfoo\n \n} lol", { |
|
|
|
{ BXParser::TokenKind::STRING, "hey" }, |
|
|
|
{ BXParser::TokenKind::EXPANSION, "foo" }, |
|
|
|
{ BXParser::TokenKind::STRING, "lol" }, |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser parsing", "[BXParser][parse]") { |
|
|
|
expecteq("hello := 10 world := 20", { |
|
|
|
expecteq("hello := 10, world := 20", { |
|
|
|
{ "hello", { "10" } }, |
|
|
|
{ "world", { "20" } }, |
|
|
|
}); |
|
|
|
|
|
|
|
expecteq("foo := hello world bar := 10 20 30 baz := 0", { |
|
|
|
expecteq("foo := hello world, bar := 10 20 30, baz := 0", { |
|
|
|
{ "foo", { "hello", "world" } }, |
|
|
|
{ "bar", { "10", "20", "30" } }, |
|
|
|
{ "baz", { "0" } }, |
|
|
@@ -76,27 +199,33 @@ TEST_CASE("BXParser parsing", "[BXParser][parse]") { |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser parsing variables", "[BXParser][parse]") { |
|
|
|
expecteq("foo := \"hello world\" bar := $foo", { |
|
|
|
expecteq("foo := \"hello world\", bar := $foo", { |
|
|
|
{ "foo", { "hello world" } }, |
|
|
|
{ "bar", { "hello world" } }, |
|
|
|
}); |
|
|
|
|
|
|
|
expecteq("foo := hello world bar := hey $foo what's up", { |
|
|
|
expecteq("foo := hello world, bar := hey $foo what's up", { |
|
|
|
{ "foo", { "hello", "world" } }, |
|
|
|
{ "bar", { "hey", "hello", "world", "what's", "up" } }, |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser append/prepend", "[BXParser][parse]") { |
|
|
|
expecteq("foo := 10 foo += 20 foo += 30", { |
|
|
|
expecteq("foo := 10, foo += 20, foo += 30", { |
|
|
|
{ "foo", { "10", "20", "30" } }, |
|
|
|
}); |
|
|
|
|
|
|
|
expecteq("foo := 10 foo =+ 20 foo =+ 30", { |
|
|
|
expecteq("foo := 10, foo =+ 20, foo =+ 30", { |
|
|
|
{ "foo", { "30", "20", "10" } }, |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser |=", "[BXParser][parse]") { |
|
|
|
expecteq("foo := 10, foo |= 10, foo |= 20", { |
|
|
|
{ "foo", { "10", "20" } }, |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser newline separation", "[BXParser][parse]") { |
|
|
|
expecteq( |
|
|
|
"foo := 10 20\n" |
|
|
@@ -105,3 +234,14 @@ TEST_CASE("BXParser newline separation", "[BXParser][parse]") { |
|
|
|
{ "bar", { "30", "40" } }, |
|
|
|
}); |
|
|
|
} |
|
|
|
|
|
|
|
TEST_CASE("BXParser newline continuation", "[BXParser][parse]") { |
|
|
|
expecteq( |
|
|
|
"foo := 10 20\n" |
|
|
|
"\t30 40\n" |
|
|
|
"bar := hello world\n" |
|
|
|
"\tbaz \":=\" 30\n", { |
|
|
|
{ "foo", { "10", "20", "30", "40" } }, |
|
|
|
{ "bar", { "hello", "world", "baz", ":=", "30" } }, |
|
|
|
}); |
|
|
|
} |