20 changes: 13 additions & 7 deletions src/aggregate.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,14 @@ enum Sizeok
SIZEOKfwd, // error in computing size of aggregate
};

enum Baseok
{
BASEOKnone, // base classes not computed yet
BASEOKin, // in process of resolving base classes
BASEOKdone, // all base classes are resolved
BASEOKsemanticdone, // all base classes semantic done
};

enum StructPOD
{
ISPODno, // struct is not POD
Expand Down Expand Up @@ -69,7 +77,7 @@ class AggregateDeclaration : public ScopeDsymbol
unsigned structsize; // size of struct
unsigned alignsize; // size of struct for alignment purposes
VarDeclarations fields; // VarDeclaration fields
Sizeok sizeok; // set when structsize contains valid data
Sizeok sizeok; // set when structsize contains valid data
Dsymbol *deferred; // any deferred semantic2() or semantic3() symbol
bool isdeprecated; // true if deprecated
bool mutedeprecation; // true while analysing RTInfo to avoid deprecation message
Expand Down Expand Up @@ -104,6 +112,7 @@ class AggregateDeclaration : public ScopeDsymbol
void semantic2(Scope *sc);
void semantic3(Scope *sc);
unsigned size(Loc loc);
virtual void finalizeSize(Scope *sc) = 0;
static void alignmember(structalign_t salign, unsigned size, unsigned *poffset);
static unsigned placeField(unsigned *nextoffset,
unsigned memsize, unsigned memalignsize, structalign_t memalign,
Expand Down Expand Up @@ -209,9 +218,6 @@ struct BaseClass
void copyBaseInterfaces(BaseClasses *);
};

#define CLASSINFO_SIZE_64 0x98 // value of ClassInfo.size
#define CLASSINFO_SIZE (0x3C+12+4) // value of ClassInfo.size

struct ClassFlags
{
typedef unsigned Type;
Expand Down Expand Up @@ -259,9 +265,7 @@ class ClassDeclaration : public AggregateDeclaration
bool isscope; // true if this is a scope class
bool isabstract; // true if abstract class
int inuse; // to prevent recursive attempts
Semantic doAncestorsSemantic; // Before searching symbol, whole ancestors should finish
// calling semantic() at least once, due to fill symtab
// and do addMember(). [== Semantic(Start,In,Done)]
Baseok baseok; // set the progress of base classes resolving

ClassDeclaration(Loc loc, Identifier *id, BaseClasses *baseclasses, bool inObject = false);
Dsymbol *syntaxCopy(Dsymbol *s);
Expand All @@ -274,6 +278,7 @@ class ClassDeclaration : public AggregateDeclaration
bool isBaseInfoComplete();
Dsymbol *search(Loc, Identifier *ident, int flags = IgnoreNone);
ClassDeclaration *searchBase(Loc, Identifier *ident);
void finalizeSize(Scope *sc);
bool isFuncHidden(FuncDeclaration *fd);
FuncDeclaration *findFunc(Identifier *ident, TypeFunction *tf);
void interfaceSemantic(Scope *sc);
Expand All @@ -300,6 +305,7 @@ class InterfaceDeclaration : public ClassDeclaration
InterfaceDeclaration(Loc loc, Identifier *id, BaseClasses *baseclasses);
Dsymbol *syntaxCopy(Dsymbol *s);
void semantic(Scope *sc);
void finalizeSize(Scope *sc);
bool isBaseOf(ClassDeclaration *cd, int *poffset);
bool isBaseOf(BaseClass *bc, int *poffset);
const char *kind();
Expand Down
93 changes: 47 additions & 46 deletions src/aliasthis.c
Original file line number Diff line number Diff line change
Expand Up @@ -87,59 +87,60 @@ Dsymbol *AliasThis::syntaxCopy(Dsymbol *s)

void AliasThis::semantic(Scope *sc)
{
Dsymbol *parent = sc->parent;
if (parent)
parent = parent->pastMixin();
AggregateDeclaration *ad = NULL;
if (parent)
ad = parent->isAggregateDeclaration();
if (ad)
Dsymbol *p = sc->parent->pastMixin();
AggregateDeclaration *ad = p->isAggregateDeclaration();
if (!ad)
{
assert(ad->members);
Dsymbol *s = ad->search(loc, ident);
if (!s)
{
s = sc->search(loc, ident, NULL);
if (s)
::error(loc, "%s is not a member of %s", s->toChars(), ad->toChars());
else
::error(loc, "undefined identifier %s", ident->toChars());
return;
}
else if (ad->aliasthis && s != ad->aliasthis)
error("there can be only one alias this");
::error(loc, "alias this can only be a member of aggregate, not %s %s",
p->kind(), p->toChars());
return;
}

if (ad->type->ty == Tstruct && ((TypeStruct *)ad->type)->sym != ad)
{
AggregateDeclaration *ad2 = ((TypeStruct *)ad->type)->sym;
assert(ad2->type == Type::terror);
ad->aliasthis = ad2->aliasthis;
return;
}
assert(ad->members);
Dsymbol *s = ad->search(loc, ident);
if (!s)
{
s = sc->search(loc, ident, NULL);
if (s)
::error(loc, "%s is not a member of %s", s->toChars(), ad->toChars());
else
::error(loc, "undefined identifier %s", ident->toChars());
return;
}
else if (ad->aliasthis && s != ad->aliasthis)
{
::error(loc, "there can be only one alias this");
return;
}

/* disable the alias this conversion so the implicit conversion check
* doesn't use it.
*/
ad->aliasthis = NULL;
if (ad->type->ty == Tstruct && ((TypeStruct *)ad->type)->sym != ad)
{
AggregateDeclaration *ad2 = ((TypeStruct *)ad->type)->sym;
assert(ad2->type == Type::terror);
ad->aliasthis = ad2->aliasthis;
return;
}

Dsymbol *sx = s;
if (sx->isAliasDeclaration())
sx = sx->toAlias();
Declaration *d = sx->isDeclaration();
if (d && !d->isTupleDeclaration())
/* disable the alias this conversion so the implicit conversion check
* doesn't use it.
*/
ad->aliasthis = NULL;

Dsymbol *sx = s;
if (sx->isAliasDeclaration())
sx = sx->toAlias();
Declaration *d = sx->isDeclaration();
if (d && !d->isTupleDeclaration())
{
Type *t = d->type;
assert(t);
if (ad->type->implicitConvTo(t) > MATCHnomatch)
{
Type *t = d->type;
assert(t);
if (ad->type->implicitConvTo(t) > MATCHnomatch)
{
::error(loc, "alias this is not reachable as %s already converts to %s", ad->toChars(), t->toChars());
}
::error(loc, "alias this is not reachable as %s already converts to %s", ad->toChars(), t->toChars());
}

ad->aliasthis = s;
}
else
error("alias this can only appear in struct or class declaration, not %s", parent ? parent->toChars() : "nowhere");

ad->aliasthis = s;
}

const char *AliasThis::kind()
Expand Down
2 changes: 2 additions & 0 deletions src/argtypes.c
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,8 @@ TypeTuple *toArgTypes(Type *t)
case Tfloat32:
case Tint64:
case Tuns64:
case Tint128:
case Tuns128:
case Tfloat64:
case Tfloat80:
t1 = t;
Expand Down
178 changes: 98 additions & 80 deletions src/attrib.c
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
#include "parse.h"
#include "template.h"
#include "utf.h"
#include "mtype.h"


/********************************* AttribDeclaration ****************************/
Expand Down Expand Up @@ -71,14 +72,15 @@ int AttribDeclaration::apply(Dsymbol_apply_ft_t fp, void *param)
*/
Scope *AttribDeclaration::createNewScope(Scope *sc,
StorageClass stc, LINK linkage, Prot protection, int explicitProtection,
structalign_t structalign)
structalign_t structalign, PINLINE inlining)
{
Scope *sc2 = sc;
if (stc != sc->stc ||
linkage != sc->linkage ||
!protection.isSubsetOf(sc->protection) ||
explicitProtection != sc->explicitProtection ||
structalign != sc->structalign)
structalign != sc->structalign ||
inlining != sc->inlining)
{
// create new one for changes
sc2 = sc->copy();
Expand All @@ -87,6 +89,7 @@ Scope *AttribDeclaration::createNewScope(Scope *sc,
sc2->protection = protection;
sc2->explicitProtection = explicitProtection;
sc2->structalign = structalign;
sc2->inlining = inlining;
}
return sc2;
}
Expand All @@ -100,9 +103,8 @@ Scope *AttribDeclaration::newScope(Scope *sc)
return sc;
}

int AttribDeclaration::addMember(Scope *sc, ScopeDsymbol *sds, int memnum)
void AttribDeclaration::addMember(Scope *sc, ScopeDsymbol *sds)
{
int m = 0;
Dsymbols *d = include(sc, sds);

if (d)
Expand All @@ -113,13 +115,12 @@ int AttribDeclaration::addMember(Scope *sc, ScopeDsymbol *sds, int memnum)
{
Dsymbol *s = (*d)[i];
//printf("\taddMember %s to %s\n", s->toChars(), sds->toChars());
m |= s->addMember(sc2, sds, m | memnum);
s->addMember(sc2, sds);
}

if (sc2 != sc)
sc2->pop();
}
return m;
}

void AttribDeclaration::setScope(Scope *sc)
Expand Down Expand Up @@ -390,7 +391,7 @@ Scope *StorageClassDeclaration::newScope(Scope *sc)
scstc |= stc;
//printf("scstc = x%llx\n", scstc);

return createNewScope(sc, scstc, sc->linkage, sc->protection, sc->explicitProtection, sc->structalign);
return createNewScope(sc, scstc, sc->linkage, sc->protection, sc->explicitProtection, sc->structalign, sc->inlining);
}

/*************************************************
Expand Down Expand Up @@ -529,7 +530,7 @@ Dsymbol *LinkDeclaration::syntaxCopy(Dsymbol *s)

Scope *LinkDeclaration::newScope(Scope *sc)
{
return createNewScope(sc, sc->stc, this->linkage, sc->protection, sc->explicitProtection, sc->structalign);
return createNewScope(sc, sc->stc, this->linkage, sc->protection, sc->explicitProtection, sc->structalign, sc->inlining);
}

char *LinkDeclaration::toChars()
Expand Down Expand Up @@ -582,10 +583,10 @@ Scope *ProtDeclaration::newScope(Scope *sc)
{
if (pkg_identifiers)
semantic(sc);
return createNewScope(sc, sc->stc, sc->linkage, this->protection, 1, sc->structalign);
return createNewScope(sc, sc->stc, sc->linkage, this->protection, 1, sc->structalign, sc->inlining);
}

int ProtDeclaration::addMember(Scope *sc, ScopeDsymbol *sds, int memnum)
void ProtDeclaration::addMember(Scope *sc, ScopeDsymbol *sds)
{
if (pkg_identifiers)
{
Expand All @@ -604,7 +605,7 @@ int ProtDeclaration::addMember(Scope *sc, ScopeDsymbol *sds, int memnum)
m->toPrettyChars(true));
}

return AttribDeclaration::addMember(sc, sds, memnum);
return AttribDeclaration::addMember(sc, sds);
}

const char *ProtDeclaration::kind()
Expand Down Expand Up @@ -639,7 +640,7 @@ Dsymbol *AlignDeclaration::syntaxCopy(Dsymbol *s)

Scope *AlignDeclaration::newScope(Scope *sc)
{
return createNewScope(sc, sc->stc, sc->linkage, sc->protection, sc->explicitProtection, this->salign);
return createNewScope(sc, sc->stc, sc->linkage, sc->protection, sc->explicitProtection, this->salign, sc->inlining);
}

/********************************* AnonDeclaration ****************************/
Expand All @@ -665,12 +666,12 @@ void AnonDeclaration::semantic(Scope *sc)

