Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
284 changes: 158 additions & 126 deletions compiler/src/dmd/expression.d
Original file line number Diff line number Diff line change
Expand Up @@ -188,7 +188,7 @@ extern (C++) abstract class Expression : ASTNode
}

// memory never freed, so can use the faster bump-pointer-allocation
e = cast(Expression)allocmemory(size);
e = cast(Expression)allocmemoryNoFree(size, expAlign[op]);
//printf("Expression::copy(op = %d) e = %p\n", op, e);
return cast(Expression)memcpy(cast(void*)e, cast(void*)this, size);
}
Expand Down Expand Up @@ -4028,130 +4028,162 @@ private enum EbinaryAssign =
EXP.concatenateAssign, EXP.concatenateElemAssign, EXP.concatenateDcharAssign,
];

alias AliasSeq(T...) = T;
template OpType(EXP e, T)
{
enum op = e;
alias type = T;
}
alias ExpOpTypePairs = AliasSeq!
(
OpType!(EXP.negate, NegExp),
OpType!(EXP.cast_, CastExp),
OpType!(EXP.null_, NullExp),
OpType!(EXP.assert_, AssertExp),
OpType!(EXP.array, ArrayExp),
OpType!(EXP.call, CallExp),
OpType!(EXP.address, AddrExp),
OpType!(EXP.type, TypeExp),
OpType!(EXP.throw_, ThrowExp),
OpType!(EXP.new_, NewExp),
OpType!(EXP.delete_, DeleteExp),
OpType!(EXP.star, PtrExp),
OpType!(EXP.symbolOffset, SymOffExp),
OpType!(EXP.variable, VarExp),
OpType!(EXP.dotVariable, DotVarExp),
OpType!(EXP.dotIdentifier, DotIdExp),
OpType!(EXP.dotTemplateInstance, DotTemplateInstanceExp),
OpType!(EXP.dotType, DotTypeExp),
OpType!(EXP.slice, SliceExp),
OpType!(EXP.arrayLength, ArrayLengthExp),
OpType!(EXP.dollar, DollarExp),
OpType!(EXP.template_, TemplateExp),
OpType!(EXP.dotTemplateDeclaration, DotTemplateExp),
OpType!(EXP.declaration, DeclarationExp),
OpType!(EXP.dSymbol, DsymbolExp),
OpType!(EXP.typeid_, TypeidExp),
OpType!(EXP.uadd, UAddExp),
OpType!(EXP.remove, RemoveExp),
OpType!(EXP.newAnonymousClass, NewAnonClassExp),
OpType!(EXP.arrayLiteral, ArrayLiteralExp),
OpType!(EXP.assocArrayLiteral, AssocArrayLiteralExp),
OpType!(EXP.structLiteral, StructLiteralExp),
OpType!(EXP.classReference, ClassReferenceExp),
OpType!(EXP.thrownException, ThrownExceptionExp),
OpType!(EXP.delegatePointer, DelegatePtrExp),
OpType!(EXP.delegateFunctionPointer, DelegateFuncptrExp),
OpType!(EXP.lessThan, CmpExp),
OpType!(EXP.greaterThan, CmpExp),
OpType!(EXP.lessOrEqual, CmpExp),
OpType!(EXP.greaterOrEqual, CmpExp),
OpType!(EXP.equal, EqualExp),
OpType!(EXP.notEqual, EqualExp),
OpType!(EXP.identity, IdentityExp),
OpType!(EXP.notIdentity, IdentityExp),
OpType!(EXP.index, IndexExp),
OpType!(EXP.is_, IsExp),
OpType!(EXP.leftShift, ShlExp),
OpType!(EXP.rightShift, ShrExp),
OpType!(EXP.leftShiftAssign, ShlAssignExp),
OpType!(EXP.rightShiftAssign, ShrAssignExp),
OpType!(EXP.unsignedRightShift, UshrExp),
OpType!(EXP.unsignedRightShiftAssign, UshrAssignExp),
OpType!(EXP.concatenate, CatExp),
OpType!(EXP.concatenateAssign, CatAssignExp),
OpType!(EXP.concatenateElemAssign, CatElemAssignExp),
OpType!(EXP.concatenateDcharAssign, CatDcharAssignExp),
OpType!(EXP.add, AddExp),
OpType!(EXP.min, MinExp),
OpType!(EXP.addAssign, AddAssignExp),
OpType!(EXP.minAssign, MinAssignExp),
OpType!(EXP.mul, MulExp),
OpType!(EXP.div, DivExp),
OpType!(EXP.mod, ModExp),
OpType!(EXP.mulAssign, MulAssignExp),
OpType!(EXP.divAssign, DivAssignExp),
OpType!(EXP.modAssign, ModAssignExp),
OpType!(EXP.and, AndExp),
OpType!(EXP.or, OrExp),
OpType!(EXP.xor, XorExp),
OpType!(EXP.andAssign, AndAssignExp),
OpType!(EXP.orAssign, OrAssignExp),
OpType!(EXP.xorAssign, XorAssignExp),
OpType!(EXP.assign, AssignExp),
OpType!(EXP.not, NotExp),
OpType!(EXP.tilde, ComExp),
OpType!(EXP.plusPlus, PostExp),
OpType!(EXP.minusMinus, PostExp),
OpType!(EXP.construct, ConstructExp),
OpType!(EXP.blit, BlitExp),
OpType!(EXP.dot, DotExp),
OpType!(EXP.comma, CommaExp),
OpType!(EXP.question, CondExp),
OpType!(EXP.andAnd, LogicalExp),
OpType!(EXP.orOr, LogicalExp),
OpType!(EXP.prePlusPlus, PreExp),
OpType!(EXP.preMinusMinus, PreExp),
OpType!(EXP.identifier, IdentifierExp),
OpType!(EXP.string_, StringExp),
OpType!(EXP.interpolated, InterpExp),
OpType!(EXP.this_, ThisExp),
OpType!(EXP.super_, SuperExp),
OpType!(EXP.halt, HaltExp),
OpType!(EXP.tuple, TupleExp),
OpType!(EXP.error, ErrorExp),
OpType!(EXP.void_, VoidInitExp),
OpType!(EXP.int64, IntegerExp),
OpType!(EXP.float64, RealExp),
OpType!(EXP.complex80, ComplexExp),
OpType!(EXP.import_, ImportExp),
OpType!(EXP.delegate_, DelegateExp),
OpType!(EXP.function_, FuncExp),
OpType!(EXP.mixin_, MixinExp),
OpType!(EXP.in_, InExp),
OpType!(EXP.break_, CTFEExp),
OpType!(EXP.continue_, CTFEExp),
OpType!(EXP.goto_, CTFEExp),
OpType!(EXP.scope_, ScopeExp),
OpType!(EXP.traits, TraitsExp),
OpType!(EXP.overloadSet, OverExp),
OpType!(EXP.defaultInit, DefaultInitExp),
OpType!(EXP.pow, PowExp),
OpType!(EXP.powAssign, PowAssignExp),
OpType!(EXP.vector, VectorExp),
OpType!(EXP.voidExpression, CTFEExp),
OpType!(EXP.cantExpression, CTFEExp),
OpType!(EXP.showCtfeContext, CTFEExp),
OpType!(EXP.objcClassReference, ObjcClassReferenceExp),
OpType!(EXP.vectorArray, VectorArrayExp),
OpType!(EXP.compoundLiteral, CompoundLiteralExp),
OpType!(EXP._Generic, GenericExp),
OpType!(EXP.interval, IntervalExp),
OpType!(EXP.loweredAssignExp, LoweredAssignExp),
);

