summaryrefslogtreecommitdiff
path: root/compiler_and_linker/unsorted/CFunc.c
diff options
context:
space:
mode:
authorAsh Wolf <ninji@wuffs.org>2023-01-26 11:30:47 +0000
committerAsh Wolf <ninji@wuffs.org>2023-01-26 11:30:47 +0000
commit094b96ca1df4a035b5f93c351f773306c0241f3f (patch)
tree95ce05e3ebe816c7ee7996206bb37ea17d8ca33c /compiler_and_linker/unsorted/CFunc.c
parentfc0c4c0df7b583b55a08317cf1ef6a71d27c0440 (diff)
downloadMWCC-094b96ca1df4a035b5f93c351f773306c0241f3f.tar.gz
MWCC-094b96ca1df4a035b5f93c351f773306c0241f3f.zip
move lots of source files around to match their actual placement in the original treemain
Diffstat (limited to 'compiler_and_linker/unsorted/CFunc.c')
-rw-r--r--compiler_and_linker/unsorted/CFunc.c3224
1 files changed, 0 insertions, 3224 deletions
diff --git a/compiler_and_linker/unsorted/CFunc.c b/compiler_and_linker/unsorted/CFunc.c
deleted file mode 100644
index 38cfab3..0000000
--- a/compiler_and_linker/unsorted/CFunc.c
+++ /dev/null
@@ -1,3224 +0,0 @@
-#include "compiler/CFunc.h"
-#include "compiler/CABI.h"
-#include "compiler/CClass.h"
-#include "compiler/CDecl.h"
-#include "compiler/CError.h"
-#include "compiler/CException.h"
-#include "compiler/CExpr.h"
-#include "compiler/CInit.h"
-#include "compiler/CInline.h"
-#include "compiler/CInt64.h"
-#include "compiler/CMachine.h"
-#include "compiler/CMangler.h"
-#include "compiler/CParser.h"
-#include "compiler/CPrepTokenizer.h"
-#include "compiler/CSOM.h"
-#include "compiler/CTemplateTools.h"
-#include "compiler/CodeGen.h"
-#include "compiler/CompilerTools.h"
-#include "compiler/Exceptions.h"
-#include "compiler/FuncLevelAsmPPC.h"
-#include "compiler/InlineAsmPPC.h"
-#include "compiler/ObjGenMachO.h"
-#include "compiler/Switch.h"
-#include "compiler/objects.h"
-#include "compiler/scopes.h"
-#include "compiler/types.h"
-
-#ifdef __MWERKS__
-#pragma options align=mac68k
-#endif
-struct CFuncSave {
- CScopeSave scope;
- ObjectList *arguments;
- ObjectList *locals;
- CLabel *labels;
- Statement *curstmt;
- DeclBlock *firstblock;
- DeclBlock *currentblock;
- ExceptionAction *cexcept_dobjstack;
- CLabel *sinit_label;
- ENode *ainit_expr;
- CtorChain *ctor_chain;
- ParserTryBlock *trychain;
- TempNodeCB cinit_tempnodefunc;
- HashNameNode *tkidentifier;
- Object *sinit_first_object;
- FileOffsetInfo cparser_fileoffset;
- TStreamElement symdecltoken;
- SInt32 functionbodyoffset;
- HashNameNode *functionbodypath;
- SInt32 symdecloffset;
- SInt32 symdeclend;
- SInt32 sourceoffset;
- HashNameNode *sourcefilepath;
- SInt32 curstmtvalue;
- NameObjCheckCB name_obj_check;
- FuncArg *check_arglist;
- short blockcount;
- short localcount;
- short tk;
- AccessType global_access;
- Boolean cexcept_hasdobjects;
- Boolean ainit_only_one;
- Boolean cfunc_is_extern_c;
- Boolean temp_reference_init;
-};
-#ifdef __MWERKS__
-#pragma options align=reset
-#endif
-
-FuncArg elipsis;
-FuncArg oldstyle;
-ObjectList *arguments;
-ObjectList *locals;
-short localcount;
-SInt32 curstmtvalue;
-SInt32 sourceoffset;
-HashNameNode *sourcefilepath;
-SInt32 functionbodyoffset;
-HashNameNode *functionbodypath;
-InitExpr *init_expressions;
-CLabel *Labels;
-CtorChain *ctor_chain;
-Statement *curstmt;
-static short temp_destructor_object_regmem;
-static short temp_destructor_objects;
-static short temp_expression_has_conditionals;
-static DeclBlock *firstblock;
-static DeclBlock *currentblock;
-static short blockcount;
-static Object *sinit_first_object;
-static CLabel *sinit_label;
-static Boolean ainit_only_one;
-static ENode *ainit_expr;
-static FuncArg *check_arglist;
-static Boolean cfunc_is_extern_c;
-static short cfunc_staticvarcount;
-static void *destroyobjects;
-static Boolean cfunc_hasdtortemp;
-
-// forward decls
-static void statement(DeclThing *thing);
-
-static void CFunc_LoopIncrement(void) {
- if (curstmtvalue >= 0x1000) {
- if (curstmtvalue >= 0xF000)
- curstmtvalue++;
- else
- curstmtvalue += 0x1000;
- } else {
- curstmtvalue <<= 3;
- }
-}
-
-static void CFunc_LoopDecrement(void) {
- if (curstmtvalue > 0x1000) {
- if (curstmtvalue > 0xF000)
- curstmtvalue--;
- else
- curstmtvalue -= 0x1000;
- } else {
- curstmtvalue >>= 3;
- }
-
- if (curstmtvalue < 1)
- curstmtvalue = 1;
-}
-
-DeclBlock *CFunc_NewDeclBlock(void) {
- DeclBlock *block;
- NameSpace *nspace;
-
- block = lalloc(sizeof(DeclBlock));
- if (firstblock) {
- currentblock->next = block;
- currentblock = block;
- } else {
- firstblock = block;
- currentblock = block;
- }
-
- block->index = blockcount++;
- block->parent_nspace = cscope_current;
- block->dobjstack = cexcept_dobjstack;
-
- nspace = CScope_NewListNameSpace(NULL, 0);
- nspace->parent = cscope_current;
- cscope_current = nspace;
-
- return block;
-}
-
-void CFunc_RestoreBlock(DeclBlock *block) {
- if (curstmt && curstmt->dobjstack != cexcept_dobjstack) {
- Statement *stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = nullnode();
- }
-
- cscope_current = block->parent_nspace;
- cexcept_dobjstack = block->dobjstack;
-}
-
-void CFunc_SetupLocalVarInfo(Object *obj) {
- obj->u.var.info = CodeGen_GetNewVarInfo();
- obj->u.var.info->func = cscope_currentfunc;
-
- if (obj->sclass == TK_REGISTER) {
- if (!copts.optimizesize)
- obj->u.var.info->usage = 100;
- else
- obj->u.var.info->usage = 5;
- }
-
- if (obj->type && is_volatile_object(obj))
- obj->u.var.info->noregister = 1;
-}
-
-static void adjustargumenttype(DeclInfo *declinfo) {
- switch (declinfo->thetype->type) {
- case TYPECLASS:
- if (TYPE_CLASS(declinfo->thetype)->sominfo) {
- CError_Error(CErrorStr284);
- declinfo->thetype = TYPE(&stsignedint);
- }
- break;
- case TYPEFUNC:
- makethetypepointer(declinfo, 0);
- return;
- case TYPEARRAY:
- declinfo->thetype = CDecl_NewPointerType(TPTR_TARGET(declinfo->thetype));
- return;
- case TYPETEMPLATE:
- if (TYPE_TEMPLATE(declinfo->thetype)->dtype == TEMPLDEP_ARRAY)
- declinfo->thetype = CDecl_NewPointerType(TYPE_TEMPLATE(declinfo->thetype)->u.array.type);
- return;
- }
-
- if (!CanCreateObject(declinfo->thetype))
- declinfo->thetype = TYPE(&stsignedint);
-}
-
-static FuncArg *CFunc_IsInArgList(FuncArg *list, HashNameNode *name) {
- while (list) {
- if (name == list->name)
- return list;
- list = list->next;
- }
-
- return NULL;
-}
-
-static Object *CFunc_IsInObjList(ObjectList *list, HashNameNode *name) {
- while (list) {
- if (name == list->object->name)
- return list->object;
- list = list->next;
- }
-
- return NULL;
-}
-
-static void CFunc_AppendArg(FuncArg **list, FuncArg *arg) {
- FuncArg *tail;
-
- if ((tail = *list)) {
- while (tail->next)
- tail = tail->next;
- tail->next = arg;
- } else {
- *list = arg;
- }
-}
-
-static void identifier_list(DeclInfo *declinfo) {
- FuncArg *arg;
-
- declinfo->x45 = 1;
-
- while (1) {
- if (tk != TK_IDENTIFIER) {
- CError_Error(CErrorStr121);
- } else {
- if (CFunc_IsInArgList(declinfo->x18, tkidentifier))
- CError_Error(CErrorStr122, tkidentifier->name);
-
- arg = CParser_NewFuncArg();
- arg->name = tkidentifier;
- CFunc_AppendArg(&declinfo->x18, arg);
- declinfo->x44 = 1;
- }
-
- if ((tk = lex()) != ',')
- break;
- tk = lex();
- }
-}
-
-static Boolean defarg_name_obj_check(HashNameNode *name, Object *obj) {
- FuncArg *arg;
-
- if (name) {
- for (arg = check_arglist; arg; arg = arg->next) {
- if (arg->name == name) {
- CError_Error(CErrorStr205);
- return 0;
- }
- }
- }
-
- if (obj && obj->datatype == DLOCAL) {
- CError_Error(CErrorStr205);
- return 0;
- }
-
- return 1;
-}
-
-ENode *CFunc_DefaultArg(Type *type, UInt32 qual, FuncArg *args) {
- TStreamElement *element;
- ENode *expr;
- ENode *templdepexpr;
-
- name_obj_check = defarg_name_obj_check;
- check_arglist = args;
- expr = conv_assignment_expression();
- name_obj_check = NULL;
-
- if (
- !CTemplTool_IsTemplateArgumentDependentExpression(expr) &&
- !CTemplTool_IsTemplateArgumentDependentType(type)
- )
- {
- expr = argumentpromotion(expr, type, qual, 1);
- } else {
- element = CPrep_CurStreamElement();
- if (element && element->tokenfile) {
- templdepexpr = CExpr_NewTemplDepENode(TDE_SOURCEREF);
- templdepexpr->data.templdep.u.sourceref.expr = expr;
- templdepexpr->data.templdep.u.sourceref.token = galloc(sizeof(TStreamElement));
- *templdepexpr->data.templdep.u.sourceref.token = *element;
- expr = templdepexpr;
- }
- }
-
- return CInline_CopyExpression(expr, CopyMode1);
-}
-
-static FuncArg *parameter_list(DeclInfo *declinfo) {
- Boolean flag26;
- FuncArg *args;
- FuncArg *arg;
- DeclInfo my_di;
- Boolean isArray;
-
- args = NULL;
- flag26 = 1;
-
- while (1) {
- if (tk == TK_ELLIPSIS) {
- if (flag26) {
- if (!copts.cplusplus && copts.ANSIstrict)
- CError_Warning(CErrorStr127);
- args = &elipsis;
- } else {
- CFunc_AppendArg(&args, &elipsis);
- }
-
- tk = lex();
- return args;
- }
-
- memclrw(&my_di, sizeof(my_di));
- CParser_GetDeclSpecs(&my_di, 0);
- if (my_di.x48)
- CError_Error(CErrorStr127);
-
- if (
- my_di.storageclass &&
- my_di.storageclass != TK_REGISTER &&
- (!copts.cplusplus || my_di.storageclass != TK_AUTO)
- )
- {
- CError_Error(CErrorStr127);
- my_di.storageclass = 0;
- }
-
- my_di.name = NULL;
-
- scandeclarator(&my_di);
-
- if (flag26) {
- flag26 = 0;
- if (my_di.thetype == &stvoid) {
- if (my_di.storageclass || my_di.qual || my_di.name)
- CError_Error(CErrorStr127);
- return NULL;
- }
- }
-
- isArray = IS_TYPE_ARRAY(my_di.thetype);
- adjustargumenttype(&my_di);
-
- if (my_di.name) {
- if (args && CFunc_IsInArgList(args, my_di.name))
- CError_Error(CErrorStr122, my_di.name->name);
- } else {
- my_di.name = no_name_node;
- }
-
- if (my_di.thetype == &stvoid)
- CError_Error(CErrorStr126);
-
- arg = CParser_NewFuncArg();
- arg->name = my_di.name;
- arg->type = my_di.thetype;
- arg->qual = my_di.qual;
- arg->sclass = my_di.storageclass;
- arg->is_array = isArray;
- CFunc_AppendArg(&args, arg);
-
- if (copts.cplusplus && tk == '=') {
- tk = lex();
- arg->dexpr = CFunc_DefaultArg(arg->type, arg->qual, args);
- }
-
- if (tk != ',') {
- if (tk != TK_ELLIPSIS || !copts.cplusplus)
- return args;
- } else {
- tk = lex();
- }
- }
-}
-
-Boolean CFunc_ParseFakeArgList(Boolean flag) {
- DeclInfo di;
-
- if (tk == TK_ELLIPSIS)
- return 1;
-
- do {
- memclrw(&di, sizeof(di));
- CParser_GetDeclSpecs(&di, 0);
-
- if (di.x48)
- return 0;
-
- scandeclarator(&di);
-
- if (tk == '=') {
- tk = lex();
- assignment_expression();
- }
-
- switch (tk) {
- case TK_ELLIPSIS:
- return 1;
- case ',':
- if (!flag)
- tk = lex();
- else
- return 1;
- break;
- default:
- return 0;
- }
- } while (tk != TK_ELLIPSIS);
-
- return 1;
-}
-
-FuncArg *parameter_type_list(DeclInfo *declinfo) {
- FuncArg *args;
- NameSpace *nspace;
- Boolean save_in_func_arglist;
-
- declinfo->x44 = 0;
- declinfo->x45 = 0;
- declinfo->x1C = NULL;
-
- if (tk == TK_ELLIPSIS || isdeclaration(0, 0, 0, 0)) {
- if (!copts.cplusplus) {
- nspace = CScope_NewListNameSpace(NULL, 0);
- nspace->parent = cscope_current;
- cscope_current = nspace;
-
- save_in_func_arglist = in_func_arglist;
- in_func_arglist = 1;
- args = parameter_list(declinfo);
- in_func_arglist = save_in_func_arglist;
-
- cscope_current = nspace->parent;
-
- if (!CScope_IsEmptyNameSpace(nspace))
- declinfo->x1C = nspace;
- } else {
- args = parameter_list(declinfo);
- }
- } else if (copts.cplusplus) {
- args = NULL;
- if (tk != ')')
- CError_Error(CErrorStr127);
- } else {
- identifier_list(declinfo);
- args = &oldstyle;
- }
-
- return args;
-}
-
-CLabel *findlabel(void) {
- CLabel *scan;
-
- for (scan = Labels; scan; scan = scan->next) {
- if (tkidentifier == scan->name)
- return scan;
- }
-
- return NULL;
-}
-
-CLabel *newlabel(void) {
- CLabel *label = lalloc(sizeof(CLabel));
- memclrw(label, sizeof(CLabel));
-
- label->name = label->uniquename = CParser_GetUniqueName();
- return label;
-}
-
-Statement *CFunc_AppendStatement(StatementType sttype) {
- Statement *stmt = lalloc(sizeof(Statement));
-
- stmt->next = NULL;
- stmt->type = sttype;
- stmt->value = curstmtvalue;
- stmt->flags = 0;
- stmt->sourceoffset = sourceoffset;
- stmt->sourcefilepath = sourcefilepath;
- stmt->dobjstack = cexcept_dobjstack;
-
- curstmt->next = stmt;
- curstmt = stmt;
- return stmt;
-}
-
-Statement *CFunc_InsertStatement(StatementType sttype, Statement *after) {
- Statement *stmt = lalloc(sizeof(Statement));
-
- stmt->next = after->next;
- after->next = stmt;
- stmt->type = sttype;
- stmt->value = after->value;
- stmt->flags = 0;
- stmt->sourceoffset = after->sourceoffset;
- stmt->sourcefilepath = after->sourcefilepath;
- stmt->dobjstack = after->dobjstack;
-
- return stmt;
-}
-
-Statement *CFunc_InsertBeforeStatement(StatementType sttype, Statement *before) {
- Statement *stmt = lalloc(sizeof(Statement));
-
- *stmt = *before;
- before->next = stmt;
- before->type = sttype;
- before->flags = 0;
-
- return before;
-}
-
-void CheckCLabels(void) {
- CLabel *scan;
-
- for (scan = Labels; scan; scan = scan->next) {
- if (!scan->stmt)
- CError_Error(CErrorStr159, scan->name->name);
- }
-}
-
-Object *create_temp_object(Type *type) {
- Object *object = CParser_NewLocalDataObject(NULL, 1);
- object->name = CParser_GetUniqueName();
- object->type = type;
- CFunc_SetupLocalVarInfo(object);
- return object;
-}
-
-ENode *create_temp_node(Type *type) {
- ENode *node;
-
- if (cinit_tempnodefunc)
- return cinit_tempnodefunc(type, 0);
-
- node = CExpr_NewETEMPNode(type, 0);
- if (IS_TYPE_CLASS(type) && CClass_Destructor(TYPE_CLASS(type)))
- node->data.temp.needs_dtor = 1;
- return node;
-}
-
-ENode *create_temp_node2(Type *type) {
- ENode *node;
-
- if (cinit_tempnodefunc)
- return cinit_tempnodefunc(type, 1);
-
- node = CExpr_NewETEMPNode(type, 0);
- node->data.temp.needs_dtor = 1;
- return node;
-}
-
-static ENode *CFunc_DestroyReverse(ENode *expr, DtorTemp *list) {
- expr = makediadicnode(expr, CABI_DestroyObject(list->dtor, create_objectrefnode(list->object), CABIDestroy1, 1, 0), ECOMMA);
- expr->rtype = &stvoid;
- if (list->next)
- expr = CFunc_DestroyReverse(expr, list->next);
- return expr;
-}
-
-static ENode *CFunc_TempTransDestroy(ENode *expr, DtorTemp *list, Boolean flag) {
- Object *tempobj;
-
- if (flag) {
- CError_ASSERT(738, !(IS_TYPE_CLASS(expr->rtype) && CClass_Destructor(TYPE_CLASS(expr->rtype))));
- tempobj = create_temp_object(expr->rtype);
- expr = makediadicnode(create_objectnode(tempobj), expr, EASS);
- }
-
- expr = CFunc_DestroyReverse(expr, list);
-
- if (flag) {
- expr = makediadicnode(expr, create_objectnode(tempobj), ECOMMA);
- expr->rtype = tempobj->type;
- }
-
- return expr;
-}
-
-void CFunc_WarnUnused(void) {
- if (copts.warn_unusedvar) {
- ObjectList *list;
- for (list = locals; list; list = list->next) {
- if (
- !(list->object->flags & OBJECT_USED) &&
- !IsTempName(list->object->name) &&
- !(list->object->qual & Q_INLINE_DATA)
- )
- {
- CError_SetErrorToken(&list->object->u.var.info->deftoken);
- CError_Warning(CErrorStr182, &list->object->name->name);
- }
- }
- }
-
- if (copts.warn_unusedarg) {
- ObjectList *list;
- for (list = arguments; list; list = list->next) {
- if (
- !(list->object->flags & OBJECT_USED) &&
- !IsTempName(list->object->name) &&
- list->object->name != this_name_node &&
- list->object->name != self_name_node
- )
- {
- CError_SetErrorToken(&symdecltoken);
- CError_Warning(CErrorStr182, &list->object->name->name);
- }
- }
- }
-}
-
-void CFunc_CodeCleanup(Statement *stmt) {
- if (cscope_currentclass && cscope_currentclass->sominfo)
- CSOM_InitSOMSelf(cscope_currentclass, stmt);
-
- CFunc_WarnUnused();
- CExcept_ExceptionTansform(stmt);
-}
-
-static Boolean DestructorNeeded(ExceptionAction *ea, ExceptionAction *end) {
- while (ea) {
- if (CExcept_ActionNeedsDestruction(ea))
- return 1;
- if (ea == end)
- break;
- ea = ea->prev;
- }
-
- return 0;
-}
-
-static Statement *DestructLocals(Statement *stmt, ExceptionAction *ea, ExceptionAction *end) {
- while (ea) {
- stmt = CExcept_ActionCleanup(ea, stmt);
- if (ea == end)
- break;
- ea = ea->prev;
- }
-
- return stmt;
-}
-
-static Boolean NeedsDestruction(Statement *stmt1, Statement *stmt2) {
- ExceptionAction *ea2;
- ExceptionAction *ea1;
- ExceptionAction *scan;
-
- ea1 = stmt1->dobjstack;
- ea2 = stmt2->dobjstack;
-
- for (scan = ea2; scan; scan = scan->prev) {
- if (scan == ea1)
- return 0;
- }
-
- while (ea1 && ea1 != ea2) {
- if (CExcept_ActionNeedsDestruction(ea1))
- return 1;
- ea1 = ea1->prev;
- }
-
- return 0;
-}
-
-static ExceptionAction *FindLastNonCommonStackObj(Statement *stmt1, Statement *stmt2) {
- ExceptionAction *ea1;
- ExceptionAction *ea2;
-
- for (ea2 = stmt2->dobjstack; ea2; ea2 = ea2->prev) {
- for (ea1 = stmt1->dobjstack; ea1; ea1 = ea1->prev) {
- if (ea1->prev == ea2)
- return ea1;
- }
- }
-
- return NULL;
-}
-
-static void DestructorReturnTransform(Statement *stmt1, Statement *stmt2) {
- Statement *stmt;
- Object *tempobj;
-
- if (stmt1->dobjstack != stmt2->dobjstack && NeedsDestruction(stmt1, stmt2))
- stmt1 = DestructLocals(stmt1, stmt1->dobjstack, FindLastNonCommonStackObj(stmt1, stmt2));
-
- if (DestructorNeeded(stmt2->dobjstack, NULL)) {
- if (CMach_GetFunctionResultClass(TYPE_FUNC(cscope_currentfunc->type)) != 1) {
- tempobj = create_temp_object(stmt2->expr->rtype);
- stmt = CFunc_InsertStatement(ST_EXPRESSION, stmt1);
- stmt->expr = makediadicnode(create_objectnode(tempobj), stmt2->expr, EASS);
- stmt->sourceoffset = stmt2->sourceoffset;
- stmt->sourcefilepath = stmt2->sourcefilepath;
- DestructLocals(stmt, stmt2->dobjstack, NULL);
- stmt2->expr = create_objectnode(tempobj);
- } else {
- stmt = CFunc_InsertStatement(ST_EXPRESSION, stmt1);
- stmt->expr = stmt2->expr;
- stmt->sourceoffset = stmt2->sourceoffset;
- stmt->sourcefilepath = stmt2->sourcefilepath;
- DestructLocals(stmt, stmt2->dobjstack, NULL);
- stmt2->expr = nullnode();
- }
- }
-}
-
-static Statement *DestructorIfTransform(Statement *stmt) {
- CLabel *label;
- Statement *newStmt;
-
- if (stmt->type == ST_IFGOTO)
- stmt->type = ST_IFNGOTO;
- else
- stmt->type = ST_IFGOTO;
-
- label = newlabel();
- newStmt = DestructLocals(stmt, stmt->dobjstack, FindLastNonCommonStackObj(stmt, stmt->label->stmt));
- newStmt = CFunc_InsertStatement(ST_GOTO, newStmt);
- newStmt->label = stmt->label;
- newStmt = CFunc_InsertStatement(ST_LABEL, newStmt);
- newStmt->label = label;
- label->stmt = newStmt;
- stmt->label = label;
- newStmt->dobjstack = stmt->dobjstack;
- return newStmt;
-}
-
-static Boolean IsSubStack(ExceptionAction *exc1, ExceptionAction *exc2) {
- if (!exc1)
- return 1;
-
- while (exc2) {
- if (exc2 == exc1)
- return 1;
- exc2 = exc2->prev;
- }
-
- return 0;
-}
-
-static void CFunc_CheckInitSkip(Statement *stmt, ExceptionAction *exc) {
- if (stmt->dobjstack != exc && !IsSubStack(exc, stmt->dobjstack)) {
- while (exc) {
- if (CExcept_ActionNeedsDestruction(exc) && exc->type != EAT_ACTIVECATCHBLOCK) {
- CError_Warning(CErrorStr211);
- break;
- }
- exc = exc->prev;
- }
- }
-}
-
-void CFunc_DestructorCleanup(Statement *stmt) {
- Statement *scan;
- Statement *next;
- SwitchCase *swcase;
-
- if (copts.cplusplus) {
- for (scan = stmt; scan; scan = scan->next) {
- switch (scan->type) {
- case ST_NOP:
- case ST_LABEL:
- case ST_EXPRESSION:
- case ST_RETURN:
- case ST_BEGINCATCH:
- case ST_ENDCATCH:
- case ST_ENDCATCHDTOR:
- case ST_GOTOEXPR:
- case ST_ASM:
- break;
- case ST_SWITCH:
- CFunc_CheckInitSkip(scan, ((SwitchInfo *) scan->label)->defaultlabel->stmt->dobjstack);
- for (swcase = ((SwitchInfo *) scan->label)->cases; swcase; swcase = swcase->next) {
- CFunc_CheckInitSkip(scan, swcase->label->stmt->dobjstack);
- }
- break;
- case ST_GOTO:
- case ST_IFGOTO:
- case ST_IFNGOTO:
- CFunc_CheckInitSkip(scan, scan->label->stmt->dobjstack);
- break;
- default:
- CError_FATAL(1045);
- }
- }
-
- if (cexcept_hasdobjects) {
- while (1) {
- next = stmt->next;
- if (!next) {
- if (stmt->type != ST_RETURN && stmt->dobjstack)
- DestructLocals(stmt, stmt->dobjstack, NULL);
- return;
- }
-
- switch (next->type) {
- case ST_GOTO:
- if (
- stmt->dobjstack != next->label->stmt->dobjstack &&
- NeedsDestruction(stmt, next->label->stmt)
- )
- {
- DestructLocals(stmt, stmt->dobjstack, FindLastNonCommonStackObj(stmt, next->label->stmt));
- }
- stmt = next;
- continue;
-
- case ST_RETURN:
- if (next->expr && DestructorNeeded(stmt->dobjstack, NULL)) {
- DestructorReturnTransform(stmt, next);
- } else if (stmt->dobjstack) {
- DestructLocals(stmt, stmt->dobjstack, NULL);
- }
- stmt = next;
- continue;
- }
-
- switch (stmt->type) {
- case ST_GOTO:
- case ST_SWITCH:
- case ST_RETURN:
- case ST_GOTOEXPR:
- break;
- case ST_NOP:
- case ST_LABEL:
- case ST_EXPRESSION:
- case ST_IFGOTO:
- case ST_IFNGOTO:
- case ST_BEGINCATCH:
- case ST_ENDCATCH:
- case ST_ENDCATCHDTOR:
- case ST_ASM:
- if (
- stmt->dobjstack != next->dobjstack &&
- NeedsDestruction(stmt, next)
- )
- {
- DestructLocals(stmt, stmt->dobjstack, FindLastNonCommonStackObj(stmt, next));
- }
- break;
- default:
- CError_FATAL(1109);
- }
-
- switch (next->type) {
- case ST_NOP:
- case ST_LABEL:
- case ST_EXPRESSION:
- case ST_SWITCH:
- case ST_BEGINCATCH:
- case ST_ENDCATCH:
- case ST_ENDCATCHDTOR:
- case ST_ASM:
- stmt = next;
- continue;
-
- case ST_IFGOTO:
- case ST_IFNGOTO:
- if (
- next->dobjstack != next->label->stmt->dobjstack &&
- NeedsDestruction(next, next->label->stmt)
- )
- {
- stmt = DestructorIfTransform(next);
- } else {
- stmt = next;
- }
- break;
-
- default:
- CError_FATAL(1138);
- }
- }
- }
- }
-}
-
-static void scancase(DeclThing *thing) {
- SwitchCase *swcase;
- Statement *stmt;
- CInt64 min;
- CInt64 max;
-
- if (!thing->switchinfo) {
- CError_Error(CErrorStr169);
- return;
- }
-
- tk = lex();
- min = CExpr_IntConstConvert(thing->switchinfo->x8, thing->switchinfo->x8, CExpr_IntegralConstExpr());
- if (!copts.ANSIstrict && tk == TK_ELLIPSIS) {
- tk = lex();
- max = CExpr_IntConstConvert(thing->switchinfo->x8, thing->switchinfo->x8, CExpr_IntegralConstExpr());
- if (CInt64_Greater(min, max))
- CError_Error(CErrorStr366);
- if (thing->switchinfo->x8->size == stsignedlonglong.size)
- CError_Error(CErrorStr368);
- } else {
- max = min;
- }
-
- for (swcase = thing->switchinfo->cases; swcase; swcase = swcase->next) {
- if (CInt64_GreaterEqual(swcase->min, min) && CInt64_LessEqual(swcase->min, max))
- CError_Error(CErrorStr172);
- if (CInt64_GreaterEqual(swcase->max, min) && CInt64_LessEqual(swcase->max, max))
- CError_Error(CErrorStr172);
- if (CInt64_Less(swcase->min, min) && CInt64_Greater(swcase->max, max))
- CError_Error(CErrorStr172);
- }
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = newlabel();
- stmt->label->stmt = stmt;
-
- swcase = lalloc(sizeof(SwitchCase));
- swcase->min = min;
- swcase->label = stmt->label;
- swcase->next = thing->switchinfo->cases;
- thing->switchinfo->cases = swcase;
- swcase->max = max;
-
- if (tk != ':')
- CError_ErrorSkip(CErrorStr170);
- else
- tk = lex();
-
- statement(thing);
-}
-
-static void CFunc_NameLocalStaticDataObject(Object *obj, char *str) {
- char buf[64];
- HashNameNode *name;
-
- if (!(cscope_currentfunc && (cscope_currentfunc->qual & Q_INLINE)) || CParser_HasInternalLinkage(cscope_currentfunc)) {
- obj->name = CParser_AppendUniqueName(str);
- } else {
- sprintf(buf, "$localstatic%" PRId32 "$", cfunc_staticvarcount++);
- name = CMangler_GetLinkName(cscope_currentfunc);
- name = CParser_NameConcat(buf, name->name);
- name = CParser_NameConcat(str, name->name);
- obj->name = name;
- obj->qual |= Q_20000;
- obj->sclass = 0;
- }
-}
-
-static void sinit_insert_expr(ENode *expr) {
- Statement *stmt;
-
- if (!sinit_first_object) {
- sinit_first_object = CParser_NewCompilerDefDataObject();
- sinit_first_object->type = TYPE(&stsignedchar);
- sinit_first_object->sclass = TK_STATIC;
- CFunc_NameLocalStaticDataObject(sinit_first_object, "init");
- CInit_DeclareData(sinit_first_object, NULL, NULL, sinit_first_object->type->size);
-
- sinit_label = newlabel();
- stmt = CFunc_AppendStatement(ST_IFGOTO);
- stmt->expr = create_objectnode(sinit_first_object);
- stmt->label = sinit_label;
- }
-
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = expr;
-}
-
-static void ainit_insert_expr(ENode *expr) {
- Statement *stmt;
-
- if (ainit_only_one) {
- if (ainit_expr) {
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = ainit_expr;
- }
- ainit_expr = expr;
- } else {
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = expr;
- }
-}
-
-static ENode *ainit_register_object(Type *type, Object *local, SInt32 offset, Boolean flag) {
- return CExcept_RegisterDestructorObject(local, offset, CClass_Destructor(TYPE_CLASS(type)), flag);
-}
-
-static void CFunc_LocalDataDeclarator(DeclInfo *di, TStreamElement *deftoken, Boolean flag1, Boolean flag2) {
- Object *object;
- Object *aliasObject;
- NameSpace *globalNS;
- NameSpaceObjectList *nsol;
- NameSpaceName *nsname;
- Statement *stmt;
-
- if (di->nspace)
- CError_Error(CErrorStr121);
-
- CDecl_CompleteType(di->thetype);
-
- object = NULL;
-
- if ((nsol = CScope_FindName(cscope_current, di->name))) {
- switch (nsol->object->otype) {
- case OT_OBJECT:
- object = OBJECT(nsol->object);
- break;
- case OT_NAMESPACE:
- CError_Error(CErrorStr321);
- return;
- case OT_ENUMCONST:
- case OT_TYPE:
- CError_Error(CErrorStr322);
- break;
- case OT_TYPETAG:
- break;
- default:
- CError_FATAL(1344);
- }
- }
-
- if (object)
- CError_Error(CErrorStr333, object);
-
- if (di->storageclass == TK_EXTERN) {
- object = NULL;
- globalNS = CScope_FindGlobalNS(cscope_current);
- if ((nsol = CScope_FindName(globalNS, di->name))) {
- switch (nsol->object->otype) {
- case OT_OBJECT:
- object = OBJECT(nsol->object);
- break;
- case OT_NAMESPACE:
- CError_Error(CErrorStr321);
- return;
- case OT_ENUMCONST:
- case OT_TYPE:
- CError_Error(CErrorStr322);
- break;
- case OT_TYPETAG:
- break;
- default:
- CError_FATAL(1381);
- }
- }
-
- if (object) {
- if (
- !is_typesame(di->thetype, object->type) ||
- (di->qual & (Q_CONST | Q_VOLATILE | Q_PASCAL | Q_20000 | Q_WEAK | Q_ALIGNED_MASK)) != (object->qual & (Q_CONST | Q_VOLATILE | Q_PASCAL | Q_20000 | Q_WEAK | Q_ALIGNED_MASK))
- )
- {
- CError_Error(CErrorStr249, di->name->name, object->type, object->qual, di->thetype, di->qual);
- }
- } else {
- object = CParser_NewGlobalDataObject(di);
- object->nspace = globalNS;
- }
-
- CParser_NewAliasObject(object, 0);
- return;
- }
-
- if (di->storageclass != TK_STATIC)
- object = CParser_NewObject(di);
- else
- object = CParser_NewGlobalDataObject(di);
-
- object->name = di->name;
- object->type = di->thetype;
- object->qual = di->qual;
- object->sclass = di->storageclass;
-
- switch (di->storageclass) {
- case TK_STATIC:
- if (flag1) {
- CError_Error(CErrorStr177);
- return;
- }
- if (flag2)
- CError_Error(CErrorStr174);
-
- if (CanCreateObject(di->thetype)) {
- CError_QualifierCheck(di->qual & ~(Q_CONST | Q_VOLATILE | Q_PASCAL | Q_20000 | Q_WEAK | Q_ALIGNED_MASK));
- CParser_NewAliasObject(object, 0);
- object->nspace = cscope_root;
- object->datatype = DDATA;
- CFunc_NameLocalStaticDataObject(object, object->name->name);
-
- if (copts.cplusplus) {
- sinit_first_object = NULL;
- CInit_InitializeStaticData(object, sinit_insert_expr);
- if (sinit_first_object) {
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = makediadicnode(
- create_objectnode(sinit_first_object),
- intconstnode(TYPE(&stsignedchar), 1),
- EASS);
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = sinit_label;
- sinit_label->stmt = stmt;
- }
- } else {
- CInit_InitializeData(object);
- }
- }
- break;
-
- case 0:
- case TK_AUTO:
- case TK_REGISTER:
- if (CanCreateObject(di->thetype)) {
- CError_QualifierCheck(di->qual & ~(Q_CONST | Q_VOLATILE | Q_PASCAL | Q_ALIGNED_MASK));
- object->datatype = DLOCAL;
- CFunc_SetupLocalVarInfo(object);
-
- object->u.var.info->deftoken = *deftoken;
- if (object->sclass == TK_REGISTER && flag1)
- object->u.var.info->usage = 100;
-
- CScope_AddObject(cscope_current, object->name, OBJ_BASE(object));
-
- if (!flag1) {
- if (IS_TYPE_SOM_CLASS(di->thetype)) {
- CSOM_InitAutoClass(object);
- } else {
- CInit_InitializeAutoData(object, ainit_insert_expr, ainit_register_object);
- if (object->type != di->thetype && (IS_TYPE_STRUCT(object->type) || IS_TYPE_CLASS(object->type))) {
- CError_ASSERT(1478, !cscope_current->is_hash);
- CError_ASSERT(1479, nsname = CScope_FindNameSpaceName(cscope_current, object->name));
- CError_ASSERT(1480, nsname->first.object == OBJ_BASE(object));
- CError_ASSERT(1481, !nsname->first.next);
- nsname->name = CParser_AppendUniqueName(object->name->name);
-
- aliasObject = CParser_NewAliasObject(object, 0);
- aliasObject->type = di->thetype;
- }
- }
- }
-
- if (object->datatype == DLOCAL) {
- ObjectList *list = lalloc(sizeof(ObjectList));
- list->object = object;
- list->next = locals;
- locals = list;
- }
-
- IsCompleteType(di->thetype);
- }
- break;
-
- default:
- CError_FATAL(1504);
- }
-}
-
-static ENode *CFunc_ParseLocalDeclarationList(Boolean flag1, Boolean flag2, Boolean flag3, Boolean flag4) {
- Type *type;
- UInt32 qual;
- DeclInfo di;
- TStreamElement deftoken;
-
- ainit_expr = NULL;
- ainit_only_one = flag2;
-
- while (flag2 || isdeclaration(copts.cplusplus, 0, 0, 0)) {
- CPrep_GetFileOffsetInfo2(&cparser_fileoffset, &sourceoffset, &sourcefilepath);
-
- memclrw(&di, sizeof(di));
- di.is_extern_c = cfunc_is_extern_c;
- CParser_GetDeclSpecs(&di, 0);
-
- if (IS_TYPE_TEMPLATE(di.thetype)) {
- CError_Error(CErrorStr146);
- di.thetype = TYPE(&stsignedint);
- }
-
- type = di.thetype;
- qual = di.qual;
-
- if (tk != ';') {
- while (1) {
- deftoken = *CPrep_CurStreamElement();
- di.name = NULL;
- scandeclarator(&di);
-
- if (di.name) {
- if (di.storageclass != TK_TYPEDEF) {
- if (IS_TYPE_FUNC(di.thetype)) {
- if (!CDecl_FunctionDeclarator(&di, CScope_FindGlobalNS(cscope_current), 0, 0))
- break;
- } else {
- CFunc_LocalDataDeclarator(&di, &deftoken, flag1, flag2);
- }
- } else {
- CDecl_TypedefDeclarator(&di);
- }
- } else {
- CError_Error(CErrorStr134);
- }
-
- if (tk == ';')
- break;
-
- if (tk != ',') {
- if (!flag2)
- CError_Error(CErrorStr123);
- break;
- }
-
- di.nspace = NULL;
- di.thetype = type;
- di.qual = qual;
- tk = lex();
- }
- } else {
- CParser_CheckAnonymousUnion(&di, 1);
- }
-
- if (flag2)
- break;
- if (flag4)
- break;
- tk = lex();
- }
-
- if (flag2) {
- if (!ainit_expr) {
- if (!flag3) {
- CError_Error(CErrorStr141);
- ainit_expr = nullnode();
- }
- } else {
- ainit_expr = checkreference(ainit_expr);
- }
- }
-
- return ainit_expr;
-}
-
-static void makeifstatement(ENode *expr, CLabel *label1, CLabel *label2, Boolean flag1, Boolean flag2) {
- Statement *stmt;
- CLabel *tmplabel;
-
- if (!expr) {
- if (flag1) {
- stmt = CFunc_AppendStatement(ST_GOTO);
- stmt->label = label1;
- return;
- }
- return;
- }
-
- if (
- ENODE_IS(expr, ETYPCON) &&
- IS_TYPE_INT(expr->rtype) &&
- IS_TYPE_INT(expr->data.monadic->rtype) &&
- expr->rtype->size >= expr->data.monadic->rtype->size
- )
- expr = expr->data.monadic;
-
- if (isnotzero(expr)) {
- if (flag1) {
- stmt = CFunc_AppendStatement(ST_GOTO);
- stmt->label = label1;
- return;
- }
- return;
- }
-
- if (iszero(expr)) {
- if (!flag1) {
- stmt = CFunc_AppendStatement(ST_GOTO);
- stmt->label = label1;
- return;
- }
- return;
- }
-
- if (ENODE_IS(expr, ELOGNOT)) {
- makeifstatement(expr->data.monadic, label1, label2, !flag1, flag2);
- return;
- }
-
- if (ENODE_IS(expr, ELOR)) {
- tmplabel = newlabel();
- if (flag1) {
- makeifstatement(expr->data.diadic.left, label1, tmplabel, 1, flag2);
- tmplabel->stmt = CFunc_AppendStatement(ST_LABEL);
- tmplabel->stmt->label = tmplabel;
- makeifstatement(expr->data.diadic.right, label1, label2, 1, flag2);
- return;
- } else {
- makeifstatement(expr->data.diadic.left, label2, tmplabel, 1, flag2);
- tmplabel->stmt = CFunc_AppendStatement(ST_LABEL);
- tmplabel->stmt->label = tmplabel;
- makeifstatement(expr->data.diadic.right, label1, label2, 0, flag2);
- return;
- }
- }
-
- if (ENODE_IS(expr, ELAND)) {
- tmplabel = newlabel();
- if (flag1) {
- makeifstatement(expr->data.diadic.left, label2, tmplabel, 0, flag2);
- tmplabel->stmt = CFunc_AppendStatement(ST_LABEL);
- tmplabel->stmt->label = tmplabel;
- makeifstatement(expr->data.diadic.right, label1, label2, 1, flag2);
- return;
- } else {
- makeifstatement(expr->data.diadic.left, label1, tmplabel, 0, flag2);
- tmplabel->stmt = CFunc_AppendStatement(ST_LABEL);
- tmplabel->stmt->label = tmplabel;
- makeifstatement(expr->data.diadic.right, label1, label2, 0, flag2);
- return;
- }
- }
-
- stmt = CFunc_AppendStatement(ST_IFGOTO);
- stmt->label = label1;
- stmt->expr = expr;
- if (!flag1)
- stmt->type = ST_IFNGOTO;
- if (flag2)
- stmt->flags = stmt->flags | StmtFlag_4;
-}
-
-static void CFunc_HasDtorTempCallBack(ENode *expr) {
- if (expr->data.temp.needs_dtor || expr->data.temp.uniqueid)
- cfunc_hasdtortemp = 1;
-}
-
-static void ifstatement(Boolean flag1, ENode *expr, CLabel *label, Boolean flag2) {
- Statement *stmt;
- CLabel *tmplabel;
-
- if (expr && copts.cplusplus && copts.exceptions) {
- cfunc_hasdtortemp = 0;
- CExpr_SearchExprTree(expr, CFunc_HasDtorTempCallBack, 1, ETEMP);
- if (cfunc_hasdtortemp) {
- stmt = CFunc_AppendStatement(flag1 ? ST_IFGOTO : ST_IFNGOTO);
- stmt->label = label;
- stmt->expr = expr;
- if (flag2)
- stmt->flags = stmt->flags | StmtFlag_4;
- return;
- }
- }
-
- tmplabel = newlabel();
- makeifstatement(expr, label, tmplabel, flag1, flag2);
- tmplabel->stmt = CFunc_AppendStatement(ST_LABEL);
- tmplabel->stmt->label = tmplabel;
-}
-
-Statement *CFunc_GenerateLoop(Statement *stmt, Type *type, ENode *lowerBound, ENode *upperBound, ENode *increment1, ENode *increment2, ENode *(*callback)(ENode *, ENode *)) {
- ENode *var1;
- ENode *var2;
- CLabel *label;
- ENode *ind;
- ENode *ind2;
- Statement *s;
-
- var1 = CExpr_NewETEMPNode(type, 1);
- ind = lalloc(sizeof(ENode));
- *ind = *var1;
- ind = makemonadicnode(ind, EINDIRECT);
- ind->rtype = type;
-
- // initialise var1 to lowerBound
- if (stmt) {
- stmt = CFunc_InsertStatement(ST_EXPRESSION, stmt);
- s = stmt;
- } else {
- s = CFunc_AppendStatement(ST_EXPRESSION);
- }
- s->expr = makediadicnode(ind, lowerBound, EASS);
-
- if (increment2) {
- var2 = CExpr_NewETEMPNode(type, 1);
- ind = lalloc(sizeof(ENode));
- *ind = *var2;
- ind = makemonadicnode(ind, EINDIRECT);
- ind->rtype = type;
-
- // initialise var2 to upperBound
- if (stmt) {
- stmt = CFunc_InsertStatement(ST_EXPRESSION, stmt);
- s = stmt;
- } else {
- s = CFunc_AppendStatement(ST_EXPRESSION);
- }
- s->expr = makediadicnode(ind, upperBound, EASS);
- }
-
- // label for loop body
- label = newlabel();
- if (stmt) {
- stmt = CFunc_InsertStatement(ST_LABEL, stmt);
- s = stmt;
- } else {
- s = CFunc_AppendStatement(ST_LABEL);
- }
- s->label = label;
- label->stmt = s;
-
- if (callback) {
- ind = lalloc(sizeof(ENode));
- *ind = *var1;
- ind = makemonadicnode(ind, EINDIRECT);
- ind->rtype = type;
-
- if (increment2) {
- ind2 = lalloc(sizeof(ENode));
- *ind2 = *var2;
- ind2 = makemonadicnode(ind2, EINDIRECT);
- ind2->rtype = type;
- } else {
- ind2 = NULL;
- }
-
- // generate a loop body
- if ((ind = callback(ind, ind2))) {
- if (stmt) {
- stmt = CFunc_InsertStatement(ST_EXPRESSION, stmt);
- s = stmt;
- } else {
- s = CFunc_AppendStatement(ST_EXPRESSION);
- }
- s->expr = ind;
- }
- }
-
- if (increment1) {
- ind = lalloc(sizeof(ENode));
- *ind = *var1;
- ind = makemonadicnode(ind, EINDIRECT);
- ind->rtype = type;
-
- // add increment1 to var1
- if (stmt) {
- stmt = CFunc_InsertStatement(ST_EXPRESSION, stmt);
- s = stmt;
- } else {
- s = CFunc_AppendStatement(ST_EXPRESSION);
- }
- s->expr = makediadicnode(ind, increment1, EADDASS);
-
- if (increment2) {
- ind = lalloc(sizeof(ENode));
- *ind = *var2;
- ind = makemonadicnode(ind, EINDIRECT);
- ind->rtype = type;
-
- // add increment2 to var2
- if (stmt) {
- stmt = CFunc_InsertStatement(ST_EXPRESSION, stmt);
- s = stmt;
- } else {
- s = CFunc_AppendStatement(ST_EXPRESSION);
- }
- s->expr = makediadicnode(ind, increment2, EADDASS);
- }
- }
-
- ind = lalloc(sizeof(ENode));
- *ind = *var1;
- ind = makemonadicnode(ind, EINDIRECT);
- ind->rtype = type;
-
- // loop if var1 < upperBound
- if (stmt) {
- stmt = CFunc_InsertStatement(ST_IFGOTO, stmt);
- s = stmt;
- } else {
- s = CFunc_AppendStatement(ST_IFGOTO);
- }
- s->expr = makediadicnode(ind, upperBound, ELESS);
- s->expr->rtype = TYPE(&stbool);
- s->label = label;
- s->flags = StmtFlag_4;
-
- return stmt;
-}
-
-static Boolean checklabel(void) {
- HashNameNode *savename;
- short savesize;
- short token;
-
- savename = tkidentifier;
- savesize = tksize;
- token = lookahead();
- tkidentifier = savename;
- tksize = savesize;
-
- return token == ':';
-}
-
-static ENode *returnstatementadjust(ENode *expr, Type *type, UInt32 qual) {
- Object *object;
- ENode *expr2;
- ENode *objexpr;
- ObjectList *list;
- ENodeList *exprlist;
-
- for (list = arguments; list; list = list->next) {
- if (list->object->name == temp_argument_name)
- break;
- }
-
- CError_ASSERT(1907, list);
-
- object = list->object;
- if ((expr2 = CExpr_IsTempConstruction(expr, type, &objexpr)) && ENODE_IS(objexpr, ETEMP)) {
- *objexpr = *create_objectnode(object);
- return expr2;
- }
-
- if (IS_TYPE_CLASS(type)) {
- expr2 = create_objectnode(object);
- exprlist = lalloc(sizeof(ENodeList));
- exprlist->next = NULL;
- exprlist->node = expr;
- return CExpr_ConstructObject(TYPE_CLASS(type), expr2, exprlist, 1, 1, 0, 1, 0);
- }
-
- expr2 = create_objectnode(object);
- expr2 = makemonadicnode(expr2, EINDIRECT);
- expr2->rtype = type;
-
- return makediadicnode(expr2, CExpr_AssignmentPromotion(expr, type, qual, 1), EASS);
-}
-
-static void CFunc_AutoResultCheck(ENode *expr) {
- while (1) {
- while (ENODE_IS(expr, ECOMMA))
- expr = expr->data.diadic.right;
-
- switch (expr->type) {
- case EOBJREF:
- if (expr->data.objref->datatype != DLOCAL)
- break;
- case ETEMP:
- CError_Warning(CErrorStr326);
- break;
- case EADD:
- case ESUB:
- CFunc_AutoResultCheck(expr->data.diadic.left);
- expr = expr->data.diadic.right;
- continue;
- default:
- break;
- }
- break;
- }
-}
-
-static void statement(DeclThing *thing) {
- Statement *stmt;
- Statement *stmt2;
- CLabel *label;
- DeclBlock *block;
- ENode *expr;
- HashNameNode *name;
- DeclThing subthing;
-
- CPrep_GetFileOffsetInfo2(&cparser_fileoffset, &sourceoffset, &sourcefilepath);
-
- switch (tk) {
- case TK_RETURN:
- tk = lex();
- if (
- (thing->thetype == &stvoid && !copts.cplusplus) ||
- CClass_IsConstructor(cscope_currentfunc) ||
- CClass_IsDestructor(cscope_currentfunc)
- )
- {
- if (tk != ';') {
- CError_Error(CErrorStr315);
- expression();
- }
-
- stmt = CFunc_AppendStatement(ST_RETURN);
- stmt->expr = NULL;
- CError_ResetErrorSkip();
- tk = lex();
- return;
- }
-
- if (tk == ';') {
- if (thing->thetype != &stvoid && (copts.pedantic || copts.cplusplus))
- CError_Warning(CErrorStr184);
-
- stmt = CFunc_AppendStatement(ST_RETURN);
- stmt->expr = NULL;
- CError_ResetErrorSkip();
- tk = lex();
- return;
- }
-
- if (copts.old_argmatch)
- expr = expression();
- else
- expr = s_expression();
-
- if (thing->thetype == &stvoid) {
- if (expr->rtype != &stvoid)
- CError_Error(CErrorStr315);
-
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = expr;
-
- stmt = CFunc_AppendStatement(ST_RETURN);
- stmt->expr = NULL;
- } else {
- if (CMach_GetFunctionResultClass(TYPE_FUNC(cscope_currentfunc->type)) == 1)
- expr = returnstatementadjust(expr, thing->thetype, thing->qual);
- else
- expr = CExpr_AssignmentPromotion(expr, thing->thetype, thing->qual, 1);
-
- stmt = CFunc_AppendStatement(ST_RETURN);
- stmt->expr = expr;
-
- if (IS_TYPE_POINTER_ONLY(thing->thetype))
- CFunc_AutoResultCheck(expr);
- }
-
- break;
-
- case TK_CASE:
- scancase(thing);
- return;
-
- case TK_DEFAULT:
- if (!thing->switchinfo) {
- CError_Error(CErrorStr169);
- return;
- }
-
- if (lex() != ':')
- CError_ErrorSkip(CErrorStr170);
- else
- tk = lex();
-
- if (thing->switchinfo->defaultlabel)
- CError_ErrorSkip(CErrorStr173);
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = newlabel();
- stmt->label->stmt = stmt;
- thing->switchinfo->defaultlabel = stmt->label;
- statement(thing);
- return;
-
- case TK_SWITCH:
- if (lex() != '(')
- CError_ErrorSkip(CErrorStr114);
- else
- tk = lex();
-
- if (copts.cplusplus && !copts.ARMscoping && isdeclaration(1, 0, 0, '=')) {
- block = CFunc_NewDeclBlock();
- expr = CFunc_ParseLocalDeclarationList(0, 1, 0, 0);
- if (CScope_IsEmptyNameSpace(cscope_current)) {
- CFunc_RestoreBlock(block);
- block = NULL;
- }
- } else {
- expr = expression();
- block = NULL;
- }
-
- stmt = CFunc_AppendStatement(ST_SWITCH);
- stmt->expr = CExpr_ConvertToIntegral(expr);
-
- if (tk != ')')
- CError_ErrorSkip(CErrorStr115);
- else
- tk = lex();
-
- stmt->label = (CLabel *) lalloc(sizeof(SwitchInfo));
- ((SwitchInfo *) stmt->label)->defaultlabel = NULL;
- ((SwitchInfo *) stmt->label)->cases = NULL;
- ((SwitchInfo *) stmt->label)->x8 = stmt->expr->rtype;
-
- label = newlabel();
- subthing = *thing;
- subthing.loopBreak = label;
- subthing.switchinfo = (SwitchInfo *) stmt->label;
- CFunc_CompoundStatement(&subthing);
-
- if (!subthing.switchinfo->defaultlabel)
- subthing.switchinfo->defaultlabel = label;
-
- if (!subthing.switchinfo->cases) {
- stmt->type = ST_EXPRESSION;
- stmt2 = lalloc(sizeof(Statement));
- *stmt2 = *stmt;
- stmt->next = stmt2;
- stmt2->type = ST_GOTO;
- stmt2->label = subthing.switchinfo->defaultlabel;
- stmt2->dobjstack = cexcept_dobjstack;
- }
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = label;
- label->stmt = stmt;
-
- if (block)
- CFunc_RestoreBlock(block);
- return;
-
- case TK_GOTO:
- if ((tk = lex()) != TK_IDENTIFIER) {
- if (tk == '*' && !copts.ANSIstrict) {
- tk = lex();
- stmt = CFunc_AppendStatement(ST_GOTOEXPR);
- stmt->expr = expression();
- if (!IS_TYPE_POINTER_ONLY(stmt->expr->rtype)) {
- CError_Error(CErrorStr146);
- stmt->expr = nullnode();
- stmt->expr->rtype = TYPE(&void_ptr);
- }
- } else {
- CError_Error(CErrorStr107);
- return;
- }
- } else {
- stmt = CFunc_AppendStatement(ST_GOTO);
- if (!(stmt->label = findlabel())) {
- stmt->label = newlabel();
- stmt->label->next = Labels;
- Labels = stmt->label;
- stmt->label->name = tkidentifier;
- }
- tk = lex();
- }
- break;
-
- case TK_BREAK:
- if (thing->loopBreak) {
- stmt = CFunc_AppendStatement(ST_GOTO);
- stmt->label = thing->loopBreak;
- } else {
- CError_Error(CErrorStr169);
- }
- tk = lex();
- break;
-
- case TK_CONTINUE:
- if (thing->loopContinue) {
- stmt = CFunc_AppendStatement(ST_GOTO);
- stmt->label = thing->loopContinue;
- } else {
- CError_Error(CErrorStr169);
- }
- tk = lex();
- break;
-
- case TK_FOR: {
- CLabel *forLabel1;
- CLabel *forLabel2;
- CLabel *forLabel3;
- ENode *forCond;
- ENode *forInc;
-
- if (lex() != '(')
- CError_ErrorSkip(CErrorStr114);
- else
- tk = lex();
-
- block = NULL;
- if (tk != ';') {
- if (!copts.cplusplus || !isdeclaration(1, 0, 0, 0)) {
- expr = expression();
- CExpr_CheckUnusedExpression(expr);
- } else {
- if (!copts.ARMscoping)
- block = CFunc_NewDeclBlock();
- expr = CFunc_ParseLocalDeclarationList(0, 1, 1, 0);
- if (block && CScope_IsEmptyNameSpace(cscope_current)) {
- CFunc_RestoreBlock(block);
- block = NULL;
- }
- }
-
- if (expr) {
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = expr;
- }
-
- if (tk == ';')
- CError_ResetErrorSkip();
- else
- CError_Error(CErrorStr123);
- } else {
- CError_ResetErrorSkip();
- }
-
- if ((tk = lex()) != ';') {
- if (copts.cplusplus && !copts.ARMscoping && isdeclaration(1, 0, 0, '=')) {
- if (!block)
- block = CFunc_NewDeclBlock();
- expr = CFunc_ParseLocalDeclarationList(0, 1, 0, 0);
- if (CScope_IsEmptyNameSpace(cscope_current)) {
- CFunc_RestoreBlock(block);
- block = NULL;
- }
- } else {
- expr = expression();
- CExpr_CheckUnwantedAssignment(expr);
- }
-
- forCond = CExpr_ConvertToCondition(expr);
-
- if (tk == ';')
- CError_ResetErrorSkip();
- else
- CError_Error(CErrorStr123);
- } else {
- CError_ResetErrorSkip();
- forCond = NULL;
- }
-
- if ((tk = lex()) != ')') {
- forInc = expression();
- CExpr_CheckUnusedExpression(forInc);
- if (tk == ')')
- CError_ResetErrorSkip();
- else
- CError_Error(CErrorStr115);
- } else {
- CError_ResetErrorSkip();
- forInc = NULL;
- }
-
- if (copts.warn_possunwant) {
- spaceskip = 0;
- if ((tk = lex()) == ';' && !spaceskip)
- CError_Warning(CErrorStr206);
- } else {
- tk = lex();
- }
-
- if (forCond) {
- stmt = CFunc_AppendStatement(ST_GOTO);
- label = newlabel();
- stmt->label = label;
- } else {
- label = newlabel();
- }
-
- CFunc_LoopIncrement();
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- forLabel1 = stmt->label = newlabel();
- forLabel1->stmt = stmt;
-
- forLabel2 = newlabel();
- forLabel3 = newlabel();
-
- subthing = *thing;
- subthing.loopContinue = forLabel3;
- subthing.loopBreak = forLabel2;
-
- if (tk != '{') {
- DeclBlock *b = CFunc_NewDeclBlock();
- CFunc_CompoundStatement(&subthing);
- CFunc_RestoreBlock(b);
- } else {
- CFunc_CompoundStatement(&subthing);
- }
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = forLabel3;
- forLabel3->stmt = stmt;
-
- if (forInc) {
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = forInc;
- }
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = label;
- label->stmt = stmt;
-
- ifstatement(1, forCond, forLabel1, 1);
- CFunc_LoopDecrement();
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = forLabel2;
- forLabel2->stmt = stmt;
-
- if (block)
- CFunc_RestoreBlock(block);
-
- return;
- }
-
- case TK_DO: {
- CLabel *label1;
- CLabel *label2;
- CLabel *label3;
-
- CFunc_LoopIncrement();
- stmt = CFunc_AppendStatement(ST_LABEL);
- label1 = stmt->label = newlabel();
- label1->stmt = stmt;
-
- label2 = newlabel();
- label3 = newlabel();
-
- subthing = *thing;
- subthing.loopContinue = label2;
- subthing.loopBreak = label3;
-
- tk = lex();
- CFunc_CompoundStatement(&subthing);
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = label2;
- label2->stmt = stmt;
-
- if (tk != TK_WHILE)
- CError_Error(CErrorStr105);
-
- if (lex() != '(')
- CError_ErrorSkip(CErrorStr114);
- else
- tk = lex();
-
- expr = CExpr_ConvertToCondition(expression());
- CExpr_CheckUnwantedAssignment(expr);
-
- if (tk != ')')
- CError_ErrorSkip(CErrorStr115);
- else
- tk = lex();
-
- ifstatement(1, expr, label1, 1);
-
- CFunc_LoopDecrement();
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = label3;
- label3->stmt = stmt;
- break;
- }
-
- case TK_WHILE: {
- CLabel *label1;
- CLabel *label2;
- CLabel *label3;
-
- if ((tk = lex()) != '(')
- CError_ErrorSkip(CErrorStr114);
- else
- tk = lex();
-
- if (copts.cplusplus && !copts.ARMscoping && isdeclaration(1, 0, 0, '=')) {
- block = CFunc_NewDeclBlock();
- expr = CFunc_ParseLocalDeclarationList(0, 1, 0, 0);
- if (CScope_IsEmptyNameSpace(cscope_current)) {
- CFunc_RestoreBlock(block);
- block = NULL;
- }
- } else {
- expr = expression();
- block = NULL;
- CExpr_CheckUnwantedAssignment(expr);
- }
- expr = CExpr_ConvertToCondition(expr);
-
- if (tk != ')') {
- CError_ErrorSkip(CErrorStr115);
- } else {
- if (copts.warn_possunwant) {
- spaceskip = 0;
- if ((tk = lex()) == ';' && !spaceskip)
- CError_Warning(CErrorStr206);
- } else {
- tk = lex();
- }
- }
-
- stmt = CFunc_AppendStatement(ST_GOTO);
- label1 = newlabel();
- stmt->label = label1;
-
- CFunc_LoopIncrement();
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- label2 = stmt->label = newlabel();
- label2->stmt = stmt;
-
- label3 = newlabel();
-
- subthing = *thing;
- subthing.loopContinue = label1;
- subthing.loopBreak = label3;
-
- CFunc_CompoundStatement(&subthing);
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = label1;
- label1->stmt = stmt;
-
- ifstatement(1, expr, label2, 1);
-
- CFunc_LoopDecrement();
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = label3;
- label3->stmt = stmt;
-
- if (block)
- CFunc_RestoreBlock(block);
- return;
- }
-
- case TK_IF: {
- CLabel *label1;
- if ((tk = lex()) != '(')
- CError_ErrorSkip(CErrorStr114);
- else
- tk = lex();
-
- if (copts.cplusplus && !copts.ARMscoping && isdeclaration(1, 0, 0, '=')) {
- block = CFunc_NewDeclBlock();
- expr = CFunc_ParseLocalDeclarationList(0, 1, 0, 0);
- if (CScope_IsEmptyNameSpace(cscope_current)) {
- CFunc_RestoreBlock(block);
- block = NULL;
- }
- } else {
- expr = expression();
- block = NULL;
- CExpr_CheckUnwantedAssignment(expr);
- }
-
- expr = CExpr_ConvertToCondition(expr);
-
- label1 = newlabel();
- ifstatement(0, expr, label1, 0);
-
- if (tk != ')') {
- CError_ErrorSkip(CErrorStr115);
- } else {
- if (copts.warn_possunwant) {
- spaceskip = 0;
- if ((tk = lex()) == ';' && !spaceskip)
- CError_Warning(CErrorStr206);
- } else {
- tk = lex();
- }
- }
-
- CFunc_CompoundStatement(thing);
-
- if (tk == TK_ELSE) {
- if (copts.warn_possunwant) {
- spaceskip = 0;
- if ((tk = lex()) == ';' && !spaceskip)
- CError_Warning(CErrorStr206);
- } else {
- tk = lex();
- }
-
- stmt = CFunc_AppendStatement(ST_GOTO);
- label = stmt->label = newlabel();
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = label1;
- label1->stmt = stmt;
-
- CFunc_CompoundStatement(thing);
-
- label1 = label;
- }
-
- stmt = CFunc_AppendStatement(ST_LABEL);
- stmt->label = label1;
- label1->stmt = stmt;
-
- if (block)
- CFunc_RestoreBlock(block);
-
- return;
- }
-
- case '{':
- CFunc_CompoundStatement(thing);
- return;
-
- case TK_ASM:
- if (copts.cplusplus || !copts.ANSIstrict) {
- tk = lex();
- volatileasm = 0;
-
- if (tk == TK_VOLATILE || (tk == TK_IDENTIFIER && !strcmp(tkidentifier->name, "__volatile__"))) {
- tk = lex();
- volatileasm = 1;
- }
-
- if (tk == '(') {
- InlineAsm_Assemble();
- if (tk == ')') {
- tk = lex();
- break;
- } else {
- CError_Error(CErrorStr115);
- return;
- }
- }
-
- if (tk == '{') {
- InlineAsm_Assemble();
- if (tk != '}') {
- CError_Error(CErrorStr130);
- return;
- }
- if ((tk = lex()) == ';')
- tk = lex();
- CError_ResetErrorSkip();
- return;
- }
-
- CError_Error(CErrorStr114);
- } else {
- CError_Error(CErrorStr121);
- }
- return;
-
- case TK_TRY:
- tk = lex();
- CExcept_ScanTryBlock(thing, 0);
- return;
-
- case TK_USING:
- if ((tk = lex()) == TK_NAMESPACE) {
- tk = lex();
- CScope_ParseUsingDirective(cscope_current);
- } else {
- CScope_ParseUsingDeclaration(cscope_current, 0, 0);
- }
- return;
-
- case TK_NAMESPACE:
- if ((tk = lex()) != TK_IDENTIFIER) {
- CError_Error(CErrorStr107);
- return;
- }
- name = tkidentifier;
- if ((tk = lex()) != '=') {
- CError_Error(CErrorStr121);
- return;
- }
-
- CScope_ParseNameSpaceAlias(name);
- break;
-
- case ';':
- break;
-
- case TK_IDENTIFIER:
- if (checklabel()) {
- stmt = CFunc_AppendStatement(ST_LABEL);
- if ((stmt->label = findlabel())) {
- if (stmt->label->stmt)
- CError_Error(CErrorStr171, tkidentifier->name);
- } else {
- stmt->label = newlabel();
- stmt->label->next = Labels;
- Labels = stmt->label;
- stmt->label->name = tkidentifier;
- }
-
- stmt->label->stmt = stmt;
- tk = lex();
- tk = lex();
- statement(thing);
- return;
- }
- tk = TK_IDENTIFIER;
-
- default:
- if (copts.cplusplus && isdeclaration(1, 0, 0, 0)) {
- CFunc_ParseLocalDeclarationList(0, 0, 0, 1);
- tk = lex();
- return;
- }
-
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = expression();
- CExpr_CheckUnusedExpression(stmt->expr);
- }
-
- if (tk == ';') {
- CPrep_TokenStreamFlush();
- tk = lex();
- CError_ResetErrorSkip();
- } else {
- CError_ErrorSkip(CErrorStr123);
- }
-}
-
-void CFunc_CompoundStatement(DeclThing *thing) {
- DeclBlock *block;
-
- block = CFunc_NewDeclBlock();
-
- if (tk == '{') {
- tk = lex();
- if (!copts.cplusplus && isdeclaration(0, 0, 0, 0))
- CFunc_ParseLocalDeclarationList(0, 0, 0, 0);
-
- while (tk != '}')
- statement(thing);
-
- CPrep_GetFileOffsetInfo2(&cparser_fileoffset, &sourceoffset, &sourcefilepath);
- tk = lex();
- } else {
- statement(thing);
- }
-
- CFunc_RestoreBlock(block);
-}
-
-static void CFunc_InsertArgumentCopyConversion(Object *obj, Type *type1, Type *type2, Boolean flag) {
- Object *newobj;
- Statement *stmt;
- ENode *expr;
- NameSpaceObjectList *nsol;
- ObjectList *list;
-
- newobj = lalloc(sizeof(Object));
- *newobj = *obj;
- newobj->type = type2;
-
- CFunc_SetupLocalVarInfo(newobj);
-
- obj->name = CParser_GetUniqueName();
- if (flag)
- obj->type = CDecl_NewPointerType(type1);
- else
- obj->type = type1;
-
- CError_ASSERT(2527, (nsol = CScope_FindName(cscope_current, newobj->name)) && nsol->object == OBJ_BASE(obj));
- nsol->object = OBJ_BASE(newobj);
-
- list = lalloc(sizeof(ObjectList));
- list->object = newobj;
- list->next = locals;
- locals = list;
-
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- expr = create_objectnode(obj);
- if (flag) {
- expr->rtype = CDecl_NewPointerType(type1);
- expr = makemonadicnode(expr, EINDIRECT);
- }
- expr->rtype = type1;
-
- if (type1 != type2)
- expr = promote(expr, type2);
-
- stmt->expr = makediadicnode(create_objectnode(newobj), expr, EASS);
-}
-
-static void CFunc_AdjustOldStyleArgs(void) {
- ObjectList *list;
-
- for (list = arguments; list; list = list->next) {
- if (IS_TYPE_FLOAT(list->object->type) && list->object->type->size < stdouble.size)
- CFunc_InsertArgumentCopyConversion(list->object, TYPE(&stdouble), list->object->type, 0);
- }
-}
-
-void CFunc_SetupNewFuncArgs(Object *func, FuncArg *args) {
- Object *obj;
- ObjectList *newlist;
-
- arguments = NULL;
-
- if (args != &elipsis && args != &oldstyle) {
- newlist = NULL;
-
- while (args && args != &elipsis) {
- IsCompleteType(args->type);
-
- obj = CParser_NewLocalDataObject(NULL, 0);
- obj->name = !args->name ? no_name_node : args->name;
- obj->type = args->type;
- obj->qual = args->qual;
- obj->sclass = args->sclass;
-
- CFunc_SetupLocalVarInfo(obj);
-
- if (IS_TYPE_CLASS(obj->type) && CClass_ReferenceArgument(TYPE_CLASS(obj->type))) {
- obj->type = CDecl_NewPointerType(obj->type);
- TPTR_QUAL(obj->type) = Q_REFERENCE | Q_RESTRICT;
- }
-
- if (obj->name == no_name_node && copts.ANSIstrict && !copts.cplusplus && !(func->qual & Q_MANGLE_NAME))
- CError_Error(CErrorStr127);
-
- if (newlist) {
- newlist->next = lalloc(sizeof(ObjectList));
- newlist = newlist->next;
- } else {
- newlist = lalloc(sizeof(ObjectList));
- arguments = newlist;
- }
-
- newlist->next = NULL;
- newlist->object = obj;
-
- args = args->next;
- }
- }
-}
-
-static ObjectList *CFunc_CopyObjectList(const FuncArg *args) {
- Object *obj;
- ObjectList *list;
- ObjectList *last;
-
- list = NULL;
-
- while (args) {
- if (list) {
- last->next = lalloc(sizeof(ObjectList));
- last = last->next;
- } else {
- last = lalloc(sizeof(ObjectList));
- list = last;
- }
-
- obj = CParser_NewLocalDataObject(NULL, 0);
- obj->name = args->name;
- obj->type = args->type;
- obj->qual = args->qual;
- obj->sclass = args->sclass;
- CFunc_SetupLocalVarInfo(obj);
-
- last->object = obj;
- last->next = NULL;
-
- args = args->next;
- }
-
- return list;
-}
-
-static void SetupFunctionArguments(Object *func, DeclInfo *di, Statement *firstStmt) {
- ObjectList *list;
- Object *resultobj;
- Object *obj;
- Type *type;
- DeclInfo my_di;
-
- if (TYPE_FUNC(func->type)->args) {
- if (di->x45) {
- arguments = CFunc_CopyObjectList(di->x18);
- while (1) {
- if (tk == '{')
- break;
-
- memclrw(&my_di, sizeof(my_di));
- CParser_GetDeclSpecs(&my_di, 0);
-
- type = my_di.thetype;
- if (my_di.storageclass && my_di.storageclass != TK_REGISTER)
- CError_Error(CErrorStr127);
-
- while (1) {
- my_di.thetype = type;
- my_di.name = NULL;
- scandeclarator(&my_di);
- if (!my_di.name) {
- CError_Error(CErrorStr107);
- break;
- }
-
- adjustargumenttype(&my_di);
- IsCompleteType(my_di.thetype);
-
- if ((obj = CFunc_IsInObjList(arguments, my_di.name))) {
- if (obj->type)
- CError_Error(CErrorStr333, obj);
- obj->type = my_di.thetype;
- obj->sclass = my_di.storageclass;
- obj->qual = my_di.qual;
- } else {
- CError_Error(CErrorStr127);
- }
-
- if (tk != ',')
- break;
- tk = lex();
- }
-
- if (tk != ';')
- CError_ErrorSkip(CErrorStr123);
- else
- tk = lex();
- }
-
- for (list = arguments; list; list = list->next) {
- if (!list->object->type)
- list->object->type = TYPE(&stsignedint);
- }
- } else {
- CFunc_SetupNewFuncArgs(func, TYPE_FUNC(func->type)->args);
- }
- }
-
- if (CMach_GetFunctionResultClass(TYPE_FUNC(func->type)) == 1) {
- resultobj = CParser_NewLocalDataObject(NULL, 0);
- resultobj->name = temp_argument_name;
- resultobj->type = CDecl_NewPointerType(TYPE_FUNC(func->type)->functype);
- CFunc_SetupLocalVarInfo(resultobj);
-
- list = lalloc(sizeof(ObjectList));
- list->object = resultobj;
- if (CABI_GetStructResultArgumentIndex(TYPE_FUNC(func->type))) {
- CError_ASSERT(2797, arguments);
- list->next = arguments->next;
- arguments->next = list;
- } else {
- list->next = arguments;
- arguments = list;
- }
- }
-
- for (list = arguments; list; list = list->next) {
- NameSpaceObjectList *nsol = CScope_InsertName(cscope_current, list->object->name);
- nsol->object = OBJ_BASE(list->object);
- }
-}
-
-NameSpace *CFunc_FuncGenSetup(Statement *stmt, Object *func) {
- NameSpace *nspace;
- DeclBlock *block;
-
- nspace = CScope_NewListNameSpace(NULL, 0);
- nspace->parent = cscope_current;
- cscope_current = nspace;
-
- arguments = NULL;
- locals = NULL;
- Labels = NULL;
-
- localcount = 0;
- cfunc_staticvarcount = 0;
-
- CExcept_Setup();
-
- memclrw(stmt, sizeof(Statement));
- curstmt = stmt;
- stmt->type = ST_NOP;
- curstmtvalue = 1;
- stmt->value = 1;
-
- blockcount = 0;
- block = lalloc(sizeof(DeclBlock));
- memclrw(block, sizeof(DeclBlock));
- block->index = blockcount++;
- block->parent_nspace = cscope_current;
-
- firstblock = block;
- currentblock = block;
-
- return nspace;
-}
-
-CFuncSave *CFunc_GetGlobalCompilerState(void) {
- CFuncSave *state;
-
- if (!cscope_currentfunc && !cscope_currentclass && cscope_current == cscope_root)
- return NULL;
-
- locklheap();
- state = lalloc(sizeof(CFuncSave));
-
- CScope_SetNameSpaceScope(cscope_root, &state->scope);
-
- state->arguments = arguments;
- arguments = NULL;
-
- state->locals = locals;
- locals = NULL;
-
- state->labels = Labels;
- Labels = NULL;
-
- state->curstmt = curstmt;
- curstmt = NULL;
-
- state->firstblock = firstblock;
- firstblock = NULL;
-
- state->currentblock = currentblock;
- currentblock = NULL;
-
- state->cexcept_dobjstack = cexcept_dobjstack;
- cexcept_dobjstack = NULL;
-
- state->sinit_label = sinit_label;
- sinit_label = NULL;
-
- state->ainit_expr = ainit_expr;
- ainit_expr = NULL;
-
- state->ctor_chain = ctor_chain;
- ctor_chain = NULL;
-
- state->cinit_tempnodefunc = cinit_tempnodefunc;
- cinit_tempnodefunc = NULL;
-
- state->trychain = trychain;
- trychain = NULL;
-
- state->cparser_fileoffset = cparser_fileoffset;
- state->symdecltoken = symdecltoken;
-
- state->functionbodyoffset = functionbodyoffset;
- functionbodyoffset = 0;
-
- state->functionbodypath = functionbodypath;
- functionbodypath = NULL;
-
- state->symdecloffset = symdecloffset;
- symdecloffset = 0;
-
- state->symdeclend = symdeclend;
-
- state->sourceoffset = sourceoffset;
- sourceoffset = 0;
-
- state->sourcefilepath = sourcefilepath;
- sourcefilepath = NULL;
-
- state->curstmtvalue = curstmtvalue;
- curstmtvalue = 0;
-
- state->name_obj_check = name_obj_check;
- name_obj_check = NULL;
-
- state->check_arglist = check_arglist;
- check_arglist = NULL;
-
- state->blockcount = blockcount;
- blockcount = 0;
-
- state->localcount = localcount;
- localcount = 0;
-
- state->tk = tk;
- state->tkidentifier = tkidentifier;
-
- state->global_access = global_access;
-
- state->cexcept_hasdobjects = cexcept_hasdobjects;
- cexcept_hasdobjects = 0;
-
- state->sinit_first_object = sinit_first_object;
- sinit_first_object = NULL;
-
- state->ainit_only_one = ainit_only_one;
- ainit_only_one = 0;
-
- state->cfunc_is_extern_c = cfunc_is_extern_c;
- cfunc_is_extern_c = 0;
-
- state->temp_reference_init = temp_reference_init;
-
- return state;
-}
-
-void CFunc_SetGlobalCompilerState(CFuncSave *state) {
- if (state) {
- CScope_RestoreScope(&state->scope);
-
- arguments = state->arguments;
- locals = state->locals;
- Labels = state->labels;
- curstmt = state->curstmt;
- firstblock = state->firstblock;
- currentblock = state->currentblock;
- cexcept_dobjstack = state->cexcept_dobjstack;
- sinit_label = state->sinit_label;
- ainit_expr = state->ainit_expr;
- ctor_chain = state->ctor_chain;
- cinit_tempnodefunc = state->cinit_tempnodefunc;
- trychain = state->trychain;
- name_obj_check = state->name_obj_check;
- check_arglist = state->check_arglist;
- curstmtvalue = state->curstmtvalue;
- cparser_fileoffset = state->cparser_fileoffset;
- symdecltoken = state->symdecltoken;
- functionbodyoffset = state->functionbodyoffset;
- functionbodypath = state->functionbodypath;
- symdecloffset = state->symdecloffset;
- symdeclend = state->symdeclend;
- sourceoffset = state->sourceoffset;
- sourcefilepath = state->sourcefilepath;
- blockcount = state->blockcount;
- tk = state->tk;
- tkidentifier = state->tkidentifier;
- global_access = state->global_access;
- localcount = state->localcount;
- cexcept_hasdobjects = state->cexcept_hasdobjects;
- sinit_first_object = state->sinit_first_object;
- ainit_only_one = state->ainit_only_one;
- cfunc_is_extern_c = state->cfunc_is_extern_c;
- temp_reference_init = state->temp_reference_init;
-
- unlocklheap();
- }
-}
-
-void CFunc_Gen(Statement *stmt, Object *func, UInt8 unk) {
- Boolean flag;
- CI_FuncData packed;
-
- if ((TYPE_FUNC(func->type)->flags & FUNC_FLAGS_400000) && !anyerrors) {
- CInline_PackIFunctionData(&packed, stmt, func);
- flag = 1;
- } else {
- flag = 0;
- }
-
- CInline_GenFunc(stmt, func, unk);
-
- if (flag)
- CClass_DefineCovariantFuncs(func, &packed);
-}
-
-static void CFunc_CheckCtorInitializer(TypeClass *tclass, CtorChain *chain) {
- ObjMemberVar *ivar;
- CtorChain *scan;
-
- if (tclass->mode != CLASS_MODE_UNION) {
- for (ivar = tclass->ivars; ivar; ivar = ivar->next) {
- if (IS_TYPE_REFERENCE(ivar->type)) {
- for (scan = chain; scan; scan = scan->next) {
- if (scan->what == CtorChain_MemberVar && scan->u.membervar == ivar)
- break;
- }
-
- if (!scan)
- CError_Error(CErrorStr256, ivar->name->name);
- } else if (CParser_IsConst(ivar->type, ivar->qual)) {
- for (scan = chain; scan; scan = scan->next) {
- if (scan->what == CtorChain_MemberVar && scan->u.membervar == ivar)
- break;
- }
-
- if (!scan && !IS_TYPE_CLASS(ivar->type))
- CError_Error(CErrorStr255, ivar->name->name);
- }
- }
- }
-}
-
-void CFunc_CheckClassCtors(TypeClass *tclass) {
- CFunc_CheckCtorInitializer(tclass, NULL);
-}
-
-static void CFunc_ParseCtorInitializer(void) {
- CtorChain *chain;
- ENodeList *args;
- TypeClass *tclass;
- ObjMemberVar *ivar;
- ClassList *base;
- VClassList *vbase;
- ENode *expr;
- Type *origtype;
-
- ctor_chain = NULL;
-
- if (tk == ':') {
- do {
- tclass = NULL;
- switch ((tk = lex())) {
- case TK_IDENTIFIER:
- for (ivar = cscope_currentclass->ivars; ivar; ivar = ivar->next) {
- if (ivar->name == tkidentifier && lookahead() == '(')
- goto do_ivar;
- }
- for (base = cscope_currentclass->bases; base; base = base->next) {
- if (base->base->classname == tkidentifier) {
- if (lookahead() == '(') {
- tclass = base->base;
- tk = lex();
- } else {
- tkidentifier = base->base->classname;
- }
- break;
- }
- }
- break;
-
- case TK_COLON_COLON:
- break;
-
- default:
- CError_Error(CErrorStr212);
- return;
- }
-
- if (!tclass)
- tclass = CClass_GetQualifiedClass();
-
- if (tclass) {
- for (vbase = cscope_currentclass->vbases; vbase; vbase = vbase->next) {
- if (vbase->base == tclass)
- break;
- }
-
- if (vbase) {
- for (chain = ctor_chain; chain; chain = chain->next) {
- if (chain->what == CtorChain_VBase && chain->u.vbase == vbase) {
- CError_Error(CErrorStr212);
- return;
- }
- }
-
- chain = lalloc(sizeof(CtorChain));
- chain->what = CtorChain_VBase;
- chain->u.vbase = vbase;
- } else {
- for (base = cscope_currentclass->bases; base; base = base->next) {
- if (base->base == tclass)
- break;
- }
-
- if (base) {
- for (chain = ctor_chain; chain; chain = chain->next) {
- if (chain->what == CtorChain_Base && chain->u.base == base) {
- CError_Error(CErrorStr212);
- return;
- }
- }
-
- chain = lalloc(sizeof(CtorChain));
- chain->what = CtorChain_Base;
- chain->u.base = base;
- } else {
- CError_Error(CErrorStr212);
- return;
- }
- }
- } else {
- for (ivar = cscope_currentclass->ivars; ivar; ivar = ivar->next) {
- if (ivar->name == tkidentifier)
- break;
- }
-
- if (ivar) {
- do_ivar:
- for (chain = ctor_chain; chain; chain = chain->next) {
- if (chain->what == CtorChain_MemberVar && chain->u.membervar == ivar)
- CError_Error(CErrorStr212);
- }
-
- chain = lalloc(sizeof(CtorChain));
- chain->what = CtorChain_MemberVar;
- chain->u.membervar = ivar;
- } else {
- CError_Error(CErrorStr212);
- return;
- }
-
- tk = lex();
- }
-
- if (tk != '(') {
- CError_Error(CErrorStr114);
- return;
- }
-
- tk = lex();
- args = CExpr_ScanExpressionList(1);
-
- if (tk != ')') {
- CError_Error(CErrorStr115);
- return;
- }
-
- switch (chain->what) {
- case CtorChain_Base:
- expr = CABI_MakeThisExpr(NULL, chain->u.base->offset);
- chain->objexpr = CExpr_ConstructObject(chain->u.base->base, expr, args, 1, 0, 0, 0, 1);
- break;
- case CtorChain_VBase:
- expr = CABI_MakeThisExpr(chain->u.vbase->base, chain->u.vbase->offset);
- chain->objexpr = CExpr_ConstructObject(chain->u.vbase->base, expr, args, 1, 0, 0, 0, 1);
- break;
- case CtorChain_MemberVar:
- expr = CABI_MakeThisExpr(cscope_currentclass, chain->u.membervar->offset);
- expr->flags = chain->u.membervar->qual & ENODE_FLAG_QUALS;
- switch (chain->u.membervar->type->type) {
- case TYPECLASS:
- chain->objexpr = CExpr_ConstructObject(TYPE_CLASS(chain->u.membervar->type), expr, args, 1, 1, 0, 1, 1);
- break;
- case TYPEARRAY:
- if (args) {
- CError_Error(CErrorStr212);
- continue;
- }
- chain->objexpr = NULL;
- break;
- default:
- if (!args) {
- args = lalloc(sizeof(ENodeList));
- args->next = NULL;
- args->node = CExpr_DoExplicitConversion(chain->u.membervar->type, chain->u.membervar->qual, NULL);
- }
- if (args->next) {
- CError_Error(CErrorStr212);
- return;
- }
- expr = makemonadicnode(expr, EINDIRECT);
- expr->rtype = chain->u.membervar->type;
- if (IS_TYPE_BITFIELD(origtype = expr->rtype)) {
- expr->data.monadic = makemonadicnode(expr->data.monadic, EBITFIELD);
- expr->data.monadic->rtype = origtype;
- expr->rtype = TYPE_BITFIELD(origtype)->bitfieldtype;
- }
-
- chain->objexpr = makediadicnode(expr, CExpr_AssignmentPromotion(args->node, expr->rtype, expr->flags, 1), EASS);
- }
- break;
- default:
- CError_FATAL(3286);
- }
-
- chain->next = ctor_chain;
- ctor_chain = chain;
- } while ((tk = lex()) == ',');
- }
-}
-
-static void CFunc_FunctionRedefinedCheck(Object *func) {
- if (TYPE_FUNC(func->type)->flags & FUNC_AUTO_GENERATED)
- CError_Error(CErrorStr333, func);
-
- if ((TYPE_FUNC(func->type)->flags & FUNC_DEFINED) && func->datatype != DINLINEFUNC)
- CError_Error(CErrorStr333, func);
-
- TYPE_FUNC(func->type)->flags |= FUNC_DEFINED;
-}
-
-static Object *CFunc_DeclareFuncName(char *str, HashNameNode *name) {
- Object *obj;
- Object *aliasobj;
- DeclInfo di;
-
- memclrw(&di, sizeof(di));
- di.name = name;
- di.storageclass = TK_STATIC;
- di.qual = Q_CONST;
- di.thetype = CDecl_NewArrayType(TYPE(&stchar), strlen(str) + 1);
-
- obj = CParser_NewGlobalDataObject(&di);
- aliasobj = CParser_NewAliasObject(obj, 0);
- obj->nspace = cscope_root;
- obj->datatype = DDATA;
- CFunc_NameLocalStaticDataObject(obj, obj->name->name);
-
- return aliasobj;
-}
-
-void CFunc_ParseFuncDef(Object *func, DeclInfo *di, TypeClass *tclass, Boolean is_method, Boolean is_static, NameSpace *nspace) {
- Boolean has_try;
- Object *nameobj_func;
- Object *nameobj_FUNCTION;
- Object *nameobj_pretty;
- char *prettyname;
- Statement *stmt18;
- Statement *stmt16;
- Statement firstStmt;
- DeclThing thing;
- CScopeSave scope;
-
- nameobj_func = NULL;
- nameobj_FUNCTION = NULL;
- nameobj_pretty = NULL;
- prettyname = NULL;
-
- CError_ASSERT(3373, IS_TYPE_FUNC(func->type));
-
- CFunc_FunctionRedefinedCheck(func);
- CParser_UpdateObject(func, di);
-
- if (!is_method) {
- CScope_SetFunctionScope(func, &scope);
- if (tclass)
- cscope_current = tclass->nspace;
- } else {
- CScope_SetMethodScope(func, tclass, is_static, &scope);
- }
-
- if (nspace)
- cscope_current = nspace;
-
- if (cscope_currentclass)
- CClass_MemberDef(func, cscope_currentclass);
-
- cfunc_is_extern_c = di->is_extern_c;
-
- CError_ASSERT(3392, IS_TYPE_FUNC(func->type));
- if (di->x45 && (func->qual & Q_ASM))
- CError_Error(CErrorStr176);
-
- if (cparamblkptr->precompile == 1 && !(func->qual & Q_INLINE))
- CError_ErrorTerm(CErrorStr180);
-
- if (di->x49)
- CError_Error(CErrorStr127);
-
- CFunc_FuncGenSetup(&firstStmt, func);
- if (!IS_TYPE_VOID(TYPE_FUNC(func->type)->functype))
- IsCompleteType(TYPE_FUNC(func->type)->functype);
-
- SetupFunctionArguments(func, di, &firstStmt);
-
- stmt18 = curstmt;
- CPrep_GetFileOffsetInfo2(&cparser_fileoffset, &sourceoffset, &sourcefilepath);
- functionbodyoffset = sourceoffset;
- firstStmt.sourceoffset = sourceoffset;
- functionbodypath = sourcefilepath;
- firstStmt.sourcefilepath = sourcefilepath;
-
- if (di->x45)
- CFunc_AdjustOldStyleArgs();
-
- if (di->x1C)
- CScope_MergeNameSpace(cscope_current, di->x1C);
-
- if (tk == TK_TRY) {
- tk = lex();
- has_try = 1;
- } else {
- has_try = 0;
- }
-
- if (CClass_IsConstructor(func)) {
- CError_ASSERT(3445, cscope_currentclass);
- CFunc_ParseCtorInitializer();
- CFunc_CheckCtorInitializer(cscope_currentclass, ctor_chain);
- }
-
- CPrep_TokenStreamFlush();
-
- if (!(func->qual & Q_ASM)) {
- if (tk == '{') {
- if (!has_try)
- tk = lex();
- } else {
- CError_ErrorSkip(CErrorStr135);
- has_try = 0;
- }
-
- if (func->name) {
- nameobj_func = CFunc_DeclareFuncName(func->name->name, GetHashNameNode("__func__"));
- nameobj_FUNCTION = CFunc_DeclareFuncName(func->name->name, GetHashNameNode("__FUNCTION__"));
- prettyname = CError_GetObjectName(func);
- nameobj_pretty = CFunc_DeclareFuncName(prettyname, GetHashNameNode("__PRETTY_FUNCTION__"));
- }
-
- if (!copts.cplusplus)
- CFunc_ParseLocalDeclarationList(0, 0, 0, 0);
-
- thing.switchinfo = NULL;
- thing.loopContinue = NULL;
- thing.loopBreak = NULL;
- thing.thetype = TYPE_FUNC(func->type)->functype;
- thing.qual = TYPE_FUNC(func->type)->qual;
-
- if (has_try) {
- CExcept_ScanTryBlock(&thing, CClass_IsConstructor(func) || CClass_IsDestructor(func));
- if (tk != 0)
- CPrep_UnLex();
- tk = '}';
- } else {
- while (tk != '}')
- statement(&thing);
- }
-
- stmt16 = curstmt;
-
- if (stmt16->type != ST_RETURN && stmt16->type != ST_GOTO) {
- CPrep_GetFileOffsetInfo2(&cparser_fileoffset, &sourceoffset, &sourcefilepath);
- CFunc_AppendStatement(ST_RETURN);
-
- curstmt->dobjstack = NULL;
- curstmt->expr = NULL;
-
- if (
- (copts.cplusplus || copts.c9x) &&
- !strcmp(func->name->name, "main") &&
- TYPE_FUNC(func->type)->functype == TYPE(&stsignedint)
- )
- curstmt->expr = intconstnode(TYPE(&stsignedint), 0);
-
- if (
- stmt16->type == ST_EXPRESSION &&
- stmt16->expr->type == EFUNCCALL &&
- stmt16->expr->rtype == &stvoid &&
- (stmt16->expr->flags & ENODE_FLAG_VOLATILE)
- )
- curstmt->flags = curstmt->flags | StmtFlag_8;
- }
-
- CheckCLabels();
-
- if (nameobj_func && (nameobj_func->flags & OBJECT_USED))
- CInit_DeclareData(nameobj_func->u.alias.object, func->name->name, NULL, strlen(func->name->name) + 1);
- if (nameobj_FUNCTION && (nameobj_FUNCTION->flags & OBJECT_USED))
- CInit_DeclareData(nameobj_FUNCTION->u.alias.object, func->name->name, NULL, strlen(func->name->name) + 1);
- if (nameobj_pretty && (nameobj_pretty->flags & OBJECT_USED))
- CInit_DeclareData(nameobj_pretty->u.alias.object, prettyname, NULL, strlen(prettyname) + 1);
-
- if (!fatalerrors) {
- if (CClass_IsConstructor(func))
- CABI_TransConstructor(func, stmt18, cscope_currentclass, NULL, has_try);
- if (CClass_IsDestructor(func))
- CABI_TransDestructor(func, func, &firstStmt, cscope_currentclass, 0);
-
- CFunc_DestructorCleanup(&firstStmt);
- CFunc_CodeCleanup(&firstStmt);
- symdeclend = CPrep_GetFileOffsetInfo(&cparser_fileoffset);
- CFunc_Gen(&firstStmt, func, di->x45);
- }
- } else {
- if (tk == '{') {
- in_assembler = 1;
- tk = lex();
- in_assembler = 0;
- } else {
- CError_ErrorSkip(CErrorStr135);
- }
-
- CFunc_ParseLocalDeclarationList(1, 0, 0, 0);
- Assembler(func);
- }
-
- if (tk != '}')
- CError_Error(CErrorStr130);
-
- CScope_RestoreScope(&scope);
-}
-
-void InitExpr_Register(ENode *expr, Object *object) {
- InitExpr *initexpr;
- InitExpr *scan;
-
- if (
- cparamblkptr->precompile == 1 &&
- object->sclass != TK_STATIC &&
- !(object->qual & (Q_20000 | Q_WEAK))
- )
- {
- CError_Error(CErrorStr180);
- return;
- }
-
- if (copts.suppress_init_code)
- return;
-
- initexpr = galloc(sizeof(InitExpr));
- initexpr->next = NULL;
- initexpr->object = object;
- initexpr->expr = CInline_CopyExpression(expr, CopyMode1);
-
- if (init_expressions) {
- scan = init_expressions;
- while (scan->next)
- scan = scan->next;
- scan->next = initexpr;
- } else {
- init_expressions = initexpr;
- }
-}
-
-void CFunc_GenerateDummyFunction(Object *func) {
- NameSpace *nspace;
- Boolean saveDebugInfo;
- Statement firstStmt;
-
- if (!anyerrors) {
- nspace = CFunc_FuncGenSetup(&firstStmt, NULL);
-
- saveDebugInfo = copts.filesyminfo;
- copts.filesyminfo = 0;
-
- CFunc_CodeCleanup(&firstStmt);
- CFunc_Gen(&firstStmt, func, 0);
-
- cscope_current = nspace->parent;
- copts.filesyminfo = saveDebugInfo;
- }
-}
-
-void CFunc_GenerateSingleExprFunc(Object *func, ENode *expr) {
- NameSpace *nspace;
- Boolean saveDebugInfo;
- Statement firstStmt;
- Statement *stmt;
-
- if (cparamblkptr->precompile == 1) {
- CError_Error(CErrorStr180);
- return;
- }
-
- if (!anyerrors) {
- nspace = CFunc_FuncGenSetup(&firstStmt, func);
-
- saveDebugInfo = copts.filesyminfo;
- copts.filesyminfo = 0;
-
- stmt = CFunc_AppendStatement(ST_EXPRESSION);
- stmt->expr = expr;
-
- CFunc_CodeCleanup(&firstStmt);
- CInline_GenFunc(&firstStmt, func, 0);
-
- cscope_current = nspace->parent;
- copts.filesyminfo = saveDebugInfo;
- }
-}
-
-void CFunc_GenerateDummyCtorFunc(Object *func, Object *real_ctor) {
- ENode *expr;
- NameSpace *nspace;
- FuncArg *arg1;
- FuncArg *arg0;
- ENodeList *list;
- Boolean saveDebugInfo;
- Statement firstStmt;
- Statement *stmt;
-
- if (cparamblkptr->precompile == 1) {
- CError_Error(CErrorStr180);
- return;
- }
-
- if (!anyerrors) {
- cscope_currentfunc = func;
-
- nspace = CFunc_FuncGenSetup(&firstStmt, func);
-
- saveDebugInfo = copts.filesyminfo;
- copts.filesyminfo = 0;
-
- CFunc_SetupNewFuncArgs(func, TYPE_FUNC(func->type)->args);
-
- expr = CExpr_NewENode(EFUNCCALL);
- expr->type = EFUNCCALL;
- expr->cost = 200;
- expr->rtype = TYPE(&void_ptr);
- expr->data.funccall.funcref = CExpr_MakeObjRefNode(real_ctor, 0);
- expr->data.funccall.functype = TYPE_FUNC(func->type);
-
- CError_ASSERT(3716, IS_TYPE_FUNC(real_ctor->type));
- CError_ASSERT(3717, TYPE_FUNC(real_ctor->type)->flags & FUNC_METHOD);
- CError_ASSERT(3718, arg0 = TYPE_FUNC(real_ctor->type)->args);
- CError_ASSERT(3720, arg1 = arg0->next);
- CError_ASSERT(3721, arguments);
-
- list = lalloc(sizeof(ENodeList));
- expr->data.funccall.args = list;
- list->node = create_objectnode(arguments->object);
-
- if (TYPE_METHOD(real_ctor->type)->theclass->flags & CLASS_HAS_VBASES) {
- CError_ASSERT(3727, arg1 = arg1->next);
- CError_ASSERT(3728, arguments->next);
- list->next = lalloc(sizeof(ENodeList));
- list = list->next;
- list->node = create_objectnode(arguments->next->object);
- }
-
- while (arg1) {
- CError_ASSERT(3737, arg1->dexpr);
- list->next = lalloc(sizeof(ENodeList));
- list = list->next;
- list->node = CExpr_GetDefaultArgument(expr->data.funccall.funcref, arg1);
- arg1 = arg1->next;
- }
-
- list->next = NULL;
-
- stmt = CFunc_AppendStatement(ST_RETURN);
- stmt->expr = expr;
-
- CFunc_CodeCleanup(&firstStmt);
- CInline_GenFunc(&firstStmt, func, 0);
-
- cscope_current = nspace->parent;
- cscope_currentfunc = NULL;
- copts.filesyminfo = saveDebugInfo;
- }
-}