assert(sc->parent);

Dsymbol *parent = sc->parent->pastMixin();
AggregateDeclaration *ad = parent->isAggregateDeclaration();

if (!ad || (!ad->isStructDeclaration() && !ad->isClassDeclaration()))
Dsymbol *p = sc->parent->pastMixin();
AggregateDeclaration *ad = p->isAggregateDeclaration();
if (!ad)
{
error("can only be a part of an aggregate");
::error(loc, "%s can only be a part of an aggregate, not %s %s",
kind(), p->kind(), p->toChars());
return;
}

Expand Down Expand Up @@ -788,8 +789,48 @@ Dsymbol *PragmaDeclaration::syntaxCopy(Dsymbol *s)
Dsymbol::arraySyntaxCopy(decl));
}

void PragmaDeclaration::setScope(Scope *sc)
Scope *PragmaDeclaration::newScope(Scope *sc)
{
if (ident == Id::Pinline)
{
PINLINE inlining = PINLINEdefault;
if (!args || args->dim == 0)
inlining = PINLINEdefault;
else if (args->dim != 1)
{
error("one boolean expression expected for pragma(inline), not %d", args->dim);
args->setDim(1);
(*args)[0] = new ErrorExp();
}
else
{
Expression *e = (*args)[0];

if (e->op != TOKint64 || !e->type->equals(Type::tbool))
{
if (e->op != TOKerror)
{
error("pragma(inline, true or false) expected, not %s", e->toChars());
(*args)[0] = new ErrorExp();
}
}
else if (e->isBool(true))
inlining = PINLINEalways;
else if (e->isBool(false))
inlining = PINLINEnever;
}

if (decl)
{
for (size_t i = 0; i < decl->dim; i++)
{
Dsymbol *s = (*decl)[i];
s->semantic(sc);
}
}
return createNewScope(sc, sc->stc, sc->linkage, sc->protection, sc->explicitProtection, sc->structalign, inlining);
}
return sc;
}

static unsigned setMangleOverride(Dsymbol *s, char *sym)
Expand Down Expand Up @@ -920,6 +961,10 @@ void PragmaDeclaration::semantic(Scope *sc)
}
goto Lnodecl;
}
else if (ident == Id::Pinline)
{
goto Ldecl;
}
else if (ident == Id::mangle)
{
if (!args)
Expand Down Expand Up @@ -1166,7 +1211,7 @@ StaticIfDeclaration::StaticIfDeclaration(Condition *condition,
: ConditionalDeclaration(condition, decl, elsedecl)
{
//printf("StaticIfDeclaration::StaticIfDeclaration()\n");
sds = NULL;
scopesym = NULL;
addisdone = 0;
}

Expand All @@ -1178,43 +1223,52 @@ Dsymbol *StaticIfDeclaration::syntaxCopy(Dsymbol *s)
Dsymbol::arraySyntaxCopy(elsedecl));
}

/****************************************
* Different from other AttribDeclaration subclasses, include() call requires
* the completion of addMember and setScope phases.
*/
Dsymbols *StaticIfDeclaration::include(Scope *sc, ScopeDsymbol *sds)
{
//printf("StaticIfDeclaration::include(sc = %p) scope = %p\n", sc, scope);

if (condition->inc == 0)
{
/* Bugzilla 10101: Condition evaluation may cause self-recursive
* condition evaluation. To resolve it, temporarily save sc into scope.
*/
bool x = !scope && sc;
if (x) scope = sc;
Dsymbols *d = ConditionalDeclaration::include(sc, sds);
if (x) scope = NULL;
assert(scopesym); // addMember is already done
assert(scope); // setScope is already done

Dsymbols *d = ConditionalDeclaration::include(scope, scopesym);

// Set the scopes lazily.
if (scope && d)
if (d && !addisdone)
{
for (size_t i = 0; i < d->dim; i++)
{
Dsymbol *s = (*d)[i];
// Add members lazily.
for (size_t i = 0; i < d->dim; i++)
{
Dsymbol *s = (*d)[i];
s->addMember(scope, scopesym);
}

s->setScope(scope);
}
// Set the member scopes lazily.
for (size_t i = 0; i < d->dim; i++)
{
Dsymbol *s = (*d)[i];
s->setScope(scope);
}

addisdone = 1;
}
return d;
}
else
{
return ConditionalDeclaration::include(sc, sds);
return ConditionalDeclaration::include(sc, scopesym);
}
}

int StaticIfDeclaration::addMember(Scope *sc, ScopeDsymbol *sds, int memnum)
void StaticIfDeclaration::addMember(Scope *sc, ScopeDsymbol *sds)
{
//printf("StaticIfDeclaration::addMember() '%s'\n",toChars());
/* This is deferred until semantic(), so that
* expressions in the condition can refer to declarations
//printf("StaticIfDeclaration::addMember() '%s'\n", toChars());
/* This is deferred until the condition evaluated later (by the include() call),
* so that expressions in the condition can refer to declarations
* in the same scope, such as:
*
* template Foo(int i)
Expand All @@ -1224,15 +1278,7 @@ int StaticIfDeclaration::addMember(Scope *sc, ScopeDsymbol *sds, int memnum)
* const int k;
* }
*/
this->sds = sds;
int m = 0;

if (0 && memnum == 0)
{
m = AttribDeclaration::addMember(sc, sds, memnum);
addisdone = 1;
}
return m;
this->scopesym = sds;
}

void StaticIfDeclaration::importAll(Scope *sc)
Expand All @@ -1250,23 +1296,7 @@ void StaticIfDeclaration::setScope(Scope *sc)

void StaticIfDeclaration::semantic(Scope *sc)
{
Dsymbols *d = include(sc, sds);

//printf("\tStaticIfDeclaration::semantic '%s', d = %p\n",toChars(), d);
if (d)
{
if (!addisdone)
{
AttribDeclaration::addMember(sc, sds, 1);
addisdone = 1;
}

for (size_t i = 0; i < d->dim; i++)
{
Dsymbol *s = (*d)[i];
s->semantic(sc);
}
}
AttribDeclaration::semantic(sc);
}

const char *StaticIfDeclaration::kind()
Expand All @@ -1284,7 +1314,7 @@ CompileDeclaration::CompileDeclaration(Loc loc, Expression *exp)
//printf("CompileDeclaration(loc = %d)\n", loc.linnum);
this->loc = loc;
this->exp = exp;
this->sds = NULL;
this->scopesym = NULL;
this->compiled = 0;
}

Expand All @@ -1294,22 +1324,10 @@ Dsymbol *CompileDeclaration::syntaxCopy(Dsymbol *s)
return new CompileDeclaration(loc, exp->syntaxCopy());
}

int CompileDeclaration::addMember(Scope *sc, ScopeDsymbol *sds, int memnum)
void CompileDeclaration::addMember(Scope *sc, ScopeDsymbol *sds)
{
//printf("CompileDeclaration::addMember(sc = %p, sds = %p, memnum = %d)\n", sc, sds, memnum);
if (compiled)
return 1;

this->sds = sds;
if (memnum == 0)
{
/* No members yet, so parse the mixin now
*/
compileIt(sc);
memnum |= AttribDeclaration::addMember(sc, sds, memnum);
compiled = 1;
}
return memnum;
this->scopesym = sds;
}

void CompileDeclaration::setScope(Scope *sc)
Expand Down Expand Up @@ -1357,7 +1375,7 @@ void CompileDeclaration::semantic(Scope *sc)
if (!compiled)
{
compileIt(sc);
AttribDeclaration::addMember(sc, sds, 0);
AttribDeclaration::addMember(sc, scopesym);
compiled = 1;

if (scope && decl)
Expand Down
16 changes: 8 additions & 8 deletions src/attrib.h
Original file line number Diff line number Diff line change
Expand Up @@ -37,9 +37,9 @@ class AttribDeclaration : public Dsymbol
int apply(Dsymbol_apply_ft_t fp, void *param);
static Scope *createNewScope(Scope *sc,
StorageClass newstc, LINK linkage, Prot protection, int explictProtection,
structalign_t structalign);
structalign_t structalign, PINLINE inlining);
virtual Scope *newScope(Scope *sc);
int addMember(Scope *sc, ScopeDsymbol *sds, int memnum);
void addMember(Scope *sc, ScopeDsymbol *sds);
void setScope(Scope *sc);
void importAll(Scope *sc);
void semantic(Scope *sc);
Expand Down Expand Up @@ -107,7 +107,7 @@ class ProtDeclaration : public AttribDeclaration

Dsymbol *syntaxCopy(Dsymbol *s);
Scope *newScope(Scope *sc);
int addMember(Scope *sc, ScopeDsymbol *sds, int memnum);
void addMember(Scope *sc, ScopeDsymbol *sds);
const char *kind();
const char *toPrettyChars(bool unused);
void accept(Visitor *v) { v->visit(this); }
Expand Down Expand Up @@ -147,7 +147,7 @@ class PragmaDeclaration : public AttribDeclaration
PragmaDeclaration(Loc loc, Identifier *ident, Expressions *args, Dsymbols *decl);
Dsymbol *syntaxCopy(Dsymbol *s);
void semantic(Scope *sc);
void setScope(Scope *sc);
Scope *newScope(Scope *sc);
const char *kind();
void accept(Visitor *v) { v->visit(this); }
};
Expand All @@ -170,13 +170,13 @@ class ConditionalDeclaration : public AttribDeclaration
class StaticIfDeclaration : public ConditionalDeclaration
{
public:
ScopeDsymbol *sds;
ScopeDsymbol *scopesym;
int addisdone;

StaticIfDeclaration(Condition *condition, Dsymbols *decl, Dsymbols *elsedecl);
Dsymbol *syntaxCopy(Dsymbol *s);
Dsymbols *include(Scope *sc, ScopeDsymbol *sds);
int addMember(Scope *sc, ScopeDsymbol *sds, int memnum);
void addMember(Scope *sc, ScopeDsymbol *sds);
void semantic(Scope *sc);
void importAll(Scope *sc);
void setScope(Scope *sc);
Expand All @@ -191,12 +191,12 @@ class CompileDeclaration : public AttribDeclaration
public:
Expression *exp;

ScopeDsymbol *sds;
ScopeDsymbol *scopesym;
int compiled;

CompileDeclaration(Loc loc, Expression *exp);
Dsymbol *syntaxCopy(Dsymbol *s);
int addMember(Scope *sc, ScopeDsymbol *sds, int memnum);
void addMember(Scope *sc, ScopeDsymbol *sds);
void setScope(Scope *sc);
void compileIt(Scope *sc);
void semantic(Scope *sc);
Expand Down
33 changes: 33 additions & 0 deletions src/backend.d
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
// Compiler implementation of the D programming language
// Copyright (c) 1999-2015 by Digital Mars
// All Rights Reserved
// written by Walter Bright
// http://www.digitalmars.com
// Distributed under the Boost Software License, Version 1.0.
// http://www.boost.org/LICENSE_1_0.txt

module ddmd.backend;

import ddmd.aggregate, ddmd.dmodule, ddmd.dscope, ddmd.expression, ddmd.lib, ddmd.mtype, ddmd.root.file;

struct Symbol;
struct TYPE;
alias type = TYPE;
struct code;
struct block;

extern extern (C++) void backend_init();
extern extern (C++) void backend_term();
extern extern (C++) void obj_start(char* srcfile);
extern extern (C++) void obj_end(Library library, File* objfile);
extern extern (C++) void obj_write_deferred(Library library);

extern extern (C++) Type getTypeInfoType(Type t, Scope* sc);
extern extern (C++) Expression getInternalTypeInfo(Type t, Scope* sc);
extern extern (C++) void genObjFile(Module m, bool multiobj);
extern extern (C++) void genhelpers(Module m, bool multiobj);

extern extern (C++) Symbol* toInitializer(AggregateDeclaration sd);
extern extern (C++) Symbol* toModuleArray(Module m);
extern extern (C++) Symbol* toModuleAssert(Module m);
extern extern (C++) Symbol* toModuleUnittest(Module m);
42 changes: 21 additions & 21 deletions src/backend/blockopt.c
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ block *curblock; /* current block being read in */
block *block_last; // last block read in

static block * block_freelist;


////////////////////////////
// Storage allocator.

Expand Down Expand Up @@ -207,7 +207,7 @@ void block_goto(block *bgoto,block *bnew)
}