/// Given a member of the EXP enum, get the class instance size of the corresponding Expression class.
/// Needed because the classes are `extern(C++)`
private immutable ubyte[EXP.max+1] expSize = [
EXP.reserved: 0,
EXP.negate: __traits(classInstanceSize, NegExp),
EXP.cast_: __traits(classInstanceSize, CastExp),
EXP.null_: __traits(classInstanceSize, NullExp),
EXP.assert_: __traits(classInstanceSize, AssertExp),
EXP.array: __traits(classInstanceSize, ArrayExp),
EXP.call: __traits(classInstanceSize, CallExp),
EXP.address: __traits(classInstanceSize, AddrExp),
EXP.type: __traits(classInstanceSize, TypeExp),
EXP.throw_: __traits(classInstanceSize, ThrowExp),
EXP.new_: __traits(classInstanceSize, NewExp),
EXP.delete_: __traits(classInstanceSize, DeleteExp),
EXP.star: __traits(classInstanceSize, PtrExp),
EXP.symbolOffset: __traits(classInstanceSize, SymOffExp),
EXP.variable: __traits(classInstanceSize, VarExp),
EXP.dotVariable: __traits(classInstanceSize, DotVarExp),
EXP.dotIdentifier: __traits(classInstanceSize, DotIdExp),
EXP.dotTemplateInstance: __traits(classInstanceSize, DotTemplateInstanceExp),
EXP.dotType: __traits(classInstanceSize, DotTypeExp),
EXP.slice: __traits(classInstanceSize, SliceExp),
EXP.arrayLength: __traits(classInstanceSize, ArrayLengthExp),
EXP.dollar: __traits(classInstanceSize, DollarExp),
EXP.template_: __traits(classInstanceSize, TemplateExp),
EXP.dotTemplateDeclaration: __traits(classInstanceSize, DotTemplateExp),
EXP.declaration: __traits(classInstanceSize, DeclarationExp),
EXP.dSymbol: __traits(classInstanceSize, DsymbolExp),
EXP.typeid_: __traits(classInstanceSize, TypeidExp),
EXP.uadd: __traits(classInstanceSize, UAddExp),
EXP.remove: __traits(classInstanceSize, RemoveExp),
EXP.newAnonymousClass: __traits(classInstanceSize, NewAnonClassExp),
EXP.arrayLiteral: __traits(classInstanceSize, ArrayLiteralExp),
EXP.assocArrayLiteral: __traits(classInstanceSize, AssocArrayLiteralExp),
EXP.structLiteral: __traits(classInstanceSize, StructLiteralExp),
EXP.classReference: __traits(classInstanceSize, ClassReferenceExp),
EXP.thrownException: __traits(classInstanceSize, ThrownExceptionExp),
EXP.delegatePointer: __traits(classInstanceSize, DelegatePtrExp),
EXP.delegateFunctionPointer: __traits(classInstanceSize, DelegateFuncptrExp),
EXP.lessThan: __traits(classInstanceSize, CmpExp),
EXP.greaterThan: __traits(classInstanceSize, CmpExp),
EXP.lessOrEqual: __traits(classInstanceSize, CmpExp),
EXP.greaterOrEqual: __traits(classInstanceSize, CmpExp),
EXP.equal: __traits(classInstanceSize, EqualExp),
EXP.notEqual: __traits(classInstanceSize, EqualExp),
EXP.identity: __traits(classInstanceSize, IdentityExp),
EXP.notIdentity: __traits(classInstanceSize, IdentityExp),
EXP.index: __traits(classInstanceSize, IndexExp),
EXP.is_: __traits(classInstanceSize, IsExp),
EXP.leftShift: __traits(classInstanceSize, ShlExp),
EXP.rightShift: __traits(classInstanceSize, ShrExp),
EXP.leftShiftAssign: __traits(classInstanceSize, ShlAssignExp),
EXP.rightShiftAssign: __traits(classInstanceSize, ShrAssignExp),
EXP.unsignedRightShift: __traits(classInstanceSize, UshrExp),
EXP.unsignedRightShiftAssign: __traits(classInstanceSize, UshrAssignExp),
EXP.concatenate: __traits(classInstanceSize, CatExp),
EXP.concatenateAssign: __traits(classInstanceSize, CatAssignExp),
EXP.concatenateElemAssign: __traits(classInstanceSize, CatElemAssignExp),
EXP.concatenateDcharAssign: __traits(classInstanceSize, CatDcharAssignExp),
EXP.add: __traits(classInstanceSize, AddExp),
EXP.min: __traits(classInstanceSize, MinExp),
EXP.addAssign: __traits(classInstanceSize, AddAssignExp),
EXP.minAssign: __traits(classInstanceSize, MinAssignExp),
EXP.mul: __traits(classInstanceSize, MulExp),
EXP.div: __traits(classInstanceSize, DivExp),
EXP.mod: __traits(classInstanceSize, ModExp),
EXP.mulAssign: __traits(classInstanceSize, MulAssignExp),
EXP.divAssign: __traits(classInstanceSize, DivAssignExp),
EXP.modAssign: __traits(classInstanceSize, ModAssignExp),
EXP.and: __traits(classInstanceSize, AndExp),
EXP.or: __traits(classInstanceSize, OrExp),
EXP.xor: __traits(classInstanceSize, XorExp),
EXP.andAssign: __traits(classInstanceSize, AndAssignExp),
EXP.orAssign: __traits(classInstanceSize, OrAssignExp),
EXP.xorAssign: __traits(classInstanceSize, XorAssignExp),
EXP.assign: __traits(classInstanceSize, AssignExp),
EXP.not: __traits(classInstanceSize, NotExp),
EXP.tilde: __traits(classInstanceSize, ComExp),
EXP.plusPlus: __traits(classInstanceSize, PostExp),
EXP.minusMinus: __traits(classInstanceSize, PostExp),
EXP.construct: __traits(classInstanceSize, ConstructExp),
EXP.blit: __traits(classInstanceSize, BlitExp),
EXP.dot: __traits(classInstanceSize, DotExp),
EXP.comma: __traits(classInstanceSize, CommaExp),
EXP.question: __traits(classInstanceSize, CondExp),
EXP.andAnd: __traits(classInstanceSize, LogicalExp),
EXP.orOr: __traits(classInstanceSize, LogicalExp),
EXP.prePlusPlus: __traits(classInstanceSize, PreExp),
EXP.preMinusMinus: __traits(classInstanceSize, PreExp),
EXP.identifier: __traits(classInstanceSize, IdentifierExp),
EXP.string_: __traits(classInstanceSize, StringExp),
EXP.interpolated: __traits(classInstanceSize, InterpExp),
EXP.this_: __traits(classInstanceSize, ThisExp),
EXP.super_: __traits(classInstanceSize, SuperExp),
EXP.halt: __traits(classInstanceSize, HaltExp),
EXP.tuple: __traits(classInstanceSize, TupleExp),
EXP.error: __traits(classInstanceSize, ErrorExp),
EXP.void_: __traits(classInstanceSize, VoidInitExp),
EXP.int64: __traits(classInstanceSize, IntegerExp),
EXP.float64: __traits(classInstanceSize, RealExp),
EXP.complex80: __traits(classInstanceSize, ComplexExp),
EXP.import_: __traits(classInstanceSize, ImportExp),
EXP.delegate_: __traits(classInstanceSize, DelegateExp),
EXP.function_: __traits(classInstanceSize, FuncExp),
EXP.mixin_: __traits(classInstanceSize, MixinExp),
EXP.in_: __traits(classInstanceSize, InExp),
EXP.break_: __traits(classInstanceSize, CTFEExp),
EXP.continue_: __traits(classInstanceSize, CTFEExp),
EXP.goto_: __traits(classInstanceSize, CTFEExp),
EXP.scope_: __traits(classInstanceSize, ScopeExp),
EXP.traits: __traits(classInstanceSize, TraitsExp),
EXP.overloadSet: __traits(classInstanceSize, OverExp),
EXP.defaultInit: __traits(classInstanceSize, DefaultInitExp),
EXP.pow: __traits(classInstanceSize, PowExp),
EXP.powAssign: __traits(classInstanceSize, PowAssignExp),
EXP.vector: __traits(classInstanceSize, VectorExp),
EXP.voidExpression: __traits(classInstanceSize, CTFEExp),
EXP.cantExpression: __traits(classInstanceSize, CTFEExp),
EXP.showCtfeContext: __traits(classInstanceSize, CTFEExp),
EXP.objcClassReference: __traits(classInstanceSize, ObjcClassReferenceExp),
EXP.vectorArray: __traits(classInstanceSize, VectorArrayExp),
EXP.compoundLiteral: __traits(classInstanceSize, CompoundLiteralExp),
EXP._Generic: __traits(classInstanceSize, GenericExp),
EXP.interval: __traits(classInstanceSize, IntervalExp),
EXP.loweredAssignExp : __traits(classInstanceSize, LoweredAssignExp),
];
immutable ubyte[EXP.max+1] expSize = (){
ubyte[EXP.max+1] expSize;
foreach(optype; ExpOpTypePairs)
expSize[optype.op] = __traits(classInstanceSize, optype.type);
return expSize;
}();

