Skip to content

Commit

Permalink
Implement ast_to_src for strconcat, represent string concatenation in
Browse files Browse the repository at this point in the history
ASR, update tests
  • Loading branch information
dpoerio committed Mar 15, 2021
1 parent 7339f61 commit 5507fb5
Show file tree
Hide file tree
Showing 9 changed files with 47 additions and 5 deletions.
3 changes: 3 additions & 0 deletions grammar/ASR.asdl
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,7 @@ stmt
expr
= BoolOp(expr left, boolop op, expr right, ttype type)
| BinOp(expr left, binop op, expr right, ttype type)
| StrOp(expr left, strop op, expr right, ttype type)
| UnaryOp(unaryop op, expr operand, ttype type)
| Compare(expr left, cmpop op, expr right, ttype type)
| FuncCall(symbol name, expr* args, keyword* keywords, ttype type)
Expand Down Expand Up @@ -101,6 +102,8 @@ binop = Add | Sub | Mul | Div | Pow

unaryop = Invert | Not | UAdd | USub

strop = Concat

cmpop = Eq | NotEq | Lt | LtE | Gt | GtE

intent = Local | In | Out | InOut | ReturnVar | External
Expand Down
3 changes: 3 additions & 0 deletions grammar/AST.asdl
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,7 @@ stmt
expr
= BoolOp(expr left, boolop op, expr right)
| BinOp(expr left, operator op, expr right)
| StrOp(expr left, stroperator op, expr right)
| UnaryOp(unaryop op, expr operand)
| Compare(expr left, cmpop op, expr right)
| FuncCall(identifier func, fnarg* args, keyword* keywords)
Expand All @@ -107,6 +108,8 @@ boolop = And | Or | Eqv | NEqv

operator = Add | Sub | Mul | Div | Pow

stroperator = Concat

unaryop = Invert | Not | UAdd | USub

cmpop = Eq | NotEq | Lt | LtE | Gt | GtE
Expand Down
1 change: 1 addition & 0 deletions src/lfortran/asr_utils.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ static inline ASR::ttype_t* expr_type(const ASR::expr_t *f)
case ASR::exprType::ExplicitCast: { return ((ASR::ExplicitCast_t*)f)->m_type; }
case ASR::exprType::Var: { return EXPR2VAR(f)->m_type; }
case ASR::exprType::ConstantLogical: { return ((ASR::ConstantLogical_t*)f)->m_type; }
case ASR::exprType::StrOp: { return ((ASR::StrOp_t*)f)->m_type; }
default : throw LFortranException("Not implemented");
}
}
Expand Down
16 changes: 16 additions & 0 deletions src/lfortran/ast_to_src.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ using LFortran::AST::Num_t;
using LFortran::AST::BinOp_t;
using LFortran::AST::operatorType;
using LFortran::AST::BaseVisitor;
using LFortran::AST::StrOp_t;


namespace LFortran {
Expand Down Expand Up @@ -48,6 +49,13 @@ namespace {
throw LFortranException("Unknown type");
}

std::string strop2str(const AST::stroperatorType type)
{
switch (type) {
case (AST::stroperatorType::Concat) : return "\\";
}
throw LFortranException("Unknown type");
}
}

namespace AST {
Expand Down Expand Up @@ -724,6 +732,14 @@ class ASTToSRCVisitor : public BaseVisitor<ASTToSRCVisitor>
s = "(" + left + ")" + op2str(x.m_op) + "(" + right + ")";
}

void visit_StrOp(const StrOp_t &x) {
this->visit_expr(*x.m_left);
std::string left = std::move(s);
this->visit_expr(*x.m_right);
std::string right = std::move(s);
s = "(" + left + ")" + strop2str(x.m_op) + "(" + right + ")";
}