#endif


/**********************************
* Replace block numbers with block pointers.
* Also compute numblks and maxblks.
Expand All @@ -228,7 +228,7 @@ void block_ptr()
}
maxblks = 3 * numblks; /* allow for increase in # of blocks */
}


/*******************************
* Build predecessor list (Bpred) for each block.
*/
Expand All @@ -241,7 +241,7 @@ void block_pred()
list_free(&b->Bpred,FPNULL);

for (b = startblock; b; b = b->Bnext) /* for each block */
{ register list_t bp;
{ list_t bp;

//printf("b = %p, BC = ",b); WRBC(b->BC); printf("\n");
for (bp = b->Bsucc; bp; bp = list_next(bp))
Expand Down Expand Up @@ -291,7 +291,7 @@ void block_compbcount()
block_visit(startblock); // visit all reachable blocks
elimblks(); // eliminate unvisited blocks
}


/*******************************
* Free list of blocks.
*/
Expand Down Expand Up @@ -567,7 +567,7 @@ void block_endfunc(int flag)
curblock = NULL; // undefined from now on
block_last = NULL;
}


/******************************
* Perform branch optimization on basic blocks.
*/
Expand Down Expand Up @@ -655,7 +655,7 @@ void blockopt(int iter)
#endif
}
}


/***********************************
* Try to remove control structure.
* That is, try to resolve if-else, goto and return statements
Expand Down Expand Up @@ -872,7 +872,7 @@ void brcombine()
}
} while (0);
}


/***********************
* Branch optimization.
*/
Expand Down Expand Up @@ -944,9 +944,9 @@ STATIC void bropt()
}
else if (b->BC == BCswitch)
{ /* see we can evaluate this switch now */
register unsigned i,ncases;
unsigned i,ncases;
targ_llong *p,value;
register list_t bl;
list_t bl;

while (n->Eoper == OPcomma)
n = n->E2;
Expand Down Expand Up @@ -989,17 +989,17 @@ STATIC void bropt()
}
}
}


/*********************************
* Do branch rearrangement.
*/

STATIC void brrear()
{ register block *b;
{ block *b;

cmes("brrear()\n");
for (b = startblock; b; b = b->Bnext) /* for each block */
{ register list_t bl;
{ list_t bl;

for (bl = b->Bsucc; bl; bl = list_next(bl))
{ /* For each transfer of control block pointer */
Expand Down Expand Up @@ -1052,7 +1052,7 @@ STATIC void brrear()
/* L1: */

if (b->BC == BCiftrue || b->BC == BCiffalse)
{ register block *bif,*belse;
{ block *bif,*belse;

bif = list_block(b->Bsucc);
belse = list_block(list_next(b->Bsucc));
Expand All @@ -1068,7 +1068,7 @@ STATIC void brrear()
#endif
} /* for */
}


/*************************
* Compute depth first order (DFO).
* Equivalent to Aho & Ullman Fig. 13.8.
Expand All @@ -1077,7 +1077,7 @@ STATIC void brrear()

void compdfo()
{
register int i;
int i;

cmes("compdfo()\n");
assert(OPTIMIZER);
Expand Down Expand Up @@ -1130,7 +1130,7 @@ STATIC void search(block *b)
dfo[--dfotop] = b; // add to dfo[]
b->Bdfoidx = dfotop; // link back
}


/*************************
* Remove blocks not marked as visited (they aren't in dfo[]).
* A block is not in dfo[] if not visited.
Expand Down Expand Up @@ -1262,7 +1262,7 @@ STATIC int mergeblks()

/* fix up successor list of predecessors */
for (bl = bL2->Bpred; bl; bl = list_next(bl))
{ register list_t bs;
{ list_t bs;

for (bs=list_block(bl)->Bsucc; bs; bs=list_next(bs))
if (list_block(bs) == b)
Expand Down Expand Up @@ -1299,7 +1299,7 @@ STATIC int mergeblks()
}
return merge;
}


/*******************************
* Combine together blocks that are identical.
*/
Expand Down Expand Up @@ -1462,7 +1462,7 @@ STATIC void blident()
}
}
}


/**********************************
* Split out return blocks so the returns can be combined into a
* single block by blident().
Expand Down Expand Up @@ -1534,7 +1534,7 @@ STATIC void blreturn()
blident(); /* combine return blocks */
}
}


/*****************************************
* Convert expression into a list.
* Construct the list in reverse, that is, so that the right-most
Expand Down
30 changes: 13 additions & 17 deletions src/backend/cc.h
Original file line number Diff line number Diff line change
Expand Up @@ -102,10 +102,6 @@ enum LANG
#define LARGECODE 0
#endif

#ifndef __INTSIZE
#define __INTSIZE 4 // host ints are 4 bytes
#endif

#if SPP || SCPP
#include "msgs2.h"
#endif
Expand Down Expand Up @@ -195,7 +191,7 @@ typedef struct SYMTAB_S symtab_t;
struct code;

extern Config config;


/////////// Position in source file

typedef struct Srcpos
Expand Down Expand Up @@ -361,7 +357,7 @@ typedef char enum_SC;
#else
typedef enum SC enum_SC;
#endif


/******************************************
* Basic blocks:
* Basic blocks are a linked list of all the basic blocks
Expand Down Expand Up @@ -609,7 +605,7 @@ enum BC {
BCjplace = 19, // Jupiter: placeholder
BCMAX
};


/**********************************
* Functions
*/
Expand Down Expand Up @@ -741,7 +737,7 @@ typedef struct MEMINIT
/* called for it */
} meminit_t;



/************************************
* Base classes are a list of these.
*/
Expand Down Expand Up @@ -930,7 +926,7 @@ typedef struct ENUM
/* typedef enum { ... } E; */
symlist_t SEenumlist; // all members of enum
} enum_t;


/***********************************
* Special information for structs.
*/
Expand Down Expand Up @@ -1064,7 +1060,7 @@ typedef struct STRUCT

#define struct_calloc() ((struct_t *) mem_fcalloc(sizeof(struct_t)))
#define struct_free(st) ((void)(st))


/**********************************
* Symbol Table
*/
Expand Down Expand Up @@ -1348,7 +1344,7 @@ struct Aliassym : Symbol { };
inline char *prettyident(Symbol *s) { return s->Sident; }
#endif



/**********************************
* Function parameters:
* Pident identifier of parameter
Expand Down Expand Up @@ -1403,7 +1399,7 @@ struct PARAM
void print(); // print this param_t
void print_list(); // print this list of param_t's
};


/**************************************
* Element types.
* These should be combined with storage classes.
Expand Down Expand Up @@ -1459,7 +1455,7 @@ enum FL
#endif
FLMAX
};


////////// Srcfiles

#if !MARS
Expand Down Expand Up @@ -1594,19 +1590,19 @@ extern Declar gdeclar;
* w = symbol number (pointer for CPP)
* a = offset
* DTcoff offset into code segment
* DTend mark end of list
*/

struct dt_t
{ dt_t *DTnext; // next in list
char dt; // type (DTxxxx)
unsigned char Dty; // pointer type
unsigned char DTn; // DTibytes: number of bytes
union
{
struct // DTibytes
{ char DTn_; // number of bytes
#define DTn _DU._DI.DTn_
char DTdata_[8]; // data
{
#define DTibytesMax (sizeof(char *) + sizeof(unsigned) + sizeof(int) + sizeof(targ_size_t))
char DTdata_[DTibytesMax]; // data
#define DTdata _DU._DI.DTdata_
}_DI;
targ_size_t DTazeros_; // DTazeros,DTcommon,DTsymsize
Expand Down
34 changes: 5 additions & 29 deletions src/backend/cdef.h
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,6 @@
_M_AMD64 AMD 64 processor
Hosts no longer supported:
__INTSIZE==2 16 bit compilations
__OS2__ IBM OS/2
DOS386 32 bit DOS extended executable
DOS16RM Rational Systems 286 DOS extender
Expand Down Expand Up @@ -208,10 +207,6 @@ One and only one of these macros must be set by the makefile:
#define SUFFIX "a"
#elif _WIN32
#define SUFFIX "n"
#elif DOS386
#define SUFFIX "x"
#elif DOS16RM
#define SUFFIX "r"
#else
#define SUFFIX ""
#endif
Expand Down Expand Up @@ -249,14 +244,6 @@ One and only one of these macros must be set by the makefile:

#define STATEMENT_SCOPES CPP

#if __GNUC__
#define LONGLONG 1
#elif __SC__ > 0 && __SC__ < 0x700
#define LONGLONG 0
#else
#define LONGLONG 1 // add in code to support 64 bit integral types
#endif

#if __GNUC__
#define LDOUBLE 0 // no support for true long doubles
#else
Expand Down Expand Up @@ -346,7 +333,6 @@ typedef long double longdouble;
#endif
#define ARG_TRUE
#define ARG_FALSE
#define T68000(x)
#define T80x86(x) x

// For Share MEM_ macros - default to mem_xxx package
Expand Down Expand Up @@ -435,7 +421,7 @@ typedef long double longdouble;
#endif

#define TOOFFSET(a,b) (I32 ? TOLONG(a,b) : TOWORD(a,b))


/***************************
* Target machine data types as they appear on the host.
*/
Expand All @@ -447,13 +433,8 @@ typedef short targ_short;
typedef unsigned short targ_ushort;
typedef int targ_long;
typedef unsigned targ_ulong;
#if LONGLONG
typedef long long targ_llong;
typedef long long targ_llong;
typedef unsigned long long targ_ullong;
#else
#define targ_llong targ_long
#define targ_ullong targ_ulong
#endif
typedef float targ_float;
typedef double targ_double;
typedef longdouble targ_ldouble;
Expand Down Expand Up @@ -545,17 +526,10 @@ typedef targ_uns targ_size_t; /* size_t for the target machine */
#define LONGMASK 0xFFFFFFFF

/* Common constants often checked for */
#if LONGLONG
#define LLONGMASK 0xFFFFFFFFFFFFFFFFLL
#define ZEROLL 0LL
#define MINLL 0x8000000000000000LL
#define MAXLL 0x7FFFFFFFFFFFFFFFLL
#else
#define LLONGMASK 0xFFFFFFFFLL
#define ZEROLL 0L
#define MINLL 0x80000000
#define MAXLL 0x7FFFFFFF
#endif

#define Smodel 0 /* 64k code, 64k data, or flat model */

Expand Down Expand Up @@ -622,7 +596,7 @@ Written by Walter Bright"
#endif
#endif
#endif


/**********************************
* Configuration
*/
Expand Down Expand Up @@ -947,6 +921,8 @@ union eve
targ_llong Vllong;
targ_ullong Vullong;
Cent Vcent;
targ_float Vfloat4[4];
targ_double Vdouble2[2];
targ_float Vfloat;
targ_double Vdouble;
targ_ldouble Vldouble;
Expand Down
24 changes: 11 additions & 13 deletions src/backend/cgcod.c
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,7 @@ targ_size_t retoffset; /* offset from start of func to ret code */
targ_size_t retsize; /* size of function return */

static regm_t lastretregs,last2retregs,last3retregs,last4retregs,last5retregs;


/*********************************
* Generate code for a function.
* Note at the end of this routine mfuncreg will contain the mask
Expand Down Expand Up @@ -1217,7 +1217,7 @@ void stackoffsets(int flags)
free(autos);
}
}


/****************************
* Generate code for a block.
*/
Expand Down Expand Up @@ -1351,7 +1351,7 @@ STATIC void blcodgen(block *bl)
debugw && printf("code gen complete\n");
#endif
}


/*****************************************
* Add in exception handling code.
*/
Expand Down Expand Up @@ -1537,7 +1537,7 @@ STATIC void cgcod_eh()
}

#endif


/******************************
* Count the number of bits set in a register mask.
*/
Expand Down Expand Up @@ -1594,7 +1594,7 @@ unsigned findreg(regm_t regm
assert(0);
return 0;
}


/***************
* Free element (but not it's leaves! (assume they are already freed))
* Don't decrement Ecount! This is so we can detect if the common subexp
Expand Down Expand Up @@ -1909,7 +1909,7 @@ code *allocreg(regm_t *pretregs,unsigned *preg,tym_t tym
#warning cpu specific code
#endif
}


/*************************
* Mark registers as used.
*/
Expand Down Expand Up @@ -2038,7 +2038,7 @@ code *getregs_imm(regm_t r)
regcon.immed.mval = save;
return c;
}


/******************************************
* Flush all CSE's out of registers and into memory.
* Input:
Expand Down Expand Up @@ -2109,7 +2109,7 @@ bool cssave(elem *e,regm_t regm,unsigned opsflag)
}
return result;
}


/*************************************
* Determine if a computation should be done into a register.
*/
Expand Down Expand Up @@ -2181,7 +2181,7 @@ regm_t getscratch()
}
return scratch;
}


/******************************
* Evaluate an elem that is a common subexp that has been encountered
* before.
Expand Down Expand Up @@ -2442,7 +2442,7 @@ elem_print(e);
/* NOTREACHED */
return 0;
}


/***************************
* Generate code sequence for an elem.
* Input:
Expand Down Expand Up @@ -2538,9 +2538,7 @@ code *codelem(elem *e,regm_t *pretregs,bool constflag)
case TYuchar:
*pretregs |= BYTEREGS;
break;
#if JHANDLE
case TYjhandle:
#endif

case TYnptr:
#if TARGET_SEGMENTED
case TYsptr:
Expand Down
26 changes: 13 additions & 13 deletions src/backend/cgcs.c
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
// Copyright (C) 1985-1998 by Symantec
// Copyright (C) 2000-2012 by Digital Mars
// Copyright (C) 2000-2015 by Digital Mars
// All Rights Reserved
// http://www.digitalmars.com
// Written by Walter Bright
Expand Down Expand Up @@ -59,15 +59,15 @@ STATIC void touchfunc(int);
STATIC void touchstar();
STATIC void touchaccess(elem *);
STATIC void touchall();


/*******************************
* Eliminate common subexpressions across extended basic blocks.
* String together as many blocks as we can.
*/

void comsubs()
{ register block *bl,*blc,*bln;
register int n; /* # of blocks to treat as one */
{ block *bl,*blc,*bln;
int n; /* # of blocks to treat as one */

//static int xx;
//printf("comsubs() %d\n", ++xx);
Expand Down Expand Up @@ -153,7 +153,7 @@ void cgcs_term()
hcstab = NULL;
hcsmax = 0;
}


/*************************
* Eliminate common subexpressions for an element.
*/
Expand Down Expand Up @@ -455,7 +455,7 @@ STATIC void ecom(elem **pe)
*/

STATIC unsigned cs_comphash(elem *e)
{ register int hash;
{ int hash;
unsigned op;

elem_debug(e);
Expand Down Expand Up @@ -490,7 +490,7 @@ STATIC void addhcstab(elem *e,int hash)
{
assert(h == hcsmax);
// With 32 bit compiles, we've got memory to burn
hcsmax += (__INTSIZE == 4) ? (hcsmax + 128) : 100;
hcsmax += hcsmax + 128;
assert(h < hcsmax);
#if TX86
hcstab = (hcs *) util_realloc(hcstab,hcsmax,sizeof(hcs));
Expand All @@ -503,7 +503,7 @@ STATIC void addhcstab(elem *e,int hash)
hcstab[h].Hhash = hash;
hcsarray.top++;
}


/***************************
* "touch" the elem.
* If it is a pointer, "touch" all the suspects
Expand Down Expand Up @@ -568,7 +568,7 @@ STATIC void touchlvalue(elem *e)
assert(0);
}
}


/**************************
* "touch" variables that could be changed by a function call or
* an indirect assignment.
Expand Down Expand Up @@ -653,8 +653,8 @@ STATIC void touchfunc(int flag)
*/

STATIC void touchstar()
{ register int i;
register elem *e;
{ int i;
elem *e;

for (i = hcsarray.touchstari; i < hcsarray.top; i++)
{ e = hcstab[i].Helem;
Expand Down Expand Up @@ -686,8 +686,8 @@ STATIC void touchall()
*/

STATIC void touchaccess(elem *ev)
{ register int i;
register elem *e;
{ int i;
elem *e;

ev = ev->E1;
for (i = 0; i < hcsarray.top; i++)
Expand Down
25 changes: 5 additions & 20 deletions src/backend/cgcv.c
Original file line number Diff line number Diff line change
Expand Up @@ -365,14 +365,12 @@ idx_t cv_debtyp(debtyp_t *d)
debtypmax += 10;
#else
debtypmax += debtypmax + 16;
#if __INTSIZE == 4
if (debtypmax > 0xE000)
debtypmax = 0xE000;
#if SCPP
if (debtyptop >= debtypmax)
err_fatal(EM_2manytypes,debtypmax); // too many types
#endif
#endif
#endif
// Don't use MEM here because we can allocate pretty big
// arrays with this, and we don't want to overflow the PH
Expand Down Expand Up @@ -561,7 +559,7 @@ void cv_init()
#endif
cv_debtyp(d);
}


/////////////////////////// CodeView 4 ///////////////////////////////

/***********************************
Expand Down Expand Up @@ -1803,16 +1801,6 @@ unsigned cv4_typidx(type *t)
typidx = dt;
break;

#if JHANDLE
case TYjhandle:
#if SYMDEB_TDB
if (config.fulltypes == CVTDB) {
attribute |= 20;
goto L2;
}
#endif
goto Lptr;
#endif
case TYnptr:
#if MARS
if (t->Tkey)
Expand Down Expand Up @@ -2162,6 +2150,7 @@ unsigned cv4_typidx(type *t)
#endif
#if MARS
case TYref:
case TYnref:
attribute |= 0x20; // indicate reference pointer
tym = TYnptr; // convert to C data type
goto L1; // and try again
Expand Down Expand Up @@ -2226,7 +2215,7 @@ unsigned cv4_typidx(type *t)
assert(typidx);
return typidx;
}


/******************************************
* Write out symbol s.
*/
Expand Down Expand Up @@ -2608,15 +2597,13 @@ STATIC void cv4_func(Funcsym *s)

case TYint:
case TYuint:
#if JHANDLE
case TYjhandle:
#endif
#if TARGET_SEGMENTED
case TYsptr:
case TYcptr:
#endif
case TYnullptr:
case TYnptr:
case TYnref:
if (I32)
goto case_eax;
else
Expand Down Expand Up @@ -2747,7 +2734,7 @@ STATIC void cv4_func(Funcsym *s)

cv_outlist();
}


//////////////////////////////////////////////////////////

/******************************************
Expand Down Expand Up @@ -2926,5 +2913,3 @@ unsigned cv_typidx(type *t)
}

#endif // !SPP


44 changes: 18 additions & 26 deletions src/backend/cgelem.c
Original file line number Diff line number Diff line change
Expand Up @@ -132,9 +132,6 @@ int elemisone(elem *e)
case TYllong:
case TYullong:
case TYnullptr:
#if JHANDLE
case TYjhandle:
#endif
#if TARGET_SEGMENTED
case TYsptr:
case TYcptr:
Expand Down Expand Up @@ -198,9 +195,6 @@ int elemisnegone(elem *e)
case TYullong:
case TYnullptr:
case TYnptr:
#if JHANDLE
case TYjhandle:
#endif
#if TARGET_SEGMENTED
case TYsptr:
case TYcptr:
Expand Down Expand Up @@ -239,7 +233,7 @@ int elemisnegone(elem *e)
nomatch:
return FALSE;
}


/**********************************
* Swap relational operators (like if we swapped the leaves).
*/
Expand All @@ -251,7 +245,7 @@ unsigned swaprel(unsigned op)
op = rel_swap(op);
return op;
}


/**************************
* Replace e1 by t=e1, replace e2 by t.
*/
Expand Down Expand Up @@ -322,7 +316,7 @@ int fcost(elem *e)
cost = 8;
return cost;
}


/*******************************
* The lvalue of an op= is a conversion operator. Since the code
* generator cannot handle this, we will have to fix it here. The
Expand Down Expand Up @@ -523,7 +517,7 @@ STATIC elem *fixconvop(elem *e)
//elem_print(e);
return e;
}


STATIC elem * elerr(elem *e, goal_t goal)
{
#ifdef DEBUG
Expand All @@ -537,7 +531,7 @@ STATIC elem * elerr(elem *e, goal_t goal)

STATIC elem * elzot(elem *e, goal_t goal)
{ return e; }


/****************************
*/

Expand Down Expand Up @@ -769,7 +763,7 @@ STATIC elem * elmemxxx(elem *e, goal_t goal)
return e;
}



/***********************
* + # (combine offsets with addresses)
* / \ => |
Expand Down Expand Up @@ -1045,7 +1039,7 @@ STATIC elem * elmul(elem *e, goal_t goal)
again = 1;
return e;
}


/************************
* Subtract
* - +
Expand Down Expand Up @@ -1850,7 +1844,7 @@ STATIC elem * elnot(elem *e, goal_t goal)
}
return e;
}


/*************************
* Complement
* ~ ~ e => e
Expand Down Expand Up @@ -2219,7 +2213,7 @@ STATIC elem * elcomma(elem *e, goal_t goal)
again = changes != 0;
return e;
}


/********************************
*/

Expand Down Expand Up @@ -2342,7 +2336,7 @@ STATIC elem * eldiv(elem *e, goal_t goal)

return e;
}


/**************************
* Convert (a op b) op c to a op (b op c).
*/
Expand Down Expand Up @@ -2783,7 +2777,7 @@ STATIC elem * elandand(elem *e, goal_t goal)
L1:
return e;
}


/**************************
* Reference to bit field
* bit
Expand Down Expand Up @@ -3041,7 +3035,7 @@ STATIC elem * elcall(elem *e, goal_t goal)
e = cgel_lvalue(e);
return e;
}


/***************************
* Walk tree, converting types to tym.
*/
Expand Down Expand Up @@ -3510,13 +3504,11 @@ STATIC elem * eleq(elem *e, goal_t goal)
es->EV.Vlong = 0x80000000;
break;
case DOUBLESIZE:
#if LONGLONG
if (I32)
{ ty = TYllong;
es->EV.Vllong = 0x8000000000000000LL;
break;
}
#endif
default:
el_free(es);
goto L8;
Expand Down Expand Up @@ -3596,7 +3588,7 @@ STATIC elem * eleq(elem *e, goal_t goal)
return optelem(eres,GOALvalue);
#endif
}