immutable ubyte[EXP.max+1] expAlign = (){
ubyte[EXP.max+1] expAlign;
foreach(optype; ExpOpTypePairs)
static if (__VERSION__ >= 2101) // support for classInstanceAlignment ?
expAlign[optype.op] = __traits(classInstanceAlignment, optype.type);
else
expAlign[optype.op] = 16; // worst case, GC doesn't guarantee more anyway
return expAlign;
}();

shared static this()
{
import dmd.root.rmem;
foreach(optype; ExpOpTypePairs)
static if (__VERSION__ >= 2101) // support for classInstanceAlignment ?
if (__traits(classInstanceAlignment, optype.type) > DEFAULT_ALIGNMENT)
registerAlignment(typeid(optype.type), __traits(classInstanceAlignment, optype.type));
}
76 changes: 51 additions & 25 deletions compiler/src/dmd/mtype.d
Original file line number Diff line number Diff line change
Expand Up @@ -494,35 +494,61 @@ extern (C++) abstract class Type : ASTNode
extern (C++) __gshared Type[TMAX] basic;

extern (D) __gshared StringTable!Type stringtable;

alias AliasSeq(T...) = T;
template TyType(TY t, T)
{
enum ty = t;
alias type = T;
}
alias TyTypePairs = AliasSeq!
(
TyType!(Tsarray, TypeSArray),
TyType!(Tarray, TypeDArray),
TyType!(Taarray, TypeAArray),
TyType!(Tpointer, TypePointer),
TyType!(Treference, TypeReference),
TyType!(Tfunction, TypeFunction),
TyType!(Tdelegate, TypeDelegate),
TyType!(Tident, TypeIdentifier),
TyType!(Tinstance, TypeInstance),
TyType!(Ttypeof, TypeTypeof),
TyType!(Tenum, TypeEnum),
TyType!(Tstruct, TypeStruct),
TyType!(Tclass, TypeClass),
TyType!(Ttuple, TypeTuple),
TyType!(Tslice, TypeSlice),
TyType!(Treturn, TypeReturn),
TyType!(Terror, TypeError),
TyType!(Tnull, TypeNull),
TyType!(Tvector, TypeVector),
TyType!(Ttraits, TypeTraits),
TyType!(Tmixin, TypeMixin),
TyType!(Tnoreturn, TypeNoreturn),
TyType!(Ttag, TypeTag),
);

