Skip to content

Commit

Permalink
minor refactor to improve comments and error recovery
Browse files Browse the repository at this point in the history
  • Loading branch information
WalterBright committed Oct 17, 2014
1 parent f150674 commit 01f25dd
Showing 1 changed file with 62 additions and 39 deletions.
101 changes: 62 additions & 39 deletions src/expression.c
Expand Up @@ -982,6 +982,10 @@ int arrayExpressionCanThrow(Expressions *exps, FuncDeclaration *func, bool mustN

/****************************************
* Expand tuples.
* Input:
* exps aray of Expressions
* Output:
* exps rewritten in place
*/

void expandTuples(Expressions *exps)
Expand Down Expand Up @@ -1102,10 +1106,17 @@ int expandAliasThisTuples(Expressions *exps, size_t starti)
return -1;
}

/****************************************
* The common type is determined by applying ?: to each pair.
* Output:
* exps[] properties resolved, implicitly cast to common type, rewritten in place
* *pt if pt is not NULL, set to the common type
* Returns:
* true a semantic error was detected
*/

bool arrayExpressionToCommonType(Scope *sc, Expressions *exps, Type **pt)
{
/* The type is determined by applying ?: to each pair.
*/
/* Still have a problem with:
* ubyte[][] = [ cast(ubyte[])"hello", [1]];
* which works if the array literal is initialized top down with the ubyte[][]
Expand Down Expand Up @@ -1216,6 +1227,10 @@ TemplateDeclaration *getFuncTemplateDecl(Dsymbol *s)

/****************************************
* Preprocess arguments to function.
* Output:
* exps[] tuples expanded, properties resolved, rewritten in place
* Returns:
* true a semantic error occurred
*/

bool preFunctionParameters(Loc loc, Scope *sc, Expressions *exps)
Expand All @@ -1236,7 +1251,7 @@ bool preFunctionParameters(Loc loc, Scope *sc, Expressions *exps)
arg = new ErrorExp();
err = true;
}
if (checkNonAssignmentArrayOp(arg))
else if (checkNonAssignmentArrayOp(arg))
{
arg = new ErrorExp();
err = true;
Expand Down Expand Up @@ -1291,7 +1306,10 @@ Expression *valueNoDtor(Expression *e)
}

/********************************************
* Determine if t is an array of structs that need a default construction.
* Issue an error if default construction is disabled for type t.
* Default construction is required for arrays and 'out' parameters.
* Returns:
* true an error was issued
*/
bool checkDefCtor(Loc loc, Type *t)
{
Expand Down Expand Up @@ -1337,7 +1355,9 @@ bool Expression::checkPostblit(Scope *sc, Type *t)
}

/*********************************************
* Call copy constructor for struct value argument.
* If e is an instance of a struct, and that struct has a copy constructor,
* rewrite e as:
* (tmp = e),tmp
* Input:
* sc just used to specify the scope of created temporary variable
*/
Expand Down Expand Up @@ -1379,24 +1399,30 @@ Expression *callCpCtor(Scope *sc, Expression *e)
* 4. add hidden _arguments[] argument
* 5. call copy constructor for struct value arguments
* Input:
* tf type of the function
* fd the function being called, NULL if called indirectly
* Output:
* *prettype return type of function
* Returns:
* return type from function
* true errors happened
*/

Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
Type *tthis, Expressions *arguments, FuncDeclaration *fd)
bool functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
Type *tthis, Expressions *arguments, FuncDeclaration *fd, Type **prettype)
{
//printf("functionParameters()\n");
assert(arguments);
assert(fd || tf->next);
size_t nargs = arguments ? arguments->dim : 0;
size_t nparams = Parameter::dim(tf->parameters);
unsigned olderrors = global.errors;
bool err = false;
*prettype = Type::terror;

if (nargs > nparams && tf->varargs == 0)
{
error(loc, "expected %llu arguments, not %llu for non-variadic function type %s", (ulonglong)nparams, (ulonglong)nargs, tf->toChars());
return Type::terror;
return true;
}

// If inferring return type, and semantic3() needs to be run if not already run
Expand All @@ -1416,7 +1442,10 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,

size_t n = (nargs > nparams) ? nargs : nparams; // n = max(nargs, nparams)

unsigned char wildmatch = 0;
/* If the function return type has wildcards in it, we'll need to figure out the actual type
* based on the actual argument types.
*/
MOD wildmatch = 0;
if (tthis && tf->isWild() && !isCtorCall)
{
Type *t = tthis;
Expand Down Expand Up @@ -1453,7 +1482,7 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
if (tf->varargs == 2 && i + 1 == nparams)
goto L2;
error(loc, "expected %llu function arguments, not %llu", (ulonglong)nparams, (ulonglong)nargs);
return Type::terror;
return true;
}
arg = p->defaultArg;
arg = inlineCopy(arg, sc);
Expand All @@ -1474,7 +1503,7 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
goto L2;
else if (nargs != nparams)
{ error(loc, "expected %llu function arguments, not %llu", (ulonglong)nparams, (ulonglong)nargs);
return Type::terror;
return true;
}
goto L1;
}
Expand Down Expand Up @@ -1541,7 +1570,7 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
if (!arg)
{
error(loc, "not enough arguments");
return Type::terror;
return true;
}
break;
}
Expand Down Expand Up @@ -1608,7 +1637,7 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
Linouterr:
const char *s = wildmatch == MODmutable ? "mutable" : MODtoChars(wildmatch);
error(loc, "modify inout to %s is not allowed inside inout function", s);
return Type::terror;
return true;
}
}