/**********************************
*/

Expand All @@ -3605,7 +3597,7 @@ STATIC elem * elnegass(elem *e, goal_t goal)
e = cgel_lvalue(e);
return e;
}


/**************************
* Add assignment. Replace bit field assignment with
* equivalent tree.
Expand Down Expand Up @@ -3787,7 +3779,7 @@ STATIC elem * elopass(elem *e, goal_t goal)
}
return e;
}


/**************************
* Add assignment. Replace bit field post assignment with
* equivalent tree.
Expand Down Expand Up @@ -3823,7 +3815,7 @@ STATIC elem * elpost(elem *e, goal_t goal)
e = el_bin(OPand,ty,e,el_long(ty,m));
return optelem(e,GOALvalue);
}


/***************************
* Take care of compares.
* (e == 0) => (!e)
Expand Down Expand Up @@ -4240,7 +4232,7 @@ STATIC elem * elvptrfptr(elem *e, goal_t goal)
}

#endif


/************************
* Optimize conversions of longs to ints.
* Also used for (OPoffset) (TYfptr|TYvptr).
Expand Down Expand Up @@ -5400,7 +5392,7 @@ STATIC elem * optelem(elem *e, goal_t goal)
return (*elxxx[op])(e, goal);
#endif
}


/********************************
* Optimize and canonicalize an expression tree.
* Fiddle with double operators so that the rvalue is a pointer
Expand Down
6 changes: 3 additions & 3 deletions src/backend/cgen.c
Original file line number Diff line number Diff line change
Expand Up @@ -153,7 +153,7 @@ code * cat4(code *c1,code *c2,code *c3,code *c4)

code * cat6(code *c1,code *c2,code *c3,code *c4,code *c5,code *c6)
{ return cat(cat4(c1,c2,c3,c4),cat(c5,c6)); }


/*****************************
* Add code to end of linked list.
* Note that unused operands are garbage.
Expand Down Expand Up @@ -404,7 +404,7 @@ code *gennop(code *c)
return gen1(c,NOP);
}



/****************************************
* Clean stack after call to codelem().
*/
Expand All @@ -426,7 +426,7 @@ code *gencodelem(code *c,elem *e,regm_t *pretregs,bool constflag)
}
return c;
}


/**********************************
* Determine if one of the registers in regm has value in it.
* If so, return !=0 and set *preg to which register it is.
Expand Down
13 changes: 1 addition & 12 deletions src/backend/cgobj.c
Original file line number Diff line number Diff line change
Expand Up @@ -379,7 +379,7 @@ void too_many_symbols()
#endif
}

#if !DEBUG && TX86 && __INTSIZE == 4 && !defined(_MSC_VER)
#if !DEBUG && TX86 && !defined(_MSC_VER)
__declspec(naked) int __pascal insidx(char *p,unsigned index)
{
#undef AL
Expand Down Expand Up @@ -936,19 +936,8 @@ void Obj::linnum(Srcpos srcpos,targ_size_t offset)
obj.linvec = vec_realloc(obj.linvec,linnum + 1000);
if (offset >= vec_numbits(obj.offvec))
{
#if __INTSIZE == 2
unsigned newsize = (unsigned)offset * 2;

if (offset >= 0x8000)
{ newsize = 0xFF00;
assert(offset < newsize);
}
if (newsize != vec_numbits(obj.offvec))
obj.offvec = vec_realloc(obj.offvec,newsize);
#else
if (offset < 0xFF00) // otherwise we overflow ph_malloc()
obj.offvec = vec_realloc(obj.offvec,offset * 2);
#endif
}
if (
#if 1 // disallow multiple offsets per line
Expand Down
4 changes: 0 additions & 4 deletions src/backend/cod1.c
Original file line number Diff line number Diff line change
Expand Up @@ -659,8 +659,6 @@ code *loadea(elem *e,code *cs,unsigned op,unsigned reg,targ_size_t offset,
}
else if (reg == 6) // if DIV
{ cd = genregs(cd,0x33,DX,DX); // XOR DX,DX
if (I64 && sz == 8)
code_orrex(cd, REX_W);
}
}

Expand Down Expand Up @@ -3946,10 +3944,8 @@ code *params(elem *e,unsigned stackalign)
else if (I16 && (tym == TYdouble || tym == TYdouble_alias))
retregs = mSTACK;
}
#if LONGLONG
else if (I16 && sz == 8) // if long long
retregs = mSTACK;
#endif
c = cat(c,scodelem(e,&retregs,0,TRUE));
if (retregs != mSTACK) /* if stackpush not already inc'd */
stackpush += sz;
Expand Down
4 changes: 2 additions & 2 deletions src/backend/cod2.c
Original file line number Diff line number Diff line change
Expand Up @@ -2103,7 +2103,7 @@ code *cdcond(elem *e,regm_t *pretregs)
cgstate.stackclean--;
return c;
}


/*********************
* Comma operator
*/
Expand Down Expand Up @@ -3315,7 +3315,7 @@ code *cdmemcmp(elem *e,regm_t *pretregs)
*pretregs &= ~mPSW;
return cat4(c1,c2,c3,fixresult(e,mAX,pretregs));
}


/*********************************
* Generate code for strcpy(s1,s2) intrinsic.
*/
Expand Down
111 changes: 75 additions & 36 deletions src/backend/cod3.c
Original file line number Diff line number Diff line change
Expand Up @@ -541,7 +541,7 @@ void cod3_buildmodulector(Outbuffer* buf, int codeOffset, int refOffset)

#endif



/*****************************
* Given a type, return a mask of
* registers to hold that type.
Expand All @@ -566,11 +566,9 @@ regm_t regmask(tym_t tym, tym_t tyf)
case TYushort:
case TYint:
case TYuint:
#if JHANDLE
case TYjhandle:
#endif
case TYnullptr:
case TYnptr:
case TYnref:
#if TARGET_SEGMENTED
case TYsptr:
case TYcptr:
Expand Down Expand Up @@ -723,7 +721,7 @@ void cgreg_set_priorities(tym_t ty, char **pseq, char **pseqmsw)
}
}



/*******************************
* Generate block exit code
*/
Expand Down Expand Up @@ -1220,11 +1218,7 @@ void doswitch(block *b)
code *c;
code *ce = NULL;

#if LONGLONG
targ_ulong msw;
#else
unsigned msw;
#endif

#if TARGET_SEGMENTED
// If switch tables are in code segment and we need a CS: override to get at them
Expand Down Expand Up @@ -1393,6 +1387,8 @@ void doswitch(block *b)
if (vmax - vmin != REGMASK) /* if there is a maximum */
{ /* CMP reg,vmax-vmin */
c = genc2(c,0x81,modregrm(3,7,reg),vmax-vmin);
if (I64)
code_orrex(c, REX_W);
genjmp(c,JA,FLblock,list_block(b->Bsucc)); /* JA default */
}
if (I64)
Expand Down Expand Up @@ -1830,7 +1826,7 @@ void outswitab(block *b)
}
assert(*poffset == offset + ncases * tysize[TYnptr]);
}


/*****************************
* Return a jump opcode relevant to the elem for a JMP TRUE.
*/
Expand Down Expand Up @@ -1970,7 +1966,7 @@ int jmpopcode(elem *e)
assert((jp & 0xF0) == 0x70);
return jp;
}


/**********************************
* Append code to *pc which validates pointer described by
* addressing mode in *pcs. Modify addressing mode in *pcs.
Expand Down Expand Up @@ -2647,8 +2643,6 @@ code *movregconst(code *c,unsigned reg,targ_size_t value,regm_t flags)
switch (value)
{ case 0:
c = genclrreg(c,reg);
if (flags & 64)
code_orrex(c, REX_W);
break;
case 1:
if (I64)
Expand All @@ -2664,12 +2658,14 @@ code *movregconst(code *c,unsigned reg,targ_size_t value,regm_t flags)
L4:
if (flags & 64)
{
c = genc2(c,0xC7,(REX_W << 16) | modregrmx(3,0,reg),value); // MOV reg,value64
c = genc2(c,0xB8 + (reg&7),REX_W << 16 | (reg&8) << 13,value); // MOV reg,value64
gentstreg(c,reg);
code_orrex(c, REX_W);
}
else
{ c = genc2(c,0xC7,modregrmx(3,0,reg),value); /* MOV reg,value */
{
value &= 0xFFFFFFFF;
c = genc2(c,0xB8 + (reg&7),(reg&8) << 13,value); /* MOV reg,value */
gentstreg(c,reg);
}
break;
Expand Down Expand Up @@ -2712,8 +2708,6 @@ code *movregconst(code *c,unsigned reg,targ_size_t value,regm_t flags)
}
if (value == 0 && !(flags & 8) && config.target_cpu >= TARGET_80486)
{ c = genclrreg(c,reg); // CLR reg
if (flags & 64)
code_orrex(c, REX_W);
goto done;
}

Expand Down Expand Up @@ -2750,8 +2744,6 @@ code *movregconst(code *c,unsigned reg,targ_size_t value,regm_t flags)

if (value == 0 && !(flags & 8))
{ c = genclrreg(c,reg); // CLR reg
if (flags & 64)
code_orrex(c, REX_W);
}
else
{ /* See if we can just load a byte */
Expand All @@ -2771,11 +2763,11 @@ code *movregconst(code *c,unsigned reg,targ_size_t value,regm_t flags)
}
}
if (flags & 64)
c = genc2(c,0xC7,(REX_W << 16) | modregrmx(3,0,reg),value); // MOV reg,value64
c = genc2(c,0xB8 + (reg&7),REX_W << 16 | (reg&8) << 13,value); // MOV reg,value64
else
{ c = genc2(c,0xC7,modregrmx(3,0,reg),value); // MOV reg,value
if (I64)
value &= 0xFFFFFFFF;
{
value &= 0xFFFFFFFF;
c = genc2(c,0xB8 + (reg&7),(reg&8) << 13,value); /* MOV reg,value */
}
}
}
Expand Down Expand Up @@ -4542,7 +4534,7 @@ void assignaddrc(code *c)
{
#if OMFOBJ
case FLdata:
if (I64 || s->Sclass == SCcomdat)
if (config.objfmt == OBJ_MSCOFF || s->Sclass == SCcomdat)
{ c->IFL1 = FLextern;
goto do2;
}
Expand All @@ -4556,7 +4548,7 @@ void assignaddrc(code *c)
goto do2;

case FLudata:
if (I64)
if (config.objfmt == OBJ_MSCOFF)
{ c->IFL1 = FLextern;
goto do2;
}
Expand Down Expand Up @@ -4785,7 +4777,7 @@ void assignaddrc(code *c)
;
}
}


/*******************************
* Return offset from BP of symbol s.
*/
Expand Down Expand Up @@ -4817,7 +4809,7 @@ targ_size_t cod3_bpoffset(symbol *s)
return offset;
}