void visit_UnaryOp(const UnaryOp_t &x) {
this->visit_expr(*x.m_operand);
if (x.m_op == AST::unaryopType::USub) {
Expand Down
4 changes: 3 additions & 1 deletion src/lfortran/parser/semantics.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ using LFortran::AST::down_cast2;
using LFortran::AST::astType;
using LFortran::AST::exprType;
using LFortran::AST::operatorType;
using LFortran::AST::stroperatorType;
using LFortran::AST::unaryopType;
using LFortran::AST::boolopType;
using LFortran::AST::cmpopType;
Expand Down Expand Up @@ -67,6 +68,7 @@ using LFortran::AST::make_Module_t;
using LFortran::AST::make_Private_t;
using LFortran::AST::make_Public_t;
using LFortran::AST::make_Interface_t;
using LFortran::AST::make_StrOp_t;


static inline expr_t* EXPR(const ast_t *f)
Expand Down Expand Up @@ -409,7 +411,7 @@ static inline LFortran::AST::reduce_opType convert_id_to_reduce_type(
#define TRUE(l) make_Constant_t(p.m_a, l, true)
#define FALSE(l) make_Constant_t(p.m_a, l, false)

#define STRCONCAT(x, y, l) x /* TODO: concacenate */
#define STRCONCAT(x, y, l) make_StrOp_t(p.m_a, l, EXPR(x), stroperatorType::Concat, EXPR(y))

#define EQ(x, y, l) make_Compare_t(p.m_a, l, EXPR(x), cmpopType::Eq, EXPR(y))
#define NE(x, y, l) make_Compare_t(p.m_a, l, EXPR(x), cmpopType::NotEq, EXPR(y))
Expand Down
17 changes: 17 additions & 0 deletions src/lfortran/semantics/ast_to_asr.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1228,6 +1228,23 @@ class BodyVisitor : public AST::BaseVisitor<BodyVisitor>
left, op, right, dest_type);
}

void visit_StrOp(const AST::StrOp_t &x) {
this->visit_expr(*x.m_left);
ASR::expr_t *left = EXPR(tmp);
this->visit_expr(*x.m_right);
ASR::expr_t *right = EXPR(tmp);
ASR::stropType op;
switch (x.m_op) {
case (AST::Concat) :
op = ASR::Concat;
}
ASR::ttype_t *right_type = expr_type(right);
ASR::ttype_t *dest_type = right_type;
// TODO: Type check here?
tmp = ASR::make_StrOp_t(al, x.base.base.loc,
left, op, right, dest_type);
}

void visit_UnaryOp(const AST::UnaryOp_t &x) {
this->visit_expr(*x.m_operand);
ASR::expr_t *operand = EXPR(tmp);
Expand Down
4 changes: 2 additions & 2 deletions src/lfortran/tests/ref_pickle.txt
Original file line number Diff line number Diff line change
Expand Up @@ -96,8 +96,8 @@ a
(Str "a''c")
(Str "a''b''c")
(Str "''zippo''")
(Str "aaa")
(Str "a")
(StrOp (StrOp (Str "aaa") Concat (FuncCallOrArray str [(() x ())] [])) Concat (Str "bb"))
(StrOp (Str "a") Concat (Str "b"))
(BoolOp 1 And 2)
(BoolOp a And b)
(BoolOp (== a 1) And (== b 2))
Expand Down
2 changes: 1 addition & 1 deletion tests/reference/ast-write1-170ef53.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
"outfile": null,
"outfile_hash": null,
"stdout": "ast-write1-170ef53.stdout",
"stdout_hash": "b7e6ea34393017dd182b5463329dde5f5261f585d27405aaf3970c6e",
"stdout_hash": "dc1113be69fdcf485d020121016bf97f7da82ae34b0fac0a16472459",
"stderr": null,
"stderr_hash": null,
"returncode": 0
Expand Down
2 changes: 1 addition & 1 deletion tests/reference/ast-write1-170ef53.stdout
Original file line number Diff line number Diff line change
@@ -1 +1 @@
(TranslationUnit [(Print () [(Str "a") 2]) (Print () []) (Print () [a]) (Print () [index]) (Print () [(Str "Scalar_in = ") scalar_in]) (Print () [int_src int_given int_expected]) (Print () [max_angle]) (Print () [n n]) (Print () [(FuncCallOrArray trim [(() prog ())] [])]) (Print () [(Str "Assertion failed at ") line]) (Print () [(Str "exactly_conservative= ") exactly_conservative]) (Print () [vec]) (Print () [(FuncCallOrArray trim [(() input_string ())] []) (Str ": ")]) (Print () [(Str "2")]) (Print () []) (Print "(a, es22.14)" [(Str "Ekin: ") Ekin])])
(TranslationUnit [(Print () [(Str "a") 2]) (Print () []) (Print () [a]) (Print () [index]) (Print () [(Str "Scalar_in = ") scalar_in]) (Print () [int_src int_given int_expected]) (Print () [max_angle]) (Print () [n n]) (Print () [(StrOp (StrOp (FuncCallOrArray trim [(() prog ())] []) Concat (Str ": ")) Concat message)]) (Print () [(StrOp (StrOp (Str "Assertion failed at ") Concat file) Concat (Str ":")) line]) (Print () [(Str "exactly_conservative= ") exactly_conservative]) (Print () [vec]) (Print () [(FuncCallOrArray trim [(() input_string ())] []) (Str ": ")]) (Print () [(Str "2")]) (Print () []) (Print "(a, es22.14)" [(Str "Ekin: ") Ekin])])

0 comments on commit 5507fb5

Please sign in to comment.