Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Possible fix for several syntax-related crashes as well as for use syntax mylang not functioning correctly. #373

Closed
wants to merge 5 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions kernel/daoVmspace.c
Original file line number Diff line number Diff line change
Expand Up @@ -1846,6 +1846,12 @@ int DaoVmSpace_CompleteModuleName( DaoVmSpace *self, DString *fname, int types )
}else if( (types & DAO_MODULE_DLL) && size > slen && DString_FindChars( fname, DAO_DLL_SUFFIX, 0 ) == size - slen ){
DaoVmSpace_SearchPath( self, fname, DAO_FILE_PATH, 1 );
if( DaoVmSpace_TestFile( self, fname ) ) modtype = DAO_MODULE_DLL;
//If we're given a filename (i.e., if it has an extension) and it's not a known filetype, load it anyway.
//With custom syntaxes people can use custom extensions, and we should allow them to load with those.
//In this case, always treat the extension as DAO_MODULE_DAO; that's all we'll support for custom extensions.
}else if( (types & DAO_MODULE_DAO) && size >1 && DString_FindChars( fname, ".", 0 ) != -1 ){
DaoVmSpace_SearchPath( self, fname, DAO_FILE_PATH, 1 );
if( DaoVmSpace_TestFile( self, fname ) ) modtype = DAO_MODULE_DAO;
}else{
DString *fn = DString_New();
DString *path = DString_New();
Expand Down
169 changes: 159 additions & 10 deletions modules/macro/dao_macro.c
Original file line number Diff line number Diff line change
Expand Up @@ -95,12 +95,12 @@ static void DaoParser_ErrorX( DaoParser *self, int code, DString *ext )
}
static void DaoParser_ErrorX2( DaoParser *self, int code, int m, int n, int single_line )
{
DaoParser_ErrorX2( self, code, m, n, single_line );
DaoParser_Error2( self, code, m, n, single_line );
DaoParser_UpdateError( self );
}
static void DaoParser_ErrorX3( DaoParser *self, int code, int m )
{
DaoParser_ErrorX3( self, code, m );
DaoParser_Error3( self, code, m );
DaoParser_UpdateError( self );
}