/*******************************
* Find shorter versions of the same instructions.
* Does these optimizations:
Expand Down Expand Up @@ -5156,7 +5148,14 @@ void pinholeopt(code *c,block *b)
if ((ins & R) && (rm & 0xC0) == 0xC0)
{ switch (op)
{ case 0xC6: op = 0xB0 + ereg; break;
case 0xC7: op = 0xB8 + ereg; break;
case 0xC7: // if no sign extension
if (!(c->Irex & REX_W && c->IEV2.Vint < 0))
{
c->Irm = 0;
c->Irex &= ~REX_W;
op = 0xB8 + ereg;
}
break;
case 0xFF:
switch (reg)
{ case 6<<3: op = 0x50+ereg; break;/* PUSH*/
Expand All @@ -5173,6 +5172,15 @@ void pinholeopt(code *c,block *b)
c->Iop = op;
}

// Look to remove redundant REX prefix on XOR
if (c->Irex == REX_W // ignore ops involving R8..R15
&& (op == 0x31 || op == 0x33) // XOR
&& ((rm & 0xC0) == 0xC0) // register direct
&& ((reg >> 3) == ereg)) // register with itself
{
c->Irex = 0;
}

// Look to replace SHL reg,1 with ADD reg,reg
if ((op & ~1) == 0xD0 &&
(rm & modregrm(3,7,0)) == modregrm(3,4,0) &&
Expand Down Expand Up @@ -5263,6 +5271,22 @@ void pinholeopt(code *c,block *b)
switch (op)
{
default:
// Look for MOV r64, immediate
if ((c->Irex & REX_W) && (op & ~7) == 0xB8)
{
/* Look for zero extended immediate data */
if (c->IEV2.Vsize_t == c->IEV2.Vuns)
{
c->Irex &= ~REX_W;
}
/* Look for sign extended immediate data */
else if (c->IEV2.Vsize_t == c->IEV2.Vint)
{
c->Irm = modregrm(3,0,op & 7);
c->Iop = op = 0xC7;
c->IEV2.Vsize_t = c->IEV2.Vuns;
}
}
if ((op & ~0x0F) != 0x70)
break;
case JMP:
Expand Down Expand Up @@ -5323,7 +5347,11 @@ void pinholeopt(code *c,block *b)
STATIC void pinholeopt_unittest()
{
//printf("pinholeopt_unittest()\n");
struct CS { unsigned model,op,ea,ev1,ev2,flags; } tests[][2] =
struct CS {
unsigned model,op,ea;
targ_size_t ev1,ev2;
unsigned flags;
} tests[][2] =
{
// XOR reg,immed NOT regL
{{ 16,0x81,modregrm(3,6,BX),0,0xFF,0 }, { 0,0xF6,modregrm(3,2,BX),0,0xFF }},
Expand Down Expand Up @@ -5353,6 +5381,17 @@ STATIC void pinholeopt_unittest()
{{ 32,0x68,0,0,0x80,CFopsize }, { 0,0x68,0,0,0x80,CFopsize }},
{{ 32,0x68,0,0,0x10000,CFopsize }, { 0,0x6A,0,0,0x10000,CFopsize }},
{{ 32,0x68,0,0,0x8000,CFopsize }, { 0,0x68,0,0,0x8000,CFopsize }},

// clear r64, for r64 != R8..R15
{{ 64,0x31,0x800C0,0,0,0 }, { 0,0x31,0xC0,0,0,0}},
{{ 64,0x33,0x800C0,0,0,0 }, { 0,0x33,0xC0,0,0,0}},

// MOV r64, immed
{{ 64,0xC7,0x800C0,0,0xFFFFFFFF,0 }, { 0,0xC7,0x800C0,0,0xFFFFFFFF,0}},
{{ 64,0xC7,0x800C0,0,0x7FFFFFFF,0 }, { 0,0xB8,0,0,0x7FFFFFFF,0}},
{{ 64,0xB8,0x80000,0,0xFFFFFFFF,0 }, { 0,0xB8,0,0,0xFFFFFFFF,0 }},
{{ 64,0xB8,0x80000,0,0x1FFFFFFFF,0 }, { 0,0xB8,0x80000,0,0x1FFFFFFFF,0 }},
{{ 64,0xB8,0x80000,0,0xFFFFFFFFFFFFFFFF,0 }, { 0,0xC7,0x800C0,0,0xFFFFFFFF,0}},
};

//config.flags4 |= CFG4space;
Expand All @@ -5375,17 +5414,17 @@ STATIC void pinholeopt_unittest()
cs.Iea = pin->ea;
cs.IFL1 = FLconst;
cs.IFL2 = FLconst;
cs.IEV1.Vuns = pin->ev1;
cs.IEV2.Vuns = pin->ev2;
cs.IEV1.Vsize_t = pin->ev1;
cs.IEV2.Vsize_t = pin->ev2;
cs.Iflags = pin->flags;
pinholeopt(&cs, NULL);
if (cs.Iop != pout->op)
{ printf("[%d] Iop = x%02x, pout = x%02x\n", i, cs.Iop, pout->op);
assert(0);
}
assert(cs.Iea == pout->ea);
assert(cs.IEV1.Vuns == pout->ev1);
assert(cs.IEV2.Vuns == pout->ev2);
assert(cs.IEV1.Vsize_t == pout->ev1);
assert(cs.IEV2.Vsize_t == pout->ev2);
assert(cs.Iflags == pout->flags);
}
}
Expand Down Expand Up @@ -5483,7 +5522,7 @@ void jmpaddr(code *c)
c = code_next(c);
}
}


/*******************************
* Calculate bl->Bsize.
*/
Expand Down Expand Up @@ -5791,7 +5830,7 @@ int code_match(code *c1,code *c2)
}

#endif


/**************************
* Write code to intermediate file.
* Code starts at offset.
Expand Down Expand Up @@ -6955,7 +6994,7 @@ void code_dehydrate(code **pc)
}
}
#endif


/***************************
* Debug code to dump code stucture.
*/
Expand Down
2 changes: 1 addition & 1 deletion src/backend/cod4.c
Original file line number Diff line number Diff line change
Expand Up @@ -2586,7 +2586,7 @@ code *longcmp(elem *e,bool jcond,unsigned fltarg,code *targ)
freenode(e);
return cat6(cl,cr,c,cmsw,clsw,ce);
}


/*****************************
* Do conversions.
* Depends on OPd_s32 and CLIBdbllng being in sequence.
Expand Down
43 changes: 29 additions & 14 deletions src/backend/code.c
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
// Copyright (C) 1987-1998 by Symantec
// Copyright (C) 2000-2013 by Digital Mars
// Copyright (C) 2000-2015 by Digital Mars
// All Rights Reserved
// http://www.digitalmars.com
// Written by Walter Bright
Expand Down Expand Up @@ -30,11 +30,20 @@ code *code_calloc()
{
//printf("code %d\n", sizeof(code));
code *c = code_list;
if (c)
code_list = code_next(c);
else
c = (code *)mem_fmalloc(sizeof(*c));
if (!c)
{
const size_t n = 4096 / sizeof(*c);
code *chunk = (code *)mem_fmalloc(n * sizeof(code));
for (size_t i = 0; i < n - 1; ++i)
{
code_next(&chunk[i]) = &chunk[i + 1];
}
code_next(&chunk[n - 1]) = NULL;
code_list = chunk;
c = chunk;
}

code_list = code_next(c);
MEMCLEAR(c, sizeof(*c));

//dbg_printf("code_calloc: %p\n",c);
Expand All @@ -47,18 +56,24 @@ code *code_calloc()
*/

void code_free(code *cstart)
{ code **pc;
code *c;

for (pc = &cstart; (c = *pc) != NULL; pc = &code_next(c))
{
if (cstart)
{
if (c->Iop == ASM)
code *c = cstart;
while (1)
{
mem_free(c->IEV1.as.bytes);
if (c->Iop == ASM)
{
mem_free(c->IEV1.as.bytes);
}
code *cnext = code_next(c);
if (!cnext)
break;
c = cnext;
}
code_next(c) = code_list;
code_list = cstart;
}
*pc = code_list;
code_list = cstart;
}

/*****************
Expand All @@ -73,7 +88,7 @@ void code_term()

while (code_list)
{ cn = code_next(code_list);
mem_ffree(code_list);
//mem_ffree(code_list);
code_list = cn;
count++;
}
Expand Down
8 changes: 3 additions & 5 deletions src/backend/cppman.c
Original file line number Diff line number Diff line change
Expand Up @@ -300,7 +300,7 @@ char *cpp_operator(int *poper,type **pt)
}

#endif


/***********************************
* Generate and return a pointer to a string constructed from
* the type, appended to the prefix.
Expand Down Expand Up @@ -354,10 +354,8 @@ char *cpp_typetostring(type *t,char *prefix)
case TYshort: c2 = 's'; break;
case TYuint: c1 = 'U';
case TYint: c2 = 'i'; break;
#if LONGLONG && __INTSIZE == 4 // DJB
case TYullong: c1 = 'U';
case TYllong: c2 = 'x'; break;
#endif
case TYulong: c1 = 'U';
case TYlong: c2 = 'l'; break;
#if M_UNIX
Expand Down Expand Up @@ -535,7 +533,7 @@ char *cpp_typetostring(type *t,char *prefix)
cpp_name[i] = 0; // terminate the string
return cpp_name;
}


/***********************************
* Create mangled name for template instantiation.
*/
Expand Down Expand Up @@ -698,7 +696,7 @@ char *template_mangle(symbol *s,param_t *arglist)
}

#endif


/*********************************
* Mangle a vtbl or vbtbl name.
* Returns:
Expand Down
16 changes: 15 additions & 1 deletion src/backend/cv8.c
Original file line number Diff line number Diff line change
Expand Up @@ -1003,6 +1003,8 @@ idx_t cv8_daarray(type *t, idx_t keyidx, idx_t validx)
/* Put out a struct:
* struct dAssocArray {
* void* ptr;
* typedef key-type __key_t;
* typedef val-type __val_t;
* }
*/

Expand All @@ -1028,12 +1030,24 @@ idx_t cv8_daarray(type *t, idx_t keyidx, idx_t validx)
0x00, 0x00, 0x00, 0x00, // void*
0x00, 0x00, // offset
'p','t','r',0, // "ptr"
0xf2, 0xf1, // align to 4-byte including length word before data
0xf2, 0xf1, // align to 4-byte including field id
// offset 18
0x10, 0x15, // LF_NESTTYPE_V3
0x00, 0x00, // padding
0x00, 0x00, 0x00, 0x00, // key type
'_','_','k','e','y','_','t',0, // "__key_t"
// offset 34
0x10, 0x15, // LF_NESTTYPE_V3
0x00, 0x00, // padding
0x00, 0x00, 0x00, 0x00, // value type
'_','_','v','a','l','_','t',0, // "__val_t"
};

debtyp_t *f = debtyp_alloc(sizeof(fl));
memcpy(f->data,fl,sizeof(fl));
TOLONG(f->data + 6, pvidx);
TOLONG(f->data + 22, keyidx);
TOLONG(f->data + 38, validx);
idx_t fieldlist = cv_debtyp(f);

const char *id = "dAssocArray";
Expand Down
6 changes: 3 additions & 3 deletions src/backend/debug.c
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@ void WRBC(unsigned bc)
assert(bc < BCMAX);
dbg_printf("BC%s",bcs[bc]);
}


/************************
* Write arglst
*/
Expand All @@ -133,7 +133,7 @@ void WRarglst(list_t a)
n++;
}
}


/***************************
* Write out equation elem.
*/
Expand Down Expand Up @@ -251,7 +251,7 @@ void WRdefnod()
dbg_printf(");\n");
}
}


