xo-reader: feat: mvp lambda parsing [untested]
This commit is contained in:
parent
0841fd7dbd
commit
1628d8f44c
5 changed files with 134 additions and 27 deletions
|
|
@ -11,34 +11,63 @@
|
||||||
|
|
||||||
namespace xo {
|
namespace xo {
|
||||||
namespace scm {
|
namespace scm {
|
||||||
|
/**
|
||||||
|
* ( name(1) : type(1) , ..., )
|
||||||
|
* ^ ^ ^ ^ ^
|
||||||
|
* | | | | |
|
||||||
|
* | | | | argl_1b
|
||||||
|
* | argl_1a | argla
|
||||||
|
* argl_0 argl_1b
|
||||||
|
*
|
||||||
|
* argl_0 --on_leftparen_token()--> argl_1a
|
||||||
|
* argl_1a --on_formal()--> argl_1b
|
||||||
|
* argl_1b -+-on_comma_token()--> argl_1a
|
||||||
|
* \-on_rightparen_token()--> (done)
|
||||||
|
**/
|
||||||
enum class formalarglstatetype {
|
enum class formalarglstatetype {
|
||||||
invalid = -1,
|
invalid = -1,
|
||||||
|
|
||||||
argl_0,
|
argl_0,
|
||||||
argl_1,
|
argl_1a,
|
||||||
|
argl_1b,
|
||||||
|
|
||||||
n_formalarglstatetype,
|
n_formalarglstatetype,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
extern const char *
|
||||||
|
formalarglstatetype_descr(formalarglstatetype x);
|
||||||
|
|
||||||
|
inline std::ostream &
|
||||||
|
operator<< (std::ostream & os, formalarglstatetype x) {
|
||||||
|
os << formalarglstatetype_descr(x);
|
||||||
|
return os;
|
||||||
|
}
|
||||||
|
|
||||||
/** @class expect_formal_arglist
|
/** @class expect_formal_arglist
|
||||||
* @brief parser state-machine for a formal parameter list
|
* @brief parser state-machine for a formal parameter list
|
||||||
*
|
|
||||||
* ( name(1) : type(1), ..., )
|
|
||||||
* ^
|
|
||||||
* |
|
|
||||||
* argl_0
|
|
||||||
**/
|
**/
|
||||||
class expect_formal_arglist_xs : public exprstate {
|
class expect_formal_arglist_xs : public exprstate {
|
||||||
|
public:
|
||||||
|
using Variable = xo::ast::Variable;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
expect_formal_arglist_xs();
|
expect_formal_arglist_xs();
|
||||||
|
|
||||||
static std::unique_ptr<expect_formal_arglist_xs> make();
|
static std::unique_ptr<expect_formal_arglist_xs> make();
|
||||||
|
|
||||||
const std::vector<formal_arg> & argl() const { return argl_; }
|
|
||||||
|
|
||||||
virtual void on_leftparen_token(const token_type & tk,
|
virtual void on_leftparen_token(const token_type & tk,
|
||||||
exprstatestack * p_stack,
|
exprstatestack * p_stack,
|
||||||
rp<Expression> * p_emit_expr) override;
|
rp<Expression> * p_emit_expr) override;
|
||||||
|
virtual void on_formal(const rp<Variable> & formal,
|
||||||
|
exprstatestack * p_stack,
|
||||||
|
rp<Expression> * p_emit_expr) override;
|
||||||
|
virtual void on_comma_token(const token_type & tk,
|
||||||
|
exprstatestack * p_stack,
|
||||||
|
rp<Expression> * p_emit_expr) override;
|
||||||
|
virtual void on_rightparen_token(const token_type & tk,
|
||||||
|
exprstatestack * p_stack,
|
||||||
|
rp<Expression> * p_emit_expr) override;
|
||||||
|
virtual void print(std::ostream & os) const override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
/** parsing state-machine state **/
|
/** parsing state-machine state **/
|
||||||
|
|
@ -46,7 +75,7 @@ namespace xo {
|
||||||
/** populate with (parmaeter-name, parameter-type) list
|
/** populate with (parmaeter-name, parameter-type) list
|
||||||
* as they're encountered
|
* as they're encountered
|
||||||
**/
|
**/
|
||||||
std::vector<formal_arg> argl_;
|
std::vector<rp<Variable>> argl_;
|
||||||
};
|
};
|
||||||
} /*namespace scm*/
|
} /*namespace scm*/
|
||||||
} /*namespace xo*/
|
} /*namespace xo*/
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,9 @@ namespace xo {
|
||||||
* | formal_1
|
* | formal_1
|
||||||
* formal_0
|
* formal_0
|
||||||
*
|
*
|
||||||
|
* formal_0 --on_symbol()--> formal_1
|
||||||
|
* formal_1 --on_colon_token()--> formal_2
|
||||||
|
* formal_2 --on_typedescr()--> (done)
|
||||||
**/
|
**/
|
||||||
enum class formalstatetype {
|
enum class formalstatetype {
|
||||||
invalid = -1,
|
invalid = -1,
|
||||||
|
|
@ -44,6 +47,8 @@ namespace xo {
|
||||||
public:
|
public:
|
||||||
expect_formal_xs() = default;
|
expect_formal_xs() = default;
|
||||||
|
|
||||||
|
static std::unique_ptr<expect_formal_xs> make();
|
||||||
|
|
||||||
virtual void on_symbol(const std::string & symbol_name,
|
virtual void on_symbol(const std::string & symbol_name,
|
||||||
exprstatestack * p_stack,
|
exprstatestack * p_stack,
|
||||||
rp<Expression> * p_emit_expr) override;
|
rp<Expression> * p_emit_expr) override;
|
||||||
|
|
@ -68,7 +73,7 @@ namespace xo {
|
||||||
|
|
||||||
private:
|
private:
|
||||||
/** parsing state-machine state **/
|
/** parsing state-machine state **/
|
||||||
formalstatetype formalxs_type_;
|
formalstatetype formalxs_type_ = formalstatetype::formal_0;
|
||||||
/** populate with {parameter-name, parameter-type}
|
/** populate with {parameter-name, parameter-type}
|
||||||
* as they're encountered
|
* as they're encountered
|
||||||
**/
|
**/
|
||||||
|
|
|
||||||
|
|
@ -4,9 +4,30 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "expect_formal_arglist_xs.hpp"
|
#include "expect_formal_arglist_xs.hpp"
|
||||||
|
#include "expect_formal_xs.hpp"
|
||||||
|
#include "xo/expression/Variable.hpp"
|
||||||
|
#include "xo/indentlog/print/vector.hpp"
|
||||||
|
|
||||||
namespace xo {
|
namespace xo {
|
||||||
namespace scm {
|
namespace scm {
|
||||||
|
const char *
|
||||||
|
formalarglstatetype_descr(formalarglstatetype x) {
|
||||||
|
switch (x) {
|
||||||
|
case formalarglstatetype::invalid:
|
||||||
|
return "invalid";
|
||||||
|
case formalarglstatetype::argl_0:
|
||||||
|
return "argl_0";
|
||||||
|
case formalarglstatetype::argl_1a:
|
||||||
|
return "argl_1a";
|
||||||
|
case formalarglstatetype::argl_1b:
|
||||||
|
return "argl_1b";
|
||||||
|
case formalarglstatetype::n_formalarglstatetype:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return "?formalarglstatetype";
|
||||||
|
}
|
||||||
|
|
||||||
std::unique_ptr<expect_formal_arglist_xs>
|
std::unique_ptr<expect_formal_arglist_xs>
|
||||||
expect_formal_arglist_xs::make() {
|
expect_formal_arglist_xs::make() {
|
||||||
return std::make_unique<expect_formal_arglist_xs>
|
return std::make_unique<expect_formal_arglist_xs>
|
||||||
|
|
@ -23,13 +44,62 @@ namespace xo {
|
||||||
rp<Expression> * p_emit_expr)
|
rp<Expression> * p_emit_expr)
|
||||||
{
|
{
|
||||||
if (farglxs_type_ == formalarglstatetype::argl_0) {
|
if (farglxs_type_ == formalarglstatetype::argl_0) {
|
||||||
this->farglxs_type_ = formalarglstatetype::argl_1;
|
this->farglxs_type_ = formalarglstatetype::argl_1a;
|
||||||
return;
|
p_stack->push_exprstate(expect_formal_xs::make());
|
||||||
|
} else {
|
||||||
|
exprstate::on_leftparen_token(tk, p_stack, p_emit_expr);
|
||||||
}
|
}
|
||||||
|
|
||||||
exprstate::on_leftparen_token(tk, p_stack, p_emit_expr);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
expect_formal_arglist_xs::on_formal(const rp<Variable> & formal,
|
||||||
|
exprstatestack * p_stack,
|
||||||
|
rp<Expression> * p_emit_expr)
|
||||||
|
{
|
||||||
|
if (farglxs_type_ == formalarglstatetype::argl_1a) {
|
||||||
|
this->farglxs_type_ = formalarglstatetype::argl_1b;
|
||||||
|
this->argl_.push_back(formal);
|
||||||
|
} else {
|
||||||
|
exprstate::on_formal(formal, p_stack, p_emit_expr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
expect_formal_arglist_xs::on_comma_token(const token_type & tk,
|
||||||
|
exprstatestack * p_stack,
|
||||||
|
rp<Expression> * p_emit_expr)
|
||||||
|
{
|
||||||
|
if (farglxs_type_ == formalarglstatetype::argl_1b) {
|
||||||
|
this->farglxs_type_ = formalarglstatetype::argl_1a;
|
||||||
|
p_stack->push_exprstate(expect_formal_xs::make());
|
||||||
|
} else {
|
||||||
|
exprstate::on_comma_token(tk, p_stack, p_emit_expr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
expect_formal_arglist_xs::on_rightparen_token(const token_type & tk,
|
||||||
|
exprstatestack * p_stack,
|
||||||
|
rp<Expression> * p_emit_expr)
|
||||||
|
{
|
||||||
|
if (farglxs_type_ == formalarglstatetype::argl_1b) {
|
||||||
|
std::unique_ptr<exprstate> self = p_stack->pop_exprstate();
|
||||||
|
|
||||||
|
p_stack->top_exprstate().on_formal_arglist(this->argl_,
|
||||||
|
p_stack, p_emit_expr);
|
||||||
|
} else {
|
||||||
|
exprstate::on_rightparen_token(tk, p_stack, p_emit_expr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
expect_formal_arglist_xs::print(std::ostream & os) const {
|
||||||
|
os << "<expect_formal_arglist_xs"
|
||||||
|
<< xtag("type", farglxs_type_);
|
||||||
|
os << xtag("farglxs_type", farglxs_type_);
|
||||||
|
os << xtag("argl", argl_);
|
||||||
|
os << ">";
|
||||||
|
}
|
||||||
} /*namespace scm*/
|
} /*namespace scm*/
|
||||||
} /*namespace xo*/
|
} /*namespace xo*/
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -4,8 +4,10 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "expect_formal_xs.hpp"
|
#include "expect_formal_xs.hpp"
|
||||||
|
#include "xo/expression/Variable.hpp"
|
||||||
|
|
||||||
namespace xo {
|
namespace xo {
|
||||||
|
using xo::ast::Variable;
|
||||||
using xo::reflect::TypeDescr;
|
using xo::reflect::TypeDescr;
|
||||||
|
|
||||||
namespace scm{
|
namespace scm{
|
||||||
|
|
@ -26,6 +28,11 @@ namespace xo {
|
||||||
return "???formalstatetype";
|
return "???formalstatetype";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::unique_ptr<expect_formal_xs>
|
||||||
|
expect_formal_xs::make() {
|
||||||
|
return std::make_unique<expect_formal_xs>(expect_formal_xs());
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
expect_formal_xs::on_symbol(const std::string & symbol_name,
|
expect_formal_xs::on_symbol(const std::string & symbol_name,
|
||||||
exprstatestack * p_stack,
|
exprstatestack * p_stack,
|
||||||
|
|
@ -64,7 +71,10 @@ namespace xo {
|
||||||
|
|
||||||
std::unique_ptr<exprstate> self = p_stack->pop_exprstate();
|
std::unique_ptr<exprstate> self = p_stack->pop_exprstate();
|
||||||
|
|
||||||
//p_stack->top_exprstate().on_formal(result_, p_stack, p_emit_expr);
|
rp<Variable> var = Variable::make(result_.name(),
|
||||||
|
result_.td());
|
||||||
|
|
||||||
|
p_stack->top_exprstate().on_formal(var, p_stack, p_emit_expr);
|
||||||
} else {
|
} else {
|
||||||
exprstate::on_typedescr(td, p_stack, p_emit_expr);
|
exprstate::on_typedescr(td, p_stack, p_emit_expr);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -24,12 +24,9 @@ namespace xo {
|
||||||
if (lmxs_type_ == lambdastatetype::lm_0) {
|
if (lmxs_type_ == lambdastatetype::lm_0) {
|
||||||
this->lmxs_type_ = lambdastatetype::lm_1;
|
this->lmxs_type_ = lambdastatetype::lm_1;
|
||||||
p_stack->push_exprstate(expect_formal_arglist_xs::make());
|
p_stack->push_exprstate(expect_formal_arglist_xs::make());
|
||||||
return;
|
} else {
|
||||||
|
exprstate::on_lambda_token(tk, p_stack, p_emit_expr);
|
||||||
}
|
}
|
||||||
|
|
||||||
exprstate::on_lambda_token(tk,
|
|
||||||
p_stack,
|
|
||||||
p_emit_expr);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|
@ -41,12 +38,9 @@ namespace xo {
|
||||||
this->lmxs_type_ = lambdastatetype::lm_2;
|
this->lmxs_type_ = lambdastatetype::lm_2;
|
||||||
this->argl_ = argl;
|
this->argl_ = argl;
|
||||||
p_stack->push_exprstate(expect_expr_xs::expect_rhs_expression());
|
p_stack->push_exprstate(expect_expr_xs::expect_rhs_expression());
|
||||||
return;
|
} else {
|
||||||
|
exprstate::on_formal_arglist(argl, p_stack, p_emit_expr);
|
||||||
}
|
}
|
||||||
|
|
||||||
exprstate::on_formal_arglist(argl,
|
|
||||||
p_stack,
|
|
||||||
p_emit_expr);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|
@ -57,10 +51,9 @@ namespace xo {
|
||||||
if (lmxs_type_ == lambdastatetype::lm_2) {
|
if (lmxs_type_ == lambdastatetype::lm_2) {
|
||||||
this->lmxs_type_ = lambdastatetype::lm_3;
|
this->lmxs_type_ = lambdastatetype::lm_3;
|
||||||
this->body_ = expr.promote();
|
this->body_ = expr.promote();
|
||||||
return;
|
} else {
|
||||||
|
exprstate::on_expr(expr, p_stack, p_emit_expr);
|
||||||
}
|
}
|
||||||
|
|
||||||
exprstate::on_expr(expr, p_stack, p_emit_expr);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue