# HG changeset patch # User korDen # Date 1283686342 -14400 # Node ID 010eb8f0e18deb24d2ad16c8ba9f6817df18256b # Parent e6e542f37b947fd7466c2f2534f8c0a91daa2f81 further work on dmd test suite diff -r e6e542f37b94 -r 010eb8f0e18d dmd/CastExp.d --- a/dmd/CastExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/CastExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -2,6 +2,7 @@ import dmd.common; import dmd.Expression; +import dmd.GlobalExpressions; import dmd.TY; import dmd.TypeStruct; import dmd.ErrorExp; @@ -365,7 +366,22 @@ override Expression interpret(InterState istate) { - assert(false); + Expression e; + Expression e1; + +version (LOG) { + printf("CastExp.interpret() %.*s\n", toChars()); +} + e1 = this.e1.interpret(istate); + if (e1 is EXP_CANT_INTERPRET) + goto Lcant; + return Cast(type, to, e1); + + Lcant: +version (LOG) { + printf("CastExp.interpret() %.*s CANT\n", toChars()); +} + return EXP_CANT_INTERPRET; } override bool checkSideEffect(int flag) diff -r e6e542f37b94 -r 010eb8f0e18d dmd/ComplexExp.d --- a/dmd/ComplexExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/ComplexExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -14,6 +14,7 @@ import dmd.TY; import dmd.Port; import dmd.Complex; +import dmd.expression.Util; import dmd.backend.dt_t; import dmd.backend.elem; @@ -118,10 +119,15 @@ override void toMangleBuffer(OutBuffer buf) { - assert(false); + buf.writeByte('c'); + real r = toReal(); + realToMangleBuffer(buf, r); + buf.writeByte('c'); // separate the two + r = toImaginary(); + realToMangleBuffer(buf, r); } + version (_DH) { - OutBuffer hexp; } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/CondExp.d --- a/dmd/CondExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/CondExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -6,6 +6,7 @@ import dmd.PtrExp; import dmd.MATCH; import dmd.Expression; +import dmd.GlobalExpressions; import dmd.Scope; import dmd.InterState; import dmd.OutBuffer; @@ -161,7 +162,20 @@ override Expression interpret(InterState istate) { - assert(false); +version (LOG) { + printf("CondExp.interpret() %.*s\n", toChars()); +} + Expression e = econd.interpret(istate); + if (e !is EXP_CANT_INTERPRET) + { + if (e.isBool(true)) + e = e1.interpret(istate); + else if (e.isBool(false)) + e = e2.interpret(istate); + else + e = EXP_CANT_INTERPRET; + } + return e; } override void checkEscape() diff -r e6e542f37b94 -r 010eb8f0e18d dmd/DebugCondition.d --- a/dmd/DebugCondition.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/DebugCondition.d Sun Sep 05 15:32:22 2010 +0400 @@ -52,9 +52,9 @@ else { if (!mod.debugidsNot) - mod.debugidsNot = new Array(); + mod.debugidsNot = new Vector!string(); - mod.debugidsNot.push(cast(void*)new String(ident.toChars())); + mod.debugidsNot.push(ident.toChars()); } } else if (level <= global.params.debuglevel || level <= mod.debuglevel) diff -r e6e542f37b94 -r 010eb8f0e18d dmd/DebugSymbol.d --- a/dmd/DebugSymbol.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/DebugSymbol.d Sun Sep 05 15:32:22 2010 +0400 @@ -6,45 +6,91 @@ import dmd.Loc; import dmd.Scope; import dmd.ScopeDsymbol; +import dmd.Module; import dmd.HdrGenState; +import dmd.Array; import dmd.OutBuffer; +import dmd.condition.util.findCondition; + +/* DebugSymbol's happen for statements like: + * debug = identifier; + * debug = integer; + */ class DebugSymbol : Dsymbol { uint level; this(Loc loc, Identifier ident) { - assert(false); + super(ident); + this.loc = loc; } this(Loc loc, uint level) { - assert(false); + this.level = level; + this.loc = loc; } override Dsymbol syntaxCopy(Dsymbol s) { - assert(false); + assert(!s); + DebugSymbol ds = new DebugSymbol(loc, ident); + ds.level = level; + return ds; } - override bool addMember(Scope sc, ScopeDsymbol s, bool memnum) + override bool addMember(Scope sc, ScopeDsymbol sd, bool memnum) { - assert(false); + //printf("DebugSymbol.addMember('%s') %s\n", sd.toChars(), toChars()); + Module m; + + // Do not add the member to the symbol table, + // just make sure subsequent debug declarations work. + m = sd.isModule(); + if (ident) + { + if (!m) + error("declaration must be at module level"); + else + { + if (findCondition(m.debugidsNot, ident)) + error("defined after use"); + if (!m.debugids) + m.debugids = new Vector!string(); + m.debugids.push(ident.toChars()); /// + } + } + else + { + if (!m) + error("level declaration must be at module level"); + else + m.debuglevel = level; + } + + return false; } override void semantic(Scope sc) { - assert(false); + //printf("DebugSymbol.semantic() %s\n", toChars()); } override void toCBuffer(OutBuffer buf, HdrGenState* hgs) { - assert(false); + buf.writestring("debug = "); + if (ident) + buf.writestring(ident.toChars()); + else + buf.printf("%u", level); + buf.writestring(";"); + buf.writenl(); } override string kind() { - assert(false); + return "debug"; } } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/Declaration.d --- a/dmd/Declaration.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/Declaration.d Sun Sep 05 15:32:22 2010 +0400 @@ -252,7 +252,6 @@ } case LINK.LINKdefault: - assert(false); error("forward declaration"); return ident.toChars(); diff -r e6e542f37b94 -r 010eb8f0e18d dmd/DotExp.d --- a/dmd/DotExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/DotExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -4,6 +4,9 @@ import dmd.Expression; import dmd.Loc; import dmd.Scope; +import dmd.ScopeExp; +import dmd.TemplateDeclaration; +import dmd.DotTemplateExp; import dmd.BinExp; import dmd.TOK; @@ -11,13 +14,31 @@ { this(Loc loc, Expression e1, Expression e2) { - assert(false); - super(loc, TOK.init, 0, e1, e2); + super(loc, TOKdotexp, DotExp.sizeof, e1, e2); } override Expression semantic(Scope sc) { - assert(false); +version (LOGSEMANTIC) { + printf("DotExp.semantic('%s')\n", toChars()); + if (type) printf("\ttype = %s\n", type.toChars()); +} + e1 = e1.semantic(sc); + e2 = e2.semantic(sc); + if (e2.op == TOKimport) + { + ScopeExp se = cast(ScopeExp)e2; + TemplateDeclaration td = se.sds.isTemplateDeclaration(); + if (td) + { + Expression e = new DotTemplateExp(loc, e1, td); + e = e.semantic(sc); + return e; + } + } + if (!type) + type = e2.type; + return this; } } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/DotTypeExp.d --- a/dmd/DotTypeExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/DotTypeExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -14,6 +14,8 @@ import dmd.PREC; import dmd.expression.Util; +import dmd.backend.Util; + class DotTypeExp : UnaExp { Dsymbol sym; @@ -43,7 +45,13 @@ override elem* toElem(IRState* irs) { - assert(false); + // Just a pass-thru to e1 + elem *e; + + //printf("DotTypeExp.toElem() %s\n", toChars()); + e = e1.toElem(irs); + el_setLoc(e,loc); + return e; } } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/Dsymbol.d --- a/dmd/Dsymbol.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/Dsymbol.d Sun Sep 05 15:32:22 2010 +0400 @@ -579,7 +579,7 @@ AggregateDeclaration isThis() // is a 'this' required to access the member { - assert(false); + return null; } ClassDeclaration isClassMember() // are we a member of a class? diff -r e6e542f37b94 -r 010eb8f0e18d dmd/IndexExp.d --- a/dmd/IndexExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/IndexExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -13,6 +13,7 @@ import dmd.ScopeDsymbol; import dmd.TY; import dmd.ArrayScopeSymbol; +import dmd.PREC; import dmd.TypeNext; import dmd.TypeSArray; import dmd.TypeAArray; @@ -35,6 +36,7 @@ import dmd.expression.util.arrayTypeCompatible; import dmd.expression.Util; import dmd.expression.Index; +import dmd.expression.ArrayLength; import dmd.backend.Symbol; import dmd.backend.Util; @@ -188,7 +190,7 @@ override int isLvalue() { - assert(false); + return true; } override Expression toLvalue(Scope sc, Expression e) @@ -213,7 +215,10 @@ override void toCBuffer(OutBuffer buf, HdrGenState* hgs) { - assert(false); + expToCBuffer(buf, hgs, e1, PREC.PREC_primary); + buf.writeByte('['); + expToCBuffer(buf, hgs, e2, PREC.PREC_assign); + buf.writeByte(']'); } override Expression optimize(int result) @@ -246,7 +251,35 @@ override Expression interpret(InterState istate) { - assert(false); + Expression e; + Expression e1; + Expression e2; + + version (LOG) { + printf("IndexExp.interpret() %s\n", toChars()); + } + e1 = this.e1.interpret(istate); + if (e1 is EXP_CANT_INTERPRET) + goto Lcant; + + if (e1.op == TOKstring || e1.op == TOKarrayliteral) + { + /* Set the $ variable + */ + e = ArrayLength(Type.tsize_t, e1); + if (e is EXP_CANT_INTERPRET) + goto Lcant; + if (lengthVar) + lengthVar.value = e; + } + + e2 = this.e2.interpret(istate); + if (e2 is EXP_CANT_INTERPRET) + goto Lcant; + return Index(type, e1, e2); + + Lcant: + return EXP_CANT_INTERPRET; } override Expression doInline(InlineDoState ids) diff -r e6e542f37b94 -r 010eb8f0e18d dmd/Module.d --- a/dmd/Module.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/Module.d Sun Sep 05 15:32:22 2010 +0400 @@ -223,8 +223,8 @@ ModuleInfoDeclaration vmoduleinfo; uint debuglevel; // debug level - Array debugids; // debug identifiers - Array debugidsNot; // forward referenced debug identifiers + Vector!string debugids; // debug identifiers + Vector!string debugidsNot; // forward referenced debug identifiers uint versionlevel; // version level Array versionids; // version identifiers @@ -297,7 +297,7 @@ symfile = new File(symfilename); } - static Module load(Loc loc, Identifiers packages, Identifier ident) + static Module load(Loc loc, Vector!Identifier packages, Identifier ident) { Module m; string filename; @@ -311,7 +311,8 @@ filename = ident.toChars(); if (packages && packages.dim) { - scope buf = new OutBuffer(); + scope OutBuffer buf = new OutBuffer(); + int i; foreach (pid; packages) { diff -r e6e542f37b94 -r 010eb8f0e18d dmd/Param.d --- a/dmd/Param.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/Param.d Sun Sep 05 15:32:22 2010 +0400 @@ -65,7 +65,7 @@ string xfilename; // write JSON file to xfilename uint debuglevel; // debug level - Array debugids; // debug identifiers + Vector!string debugids; // debug identifiers uint versionlevel; // version level Array versionids; // version identifiers diff -r e6e542f37b94 -r 010eb8f0e18d dmd/RealExp.d --- a/dmd/RealExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/RealExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -1,6 +1,7 @@ module dmd.RealExp; import dmd.common; +import dmd.Complex; import dmd.Expression; import dmd.backend.elem; import dmd.InterState; @@ -15,13 +16,13 @@ import dmd.Port; import dmd.TY; +import dmd.expression.Util; + import dmd.backend.dt_t; import dmd.backend.Util; import dmd.backend.TYM; import dmd.backend.mTY; -import dmd.Complex; - import std.stdio; class RealExp : Expression @@ -38,7 +39,20 @@ override bool equals(Object o) { - assert(false); + if (this is o) + return true; + + Expression e = cast(Expression)o; + if (e.op == TOKfloat64) { + RealExp ne = cast(RealExp)e; + if (type.toHeadMutable().equals(ne.type.toHeadMutable())) { + if (RealEquals(value, ne.value)) { + return true; + } + } + } + + return 0; } override Expression semantic(Scope sc) @@ -120,7 +134,8 @@ override void toMangleBuffer(OutBuffer buf) { - assert(false); + buf.writeByte('e'); + realToMangleBuffer(buf, value); } override elem* toElem(IRState* irs) diff -r e6e542f37b94 -r 010eb8f0e18d dmd/Scope.d --- a/dmd/Scope.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/Scope.d Sun Sep 05 15:32:22 2010 +0400 @@ -171,13 +171,7 @@ Scope clone() { - // similar code is used in Type.clone() - // TODO: move to Util or something... - size_t size = __traits(classInstanceSize, typeof(this)); - void* mem = GC.malloc(size); - memcpy(mem, cast(void*)this, size); - - return cast(typeof(this))mem; + return cloneThis(this); } Scope push() diff -r e6e542f37b94 -r 010eb8f0e18d dmd/StringExp.d --- a/dmd/StringExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/StringExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -108,7 +108,7 @@ case 'd': for (u = 0; u < len;) { - p = utf_decodeChar(cast(string)string_[0..len], &u, &c); + p = utf_decodeChar((cast(char*)string_)[0..len], &u, &c); if (p !is null) { error("%s", p); @@ -132,7 +132,7 @@ case 'w': for (u = 0; u < len;) { - p = utf_decodeChar(cast(string)string_[0..len], &u, &c); + p = utf_decodeChar((cast(char*)string_)[0..len], &u, &c); if (p !is null) { error("%s", p); @@ -191,7 +191,7 @@ case 1: for (size_t u = 0; u < len;) { - p = utf_decodeChar(cast(string)string_[0..len], &u, &c); + p = utf_decodeChar((cast(char*)string_)[0..len], &u, &c); if (p) { error("%s", p); @@ -205,7 +205,7 @@ case 2: for (size_t u = 0; u < len;) { - p = utf_decodeWchar(cast(wstring)string_[0..len], &u, &c); + p = utf_decodeWchar((cast(wchar*)string_)[0..len], &u, &c); if (p) { error("%s", p); break; @@ -446,7 +446,7 @@ for (size_t u = 0; u < len;) { dchar c; - string p = utf_decodeChar(cast(string)se.string_[0..len], &u, &c); + string p = utf_decodeChar((cast(char*)se.string_)[0..len], &u, &c); if (p !is null) error("%s", p); else @@ -460,7 +460,7 @@ for (size_t u = 0; u < len;) { dchar c; - string p = utf_decodeChar(cast(string)se.string_[0..len], &u, &c); + string p = utf_decodeChar((cast(char*)se.string_)[0..len], &u, &c); if (p !is null) error("%s", p); buffer.write4(c); @@ -473,7 +473,7 @@ for (size_t u = 0; u < len;) { dchar c; - string p = utf_decodeWchar(cast(wstring)se.string_[0..len], &u, &c); + string p = utf_decodeWchar((cast(wchar*)se.string_)[0..len], &u, &c); if (p) error("%s", p); else @@ -487,7 +487,7 @@ for (size_t u = 0; u < len;) { dchar c; - string p = utf_decodeWchar(cast(wstring)se.string_[0..len], &u, &c); + string p = utf_decodeWchar((cast(wchar*)se.string_)[0..len], &u, &c); if (p) error("%s", p); buffer.write4(c); @@ -733,7 +733,7 @@ m = 'w'; for (u = 0; u < len; ) { - p = utf_decodeWchar(cast(wstring)string_[0..len], &u, &c); + p = utf_decodeWchar((cast(wchar*)string_)[0..len], &u, &c); if (p) error("%s", p); else diff -r e6e542f37b94 -r 010eb8f0e18d dmd/StructDeclaration.d --- a/dmd/StructDeclaration.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/StructDeclaration.d Sun Sep 05 15:32:22 2010 +0400 @@ -61,6 +61,8 @@ import dmd.backend.FL; import dmd.backend.glue; +import std.stdio; + class StructDeclaration : AggregateDeclaration { bool zeroInit; // true if initialize with 0 fill @@ -203,23 +205,33 @@ int members_dim = members.dim; foreach(Dsymbol s; members) { - s.semantic(sc2); - if (isUnionDeclaration()) - sc2.offset = 0; + s.semantic(sc2); + if (isUnionDeclaration()) + sc2.offset = 0; static if (false) { - if (sizeok == 2) - { //printf("forward reference\n"); - break; - } + if (sizeok == 2) + { //printf("forward reference\n"); + break; + } } - Type t; - if (s.isDeclaration() && - (t = s.isDeclaration().type) !is null && - t.toBasetype().ty == TY.Tstruct) - { StructDeclaration sd = cast(StructDeclaration)t.toDsymbol(sc); - if (sd.isnested) - error("inner struct %s cannot be a field", sd.toChars()); - } + if (auto d = s.isDeclaration()) + { + if (auto t = d.type) { + if (t.toBasetype().ty == TY.Tstruct) { + auto ad = t.toDsymbol(sc).isThis(); + /* + StructDeclaration sd = cast(StructDeclaration)foo; + if (foo && !sd) { + writeln(t.classin); + writeln(foo.classinfo.name); + assert(false); + } + */ + if (ad && ad.isnested) + error("inner struct %s cannot be a field", ad.toChars()); + } + } + } } /* The TypeInfo_Struct is expecting an opEquals and opCmp with @@ -231,22 +243,22 @@ TypeFunction tfeqptr; { - auto arguments = new Arguments; - auto arg = new Argument(STC.STCin, handle, Id.p, null); + Arguments arguments = new Arguments; + Argument arg = new Argument(STC.STCin, handle, Id.p, null); - arguments.push(arg); - tfeqptr = new TypeFunction(arguments, Type.tint32, 0, LINK.LINKd); - tfeqptr = cast(TypeFunction)tfeqptr.semantic(Loc(0), sc); + arguments.push(arg); + tfeqptr = new TypeFunction(arguments, Type.tint32, 0, LINK.LINKd); + tfeqptr = cast(TypeFunction)tfeqptr.semantic(Loc(0), sc); } TypeFunction tfeq; { - auto arguments = new Arguments; - auto arg = new Argument(STC.STCin, type, null, null); + Arguments arguments = new Arguments; + Argument arg = new Argument(STC.STCin, type, null, null); - arguments.push(arg); - tfeq = new TypeFunction(arguments, Type.tint32, 0, LINK.LINKd); - tfeq = cast(TypeFunction)tfeq.semantic(Loc(0), sc); + arguments.push(arg); + tfeq = new TypeFunction(arguments, Type.tint32, 0, LINK.LINKd); + tfeq = cast(TypeFunction)tfeq.semantic(Loc(0), sc); } Identifier id = Id.eq; @@ -437,8 +449,8 @@ FuncDeclaration fop = null; - auto param = new Argument(STC.STCnodtor, type, Id.p, null); - auto fparams = new Arguments; + Argument param = new Argument(STC.STCnodtor, type, Id.p, null); + Arguments fparams = new Arguments; fparams.push(param); Type ftype = new TypeFunction(fparams, handle, false, LINK.LINKd); version (STRUCTTHISREF) { @@ -650,41 +662,41 @@ */ if (postblit) { - //printf("generating cpctor\n"); + //printf("generating cpctor\n"); - auto param = new Argument(STC.STCref, type, Id.p, null); - auto fparams = new Arguments; - fparams.push(param); - Type ftype = new TypeFunction(fparams, Type.tvoid, false, LINK.LINKd); + Argument param = new Argument(STC.STCref, type, Id.p, null); + Arguments fparams = new Arguments; + fparams.push(param); + Type ftype = new TypeFunction(fparams, Type.tvoid, false, LINK.LINKd); - fcp = new FuncDeclaration(Loc(0), Loc(0), Id.cpctor, STC.STCundefined, ftype); + fcp = new FuncDeclaration(Loc(0), Loc(0), Id.cpctor, STC.STCundefined, ftype); - // Build *this = p; - Expression e = new ThisExp(Loc(0)); + // Build *this = p; + Expression e = new ThisExp(Loc(0)); version (STRUCTTHISREF) { } else { - e = new PtrExp(Loc(0), e); + e = new PtrExp(Loc(0), e); } - auto ea = new AssignExp(Loc(0), e, new IdentifierExp(Loc(0), Id.p)); - ea.op = TOK.TOKblit; - Statement s = new ExpStatement(Loc(0), ea); + AssignExp ea = new AssignExp(Loc(0), e, new IdentifierExp(Loc(0), Id.p)); + ea.op = TOK.TOKblit; + Statement s = new ExpStatement(Loc(0), ea); - // Build postBlit(); - e = new VarExp(Loc(0), postblit, 0); - e = new CallExp(Loc(0), e); + // Build postBlit(); + e = new VarExp(Loc(0), postblit, 0); + e = new CallExp(Loc(0), e); - s = new CompoundStatement(Loc(0), s, new ExpStatement(Loc(0), e)); - fcp.fbody = s; + s = new CompoundStatement(Loc(0), s, new ExpStatement(Loc(0), e)); + fcp.fbody = s; - members.push(fcp); + members.push(fcp); - sc = sc.push(); - sc.stc = STC.STCundefined; - sc.linkage = LINK.LINKd; + sc = sc.push(); + sc.stc = STC.STCundefined; + sc.linkage = LINK.LINKd; - fcp.semantic(sc); + fcp.semantic(sc); - sc.pop(); + sc.pop(); } return fcp; diff -r e6e542f37b94 -r 010eb8f0e18d dmd/SymOffExp.d --- a/dmd/SymOffExp.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/SymOffExp.d Sun Sep 05 15:32:22 2010 +0400 @@ -75,7 +75,7 @@ override bool isBool(bool result) { - assert(false); + return result; } override Expression doInline(InlineDoState ids) diff -r e6e542f37b94 -r 010eb8f0e18d dmd/TypeAArray.d --- a/dmd/TypeAArray.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/TypeAArray.d Sun Sep 05 15:32:22 2010 +0400 @@ -357,12 +357,12 @@ override bool isZeroInit(Loc loc) { - assert(false); + return true; } override bool checkBoolean() { - assert(false); + return true; } override TypeInfoDeclaration getTypeInfoDeclaration() diff -r e6e542f37b94 -r 010eb8f0e18d dmd/TypeFunction.d --- a/dmd/TypeFunction.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/TypeFunction.d Sun Sep 05 15:32:22 2010 +0400 @@ -15,6 +15,7 @@ import dmd.PROT; import dmd.TypeIdentifier; import dmd.TemplateParameter; +import dmd.TypeInfoFunctionDeclaration; import dmd.Tuple; import dmd.Type; import dmd.Loc; @@ -42,6 +43,8 @@ import core.stdc.stdlib; import core.stdc.string; +import std.stdio; + class TypeFunction : TypeNext { // .next is the return type @@ -103,11 +106,10 @@ if (parameters) { t.parameters = parameters.copy(); - for (size_t i = 0; i < parameters.dim; i++) + foreach (arg; parameters) { - Argument arg = cast(Argument)parameters.data[i]; Argument cpy = arg.clone(); - t.parameters.data[i] = cast(void*)cpy; + t.parameters[i] = cpy; } } @@ -116,7 +118,7 @@ TypeFunction clone() { - assert(this.classinfo == TypeFunction.classinfo); + assert(this.classinfo is TypeFunction.classinfo); return cloneTo(new TypeFunction(null, next, varargs, linkage)); } } @@ -135,7 +137,7 @@ * as semantic() will get called again on this. */ - TypeFunction tf = cast(TypeFunction)clone(); + TypeFunction tf = cloneThis(this); if (sc.stc & STC.STCpure) tf.ispure = true; @@ -151,20 +153,23 @@ version(SARRAYVALUE) {} else { if (tf.next.toBasetype().ty == TY.Tsarray) - { error(loc, "functions cannot return static array %s", tf.next.toChars()); + { + error(loc, "functions cannot return static array %s", tf.next.toChars()); tf.next = Type.terror; } } if (tf.next.toBasetype().ty == TY.Tfunction) - { error(loc, "functions cannot return a function"); + { + error(loc, "functions cannot return a function"); tf.next = Type.terror; } if (tf.next.toBasetype().ty == TY.Ttuple) - { error(loc, "functions cannot return a tuple"); + { + error(loc, "functions cannot return a tuple"); tf.next = Type.terror; } if (tf.next.isauto() && !(sc.flags & SCOPE.SCOPEctor)) - error(loc, "functions cannot return scope %s", tf.next.toChars()); + error(loc, "functions cannot return scope %s", tf.next.toChars()); } if (tf.parameters) @@ -498,7 +503,7 @@ override TypeInfoDeclaration getTypeInfoDeclaration() { - assert(false); + return new TypeInfoFunctionDeclaration(this); } override Type reliesOnTident() diff -r e6e542f37b94 -r 010eb8f0e18d dmd/TypeInfoFunctionDeclaration.d --- a/dmd/TypeInfoFunctionDeclaration.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/TypeInfoFunctionDeclaration.d Sun Sep 05 15:32:22 2010 +0400 @@ -3,7 +3,12 @@ import dmd.common; import dmd.Type; import dmd.TypeInfoDeclaration; +import dmd.TypeFunction; +import dmd.TY; + import dmd.backend.dt_t; +import dmd.backend.Util; +import dmd.backend.TYM; class TypeInfoFunctionDeclaration : TypeInfoDeclaration { @@ -15,7 +20,16 @@ override void toDt(dt_t** pdt) { - assert(false); + //printf("TypeInfoFunctionDeclaration.toDt()\n"); + dtxoff(pdt, Type.typeinfofunction.toVtblSymbol(), 0, TYnptr); // vtbl for TypeInfo_Function + dtdword(pdt, 0); // monitor + + assert(tinfo.ty == Tfunction); + + TypeFunction tc = cast(TypeFunction)tinfo; + + tc.next.getTypeInfo(null); + dtxoff(pdt, tc.next.vtinfo.toSymbol(), 0, TYnptr); // TypeInfo for function return value } } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/Util.d --- a/dmd/Util.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/Util.d Sun Sep 05 15:32:22 2010 +0400 @@ -14,6 +14,9 @@ import std.process : getenv; import std.c.string; import std.stdio : writef, writefln, write; + +import core.memory; + version (Windows) { import std.c.process : spawnl, spawnlp; @@ -99,6 +102,17 @@ global.errors++; } +T cloneThis(T)(T ptr) +{ + // similar code is used in Type.clone() + // TODO: move to Util or something... + size_t size = __traits(classInstanceSize, T); + void* mem = GC.malloc(size); + memcpy(mem, cast(void*)ptr, size); + + return cast(T)mem; +} + char* strupr(char* s) { char* t = s; diff -r e6e542f37b94 -r 010eb8f0e18d dmd/VersionSymbol.d --- a/dmd/VersionSymbol.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/VersionSymbol.d Sun Sep 05 15:32:22 2010 +0400 @@ -13,14 +13,14 @@ import dmd.String; import dmd.OutBuffer; +/* VersionSymbol's happen for statements like: + * version = identifier; + * version = integer; + */ class VersionSymbol : Dsymbol { uint level; - /* VersionSymbol's happen for statements like: - * version = identifier; - * version = integer; - */ this(Loc loc, Identifier ident) { super(ident); @@ -37,7 +37,10 @@ override Dsymbol syntaxCopy(Dsymbol s) { - assert(false); + assert(!s); + VersionSymbol ds = new VersionSymbol(loc, ident); + ds.level = level; + return ds; } override bool addMember(Scope sc, ScopeDsymbol s, bool memnum) @@ -78,11 +81,17 @@ override void toCBuffer(OutBuffer buf, HdrGenState* hgs) { - assert(false); + buf.writestring("version = "); + if (ident) + buf.writestring(ident.toChars()); + else + buf.printf("%u", level); + buf.writestring(";"); + buf.writenl(); } override string kind() { - assert(false); + return "version"; } } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/WithScopeSymbol.d --- a/dmd/WithScopeSymbol.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/WithScopeSymbol.d Sun Sep 05 15:32:22 2010 +0400 @@ -13,12 +13,13 @@ this(WithStatement withstate) { - assert(false); + this.withstate = withstate; } override Dsymbol search(Loc loc, Identifier ident, int flags) { - assert(false); + // Acts as proxy to the with class declaration + return withstate.exp.type.toDsymbol(null).search(loc, ident, 0); } override WithScopeSymbol isWithScopeSymbol() { return this; } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/WithStatement.d --- a/dmd/WithStatement.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/WithStatement.d Sun Sep 05 15:32:22 2010 +0400 @@ -6,12 +6,29 @@ import dmd.VarDeclaration; import dmd.Loc; import dmd.OutBuffer; +import dmd.ScopeDsymbol; +import dmd.TypeExp; +import dmd.TOK; +import dmd.Initializer; +import dmd.ExpInitializer; +import dmd.Id; +import dmd.ScopeExp; +import dmd.WithScopeSymbol; +import dmd.TY; +import dmd.Type; import dmd.HdrGenState; import dmd.InlineScanState; import dmd.IRState; import dmd.Scope; import dmd.BE; +import dmd.backend.Symbol; +import dmd.backend.block; +import dmd.backend.Blockx; +import dmd.backend.elem; +import dmd.backend.Util; +import dmd.backend.OPER; + class WithStatement : Statement { Expression exp; @@ -28,12 +45,74 @@ override Statement syntaxCopy() { - assert(false); + WithStatement s = new WithStatement(loc, exp.syntaxCopy(), body_ ? body_.syntaxCopy() : null); + return s; } override Statement semantic(Scope sc) { - assert(false); + ScopeDsymbol sym; + Initializer init; + + //printf("WithStatement.semantic()\n"); + exp = exp.semantic(sc); + exp = resolveProperties(sc, exp); + if (exp.op == TOKimport) + { + ScopeExp es = cast(ScopeExp)exp; + + sym = es.sds; + } + else if (exp.op == TOKtype) + { + TypeExp es = cast(TypeExp)exp; + + sym = es.type.toDsymbol(sc).isScopeDsymbol(); + if (!sym) + { + error("%s has no members", es.toChars()); + body_ = body_.semantic(sc); + return this; + } + } + else + { + Type t = exp.type; + + assert(t); + t = t.toBasetype(); + if (t.isClassHandle()) + { + init = new ExpInitializer(loc, exp); + wthis = new VarDeclaration(loc, exp.type, Id.withSym, init); + wthis.semantic(sc); + + sym = new WithScopeSymbol(this); + sym.parent = sc.scopesym; + } + else if (t.ty == Tstruct) + { + Expression e = exp.addressOf(sc); + init = new ExpInitializer(loc, e); + wthis = new VarDeclaration(loc, e.type, Id.withSym, init); + wthis.semantic(sc); + sym = new WithScopeSymbol(this); + sym.parent = sc.scopesym; + } + else + { + error("with expressions must be class objects, not '%s'", exp.type.toChars()); + return null; + } + } + sc = sc.push(sym); + + if (body_) + body_ = body_.semantic(sc); + + sc.pop(); + + return this; } override void toCBuffer(OutBuffer buf, HdrGenState* hgs) @@ -48,7 +127,14 @@ override BE blockExit() { - assert(false); + BE result = BEnone; + if (exp.canThrow()) + result = BEthrow; + if (body_) + result |= body_.blockExit(); + else + result |= BEfallthru; + return result; } override Statement inlineScan(InlineScanState* iss) @@ -58,6 +144,34 @@ override void toIR(IRState* irs) { - assert(false); + Symbol* sp; + elem* e; + elem* ei; + ExpInitializer ie; + Blockx* blx = irs.blx; + + //printf("WithStatement.toIR()\n"); + if (exp.op == TOKimport || exp.op == TOKtype) + { + } + else + { + // Declare with handle + sp = wthis.toSymbol(); + symbol_add(sp); + + // Perform initialization of with handle + ie = wthis.init.isExpInitializer(); + assert(ie); + ei = ie.exp.toElem(irs); + e = el_var(sp); + e = el_bin(OPeq,e.Ety, e, ei); + elem_setLoc(e, loc); + incUsage(irs, loc); + block_appendexp(blx.curblock,e); + } + // Execute with block + if (body_) + body_.toIR(irs); } } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/condition/util/findCondition.d --- a/dmd/condition/util/findCondition.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/condition/util/findCondition.d Sun Sep 05 15:32:22 2010 +0400 @@ -5,15 +5,15 @@ import dmd.Array; import dmd.Identifier; -bool findCondition(Array ids, Identifier ident) +bool findCondition(Vector!string ids, Identifier ident) { if (ids) { for (int i = 0; i < ids.dim; i++) { - String id = cast(String)ids.data[i]; + string id = ids[i]; - if (id.str == ident.toChars()) { + if (id == ident.toChars()) { return true; } } diff -r e6e542f37b94 -r 010eb8f0e18d dmd/expression/Util.d --- a/dmd/expression/Util.d Sat Sep 04 01:33:05 2010 +0100 +++ b/dmd/expression/Util.d Sun Sep 05 15:32:22 2010 +0400 @@ -67,6 +67,8 @@ import std.stdio : writef; +import core.stdc.math; +import core.stdc.string; /*********************************** * Utility to build a function call out of this reference and argument. @@ -952,11 +954,11 @@ /* Create the TypeTuple corresponding to the types of args[] */ - auto args = new Arguments; + Arguments args = new Arguments; args.setDim(dim); for (size_t i = 0; i < dim; i++) { - auto arg = new Argument(STCin, exps[i].type, null, null); + Argument arg = new Argument(STCin, exps[i].type, null, null); args[i] = arg; } TypeTuple tup = new TypeTuple(args); @@ -1284,14 +1286,14 @@ if (u == arguments.dim) return; - auto arg = arguments[u]; + Argument arg = arguments[u]; if (!arg.type) break; } AggregateDeclaration ad; - auto arg = arguments[0]; + Argument arg = arguments[0]; Type taggr = aggr.type; if (!taggr) return; @@ -1465,7 +1467,7 @@ for (size_t u = 0; u < nparams; u++) { - auto arg = arguments[u]; + Argument arg = arguments[u]; Argument param = Argument.getNth(tf.parameters, u); if (arg.type) { @@ -1558,4 +1560,64 @@ } } } +} + +void realToMangleBuffer(OutBuffer buf, real value) +{ + /* Rely on %A to get portable mangling. + * Must munge result to get only identifier characters. + * + * Possible values from %A => mangled result + * NAN => NAN + * -INF => NINF + * INF => INF + * -0X1.1BC18BA997B95P+79 => N11BC18BA997B95P79 + * 0X1.9P+2 => 19P2 + */ + + if (isnan(value)) + buf.writestring("NAN"); // no -NAN bugs + else + { + char buffer[32]; + int n = sprintf(buffer.ptr, "%LA", value); + assert(n > 0 && n < buffer.sizeof); + for (int i = 0; i < n; i++) + { char c = buffer[i]; + + switch (c) + { + case '-': + buf.writeByte('N'); + break; + + case '+': + case 'X': + case '.': + break; + + case '0': + if (i < 2) + break; // skip leading 0X + default: + buf.writeByte(c); + break; + } + } + } +} + +/******************************** + * Test to see if two reals are the same. + * Regard NaN's as equivalent. + * Regard +0 and -0 as different. + */ + +int RealEquals(real x1, real x2) +{ + return (isnan(x1) && isnan(x2)) || + /* In some cases, the REALPAD bytes get garbage in them, + * so be sure and ignore them. + */ + memcmp(&x1, &x2, REALSIZE - REALPAD) == 0; } \ No newline at end of file