void WRFL(enum FL fl)
{ static char fls[FLMAX][7] =
{"unde ","const ","oper ","func ","data ",
Expand Down
146 changes: 125 additions & 21 deletions src/backend/dt.c
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
// Copyright (C) 1984-1998 by Symantec
// Copyright (C) 2000-2013 by Digital Mars
// Copyright (C) 2000-2015 by Digital Mars
// All Rights Reserved
// http://www.digitalmars.com
// Written by Walter Bright
Expand Down Expand Up @@ -33,17 +33,25 @@ static dt_t *dt_freelist;

static dt_t *dt_calloc(int dtx)
{
dt_t *dt;
static dt_t dtzero;

if (dt_freelist)
dt_t *dt = dt_freelist;
if (!dt)
{
dt = dt_freelist;
dt_freelist = dt->DTnext;
*dt = dtzero;
const size_t n = 4096 / sizeof(dt_t);
dt_t *chunk = (dt_t *)mem_fmalloc(n * sizeof(dt_t));
for (size_t i = 0; i < n - 1; ++i)
{
chunk[i].DTnext = &chunk[i + 1];
}
chunk[n - 1].DTnext = NULL;
dt_freelist = chunk;
dt = chunk;
}
else
dt = (dt_t *) mem_fcalloc(sizeof(dt_t));

dt_freelist = dt->DTnext;
#ifdef DEBUG
memset(dt, 0xBE, sizeof(*dt));
#endif
dt->DTnext = NULL;
dt->dt = dtx;
return dt;
}
Expand All @@ -53,19 +61,25 @@ static dt_t *dt_calloc(int dtx)
*/

void dt_free(dt_t *dt)
{ dt_t *dtn;

for (; dt; dt = dtn)
{
if (dt)
{
switch (dt->dt)
dt_t *dtn = dt;
while (1)
{
case DT_abytes:
case DT_nbytes:
mem_free(dt->DTpbytes);
switch (dtn->dt)
{
case DT_abytes:
case DT_nbytes:
mem_free(dtn->DTpbytes);
break;
}
dt_t *dtnext = dtn->DTnext;
if (!dtnext)
break;
dtn = dtnext;
}
dtn = dt->DTnext;
dt->DTnext = dt_freelist;
dtn->DTnext = dt_freelist;
dt_freelist = dt;
}
}
Expand All @@ -76,7 +90,7 @@ void dt_free(dt_t *dt)

void dt_term()
{
#if TERMCODE
#if 0 && TERMCODE
dt_t *dtn;

while (dt_freelist)
Expand Down Expand Up @@ -139,7 +153,7 @@ dt_t ** dtnbytes(dt_t **pdtend,unsigned size,const char *ptr)
pdtend = &((*pdtend)->DTnext);
if (size)
{
if (size <= 7)
if (size < DTibytesMax)
{ dt = dt_calloc(DT_ibytes);
dt->DTn = size;
memcpy(dt->DTdata,ptr,size);
Expand Down Expand Up @@ -300,6 +314,96 @@ dt_t **dtdtoff(dt_t **pdtend, dt_t *dt, unsigned offset)
return dtxoff(pdtend, s, offset);
}

/**************************************
* Repeat a list of dt_t's count times.
*/
dt_t **dtrepeat(dt_t **pdtend, dt_t *dt, size_t count)
{
unsigned size = dt_size(dt);

if (dtallzeros(dt))
return dtnzeros(pdtend, size * count);

while (*pdtend)
pdtend = &((*pdtend)->DTnext);

if (count == 0)
return pdtend;

if (dtpointers(dt))
{
dt_t *dtp = NULL;
dt_t **pdt = &dtp;
for (size_t i = 0; i < count; ++i)
{
for (dt_t *dtn = dt; dtn; dtn = dtn->DTnext)
{
dt_t *dtx = dt_calloc(dtn->dt);
*dtx = *dtn;
dtx->DTnext = NULL;
switch (dtx->dt)
{
case DT_abytes:
case DT_nbytes:
dtx->DTpbytes = (char *) MEM_PH_MALLOC(dtx->DTnbytes);
memcpy(dtx->DTpbytes, dtn->DTpbytes, dtx->DTnbytes);
break;
}

*pdt = dtx;
pdt = &dtx->DTnext;
}
}
*pdtend = dtp;
return pdt;
}

char *p = (char *)MEM_PH_MALLOC(size * count);
size_t offset = 0;

if (count)
{
for (dt_t *dtn = dt; dtn; dtn = dtn->DTnext)
{
switch (dtn->dt)
{
case DT_nbytes:
memcpy(p + offset, dtn->DTpbytes, dtn->DTnbytes);
offset += dtn->DTnbytes;
break;
case DT_ibytes:
memcpy(p + offset, dtn->DTdata, dtn->DTn);
offset += dtn->DTn;
break;
case DT_symsize:
case DT_azeros:
memset(p + offset, 0, dtn->DTazeros);
offset += dtn->DTazeros;
break;
default:
#ifdef DEBUG
dbg_printf("dt = %p, dt = %d\n",dt,dt->dt);
#endif
assert(0);
}
}
assert(offset == size);
}

for (size_t i = 1; i < count; ++i)
{
memcpy(p + offset, p, size);
offset += size;
}

dt_t *dtx = dt_calloc(DT_nbytes);
dtx->DTnbytes = size * count;
dtx->DTpbytes = p;
*pdtend = dtx;
pdtend = &dtx->DTnext;
return pdtend;
}

/**************************
* 'Optimize' a list of dt_t's.
* (Try to collapse it into one DT_azeros object.)
Expand Down
1 change: 1 addition & 0 deletions src/backend/dt.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ dt_t **dtxoff(dt_t **pdtend,Symbol *s,unsigned offset);
dt_t **dtdtoff(dt_t **pdtend, dt_t *dt, unsigned offset);
dt_t **dtcoff(dt_t **pdtend,unsigned offset);
dt_t ** dtcat(dt_t **pdtend,dt_t *dt);
dt_t ** dtrepeat(dt_t **pdtend, dt_t *dt, size_t count);
void dt_optimize(dt_t *dt);
void dtsymsize(Symbol *);
void init_common(Symbol *);
Expand Down
244 changes: 67 additions & 177 deletions src/backend/dwarf.c

Large diffs are not rendered by default.

3 changes: 1 addition & 2 deletions src/backend/dwarf.h
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,7 @@

/* ==================== Dwarf debug ======================= */

// #define USE_DWARF_D_EXTENSIONS
#define DWARF_VERSION 2
#define DWARF_VERSION 3

void dwarf_initfile(const char *filename);
void dwarf_termfile();
Expand Down
84 changes: 57 additions & 27 deletions src/backend/dwarf2.h
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,7 @@ enum
DW_TAG_variable = 0x34,
DW_TAG_volatile_type = 0x35,

/* DWARF v3 */
DW_TAG_dwarf_procedure = 0x36,
DW_TAG_restrict_type = 0x37,
DW_TAG_interface_type = 0x38,
Expand All @@ -64,12 +65,10 @@ enum
DW_TAG_condition = 0x3F,
DW_TAG_shared_type = 0x40,

// D programming language extensions
#ifdef USE_DWARF_D_EXTENSIONS
DW_TAG_darray_type = 0x41,
DW_TAG_aarray_type = 0x42,
DW_TAG_delegate_type = 0x43,
#endif
/* DWARF v4 */
DW_TAG_type_unit = 0x41,
DW_TAG_rvalue_reference_type = 0x42,
DW_TAG_template_alias = 0x43,

DW_TAG_lo_user = 0x4080,
DW_TAG_hi_user = 0xFFFF,
Expand Down Expand Up @@ -143,6 +142,7 @@ enum
DW_AT_virtuality = 0x4C,
DW_AT_vtable_elem_location = 0x4D,

/* DWARF v3 */
DW_AT_allocated = 0x4E,
DW_AT_associated = 0x4F,
DW_AT_data_location = 0x50,
Expand Down Expand Up @@ -171,6 +171,14 @@ enum
DW_AT_pure = 0x67,
DW_AT_recursive = 0x68,

/* DWARF v4 */
DW_AT_signature = 0x69,
DW_AT_main_subprogram = 0x6a,
DW_AT_data_bit_offset = 0x6b,
DW_AT_const_expr = 0x6c,
DW_AT_enum_class = 0x6d,
DW_AT_linkage_name = 0x6e,

DW_AT_lo_user = 0x2000,
DW_AT_MIPS_linkage_name = 0x2007,
DW_AT_GNU_vector = 0x2107,
Expand All @@ -179,27 +187,33 @@ enum

enum
{
DW_FORM_addr = 0x01,
DW_FORM_block2 = 0x03,
DW_FORM_block4 = 0x04,
DW_FORM_data2 = 0x05,
DW_FORM_data4 = 0x06,
DW_FORM_data8 = 0x07,
DW_FORM_string = 0x08,
DW_FORM_block = 0x09,
DW_FORM_block1 = 0x0A,
DW_FORM_data1 = 0x0B,
DW_FORM_flag = 0x0C,
DW_FORM_sdata = 0x0D,
DW_FORM_strp = 0x0E,
DW_FORM_udata = 0x0F,
DW_FORM_ref_addr = 0x10,
DW_FORM_ref1 = 0x11,
DW_FORM_ref2 = 0x12,
DW_FORM_ref4 = 0x13,
DW_FORM_ref8 = 0x14,
DW_FORM_ref_udata = 0x15,
DW_FORM_indirect = 0x16,
DW_FORM_addr = 0x01,
DW_FORM_block2 = 0x03,
DW_FORM_block4 = 0x04,
DW_FORM_data2 = 0x05,
DW_FORM_data4 = 0x06,
DW_FORM_data8 = 0x07,
DW_FORM_string = 0x08,
DW_FORM_block = 0x09,
DW_FORM_block1 = 0x0A,
DW_FORM_data1 = 0x0B,
DW_FORM_flag = 0x0C,
DW_FORM_sdata = 0x0D,
DW_FORM_strp = 0x0E,
DW_FORM_udata = 0x0F,
DW_FORM_ref_addr = 0x10,
DW_FORM_ref1 = 0x11,
DW_FORM_ref2 = 0x12,
DW_FORM_ref4 = 0x13,
DW_FORM_ref8 = 0x14,
DW_FORM_ref_udata = 0x15,
DW_FORM_indirect = 0x16,

/* DWARF v4 */
DW_FORM_sec_offset = 0x17,
DW_FORM_exprloc = 0x18,
DW_FORM_flag_present = 0x19,
DW_FORM_ref_sig8 = 0x20,
};

enum
Expand Down Expand Up @@ -263,13 +277,20 @@ enum
DW_OP_deref_size = 0x94,
DW_OP_xderef_size = 0x95,
DW_OP_nop = 0x96,

/* DWARF v3 */
DW_OP_push_object_address = 0x97,
DW_OP_call2 = 0x98,
DW_OP_call4 = 0x99,
DW_OP_call_ref = 0x9a,
DW_OP_form_tls_address = 0x9b,
DW_OP_call_frame_cfa = 0x9c,
DW_OP_bit_piece = 0x9d,

/* DWARF v4 */
DW_OP_implicit_value = 0x9e,
DW_OP_stack_value = 0x9f,

DW_OP_lo_user = 0xe0,
DW_OP_hi_user = 0xff,

Expand All @@ -287,13 +308,19 @@ enum
DW_ATE_signed_char = 0x06,
DW_ATE_unsigned = 0x07,
DW_ATE_unsigned_char = 0x08,

/* DWARF v3 */
DW_ATE_imaginary_float = 0x09,
DW_ATE_packed_decimal = 0x0a,
DW_ATE_numeric_string = 0x0b,
DW_ATE_editted = 0x0c,
DW_ATE_signed_fixed = 0x0d,
DW_ATE_unsigned_fixed = 0x0e,
DW_ATE_decimal_float = 0x0f,

/* DWARF v4 */
DW_ATE_UTF = 0x10,

DW_ATE_lo_user = 0x80,
DW_ATE_hi_user = 0xff,
};
Expand Down Expand Up @@ -453,6 +480,8 @@ enum
DW_CFA_def_cfa = 0x0c,
DW_CFA_def_cfa_register = 0x0d,
DW_CFA_def_cfa_offset = 0x0e,

/* DWARF v3 */
DW_CFA_def_cfa_expression = 0x0f,
DW_CFA_expression = 0x10,
DW_CFA_offset_extended_sf = 0x11,
Expand All @@ -462,6 +491,7 @@ enum
DW_CFA_val_offset_sf = 0x15,
DW_CFA_val_expression = 0x16,

/* GNU extensions. */
DW_CFA_GNU_window_save = 0x2d,
DW_CFA_GNU_args_size = 0x2e,
DW_CFA_GNU_negative_offset_extended = 0x2f,
Expand Down
30 changes: 18 additions & 12 deletions src/backend/el.c
Original file line number Diff line number Diff line change
Expand Up @@ -1769,7 +1769,7 @@ elem * el_ptr_offset(symbol *s,targ_size_t offset)
}

#endif


/*************************
* Returns:
* !=0 elem evaluates right-to-left
Expand Down Expand Up @@ -2517,11 +2517,9 @@ int el_match(elem *n1,elem *n2)
else
goto case_long;

#if JHANDLE
case TYjhandle:
#endif
case TYnullptr:
case TYnptr:
case TYnref:
#if TARGET_SEGMENTED
case TYsptr:
case TYcptr:
Expand Down Expand Up @@ -2590,7 +2588,19 @@ int el_match(elem *n1,elem *n2)
if (memcmp(&n1->EV,&n2->EV,sizeof(n1->EV.Vcdouble)))
goto nomatch;
break;

case TYfloat4:
case TYdouble2:
case TYschar16:
case TYuchar16:
case TYshort8:
case TYushort8:
case TYlong4:
case TYulong4:
case TYllong2:
case TYullong2:
if(n1->EV.Vcent.msw != n2->EV.Vcent.msw || n1->EV.Vcent.lsw != n2->EV.Vcent.lsw)
goto nomatch;
break;
case TYcldouble:
#if LNGDBLSIZE > 10
/* sizeof is 12, but actual size of each part is 10 */
Expand Down Expand Up @@ -2798,15 +2808,13 @@ targ_llong el_tolong(elem *e)
goto L1;
#endif

#if JHANDLE
case TYjhandle:
#endif
#if TARGET_SEGMENTED
case TYsptr:
case TYcptr:
#endif
case TYnptr:
case TYnullptr:
case TYnref:
if (NPTRSIZE == SHORTSIZE)
goto Ushort;
if (NPTRSIZE == LONGSIZE)
Expand Down Expand Up @@ -3030,7 +3038,7 @@ void el_check(elem *e)
}

#endif


/*******************************
* Write out expression elem.
*/
Expand Down Expand Up @@ -3142,15 +3150,13 @@ void elem_print_const(elem *e)
case TYuchar:
dbg_printf("%d ",e->EV.Vuchar);
break;
#if JHANDLE
case TYjhandle:
#endif
#if TARGET_SEGMENTED
case TYsptr:
case TYcptr:
#endif
case TYnullptr:
case TYnptr:
case TYnref:
if (NPTRSIZE == LONGSIZE)
goto L1;
if (NPTRSIZE == SHORTSIZE)
Expand Down
15 changes: 1 addition & 14 deletions src/backend/el.h
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,7 @@ struct elem
#define Erd EV.sp.spu.Erd // reaching definition

#define el_int(a,b) el_long(a,b)


typedef elem *elem_p; /* try to reduce the symbol table size */

void el_init(void);
Expand All @@ -142,13 +142,8 @@ elem_p el_scancommas(elem_p);
int el_countCommas(elem_p);
int el_sideeffect(elem_p);
int el_depends(elem *ea,elem *eb);
#if LONGLONG
targ_llong el_tolongt(elem_p);
targ_llong el_tolong(elem_p);
#else
targ_long el_tolongt(elem_p);
targ_long el_tolong(elem_p);
#endif
int el_allbits(elem_p,int);
int el_signx32(elem_p);
targ_ldouble el_toldouble(elem_p);
Expand All @@ -167,11 +162,7 @@ elem_p el_bint(unsigned,type *,elem_p ,elem_p);
elem_p el_unat(unsigned,type *,elem_p);
elem_p el_bin(unsigned,tym_t,elem_p ,elem_p);
elem_p el_una(unsigned,tym_t,elem_p);
#if LONGLONG // DJB
elem_p el_longt(type *,targ_llong);
#else
elem_p el_longt(type *,targ_long);
#endif
symbol *el_alloc_localgot();
elem_p el_var(symbol *);
elem_p el_settype(elem_p ,type *);
Expand All @@ -182,11 +173,7 @@ elem * el_ptr_offset(symbol *s,targ_size_t offset);
void el_replacesym(elem *,symbol *,symbol *);
elem_p el_nelems(type *);

#if LONGLONG
elem_p el_long(tym_t,targ_llong);
#else
elem_p el_long(tym_t,targ_long);
#endif

int ERTOL(elem_p);
int el_noreturn(elem_p);
Expand Down
11 changes: 5 additions & 6 deletions src/backend/evalu8.c
Original file line number Diff line number Diff line change
Expand Up @@ -188,9 +188,6 @@ int boolres(elem *e)
case TYdchar:
case TYllong:
case TYullong:
#if JHANDLE
case TYjhandle:
#endif
#if TARGET_SEGMENTED
case TYsptr:
case TYcptr:
Expand All @@ -201,6 +198,9 @@ int boolres(elem *e)
case TYnptr:
b = el_tolong(e) != 0;
break;
case TYnref: // reference can't be converted to bool
assert(0);
break;
case TYfloat:
case TYifloat:
case TYdouble:
Expand Down Expand Up @@ -261,10 +261,9 @@ int boolres(elem *e)

case TYfloat4:
{ b = 0;
targ_float *pf = (targ_float *)&e->EV.Vcent;
for (size_t i = 0; i < 4; i++)
{
if (isnan(pf[i]) || pf[i] != 0)
if (isnan(e->EV.Vfloat4[i]) || e->EV.Vfloat4[i] != 0)
{ b = 1;
break;
}
Expand Down Expand Up @@ -333,7 +332,7 @@ int iffalse(elem *e)
}
}
}


/******************************
* Constant fold expression tree.
* Calculate &symbol and &*e1 if we can.
Expand Down
61 changes: 16 additions & 45 deletions src/backend/gdag.c
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
// Copyright (C) 1986-1998 by Symantec
// Copyright (C) 2000-2011 by Digital Mars
// Copyright (C) 2000-2015 by Digital Mars
// All Rights Reserved
// http://www.digitalmars.com
// Written by Walter Bright
Expand Down Expand Up @@ -65,8 +65,8 @@ inline int cse_float(elem *e)
*/

void builddags()
{ register unsigned i;
register vec_t aevec;
{ unsigned i;
vec_t aevec;

cmes("builddags()\n");
assert(dfo);
Expand All @@ -92,7 +92,7 @@ void builddags()
/* This is the 'correct' algorithm for CSEs. We can't use it */
/* till we fix the code generator. */
for (i = 0; i < dfotop; i++)
{ register block *b;
{ block *b;

b = dfo[i];
if (b->Belem)
Expand All @@ -119,7 +119,7 @@ void builddags()
/* properly across extended basic blocks. */
aevec = vec_calloc(exptop);
for (i = 0; i < dfotop; i++)
{ register block *b;
{ block *b;

b = dfo[i];
/* if not first block and (there are more than one */
Expand Down Expand Up @@ -148,7 +148,7 @@ void builddags()
// Need 2 passes to converge on solution
for (int j = 0; j < 2; j++)
for (i = 0; i < dfotop; i++)
{ register block *b;
{ block *b;

b = dfo[i];
if (b->Belem)
Expand All @@ -160,7 +160,7 @@ void builddags()
}
}
}


/**********************************
*/

Expand All @@ -187,10 +187,10 @@ STATIC void aeclear(elem *n,vec_t ae)
* ae = vector of available expressions
*/

STATIC void aewalk(register elem **pn,register vec_t ae)
{ register vec_t aer;
register unsigned i,op;
register elem *n,*t;
STATIC void aewalk(elem **pn,vec_t ae)
{ vec_t aer;
unsigned i,op;
elem *n,*t;

n = *pn;
assert(n && ae);
Expand Down Expand Up @@ -305,7 +305,7 @@ STATIC void aewalk(register elem **pn,register vec_t ae)
if (!(s->Sflags & SFLunambig))
vec_subass(ae,starkill);
foreach (i,exptop,ae) /* for each ae elem */
{ register elem *e = expnod[i];
{ elem *e = expnod[i];

if (!e) continue;
if (OTunary(e->Eoper))
Expand Down Expand Up @@ -352,7 +352,7 @@ STATIC void aewalk(register elem **pn,register vec_t ae)
vec_setbit(n->Eexp,ae); /* mark this elem as available */
}
}


/**************************
* Remove a CSE.
* Input:
Expand Down Expand Up @@ -558,7 +558,7 @@ L1: e = *pe;
pe = &(e->E1);
goto L1;
}


/*****************************************
* Do optimizations based on if we know an expression is
* 0 or !=0, even though we don't know anything else.
Expand Down Expand Up @@ -608,7 +608,7 @@ void boolopt()
}

for (i = 0; i < dfotop; i++)
{ register block *b;
{ block *b;

b = dfo[i];
/* if not first block and (there are more than one */
Expand All @@ -635,7 +635,7 @@ void boolopt()
vec_free(aevec);
vec_free(aevecval);
}


/****************************
* Walk tree, replacing bool expressions that we know
* ae = vector of available boolean expressions
Expand Down Expand Up @@ -797,29 +797,8 @@ STATIC void abewalk(elem *n,vec_t ae,vec_t aeval)
{ elem *e = expnod[i];

if (!e) continue;
#if 1
if (el_appears(e,s))
vec_clearbit(i,ae);
#else
if (OTunary(e->Eoper))
{
if (vec_testbit(e->E1->Eexp,ae))
continue;
}
else if (OTbinary(e->Eoper))
{
if (vec_testbit(e->E1->Eexp,ae) &&
vec_testbit(e->E2->Eexp,ae))
continue;
}
else if (e->Eoper == OPvar)
{ if (e->EV.sp.Vsym != s)
continue;
}
else
continue;
vec_clearbit(i,ae);
#endif
}
}
else /* else ambiguous definition */
Expand All @@ -829,7 +808,6 @@ STATIC void abewalk(elem *n,vec_t ae,vec_t aeval)
vec_subass(ae,vptrkill);
}
/* GEN the lvalue of an assignment operator */
#if 1
if (op == OPeq && (i1 = t->Eexp) != 0 && (i2 = n->E2->Eexp) != 0)
{
if (vec_testbit(i2,ae))
Expand All @@ -841,13 +819,6 @@ STATIC void abewalk(elem *n,vec_t ae,vec_t aeval)
vec_clearbit(i1,aeval);
}
}
#else
if ((OTopeq(op) || op == OPeq || op == OPnegass) && n->E1->Eexp)
{ vec_setbit(t->Eexp,ae);
if (n->E1->Eoper == OPbit)
vec_setbit(n->E1->Eexp,ae);
}
#endif
}
else if (n->Eexp) /* if an AE */
{
Expand Down
Loading