Suite* Syntactic::suite() { Suite* node = nullptr; Node* stm = nullptr; Suite* suite = nullptr; if (lexic->type == Token::NEWLINE) { lexic->Next(); Check(Token::INDENT); stm = Stmt(); suite = _Suite(); Check(Token::DEDENT); node = new Suite(); node->nodes.push_back(stm); if(suite != nullptr) { for(auto a: suite->nodes) node->nodes.push_back(a); delete suite; } } else { stm = Simple_Stmt(); node = new Suite(); node->nodes.push_back(stm); } return node; }
Stmt IRRewriter::rewrite(Stmt s) { if (s.defined()) { s.accept(this); Stmt spilledStmts = getSpilledStmts(); if (spilledStmts.defined()) { stmt = Block::make(spilledStmts, stmt); } s = stmt; } else { s = Stmt(); } expr = Expr(); stmt = Stmt(); func = Func(); return s; }
bool Parser::OptStmtList() { if ("end" == lex) { std::cout << "OptStmtList => null\n"; return true; } if (!Stmt()) return false; if (!OptStmtList()) return false; std::cout << "OptStmtList => Stmt OptStmtList\n"; return true; }
Expr IRRewriter::rewrite(Expr e) { if (e.defined()) { e.accept(this); e = expr; } else { e = Expr(); } expr = Expr(); stmt = Stmt(); func = Func(); return e; }
Func IRRewriter::rewrite(Func f) { if (f.defined()) { f.accept(this); f = func; } else { f = Func(); } expr = Expr(); stmt = Stmt(); func = Func(); return f; }
void IRPrinter::test() { Type i32 = Int(32); Type f32 = Float(32); Expr x = new Variable(Int(32), "x"); Expr y = new Variable(Int(32), "y"); std::ostringstream expr_source; expr_source << (x + 3) * (y / 2 + 17); assert(expr_source.str() == "((x + 3)*((y/2) + 17))"); Stmt store = new Store("buf", (x * 17) / (x - 3), y - 1); Stmt for_loop = new For("x", -2, y + 2, For::Parallel, store); vector<Expr> args(1); args[0] = x % 3; Expr call = new Call(i32, "buf", args); Stmt store2 = new Store("out", call + 1, x); Stmt for_loop2 = new For("x", 0, y, For::Vectorized , store2); Stmt pipeline = new Pipeline("buf", for_loop, Stmt(), for_loop2); Stmt assertion = new AssertStmt(y > 3, "y is greater than 3"); Stmt block = new Block(assertion, pipeline); Stmt let_stmt = new LetStmt("y", 17, block); Stmt allocate = new Allocate("buf", f32, 1023, let_stmt); std::ostringstream source; source << allocate; std::string correct_source = \ "allocate buf[f32 * 1023]\n" "let y = 17\n" "assert((y > 3), \"y is greater than 3\")\n" "produce buf {\n" " parallel (x, -2, (y + 2)) {\n" " buf[(y - 1)] = ((x*17)/(x - 3))\n" " }\n" "} consume {\n" " vectorized (x, 0, y) {\n" " out[x] = (buf((x % 3)) + 1)\n" " }\n" "}\n" "free buf\n"; if (source.str() != correct_source) { std::cout << "Correct output:" << std::endl << correct_source; std::cout << "Actual output:" << std::endl << source.str(); assert(false); } std::cout << "IRPrinter test passed" << std::endl; }
Suite* Syntactic::_Suite() { Suite* node = nullptr; Node* stm = nullptr; Suite* suite = nullptr; if (lexic->type != Token::DEDENT) { stm = Stmt(); suite = _Suite(); node = new Suite(); node->nodes.push_back(stm); if(suite != nullptr) { for(auto a: suite->nodes) node->nodes.push_back(a); delete suite; } } return node; }
void IRRewriter::visit(const Block *op) { Stmt first = rewrite(op->first); Stmt rest = rewrite(op->rest); if (first == op->first && rest == op->rest) { stmt = op; } else { if (first.defined() && rest.defined()) { stmt = Block::make(first, rest); } else if (first.defined() && !rest.defined()) { stmt = first; } else if (!first.defined() && rest.defined()) { stmt = rest; } else { stmt = Stmt(); } } }
namespace test { struct Stmt { std::string stmt; std::string extraDecl; Stmt(const std::string& stmt) : stmt(stmt) { } Stmt& withExtraDecl(const std::string& decl) { extraDecl = decl; return *this; } }; std::ostream& operator<<(std::ostream& os, const Stmt& s) { os << "\"" << s.stmt << "\""; if (!s.extraDecl.empty()) os << " with \"" << s.extraDecl << "\""; return os; } struct getStmtLocationRangeTest : testing::TestWithParam<Stmt> { std::unique_ptr<test::ParsedFunction> func; std::string extraDeclarations; std::string parsedSource; void parse(const std::string& source) { func.reset(new test::ParsedFunction(source)); parsedSource = source; } void setExtraDeclarations(const std::string& decls) { extraDeclarations = decls; } LocationRange getRangeFromSource(const std::string& source) { parse(source); return getStmtLocationRange(func->getDecl()->getASTContext().getSourceManager(), **func->stmts()); } LocationRange getRangeFromStmt(const std::string& stmt) { return getRangeFromSource(extraDeclarations + " void dummy_function__() { " + stmt + "\n }"); // \n is needed because of clang bug } void expectStmtRangeIs(LocationRange range, const std::string& phrase) { auto phraseOffset = parsedSource.find(phrase); ASSERT_EQ(LocationRange(rowCol(0, phraseOffset), rowCol(0, phraseOffset + phrase.length())), range) << (*func->stmts())->getStmtClassName(); } }; TEST_F(getStmtLocationRangeTest, should_handle_multiline_statements) { auto range = getRangeFromSource("void dummy_function__() {\n int\n x;\n}"); ASSERT_EQ(LocationRange(rowCol(1, 2), rowCol(2, 3)), range); } TEST_F(getStmtLocationRangeTest, should_throw_an_exception_for_unknown_statement) { auto source = "int dummy_function__() {\n return 4 + 2;\n}"; ASSERT_THROW(getRangeFromSource(source), cppmanip::ExtractMethodError); } TEST_P(getStmtLocationRangeTest, should_find_correct_source_range_for_a_statement) { setExtraDeclarations(GetParam().extraDecl); auto range = getRangeFromStmt(GetParam().stmt); expectStmtRangeIs(range, GetParam().stmt); } INSTANTIATE_TEST_CASE_P( should_find_correct_source_range_for_all_statements, getStmtLocationRangeTest, Values( Stmt("int x;"), Stmt("int x ;"), Stmt("int z = 7;"), Stmt("int z = f();").withExtraDecl("int f();"), Stmt("float f(3.0f);"), Stmt("f(3, 4);").withExtraDecl("void f(int, int);"), Stmt("o.f();").withExtraDecl("struct O { void f(); } o;"), Stmt("for (;;);"), Stmt("for (;;) f();").withExtraDecl("void f();"), Stmt("for (;;) { }"), Stmt("for (;;) int x = 3;"), Stmt("i += 4;").withExtraDecl("int i;"), Stmt("if (true) f(7);").withExtraDecl("void f(int);"), Stmt("{}"), Stmt(";") )); }
// class Func Func::Func(const std::string& name, const std::vector<Var>& arguments, const std::vector<Var>& results, Kind kind) : Func(name, arguments, results, Stmt(), kind) { iassert(kind != Internal); }
Connection::Stmt Connection::create_statement(const std::string & sql) { return Stmt(sql, *this); }
void visit(const VarDecl *op) { varDecls.push_back(op); stmt = Stmt(); }