Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Toy v1 parser implementation #162

Merged
merged 30 commits into from
Oct 2, 2023
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
4b5a41b
Trying to test toy-v1 with a v3x/ParseHelper (ANTLR) while reusing th…
rturrado Sep 11, 2023
3b65d4e
Refactored v3x/ParseHelper and implemented it using a ScannerAntlr.
rturrado Sep 12, 2023
502b607
Started implementing the toy v1 ANTLR parser.
rturrado Sep 13, 2023
c4f5612
Amend of previous commit.
rturrado Sep 14, 2023
270a6a0
Finished writing the builder visitor (ANTLR AST to tree-gen AST).
rturrado Sep 14, 2023
9b96146
Changed ScannerAntlr to have a build visitor as a dependency injection.
rturrado Sep 15, 2023
acb42c5
Changed test/v1x/parsing.cpp to accommodate toy v1x tests.
rturrado Sep 16, 2023
b46805c
Fixed ParsingTest::TestBody.
rturrado Sep 16, 2023
232e692
Trying to fix MacOS and Windows tests.
rturrado Sep 16, 2023
83febaf
Trying to fix MacOS compilation.
rturrado Sep 16, 2023
4a932fe
Added Toy v1 res/cq files.
rturrado Sep 16, 2023
5f0f2d5
Removed some Flex/Bison warnings due to integral types redefinitions.
rturrado Sep 18, 2023
a9013e7
WIP. [skip ci]
rturrado Sep 19, 2023
37eef7b
Updated v3x parser code (ParseHelper, ScannerAntlr, AST builder, erro…
rturrado Sep 20, 2023
0d07e5e
Removed cqasm::v3x::default_analyzer. Just reusing cqasm::v1x::defaul…
rturrado Sep 20, 2023
3fd53bd
Used make_unique instead of unique_ptr.
rturrado Sep 20, 2023
fd327ef
Removed temporary comments.
rturrado Sep 20, 2023
4cefec0
Updated README.md.
rturrado Sep 21, 2023
27a104a
Addressed some of the comments from Pablo's code review.
rturrado Sep 22, 2023
e2e4b81
Trying to fix MacOS build error.
rturrado Sep 22, 2023
0e6b951
Updated tree-gen commit ID, now to one in master.
rturrado Sep 22, 2023
60db46c
Addressed some of the comments from Pablo's code review.
rturrado Sep 26, 2023
d0a4e0f
Changed grammar to use alternative labels.
rturrado Sep 26, 2023
1535365
Added asserts for checking the type of the terminal node at get_integ…
rturrado Sep 27, 2023
56f6dff
Updated README.md (added 'WIP: cQASM v3.0' section) to explain that t…
rturrado Sep 27, 2023
a920f6e
Updated tree-gen commit ID, now to one in master.
rturrado Sep 27, 2023
9852a94
Merge remote-tracking branch 'origin/develop' into toy-v1-use_case_ci…
rturrado Sep 27, 2023
c5c67ec
Merge branch 'develop' into toy-v1-use_case_circuit_for_parser_verifi…
rturrado Sep 27, 2023
fbd83f7
Preparing everything for the merge.
rturrado Sep 29, 2023
a1a31db
BuildCustomAstVisitor class can be empty.
rturrado Sep 29, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ if(POLICY CMP0148)
cmake_policy(SET CMP0148 NEW)
endif()

project(cqasm C CXX)
project(cqasm LANGUAGES C CXX)

# If cqasm was already included elsewhere in the project, don't include it again.
# There should be only one place for it and one version per project.
Expand Down
10 changes: 10 additions & 0 deletions include/v3x/BuildTreeGenAstVisitor.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,13 @@
namespace cqasm::v3x::parser {

class BuildTreeGenAstVisitor : public BuildCustomAstVisitor {
/**
* Name of the file being parsed.
*/
std::string file_name_;

std::int64_t get_integer_literal_value(antlr4::tree::TerminalNode *node);
double get_float_literal_value(antlr4::tree::TerminalNode *node);
public:
std::any visitProgram(CqasmParser::ProgramContext *context) override;
std::any visitVersion(CqasmParser::VersionContext *context) override;
Expand All @@ -21,6 +28,9 @@ class BuildTreeGenAstVisitor : public BuildCustomAstVisitor {
std::any visitExpressionList(CqasmParser::ExpressionListContext *context) override;
std::any visitExpression(CqasmParser::ExpressionContext *context) override;
std::any visitIndex(CqasmParser::IndexContext *context) override;

explicit BuildTreeGenAstVisitor(const std::string &file_name = "<unknown>")
: file_name_{ file_name } {}
};

} // namespace cqasm::v3x::parser
12 changes: 6 additions & 6 deletions include/v3x/ScannerAntlr.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,8 @@ class ScannerAntlr : public ScannerAdaptor {
cqasm::v1x::parser::ParseResult parse_(antlr4::ANTLRInputStream &is);

public:
explicit ScannerAntlr(std::unique_ptr<BuildCustomAstVisitor> build_visitor_up,
std::unique_ptr<CustomErrorListener> error_listener_up);
ScannerAntlr(std::unique_ptr<BuildCustomAstVisitor> build_visitor_up,
std::unique_ptr<CustomErrorListener> error_listener_up);

~ScannerAntlr() override;

Expand All @@ -34,8 +34,8 @@ class ScannerAntlrFile : public ScannerAntlr {
std::string file_path_;
public:
ScannerAntlrFile(std::unique_ptr<BuildCustomAstVisitor> build_visitor_up,
std::unique_ptr<CustomErrorListener> error_listener_up,
const std::string &file_path);
std::unique_ptr<CustomErrorListener> error_listener_up,
const std::string &file_path);

~ScannerAntlrFile() override;

Expand All @@ -46,8 +46,8 @@ class ScannerAntlrString : public ScannerAntlr {
std::string data_;
public:
ScannerAntlrString(std::unique_ptr<BuildCustomAstVisitor> build_visitor_up,
std::unique_ptr<CustomErrorListener> error_listener_up,
const std::string &data);
std::unique_ptr<CustomErrorListener> error_listener_up,
const std::string &data);

~ScannerAntlrString() override;

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
ERROR
input.cq:2:2: value '1.79769313486231570e+309' is out of the FLOATING_LITERAL range
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
version 3
x 1.79769313486231570e+309 # biggest double is 1.79769313486231570e+308
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
ERROR
input.cq:2:2: value '18446744073709551616' is out of the INTEGER_LITERAL range
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
version 3
x 18446744073709551616 # biggest 64-bit integer is 18446744073709551615
2 changes: 1 addition & 1 deletion src/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ include(FetchContent)
# This exposes the generate_tree() function.
FetchContent_Declare(tree-gen
GIT_REPOSITORY https://github.com/QuTech-Delft/tree-gen.git
GIT_TAG "64819883ff88d4bfa5ec160df86e6c9167c97a7e"
GIT_TAG "6a1339ea1ccb74b5ded2a86405a9143c7ef1a067"
)
FetchContent_MakeAvailable(tree-gen)

Expand Down
40 changes: 34 additions & 6 deletions src/v3x/BuildTreeGenAstVisitor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
#include "v3x/BuildTreeGenAstVisitor.hpp"

#include <algorithm> // for_each
#include <cassert> // assert
#include <antlr4-runtime.h>
#include <stdexcept> // runtime_error
#include <string> // stod, stoll

Expand All @@ -13,12 +13,40 @@ namespace cqasm::v3x::parser {
using namespace cqasm::v1x::ast;
using namespace cqasm::error;

std::int64_t get_integer_literal_value(antlr4::tree::TerminalNode *node) {
return std::stoll(node->getText());
std::int64_t BuildTreeGenAstVisitor::get_integer_literal_value(antlr4::tree::TerminalNode *node) {
auto text = node->getText();
pablolh marked this conversation as resolved.
Show resolved Hide resolved
std::int64_t ret{};
try {
ret = std::stoll(text);
rturrado marked this conversation as resolved.
Show resolved Hide resolved
} catch (std::out_of_range&) {
const auto &token = node->getSymbol();
throw std::runtime_error{
fmt::format("{}:{}:{}: value '{}' is out of the INTEGER_LITERAL range",
file_name_,
token->getLine(),
token->getCharPositionInLine(),
text
)};
}
return ret;
}

double get_float_literal_value(antlr4::tree::TerminalNode *node) {
return std::stod(node->getText());
double BuildTreeGenAstVisitor::get_float_literal_value(antlr4::tree::TerminalNode *node) {
auto text = node->getText();
double ret{};
try {
ret = std::stod(text);
} catch (std::out_of_range&) {
const auto &token = node->getSymbol();
throw std::runtime_error{
fmt::format("{}:{}:{}: value '{}' is out of the FLOATING_LITERAL range",
file_name_,
token->getLine(),
token->getCharPositionInLine(),
text
)};
}
return ret;
}

std::any BuildTreeGenAstVisitor::visitProgram(CqasmParser::ProgramContext *context) {
Expand All @@ -38,7 +66,7 @@ std::any BuildTreeGenAstVisitor::visitProgram(CqasmParser::ProgramContext *conte
std::any BuildTreeGenAstVisitor::visitVersion(CqasmParser::VersionContext *context) {
auto ret = cqasm::tree::make<Version>();
const auto& integer_literals = context->INTEGER_LITERAL();
std::for_each(integer_literals.begin(), integer_literals.end(), [&ret](auto *integer_literal_node) {
std::for_each(integer_literals.begin(), integer_literals.end(), [this, &ret](auto *integer_literal_node) {
auto number = get_integer_literal_value(integer_literal_node);
ret->items.push_back(number);
});
Expand Down
17 changes: 10 additions & 7 deletions src/v3x/ScannerAntlr.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ namespace cqasm::v3x::parser {
ScannerAdaptor::~ScannerAdaptor() {}

ScannerAntlr::ScannerAntlr(std::unique_ptr<BuildCustomAstVisitor> build_visitor_up,
std::unique_ptr<CustomErrorListener> error_listener_up)
std::unique_ptr<CustomErrorListener> error_listener_up)
: build_visitor_up_{ std::move(build_visitor_up) }
, error_listener_up_{std::move(error_listener_up)} {}

Expand All @@ -26,23 +26,26 @@ cqasm::v1x::parser::ParseResult ScannerAntlr::parse_(antlr4::ANTLRInputStream &i
CqasmLexer lexer{ &is };
lexer.removeErrorListeners();
lexer.addErrorListener(error_listener_up_.get());

antlr4::CommonTokenStream tokens{ &lexer };

CqasmParser parser{ &tokens };
parser.removeErrorListeners();
parser.addErrorListener(error_listener_up_.get());

auto ast = parser.program();
auto custom_ast = build_visitor_up_->visitProgram(ast);
return cqasm::v1x::parser::ParseResult{
std::any_cast<cqasm::v1x::ast::One<cqasm::v1x::ast::Program>> (custom_ast), // root
std::any_cast<cqasm::v1x::ast::One<cqasm::v1x::ast::Program>>(custom_ast), // root
{} // error
};
}

ScannerAntlrFile::ScannerAntlrFile(std::unique_ptr<BuildCustomAstVisitor> build_visitor_up,
std::unique_ptr<CustomErrorListener> error_listener_up,
const std::string &file_path)
std::unique_ptr<CustomErrorListener> error_listener_up,
const std::string &file_path)
: ScannerAntlr{ std::move(build_visitor_up) , std::move(error_listener_up) }
, file_path_{file_path } {
, file_path_{ file_path } {
if (!fs::exists(file_path_) || !fs::is_regular_file(file_path_)) {
throw cqasm::error::AnalysisError{ fmt::format("ScannerAntlrFile couldn't access file '{}'.", file_path_) };
}
Expand All @@ -57,8 +60,8 @@ cqasm::v1x::parser::ParseResult ScannerAntlrFile::parse() {
}

ScannerAntlrString::ScannerAntlrString(std::unique_ptr<BuildCustomAstVisitor> build_visitor_up,
std::unique_ptr<CustomErrorListener> error_listener_up,
const std::string &data)
std::unique_ptr<CustomErrorListener> error_listener_up,
const std::string &data)
: ScannerAntlr{ std::move(build_visitor_up), std::move(error_listener_up) }
, data_{ data } {}

Expand Down
4 changes: 2 additions & 2 deletions src/v3x/cqasm-parse-helper.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ namespace cqasm::v3x::parser {
* A file_name may be given in addition for use within error messages.
*/
cqasm::v1x::parser::ParseResult parse_file(const std::string &file_path, const std::string &file_name) {
auto builder_visitor_up = std::make_unique<BuildTreeGenAstVisitor>();
auto builder_visitor_up = std::make_unique<BuildTreeGenAstVisitor>(file_name);
auto error_listener_up = std::make_unique<CustomErrorListener>(file_name);
auto scanner_up = std::make_unique<ScannerAntlrFile>(
std::move(builder_visitor_up), std::move(error_listener_up), file_path);
Expand All @@ -28,7 +28,7 @@ cqasm::v1x::parser::ParseResult parse_file(const std::string &file_path, const s
* A file_name may be given in addition for use within error messages.
*/
cqasm::v1x::parser::ParseResult parse_string(const std::string &data, const std::string &file_name) {
auto builder_visitor_up = std::make_unique<BuildTreeGenAstVisitor>();
auto builder_visitor_up = std::make_unique<BuildTreeGenAstVisitor>(file_name);
auto error_listener_up = std::make_unique<CustomErrorListener>(file_name);
auto scanner_up = std::make_unique<ScannerAntlrString>(
std::move(builder_visitor_up), std::move(error_listener_up), data);
Expand Down