Expand Down Expand Up @@ -1641,9 +1670,12 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
{
Type *t = arg->type;
if (!t->isMutable() || !t->isAssignable()) // check blit assignable
{
arg->error("cannot modify struct %s with immutable members", arg->toChars());
err = true;
}
else
checkDefCtor(arg->loc, t);
err |= checkDefCtor(arg->loc, t); // t must be default constructible
arg = arg->toLvalue(sc, arg);
}
else if (p->storageClass & STClazy)
Expand Down Expand Up @@ -1696,6 +1728,7 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
}
else
{
// These will be the trailing ... arguments

// If not D linkage, do promotions
if (tf->linkage != LINKd)
Expand All @@ -1721,12 +1754,12 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
if (arg->type->ty == Tarray)
{
arg->error("cannot pass dynamic arrays to %s vararg functions", p);
arg = new ErrorExp();
err = true;
}
if (arg->type->ty == Tsarray)
{
arg->error("cannot pass static arrays to %s vararg functions", p);
arg = new ErrorExp();
err = true;
}
}
}
Expand All @@ -1735,12 +1768,9 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
if (arg->type->needsDestruction())
{
arg->error("cannot pass types that need destruction as variadic arguments");
arg = new ErrorExp();
err = true;
}

#if 0
arg = arg->isLvalue() ? callCpCtor(sc, arg) : valueNoDtor(arg);
#else
// Convert static arrays to dynamic arrays
// BUG: I don't think this is right for D2
Type *tb = arg->type->toBasetype();
Expand All @@ -1757,15 +1787,14 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
{
arg = callCpCtor(sc, arg);
}
#endif

// Give error for overloaded function addresses
if (arg->op == TOKsymoff)
{ SymOffExp *se = (SymOffExp *)arg;
if (se->hasOverloads &&
!se->var->isFuncDeclaration()->isUnique())
{ arg->error("function %s is overloaded", arg->toChars());
arg = new ErrorExp();
err = true;
}
}
arg->rvalue();
Expand Down Expand Up @@ -1803,6 +1832,7 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
const char* s2 = tthis->isNaked() ? " mutable" : tthis->modToChars();
::error(loc, "inout constructor %s creates%s object, not%s",
fd->toPrettyChars(), s1, s2);
err = true;
}
}
tret = tthis;
Expand All @@ -1813,7 +1843,8 @@ Type *functionParameters(Loc loc, Scope *sc, TypeFunction *tf,
//printf("wildmatch = x%x, tret = %s\n", wildmatch, tret->toChars());
tret = tret->substWildTo(wildmatch);
}
return tret;
*prettype = tret;
return (err || olderrors != global.errors);
}

/******************************** Expression **************************/
Expand Down Expand Up @@ -4647,9 +4678,7 @@ Expression *NewExp::semantic(Scope *sc)

if (!arguments)
arguments = new Expressions();
unsigned olderrors = global.errors;
type = functionParameters(loc, sc, tf, type, arguments, f);
if (olderrors != global.errors)
if (functionParameters(loc, sc, tf, type, arguments, f, &type))
return new ErrorExp();
}
else
Expand All @@ -4676,9 +4705,8 @@ Expression *NewExp::semantic(Scope *sc)
assert(allocator);

TypeFunction *tf = (TypeFunction *)f->type;
unsigned olderrors = global.errors;
functionParameters(loc, sc, tf, NULL, newargs, f);
if (olderrors != global.errors)
Type *rettype;
if (functionParameters(loc, sc, tf, NULL, newargs, f, &rettype))
return new ErrorExp();
}
else
Expand Down Expand Up @@ -4718,9 +4746,8 @@ Expression *NewExp::semantic(Scope *sc)
assert(allocator);

TypeFunction *tf = (TypeFunction *)f->type;
unsigned olderrors = global.errors;
functionParameters(loc, sc, tf, NULL, newargs, f);
if (olderrors != global.errors)
Type *rettype;
if (functionParameters(loc, sc, tf, NULL, newargs, f, &rettype))
return new ErrorExp();
}
else
Expand Down Expand Up @@ -4750,9 +4777,7 @@ Expression *NewExp::semantic(Scope *sc)

if (!arguments)
arguments = new Expressions();
unsigned olderrors = global.errors;
type = functionParameters(loc, sc, tf, type, arguments, f);
if (olderrors != global.errors)
if (functionParameters(loc, sc, tf, type, arguments, f, &type))
return new ErrorExp();
}
else
Expand Down Expand Up @@ -8727,9 +8752,7 @@ Expression *CallExp::semantic(Scope *sc)

if (!arguments)
arguments = new Expressions();
unsigned int olderrors = global.errors;
type = functionParameters(loc, sc, (TypeFunction *)(t1), tthis, arguments, f);
if (olderrors != global.errors)
if (functionParameters(loc, sc, (TypeFunction *)(t1), tthis, arguments, f, &type))
return new ErrorExp();

if (!type)
Expand Down

0 comments on commit 01f25dd

Please sign in to comment.