diff options
Diffstat (limited to 'deps/v8/test/unittests/torque/earley-parser-unittest.cc')
-rw-r--r-- | deps/v8/test/unittests/torque/earley-parser-unittest.cc | 84 |
1 files changed, 84 insertions, 0 deletions
diff --git a/deps/v8/test/unittests/torque/earley-parser-unittest.cc b/deps/v8/test/unittests/torque/earley-parser-unittest.cc new file mode 100644 index 00000000000..9718a404c99 --- /dev/null +++ b/deps/v8/test/unittests/torque/earley-parser-unittest.cc @@ -0,0 +1,84 @@ +// Copyright 2018 the V8 project authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "src/torque/earley-parser.h" +#include "test/unittests/test-utils.h" + +namespace v8 { +namespace internal { +namespace torque { + +namespace { + +template <int op(int, int)> +base::Optional<ParseResult> MakeBinop(ParseResultIterator* child_results) { + // Ideally, we would want to use int as a result type here instead of + // std::string. This is possible, but requires adding int to the list of + // supported ParseResult types in torque-parser.cc. To avoid changing that + // code, we use std::string here, which is already used in the Torque parser. + auto a = child_results->NextAs<std::string>(); + auto b = child_results->NextAs<std::string>(); + return ParseResult{std::to_string(op(std::stoi(a), std::stoi(b)))}; +} + +int plus(int a, int b) { return a + b; } +int minus(int a, int b) { return a - b; } +int mul(int a, int b) { return a * b; } + +} // namespace + +struct SimpleArithmeticGrammar : Grammar { + static bool MatchWhitespace(InputPosition* pos) { + while (MatchChar(std::isspace, pos)) { + } + return true; + } + + static bool MatchInteger(InputPosition* pos) { + InputPosition current = *pos; + MatchString("-", ¤t); + if (MatchChar(std::isdigit, ¤t)) { + while (MatchChar(std::isdigit, ¤t)) { + } + *pos = current; + return true; + } + return false; + } + + SimpleArithmeticGrammar() : Grammar(&sum_expression) { + SetWhitespace(MatchWhitespace); + } + + Symbol integer = {Rule({Pattern(MatchInteger)}, YieldMatchedInput)}; + + Symbol atomic_expression = {Rule({&integer}), + Rule({Token("("), &sum_expression, Token(")")})}; + + Symbol mul_expression = { + Rule({&atomic_expression}), + Rule({&mul_expression, Token("*"), &atomic_expression}, MakeBinop<mul>)}; + + Symbol sum_expression = { + Rule({&mul_expression}), + Rule({&sum_expression, Token("+"), &mul_expression}, MakeBinop<plus>), + Rule({&sum_expression, Token("-"), &mul_expression}, MakeBinop<minus>)}; +}; + +TEST(EarleyParser, SimpleArithmetic) { + SimpleArithmeticGrammar grammar; + SourceFileMap::Scope source_file_map; + CurrentSourceFile::Scope current_source_file{ + SourceFileMap::AddSource("dummy_filename")}; + std::string result1 = + grammar.Parse("-5 - 5 + (3 + 5) * 2")->Cast<std::string>(); + ASSERT_EQ("6", result1); + std::string result2 = grammar.Parse("((-1 + (1) * 2 + 3 - 4 * 5 + -6 * 7))") + ->Cast<std::string>(); + ASSERT_EQ("-58", result2); +} + +} // namespace torque +} // namespace internal +} // namespace v8 |