extern (D) private static immutable ubyte[TMAX] sizeTy = ()
{
ubyte[TMAX] sizeTy = __traits(classInstanceSize, TypeBasic);
sizeTy[Tsarray] = __traits(classInstanceSize, TypeSArray);
sizeTy[Tarray] = __traits(classInstanceSize, TypeDArray);
sizeTy[Taarray] = __traits(classInstanceSize, TypeAArray);
sizeTy[Tpointer] = __traits(classInstanceSize, TypePointer);
sizeTy[Treference] = __traits(classInstanceSize, TypeReference);
sizeTy[Tfunction] = __traits(classInstanceSize, TypeFunction);
sizeTy[Tdelegate] = __traits(classInstanceSize, TypeDelegate);
sizeTy[Tident] = __traits(classInstanceSize, TypeIdentifier);
sizeTy[Tinstance] = __traits(classInstanceSize, TypeInstance);
sizeTy[Ttypeof] = __traits(classInstanceSize, TypeTypeof);
sizeTy[Tenum] = __traits(classInstanceSize, TypeEnum);
sizeTy[Tstruct] = __traits(classInstanceSize, TypeStruct);
sizeTy[Tclass] = __traits(classInstanceSize, TypeClass);
sizeTy[Ttuple] = __traits(classInstanceSize, TypeTuple);
sizeTy[Tslice] = __traits(classInstanceSize, TypeSlice);
sizeTy[Treturn] = __traits(classInstanceSize, TypeReturn);
sizeTy[Terror] = __traits(classInstanceSize, TypeError);
sizeTy[Tnull] = __traits(classInstanceSize, TypeNull);
sizeTy[Tvector] = __traits(classInstanceSize, TypeVector);
sizeTy[Ttraits] = __traits(classInstanceSize, TypeTraits);
sizeTy[Tmixin] = __traits(classInstanceSize, TypeMixin);
sizeTy[Tnoreturn] = __traits(classInstanceSize, TypeNoreturn);
sizeTy[Ttag] = __traits(classInstanceSize, TypeTag);
foreach(tytype; TyTypePairs)
sizeTy[tytype.ty] = __traits(classInstanceSize, tytype.type);
return sizeTy;
}();

