xo-expression: + ConvertExpr
This commit is contained in:
parent
9a1a419aef
commit
0708bc7569
3 changed files with 163 additions and 0 deletions
109
include/xo/expression/ConvertExpr.hpp
Normal file
109
include/xo/expression/ConvertExpr.hpp
Normal file
|
|
@ -0,0 +1,109 @@
|
||||||
|
/* file ConvertExpr.hpp
|
||||||
|
*
|
||||||
|
* author: Roland Conybeare, Aug 2024
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "Expression.hpp"
|
||||||
|
|
||||||
|
namespace xo {
|
||||||
|
namespace ast {
|
||||||
|
/** @class Convertexpr
|
||||||
|
* @brief Convenience for automatic type conversion
|
||||||
|
*
|
||||||
|
* This is equivalent to calling a built-in primitive
|
||||||
|
* that performs the conversion.
|
||||||
|
*
|
||||||
|
* We rely on this for convenience, for example to parse
|
||||||
|
* code like
|
||||||
|
*
|
||||||
|
* def foo : i16 = 0
|
||||||
|
**/
|
||||||
|
class ConvertExpr : public Expression {
|
||||||
|
public:
|
||||||
|
static rp<ConvertExpr> make(TypeDescr dest_type,
|
||||||
|
rp<Expression> arg);
|
||||||
|
|
||||||
|
static ref::brw<ConvertExpr> from(ref::brw<Expression> x) {
|
||||||
|
return ref::brw<ConvertExpr>::from(x);
|
||||||
|
}
|
||||||
|
|
||||||
|
const rp<Expression> & arg() const { return arg_; }
|
||||||
|
|
||||||
|
// ----- Expression -----
|
||||||
|
|
||||||
|
virtual std::set<std::string> get_free_variables() const override;
|
||||||
|
|
||||||
|
virtual std::size_t visit_preorder(VisitFn visitor_fn) override {
|
||||||
|
std::size_t n = 1;
|
||||||
|
|
||||||
|
visitor_fn(this);
|
||||||
|
|
||||||
|
n += arg_->visit_preorder(visitor_fn);
|
||||||
|
|
||||||
|
return n;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual std::size_t visit_layer(VisitFn visitor_fn) override {
|
||||||
|
std::size_t n = 1;
|
||||||
|
|
||||||
|
visitor_fn(this);
|
||||||
|
|
||||||
|
n += this->arg_->visit_layer(visitor_fn);
|
||||||
|
|
||||||
|
return n;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual rp<Expression> xform_layer(TransformFn xform_fn) override {
|
||||||
|
this->arg_ = this->arg_->xform_layer(xform_fn);
|
||||||
|
|
||||||
|
return xform_fn(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void attach_envs(ref::brw<Environment> p) override {
|
||||||
|
arg_->attach_envs(p);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void display(std::ostream & os) const override;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
ConvertExpr(TypeDescr dest_type,
|
||||||
|
rp<Expression> arg)
|
||||||
|
: Expression(exprtype::convert, dest_type),
|
||||||
|
arg_{std::move(arg)}
|
||||||
|
{}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
/** source expression. Convert
|
||||||
|
* @c arg_->valuetype() to @c dest_type_
|
||||||
|
**/
|
||||||
|
rp<Expression> arg_;
|
||||||
|
};
|
||||||
|
|
||||||
|
/** @class ConvertExprAccess
|
||||||
|
* @brief ConvertExpr with writeable members.
|
||||||
|
*
|
||||||
|
* Convenient when scaffolding a parser,
|
||||||
|
* e.g. see xo-parser
|
||||||
|
**/
|
||||||
|
class ConvertExprAccess : public ConvertExpr {
|
||||||
|
public:
|
||||||
|
static rp<ConvertExprAccess> make(TypeDescr dest_type,
|
||||||
|
rp<Expression> arg);
|
||||||
|
static rp<ConvertExprAccess> make_empty();
|
||||||
|
|
||||||
|
void assign_arg(rp<Expression> arg) { this->arg_ = std::move(arg); }
|
||||||
|
|
||||||
|
private:
|
||||||
|
ConvertExprAccess(TypeDescr dest_type,
|
||||||
|
rp<Expression> arg)
|
||||||
|
: ConvertExpr(dest_type,
|
||||||
|
std::move(arg))
|
||||||
|
{}
|
||||||
|
};
|
||||||
|
} /*namespace ast*/
|
||||||
|
} /*namespace xo*/
|
||||||
|
|
||||||
|
|
||||||
|
/* end ConvertExpr.hpp */
|
||||||
|
|
@ -9,6 +9,7 @@ set(SELF_SRCS
|
||||||
Variable.cpp
|
Variable.cpp
|
||||||
IfExpr.cpp
|
IfExpr.cpp
|
||||||
LocalEnv.cpp
|
LocalEnv.cpp
|
||||||
|
ConvertExpr.cpp
|
||||||
)
|
)
|
||||||
|
|
||||||
xo_add_shared_library4(${SELF_LIB} ${PROJECT_NAME}Targets ${PROJECT_VERSION} 1 ${SELF_SRCS})
|
xo_add_shared_library4(${SELF_LIB} ${PROJECT_NAME}Targets ${PROJECT_VERSION} 1 ${SELF_SRCS})
|
||||||
|
|
|
||||||
53
src/expression/ConvertExpr.cpp
Normal file
53
src/expression/ConvertExpr.cpp
Normal file
|
|
@ -0,0 +1,53 @@
|
||||||
|
/* file ConvertExpr.cpp
|
||||||
|
*
|
||||||
|
* author: Roland Conybeare
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "ConvertExpr.hpp"
|
||||||
|
|
||||||
|
namespace xo {
|
||||||
|
namespace ast {
|
||||||
|
rp<ConvertExpr>
|
||||||
|
ConvertExpr::make(TypeDescr dest_type,
|
||||||
|
rp<Expression> arg)
|
||||||
|
{
|
||||||
|
return new ConvertExpr(dest_type,
|
||||||
|
std::move(arg));
|
||||||
|
}
|
||||||
|
|
||||||
|
std::set<std::string>
|
||||||
|
ConvertExpr::get_free_variables() const {
|
||||||
|
if (this->arg_)
|
||||||
|
return this->arg_->get_free_variables();
|
||||||
|
else
|
||||||
|
return std::set<std::string>();
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
ConvertExpr::display(std::ostream & os) const {
|
||||||
|
os << "<Convert"
|
||||||
|
<< xtag("dest_type", this->valuetype()->short_name())
|
||||||
|
<< xtag("arg", arg_)
|
||||||
|
<< ">";
|
||||||
|
}
|
||||||
|
|
||||||
|
// ----- ConvertExprAccess -----
|
||||||
|
|
||||||
|
rp<ConvertExprAccess>
|
||||||
|
ConvertExprAccess::make(TypeDescr dest_type,
|
||||||
|
rp<Expression> arg)
|
||||||
|
{
|
||||||
|
return new ConvertExprAccess(dest_type,
|
||||||
|
std::move(arg));
|
||||||
|
}
|
||||||
|
|
||||||
|
rp<ConvertExprAccess>
|
||||||
|
ConvertExprAccess::make_empty() {
|
||||||
|
return new ConvertExprAccess(nullptr /*dest_type*/,
|
||||||
|
nullptr /*arg*/);
|
||||||
|
}
|
||||||
|
} /*namespace ast*/
|
||||||
|
} /*namespace xo*/
|
||||||
|
|
||||||
|
|
||||||
|
/* end ConvertExpr.cpp */
|
||||||
Loading…
Add table
Add a link
Reference in a new issue