xo-reader2: bugfix: checkpoint before allocating SSMs

This commit is contained in:
Roland Conybeare 2026-02-16 11:03:09 -05:00
commit f7f21a4392
18 changed files with 78 additions and 36 deletions

View file

@ -87,8 +87,12 @@ namespace xo {
/** create instance using memory from @p parser_mm.
* Initial expression scaffold @p def_expr
**/
static DDefineSsm * make(DArena & parser_mm,
DDefineExpr * def_expr);
static DDefineSsm * _make(DArena & parser_mm,
DDefineExpr * def_expr);
/** create fop referring to new DDefineSsm **/
static obj<ASyntaxStateMachine,DDefineSsm> make(DArena & parser_mm,
DDefineExpr * def_expr);
/** start nested parser for a define-expression,
* on top of parser state machine @p p_psm

View file

@ -62,7 +62,10 @@ namespace xo {
/** create instance using memory from @p parser_mm
**/
static DParenSsm * make(DArena & parser_mm);
static DParenSsm * _make(DArena & parser_mm);
/** create fop pointing with new DParenSsm using memory from @p parser_mm **/
static obj<ASyntaxStateMachine,DParenSsm> make(DArena & parser_mm);
/** push DParenSsm instance onto @p p_psm stack **/
static void start(ParserStateMachine * p_psm);

View file

@ -30,9 +30,11 @@ namespace xo {
ParserStack * parent);
/** create new top of stack for syntax @p ssm, using memory from @p mm.
* previous stack given by @p parent
* previous stack given by @p parent.
* Checkpoint @p ckp will refer to stack _before_ allocating @p ssm
**/
static ParserStack * push(ParserStack * stack,
DArena::Checkpoint ckp,
DArena & mm,
obj<ASyntaxStateMachine> ssm);

View file

@ -97,8 +97,10 @@ namespace xo {
/** establish toplevel @p ssm. Must have empty stack **/
void establish_toplevel_ssm(obj<ASyntaxStateMachine> ssm);
/** push syntax @p ssm onto @ref stack_ **/
void push_ssm(obj<ASyntaxStateMachine> ssm);
/** push syntax @p ssm onto @ref stack_, restore parser stack to @p ckp
* when popped
**/
void push_ssm(DArena::Checkpoint ckp, obj<ASyntaxStateMachine> ssm);
/** pop syntax state machine from top of @ref stack_ **/
void pop_ssm();

View file

@ -89,14 +89,14 @@ namespace xo {
{
scope log(XO_DEBUG(p_psm->debug_flag()));
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
DApplySsm * apply_ssm
= DApplySsm::make(p_psm->parser_alloc(), fn_expr);
obj<ASyntaxStateMachine,DApplySsm> ssm(apply_ssm);
p_psm->push_ssm(ssm);
//OBSOLETE //p_psm->top_exprstate().on_expr(fn_expr.get(), p_psm);
//OBSOLETE //p_psm->on_token(token_type::leftparen(), p_psm);
p_psm->push_ssm(ckp, ssm);
}
syntaxstatetype

View file

@ -343,8 +343,8 @@ namespace xo {
{}
DDefineSsm *
DDefineSsm::make(DArena & mm,
DDefineExpr * def_expr)
DDefineSsm::_make(DArena & mm,
DDefineExpr * def_expr)
{
void * mem = mm.alloc(typeseq::id<DDefineSsm>(),
sizeof(DDefineSsm));
@ -352,6 +352,13 @@ namespace xo {
return new (mem) DDefineSsm(def_expr);
}
obj<ASyntaxStateMachine,DDefineSsm>
DDefineSsm::make(DArena & mm,
DDefineExpr * def_expr)
{
return obj<ASyntaxStateMachine,DDefineSsm>(_make(mm, def_expr));
}
void
DDefineSsm::start(DArena & mm,
obj<AAllocator> expr_mm,
@ -361,14 +368,13 @@ namespace xo {
assert(p_psm->stack());
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
DDefineExpr * def_expr = DDefineExpr::make_empty(expr_mm);
DDefineSsm * define_ssm = DDefineSsm::make(mm, def_expr);
auto define_ssm = DDefineSsm::make(mm, def_expr);
obj<ASyntaxStateMachine> ssm
= with_facet<ASyntaxStateMachine>::mkobj(define_ssm);
p_psm->push_ssm(ssm);
p_psm->push_ssm(ckp, define_ssm);
// note: triggers poly dispatch
p_psm->on_token(Token::def_token());

View file

@ -69,6 +69,8 @@ namespace xo {
bool cxl_on_rightbrace,
ParserStateMachine * p_psm)
{
DArena::Checkpoint ckp = mm.checkpoint();
DExpectExprSsm * exp_expr
= DExpectExprSsm::make(mm,
allow_defs,
@ -76,7 +78,7 @@ namespace xo {
obj<ASyntaxStateMachine> ssm
= with_facet<ASyntaxStateMachine>::mkobj(exp_expr);
p_psm->push_ssm(ssm);
p_psm->push_ssm(ckp, ssm);
}
void

View file

@ -56,7 +56,9 @@ namespace xo {
void
DExpectFormalArgSsm::start(ParserStateMachine * p_psm)
{
p_psm->push_ssm(DExpectFormalArgSsm::make(p_psm->parser_alloc()));
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
p_psm->push_ssm(ckp, DExpectFormalArgSsm::make(p_psm->parser_alloc()));
DExpectSymbolSsm::start(p_psm);
}

View file

@ -87,7 +87,9 @@ namespace xo {
void
DExpectFormalArglistSsm::start(ParserStateMachine * p_psm)
{
p_psm->push_ssm(DExpectFormalArglistSsm::make(p_psm->parser_alloc()));
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
p_psm->push_ssm(ckp, DExpectFormalArglistSsm::make(p_psm->parser_alloc()));
}
syntaxstatetype

View file

@ -31,6 +31,8 @@ namespace xo {
void
DExpectSymbolSsm::start(ParserStateMachine * p_psm)
{
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
DExpectSymbolSsm * sym_ssm
= DExpectSymbolSsm::make(p_psm->parser_alloc());
@ -40,7 +42,7 @@ namespace xo {
obj<ASyntaxStateMachine> ssm
= with_facet<ASyntaxStateMachine>::mkobj(sym_ssm);
p_psm->push_ssm(ssm);
p_psm->push_ssm(ckp, ssm);
}
syntaxstatetype

View file

@ -34,13 +34,15 @@ namespace xo {
void
DExpectTypeSsm::start(ParserStateMachine * p_psm)
{
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
DExpectTypeSsm * expect_type_ssm
= DExpectTypeSsm::make(p_psm->parser_alloc());
auto ssm
= with_facet<ASyntaxStateMachine>::mkobj(expect_type_ssm);
p_psm->push_ssm(ssm);
p_psm->push_ssm(ckp, ssm);
}
syntaxstatetype

View file

@ -70,13 +70,15 @@ namespace xo {
{
scope log(XO_DEBUG(p_psm->debug_flag()));
DArena::Checkpoint ckp = parser_mm.checkpoint();
DIfElseExpr * if_expr = DIfElseExpr::_make_empty(expr_mm);
DIfElseSsm * if_ssm = DIfElseSsm::_make(parser_mm, if_expr);
obj<ASyntaxStateMachine> ssm
= with_facet<ASyntaxStateMachine>::mkobj(if_ssm);
p_psm->push_ssm(ssm);
p_psm->push_ssm(ckp, ssm);
// note: triggers poly dispatch
p_psm->on_token(Token::if_token());

View file

@ -78,7 +78,9 @@ namespace xo {
void
DLambdaSsm::start(ParserStateMachine * p_psm)
{
p_psm->push_ssm(DLambdaSsm::make(p_psm->parser_alloc()));
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
p_psm->push_ssm(ckp, DLambdaSsm::make(p_psm->parser_alloc()));
p_psm->on_token(Token::lambda_token());
}

View file

@ -40,7 +40,7 @@ namespace xo {
{}
DParenSsm *
DParenSsm::make(DArena & mm)
DParenSsm::_make(DArena & mm)
{
void * mem = mm.alloc(typeseq::id<DParenSsm>(),
sizeof(DParenSsm));
@ -48,14 +48,20 @@ namespace xo {
return new (mem) DParenSsm();
}
obj<ASyntaxStateMachine,DParenSsm>
DParenSsm::make(DArena & mm)
{
return obj<ASyntaxStateMachine,DParenSsm>(_make(mm));
}
void
DParenSsm::start(ParserStateMachine * p_psm)
{
DParenSsm * paren_ssm = DParenSsm::make(p_psm->parser_alloc());
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
auto ssm = with_facet<ASyntaxStateMachine>::mkobj(paren_ssm);
auto paren_ssm = DParenSsm::make(p_psm->parser_alloc());
p_psm->push_ssm(ssm);
p_psm->push_ssm(ckp, paren_ssm);
}
syntaxstatetype

View file

@ -164,12 +164,14 @@ namespace xo {
optype op,
ParserStateMachine * p_psm)
{
DArena::Checkpoint ckp = parser_mm.checkpoint();
DProgressSsm * progress_ssm
= DProgressSsm::make(parser_mm, lhs, op);
obj<ASyntaxStateMachine,DProgressSsm> ssm(progress_ssm);
p_psm->push_ssm(ssm);
p_psm->push_ssm(ckp, ssm);
}
void
@ -324,8 +326,6 @@ namespace xo {
{
scope log(XO_DEBUG(p_psm->debug_flag()));
(void)tk;
obj<AExpression> expr = this->assemble_expr(p_psm);
p_psm->pop_ssm(); // completes self

View file

@ -22,8 +22,10 @@ namespace xo {
void
DSequenceSsm::start(ParserStateMachine * p_psm)
{
p_psm->push_ssm(DSequenceSsm::make(p_psm->parser_alloc(),
p_psm->expr_alloc()));
DArena::Checkpoint ckp = p_psm->parser_alloc().checkpoint();
p_psm->push_ssm(ckp, DSequenceSsm::make(p_psm->parser_alloc(),
p_psm->expr_alloc()));
/* want to accept anything that starts an expression,
* except that rightbrace '}' ends it
*/

View file

@ -22,11 +22,12 @@ namespace xo {
ParserStack *
ParserStack::push(ParserStack * stack,
DArena::Checkpoint ckp,
DArena & mm,
obj<ASyntaxStateMachine> ssm)
{
DArena::Checkpoint ckp = mm.checkpoint();
//DArena::Checkpoint ckp = mm.checkpoint(); // wrong, must precede allocation of ssm
void * mem = mm.alloc(typeseq::id<ParserStack>(),
sizeof(ParserStack));

View file

@ -75,18 +75,20 @@ namespace xo {
assert(stack_ == nullptr);
this->stack_ = ParserStack::push(nullptr /*stack*/, parser_alloc_, ssm);
DArena::Checkpoint ckp = parser_alloc_.checkpoint();
this->stack_ = ParserStack::push(nullptr /*stack*/, ckp, parser_alloc_, ssm);
this->parser_alloc_ckp_ = parser_alloc_.checkpoint();
}
void
ParserStateMachine::push_ssm(obj<ASyntaxStateMachine> ssm)
ParserStateMachine::push_ssm(DArena::Checkpoint ckp, obj<ASyntaxStateMachine> ssm)
{
scope log(XO_DEBUG(debug_flag_));
// note: using parser_alloc_ for parser stack, since stacklike behavior
this->stack_ = ParserStack::push(stack_, parser_alloc_, ssm);
this->stack_ = ParserStack::push(stack_, ckp, parser_alloc_, ssm);
}
void