Expand Down Expand Up @@ -274,7 +274,7 @@ static int DaoParser_MakeMacroGroup( DaoParser *self, DMacroGroup *group, DMacro
DNode *it;

/*
for( i=from; i<to; i++ ) printf( "%s ", toks[i]->chars ); printf("\n");
for( i=from; i<to; i++ ) printf( "%s ", toks[i]->string.chars ); printf("\n");
*/

i = from;
Expand Down Expand Up @@ -356,6 +356,10 @@ static int DaoParser_MakeMacroGroup( DaoParser *self, DMacroGroup *group, DMacro
unit->type = DMACRO_OP;
}else if( DString_FindChars( & tok->string, "BL", 0 ) == 1 ){
unit->type = DMACRO_BL;
}else if( strcmp( chs, "$STR" ) == 0 ){
unit->type = DMACRO_STR;
}else if( strcmp( chs, "$CAT" ) == 0 ){
unit->type = DMACRO_CAT;
}else{
DaoParser_ErrorX( self, DAO_CTW_INV_MAC_SPECTOK, & tok->string );
return 0;
Expand Down Expand Up @@ -891,20 +895,21 @@ static int DaoParser_MacroApply( DaoParser *self, DList *tokens,
int level, DString *tag, int pos0, int adjust )
{
DMacroUnit **units = (DMacroUnit**) group->units->items.pVoid;
DMacroUnit *unit;
DMacroUnit *unit, *strUnit;
DMacroGroup *grp;
DMacroNode *node, *node2;
DList *toks = DList_New( DAO_DATA_TOKEN );
DaoToken *tk = DaoToken_New();
DaoToken *literal = NULL;
DaoToken *tt = NULL;
DNode *kwnode = NULL;
DMap *check = NULL;
DMap one = { NULL, 0, 0, 0 };
int M, N = group->units->size;
int i, j, gid = -1;
int i, j, k, l, gid = -1;
int repeated = 0;
int start_mbs = -1;
int start_wcs = -1;
int prevLine = -1;
int prevEnd = -1;

if( group->repeat != DMACRO_AUTO ) level ++;

Expand All @@ -917,10 +922,12 @@ static int DaoParser_MacroApply( DaoParser *self, DList *tokens,
*/
switch( unit->type ){
case DMACRO_TOK :
repeated = 1;
DList_Append( tokens, unit->marker );
tokens->items.pToken[ tokens->size-1 ]->cpos += adjust;
break;
case DMACRO_VAR :
repeated = 1;
DaoToken_Assign( tk, unit->marker );
DString_Append( & tk->string, tag );
DList_Append( tokens, tk );
Expand Down Expand Up @@ -982,14 +989,14 @@ static int DaoParser_MacroApply( DaoParser *self, DList *tokens,
break;
case DMACRO_ZERO_OR_ONE :
gid = i;
repeated = (j>0);
repeated = 1;
if( j >=0 ){
DList_InsertList( tokens, tokens->size, toks, 0, -1 );
}
break;
case DMACRO_ZERO_OR_MORE :
gid = i;
repeated = (j>0);
repeated = 1;
if( j >=0 ){
DList_InsertList( tokens, tokens->size, toks, 0, -1 );
}
Expand Down Expand Up @@ -1019,6 +1026,148 @@ static int DaoParser_MacroApply( DaoParser *self, DList *tokens,
break;
}
break;
case DMACRO_STR:
++i;
if( tokens->size >0 ) pos0 = tokens->items.pToken[ tokens->size -1 ]->line;
self->curLine = pos0;
if(units[i]->type != DMACRO_GRP)
{
goto Failed;
}
literal = DaoToken_New();
literal->type = literal->name = DTOK_WCS;
DString_AppendChar( &literal->string, '\"' );
grp = (DMacroGroup*) units[i];
for(j = 0; j < grp->units->size; ++j)
{
strUnit = ((DMacroUnit**)grp->units->items.pVoid)[j];
//printf( ">>>\n%s level %i: \n", strUnit->marker->string.chars, level );
switch(strUnit->type)
{
case DMACRO_EXP :
case DMACRO_ID :
case DMACRO_OP :
case DMACRO_BL :
kwnode = MAP_Find( tokMap, &strUnit->marker->string );
if( kwnode ==NULL ){
DaoParser_ErrorX( self, DAO_CTW_UNDEF_MAC_MARKER, & strUnit->marker->string );
goto Failed;
}
node = (DMacroNode*) kwnode->value.pVoid;
kwnode = MAP_Find( used, strUnit );
if( kwnode == NULL ){
DMap_Insert( used, strUnit, & one );
kwnode = MAP_Find( used, strUnit );
}
check = (DMap*) kwnode->value.pVoid;
repeated = 1;

node2 = DMacroNode_FindLeaf( node, check, level );
if( node2 ){
for(k = 0; k < node2->leaves->size; ++k)
{
tt = node2->leaves->items.pToken[k];
if(k != 0)
{
if(tt->line != prevLine)
{
for(l = 0; l < tt->line - prevLine; ++l)
{
DString_AppendChar(&literal->string, '\n');
}
for(l = 0; l < tt->cpos; ++l)
{
DString_AppendChar(&literal->string, ' ');
}
}
else
{
for(l = 0; l < tt->cpos - prevEnd; ++l)
{
DString_AppendChar(&literal->string, ' ');
}
}
}
DString_AppendChars( &literal->string, tt->string.chars );
prevLine = tt->line;
prevEnd = tt->cpos + tt->string.size;
}
DMap_Insert( check, node2, NULL );
}else{
DMacroNode_RemoveEmptyLeftBranch( node, level );
goto Failed;
}
break;
default:
repeated = 0;
break;
}
}
DString_AppendChar( &literal->string, '\"' );
DList_Append( tokens, literal );

DaoToken_Delete(literal);
break;
case DMACRO_CAT:
++i;
if( tokens->size >0 ) pos0 = tokens->items.pToken[ tokens->size -1 ]->line;
self->curLine = pos0;
if(units[i]->type != DMACRO_GRP)
{
goto Failed;
}
literal = DaoToken_New();
literal->type = literal->name = DTOK_IDENTIFIER;
grp = (DMacroGroup*) units[i];
for(j = 0; j < grp->units->size; ++j)
{
strUnit = ((DMacroUnit**)grp->units->items.pVoid)[j];
switch(strUnit->type)
{
case DMACRO_TOK :
repeated = 1;
DString_AppendChars(&literal->string, strUnit->marker->string.chars );
break;
case DMACRO_EXP :
case DMACRO_ID :
case DMACRO_OP :
case DMACRO_BL :
kwnode = MAP_Find( tokMap, &strUnit->marker->string );
if( kwnode ==NULL ){
DaoParser_ErrorX( self, DAO_CTW_UNDEF_MAC_MARKER, & strUnit->marker->string );
goto Failed;
}
node = (DMacroNode*) kwnode->value.pVoid;
kwnode = MAP_Find( used, strUnit );
if( kwnode == NULL ){
DMap_Insert( used, strUnit, & one );
kwnode = MAP_Find( used, strUnit );
}
check = (DMap*) kwnode->value.pVoid;
repeated = 1;

node2 = DMacroNode_FindLeaf( node, check, level );
if( node2 ){
for(k = 0; k < node2->leaves->size; ++k)
{
tt = node2->leaves->items.pToken[k];
DString_AppendChars( &literal->string, tt->string.chars );
}
DMap_Insert( check, node2, NULL );
}else{
DMacroNode_RemoveEmptyLeftBranch( node, level );
goto Failed;
}
break;
default:
repeated = 0;
break;
}
}
DList_Append( tokens, literal );

DaoToken_Delete(literal);
break;
default : goto Failed;
}
if( group->type == DMACRO_ALT && gid >=0 ) break;
Expand Down Expand Up @@ -1429,7 +1578,7 @@ int DaoMacro_Preprocess( DaoParser *self )
}else if( tki == DKEY_USE && tki2 == DKEY_SYNTAX ){
if( DaoParser_CheckNameToken( self, start+1, to, DAO_INVALID_STATEMENT, start ) ==0 ) return -1;
DaoNamespace_ImportMacro( ns, & tokens[start+1]->string );
DList_Erase( self->tokens, start, end-start+1 );
DList_Erase( self->tokens, start, 3 );
tokens = self->tokens->items.pToken;
}else{
start ++;
Expand Down
4 changes: 3 additions & 1 deletion modules/macro/dao_macro.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,9 @@ enum DMacroUnitTypes
DMACRO_OP , /* $OP prefixed identifier: operator token */
DMACRO_BL , /* $BL prefixed identifier: code block tokens */
DMACRO_GRP , /* ( ... ) */
DMACRO_ALT /* ( ... | ... ) */
DMACRO_ALT , /* ( ... | ... ) */
DMACRO_STR , /* $STR identifier: stringify token */
DMACRO_CAT /* $CAT identifier: concatenate tokens */
};

enum DaoMacroGroupRepeatTypes
Expand Down