Open mingodad opened 3 years ago
Looking through the compiler code it seems that there is a mistake here:
void BitwiseOrExp()
{
BitwiseXorExp();
for(;;) if(_token == _SC('|'))
{BIN_EXP(_OP_BITW, &SQCompiler::BitwiseXorExp,BW_OR); ///!!!!<<< should be BitwiseOrExp ?
}else return;
}
Or else the previous ones :
void LogicalAndExp()
{
BitwiseOrExp();
for(;;) switch(_token) {
case TK_AND: {
SQInteger first_exp = _fs->PopTarget();
SQInteger trg = _fs->PushTarget();
_fs->AddInstruction(_OP_AND, trg, 0, first_exp, 0);
SQInteger jpos = _fs->GetCurrentPos();
if(trg != first_exp) _fs->AddInstruction(_OP_MOVE, trg, first_exp);
Lex(); INVOKE_EXP(&SQCompiler::LogicalAndExp); ///!!!<<< here we have full recursion could be BitwiseOrExp ?
_fs->SnoozeOpt();
SQInteger second_exp = _fs->PopTarget();
if(trg != second_exp) _fs->AddInstruction(_OP_MOVE, trg, second_exp);
_fs->SnoozeOpt();
_fs->SetInstructionParam(jpos, 1, (_fs->GetCurrentPos() - jpos));
_es.etype = EXPR;
break;
}
default:
return;
}
}
My bad they are calling different functions to generate distinct code !
It seems that the for loops here are meaningless:
@@ -469,11 +470,11 @@ public:
_es.etype = EXPR;
}
void LogicalOrExp()
{
LogicalAndExp();
- for(;;) if(_token == TK_OR) {
+ if(_token == TK_OR) {
SQInteger first_exp = _fs->PopTarget();
SQInteger trg = _fs->PushTarget();
_fs->AddInstruction(_OP_OR, trg, 0, first_exp, 0);
SQInteger jpos = _fs->GetCurrentPos();
if(trg != first_exp) _fs->AddInstruction(_OP_MOVE, trg, first_exp);
@@ -482,18 +483,16 @@ public:
SQInteger second_exp = _fs->PopTarget();
if(trg != second_exp) _fs->AddInstruction(_OP_MOVE, trg, second_exp);
_fs->SnoozeOpt();
_fs->SetInstructionParam(jpos, 1, (_fs->GetCurrentPos() - jpos));
_es.etype = EXPR;
- break;
- }else return;
+ }
}
void LogicalAndExp()
{
BitwiseOrExp();
- for(;;) switch(_token) {
- case TK_AND: {
+ if(_token == TK_AND) {
SQInteger first_exp = _fs->PopTarget();
SQInteger trg = _fs->PushTarget();
_fs->AddInstruction(_OP_AND, trg, 0, first_exp, 0);
SQInteger jpos = _fs->GetCurrentPos();
if(trg != first_exp) _fs->AddInstruction(_OP_MOVE, trg, first_exp);
@@ -502,15 +501,10 @@ public:
SQInteger second_exp = _fs->PopTarget();
if(trg != second_exp) _fs->AddInstruction(_OP_MOVE, trg, second_exp);
_fs->SnoozeOpt();
_fs->SetInstructionParam(jpos, 1, (_fs->GetCurrentPos() - jpos));
_es.etype = EXPR;
- break;
- }
-
- default:
- return;
}
}
Following the code I discovered that in literal arrays the comma separator is optional, didn't knew this before. Is this intended ?
local b = [1 2, 3 4];
print(b.len()); //Output -> 4
Yes, it was intended. In retrospect, I don't think it was a good decision but it really hasn't created any issue in my experience. FYI, this is also valid for function call parameters.
Thank you for reply an clarify it !
I'm testing this interesting parser generator https://ssw.jku.at/Research/Projects/Coco/ and as exercise I'm building a Squirrel/SquiLu grammar with it.
As usual any feedback is welcome !
This is the initial CocoR grammar just in case someone else want to try (edited with my latest):
And here is the Squirrel EBNF accepted by https://www.bottlecaps.de/rr/ui to create railroad diagrams, copy the grammar bellow and paste on the
Edit Grammar
tab then switch to theView Diagram
tab to view the railroad diagram.