extern (D) private static immutable ubyte[TMAX] alignTy = ()
{
static if (__VERSION__ >= 2101) // support for classInstanceAlignment ?
{
ubyte[TMAX] alignTy = __traits(classInstanceAlignment, TypeBasic);
foreach(tytype; TyTypePairs)
alignTy[tytype.ty] = __traits(classInstanceAlignment, tytype.type);
}
else
ubyte[TMAX] alignTy = 16; // worst case, GC doesn't guarantee more anyway
return alignTy;
}();

final extern (D) this(TY ty) scope @safe nothrow
{
this.ty = ty;
Expand All @@ -535,7 +561,7 @@ extern (C++) abstract class Type : ASTNode

final Type copy() nothrow const
{
Type t = cast(Type)mem.xmalloc(sizeTy[ty]);
Type t = cast(Type)allocmemoryNoFree(sizeTy[ty], alignTy[ty]);
memcpy(cast(void*)t, cast(void*)this, sizeTy[ty]);
return t;
}
Expand Down Expand Up @@ -711,7 +737,7 @@ extern (C++) abstract class Type : ASTNode
final Type nullAttributes() nothrow const
{
uint sz = sizeTy[ty];
Type t = cast(Type)mem.xmalloc(sz);
Type t = cast(Type)allocmemoryNoFree(sz, alignTy[ty]);
memcpy(cast(void*)t, cast(void*)this, sz);
// t.mod = NULL; // leave mod unchanged
t.deco = null;
Expand Down
Loading
Loading