static void ParseArg (ArgDesc* Arg, Type* Type) /* Parse one argument but do not push it onto the stack. Make all fields in * Arg valid. */ { /* We have a prototype, so chars may be pushed as chars */ Arg->Flags = CF_FORCECHAR; /* Remember the required argument type */ Arg->ArgType = Type; /* Read the expression we're going to pass to the function */ MarkedExprWithCheck (hie1, &Arg->Expr); /* Remember the actual argument type */ Arg->Type = Arg->Expr.Type; /* Convert this expression to the expected type */ TypeConversion (&Arg->Expr, Type); /* Remember the following code position */ GetCodePos (&Arg->Load); /* If the value is a constant, set the flag, otherwise load it into the * primary register. */ if (ED_IsConstAbsInt (&Arg->Expr) && ED_CodeRangeIsEmpty (&Arg->Expr)) { /* Remember that we have a constant value */ Arg->Flags |= CF_CONST; } else { /* Load into the primary */ LoadExpr (CF_NONE, &Arg->Expr); } /* Remember the following code position */ GetCodePos (&Arg->Push); GetCodePos (&Arg->End); /* Use the type of the argument for the push */ Arg->Flags |= TypeOf (Arg->Expr.Type); }
static void ReturnStatement (void) /* Handle the 'return' statement */ { ExprDesc Expr; NextToken (); if (CurTok.Tok != TOK_SEMI) { /* Evaluate the return expression */ hie0 (&Expr); /* If we return something in a void function, print an error and ** ignore the value. Otherwise convert the value to the type of the ** return. */ if (F_HasVoidReturn (CurrentFunc)) { Error ("Returning a value in function with return type void"); } else { /* Convert the return value to the type of the function result */ TypeConversion (&Expr, F_GetReturnType (CurrentFunc)); /* Load the value into the primary */ LoadExpr (CF_NONE, &Expr); } } else if (!F_HasVoidReturn (CurrentFunc) && !F_HasOldStyleIntRet (CurrentFunc)) { Error ("Function `%s' must return a value", F_GetFuncName (CurrentFunc)); } /* Mark the function as having a return statement */ F_ReturnFound (CurrentFunc); /* Cleanup the stack in case we're inside a block with locals */ g_space (StackPtr - F_GetTopLevelSP (CurrentFunc)); /* Output a jump to the function exit code */ g_jump (F_GetRetLab (CurrentFunc)); }