Skip to content

Commit 57c5b07

Browse files
thewilsonatorrikkimaxkinkedkorpelRazvanN7
authored
Rebase stable6 (#16967)
* Document template instance duplication status as part of its field documentation. (#16643) * Fix Bugzilla 24599 - Wrongly elided TypeInfo emission (#15868) Reverting #14844, which caused such missing TypeInfos, *and* making sure the special TypeInfo members are fully analyzed and ready for codegen (otherwise hitting an assertion for the real-world project). * Reorganize backend build files to match target and make more similar per line (#16672) * Remove redundant suggestions on linker errors (#16711) * Fix bugzilla 24337 - Segfault when printing an int[] cast from a string (#16729) * Add BitFieldStyle.Gcc_Clang_ARM Required for 32-bit ARM, and non-Apple 64-bit ARM targets. The only difference to `Gcc_Clang` is that anonymous and 0-length bit-fields do contribute to the aggregate alignment. Caught by existing proper C interop tests in runnable_cxx/testbitfields.d on such targets. The hardcoded bad tests in runnable/{bitfieldsposix64.c,dbitfieldsposix64.d} however now fail after the fix, on such targets again. * [refactor to `TargetC.contributesToAggregateAlignment(BitFieldDeclaration)` hook] * Fix Bugzilla Issue 24687 - [REG2.110] Cannot cast string-imports to select overload anymore * Also make deprecationSupplemental adhere to error limit (#16779) Co-authored-by: Dennis Korpel <[email protected]> * Fix bugzilla 24699 - [REG2.108] No short-circuit evaluation of mixing template bool argument * Fix bugzilla 24731 - IFTI cannot handle integer expressions (#16822) * Fix Bugzilla Issue 24760 - ICE on variadic after default argument * Fix bugzilla 24790 - -vcg-ast ICE on lowered assign exp (#16914) Co-authored-by: Dennis Korpel <[email protected]> * Fix bugzilla 24764 - ICE when -vcg-ast prints imported invariant (#16917) Co-authored-by: Dennis Korpel <[email protected]> * Fix bugzilla 24431 - dmd -vcg-ast crashes printing failed template in… (#16916) --------- Co-authored-by: Richard (Rikki) Andrew Cattermole <[email protected]> Co-authored-by: Martin Kinkelin <[email protected]> Co-authored-by: Dennis <[email protected]> Co-authored-by: Martin Kinkelin <[email protected]> Co-authored-by: Martin Kinkelin <[email protected]> Co-authored-by: RazvanN7 <[email protected]> Co-authored-by: Dennis Korpel <[email protected]> Co-authored-by: Dennis Korpel <[email protected]>
1 parent 4c02e46 commit 57c5b07

35 files changed

+359
-146
lines changed

compiler/src/build.d

Lines changed: 16 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1581,10 +1581,12 @@ auto sourceFiles()
15811581
cparse.d
15821582
"),
15831583
backendHeaders: fileArray(env["C"], "
1584-
cc.d cdef.d cgcv.d code.d cv4.d dt.d el.d global.d
1585-
obj.d oper.d rtlsym.d x86/code_x86.d iasm.d codebuilder.d
1586-
ty.d type.d mach.d mscoff.d dwarf.d dwarf2.d x86/xmm.d
1587-
dlist.d melf.d
1584+
cc.d cdef.d cgcv.d code.d dt.d el.d global.d
1585+
obj.d oper.d rtlsym.d iasm.d codebuilder.d
1586+
ty.d type.d dlist.d
1587+
dwarf.d dwarf2.d cv4.d
1588+
melf.d mscoff.d mach.d
1589+
x86/code_x86.d x86/xmm.d
15881590
"),
15891591
};
15901592
foreach (member; __traits(allMembers, DmdSources))
@@ -1620,13 +1622,16 @@ auto sourceFiles()
16201622
"),
16211623
backend: fileArray(env["C"], "
16221624
bcomplex.d evalu8.d divcoeff.d dvec.d go.d gsroa.d glocal.d gdag.d gother.d gflow.d
1623-
dout.d inliner.d
1624-
gloop.d cgelem.d cgcs.d ee.d x86/cod4.d x86/cod5.d eh.d x86/nteh.d blockopt.d mem.d cg.d x86/cgreg.d
1625-
dtype.d debugprint.d fp.d symbol.d symtab.d elem.d dcode.d cgsched.d x86/cg87.d x86/cgxmm.d x86/cgcod.d x86/cod1.d x86/cod2.d
1626-
x86/cod3.d cv8.d dcgcv.d pdata.d util2.d var.d backconfig.d drtlsym.d dwarfeh.d ptrntab.d
1627-
dvarstats.d dwarfdbginf.d cgen.d goh.d barray.d cgcse.d elpicpie.d
1628-
machobj.d elfobj.d mscoffobj.d filespec.d aarray.d x86/disasm86.d arm/disasmarm.d arm/instr.d
1629-
arm/cod1.d arm/cod2.d arm/cod3.d arm/cod4.d
1625+
dout.d inliner.d eh.d filespec.d aarray.d
1626+
gloop.d cgelem.d cgcs.d ee.d blockopt.d mem.d cg.d
1627+
dtype.d debugprint.d fp.d symbol.d symtab.d elem.d dcode.d cgsched.d
1628+
pdata.d util2.d var.d backconfig.d drtlsym.d ptrntab.d
1629+
dvarstats.d cgen.d goh.d barray.d cgcse.d elpicpie.d
1630+
dwarfeh.d dwarfdbginf.d cv8.d dcgcv.d
1631+
machobj.d elfobj.d mscoffobj.d
1632+
x86/nteh.d x86/cgreg.d x86/cg87.d x86/cgxmm.d x86/disasm86.d
1633+
x86/cgcod.d x86/cod1.d x86/cod2.d x86/cod3.d x86/cod4.d x86/cod5.d
1634+
arm/disasmarm.d arm/instr.d arm/cod1.d arm/cod2.d arm/cod3.d arm/cod4.d
16301635
"
16311636
),
16321637
};

compiler/src/dmd/dcast.d

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -705,7 +705,7 @@ MATCH implicitConvTo(Expression e, Type t)
705705
return MATCH.nomatch;
706706
m = MATCH.constant;
707707
}
708-
if (e.hexString && tn.isIntegral && (tn.size == e.sz || (!e.committed && (e.len % tn.size) == 0)))
708+
if (e.type != t && e.hexString && tn.isIntegral && (tn.size == e.sz || (!e.committed && (e.len % tn.size) == 0)))
709709
{
710710
m = MATCH.convert;
711711
return m;

compiler/src/dmd/dsymbolsem.d

Lines changed: 34 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -1832,7 +1832,7 @@ private extern(C++) final class DsymbolSemanticVisitor : Visitor
18321832
{
18331833
//printf("MixinDeclaration::compileIt(loc = %d) %s\n", cd.loc.linnum, cd.exp.toChars());
18341834
OutBuffer buf;
1835-
if (expressionsToString(buf, sc, cd.exps))
1835+
if (expressionsToString(buf, sc, cd.exps, cd.loc, null, true))
18361836
return null;
18371837

18381838
const errors = global.errors;
@@ -7113,12 +7113,19 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
71137113
error(bfd.loc, "bit field width %d is larger than type", bfd.fieldWidth);
71147114

71157115
const style = target.c.bitFieldStyle;
7116+
if (style != TargetC.BitFieldStyle.MS && style != TargetC.BitFieldStyle.Gcc_Clang)
7117+
assert(0, "unsupported bit-field style");
7118+
7119+
const isMicrosoftStyle = style == TargetC.BitFieldStyle.MS;
7120+
const contributesToAggregateAlignment = target.c.contributesToAggregateAlignment(bfd);
71167121

71177122
void startNewField()
71187123
{
71197124
if (log) printf("startNewField()\n");
71207125
uint alignsize;
7121-
if (style == TargetC.BitFieldStyle.Gcc_Clang)
7126+
if (isMicrosoftStyle)
7127+
alignsize = memsize; // not memalignsize
7128+
else
71227129
{
71237130
if (bfd.fieldWidth > 32)
71247131
alignsize = memalignsize;
@@ -7129,15 +7136,13 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
71297136
else
71307137
alignsize = 1;
71317138
}
7132-
else
7133-
alignsize = memsize; // not memalignsize
71347139

71357140
uint dummy;
71367141
bfd.offset = placeField(bfd.loc,
71377142
fieldState.offset,
71387143
memsize, alignsize, bfd.alignment,
71397144
ad.structsize,
7140-
(anon && style == TargetC.BitFieldStyle.Gcc_Clang) ? dummy : ad.alignsize,
7145+
contributesToAggregateAlignment ? ad.alignsize : dummy,
71417146
isunion);
71427147

71437148
fieldState.inFlight = true;
@@ -7146,53 +7151,38 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
71467151
fieldState.fieldSize = memsize;
71477152
}
71487153

7149-
if (style == TargetC.BitFieldStyle.Gcc_Clang)
7154+
if (ad.alignsize == 0)
7155+
ad.alignsize = 1;
7156+
if (!isMicrosoftStyle && contributesToAggregateAlignment && ad.alignsize < memalignsize)
7157+
ad.alignsize = memalignsize;
7158+
7159+
if (bfd.fieldWidth == 0)
71507160
{
7151-
if (bfd.fieldWidth == 0)
7161+
if (!isMicrosoftStyle && !isunion)
71527162
{
7153-
if (!isunion)
7154-
{
7155-
// Use type of zero width field to align to next field
7156-
fieldState.offset = (fieldState.offset + memalignsize - 1) & ~(memalignsize - 1);
7157-
ad.structsize = fieldState.offset;
7158-
}
7159-
7160-
fieldState.inFlight = false;
7161-
return;
7163+
// Use type of zero width field to align to next field
7164+
fieldState.offset = (fieldState.offset + memalignsize - 1) & ~(memalignsize - 1);
7165+
ad.structsize = fieldState.offset;
71627166
}
7163-
7164-
if (ad.alignsize == 0)
7165-
ad.alignsize = 1;
7166-
if (!anon &&
7167-
ad.alignsize < memalignsize)
7168-
ad.alignsize = memalignsize;
7169-
}
7170-
else if (style == TargetC.BitFieldStyle.MS)
7171-
{
7172-
if (ad.alignsize == 0)
7173-
ad.alignsize = 1;
7174-
if (bfd.fieldWidth == 0)
7167+
else if (isMicrosoftStyle && fieldState.inFlight && !isunion)
71757168
{
7176-
if (fieldState.inFlight && !isunion)
7177-
{
7178-
// documentation says align to next int
7179-
//const alsz = cast(uint)Type.tint32.size();
7180-
const alsz = memsize; // but it really does this
7181-
fieldState.offset = (fieldState.offset + alsz - 1) & ~(alsz - 1);
7182-
ad.structsize = fieldState.offset;
7183-
}
7184-
7185-
fieldState.inFlight = false;
7186-
return;
7169+
// documentation says align to next int
7170+
//const alsz = cast(uint)Type.tint32.size();
7171+
const alsz = memsize; // but it really does this
7172+
fieldState.offset = (fieldState.offset + alsz - 1) & ~(alsz - 1);
7173+
ad.structsize = fieldState.offset;
71877174
}
7175+
7176+
fieldState.inFlight = false;
7177+
return;
71887178
}
71897179

71907180
if (!fieldState.inFlight)
71917181
{
71927182
//printf("not in flight\n");
71937183
startNewField();
71947184
}
7195-
else if (style == TargetC.BitFieldStyle.Gcc_Clang)
7185+
else if (!isMicrosoftStyle)
71967186
{
71977187
// If the bit-field spans more units of alignment than its type
71987188
// and is at the alignment boundary, start a new field at the
@@ -7217,7 +7207,7 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
72177207
}
72187208
}
72197209
}
7220-
else if (style == TargetC.BitFieldStyle.MS)
7210+
else
72217211
{
72227212
if (memsize != fieldState.fieldSize ||
72237213
fieldState.bitOffset + bfd.fieldWidth > fieldState.fieldSize * 8)
@@ -7226,14 +7216,14 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
72267216
startNewField();
72277217
}
72287218
}
7229-
else
7230-
assert(0);
72317219

72327220
bfd.offset = fieldState.fieldOffset;
72337221
bfd.bitOffset = fieldState.bitOffset;
72347222

72357223
const pastField = bfd.bitOffset + bfd.fieldWidth;
7236-
if (style == TargetC.BitFieldStyle.Gcc_Clang)
7224+
if (isMicrosoftStyle)
7225+
fieldState.fieldSize = memsize;
7226+
else
72377227
{
72387228
auto size = (pastField + 7) / 8;
72397229
fieldState.fieldSize = size;
@@ -7247,8 +7237,6 @@ private extern(C++) class SetFieldOffsetVisitor : Visitor
72477237
else
72487238
ad.structsize = bfd.offset + size;
72497239
}
7250-
else
7251-
fieldState.fieldSize = memsize;
72527240
//printf("at end: ad.structsize = %d\n", cast(int)ad.structsize);
72537241
//print(fieldState);
72547242

compiler/src/dmd/dtemplate.d

Lines changed: 32 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1695,7 +1695,9 @@ MATCH deduceType(RootObject o, Scope* sc, Type tparam, ref TemplateParameters pa
16951695
edim = s ? getValue(s) : getValue(e);
16961696
}
16971697
}
1698-
if (tp && tp.matchArg(sc, t.dim, i, &parameters, dedtypes, null) || edim && edim.toInteger() == t.dim.toInteger())
1698+
if ((tp && tp.matchArg(sc, t.dim, i, &parameters, dedtypes, null)) ||
1699+
(edim && edim.isIntegerExp() && edim.toInteger() == t.dim.toInteger())
1700+
)
16991701
{
17001702
result = deduceType(t.next, sc, tparam.nextOf(), parameters, dedtypes, wm);
17011703
return;
@@ -3653,7 +3655,22 @@ extern (C++) class TemplateInstance : ScopeDsymbol
36533655
Dsymbol tempdecl; // referenced by foo.bar.abc
36543656
Dsymbol enclosing; // if referencing local symbols, this is the context
36553657
Dsymbol aliasdecl; // !=null if instance is an alias for its sole member
3656-
TemplateInstance inst; // refer to existing instance
3658+
3659+
/**
3660+
If this is not null and it has a value that is not the current object,
3661+
then this field points to an existing template instance
3662+
and that object has been duplicated into us.
3663+
3664+
If this object is a duplicate,
3665+
the ``memberOf`` field will be set to a root module (passed on CLI).
3666+
3667+
This information is useful to deduplicate analysis that may occur
3668+
after semantic 3 has completed.
3669+
3670+
See_Also: memberOf
3671+
*/
3672+
TemplateInstance inst;
3673+
36573674
ScopeDsymbol argsym; // argument symbol table
36583675
size_t hash; // cached result of toHash()
36593676

@@ -3665,7 +3682,15 @@ extern (C++) class TemplateInstance : ScopeDsymbol
36653682

36663683
TemplateInstances* deferred;
36673684

3668-
Module memberOf; // if !null, then this TemplateInstance appears in memberOf.members[]
3685+
/**
3686+
If this is not null then this template instance appears in a root module's members.
3687+
3688+
Note: This is not useful for determining duplication status of this template instance.
3689+
Use the field ``inst`` for determining if a template instance has been duplicated into this object.
3690+
3691+
See_Also: inst
3692+
*/
3693+
Module memberOf;
36693694

36703695
// Used to determine the instance needs code generation.
36713696
// Note that these are inaccurate until semantic analysis phase completed.
@@ -4482,9 +4507,13 @@ extern (C++) class TemplateInstance : ScopeDsymbol
44824507

44834508
// The arguments are not treated as part of a default argument,
44844509
// because they are evaluated at compile time.
4510+
const inCondition = sc.condition;
44854511
sc = sc.push();
44864512
sc.inDefaultArg = false;
44874513

4514+
// https://issues.dlang.org/show_bug.cgi?id=24699
4515+
sc.condition = inCondition;
4516+
44884517
for (size_t j = 0; j < tiargs.length; j++)
44894518
{
44904519
RootObject o = (*tiargs)[j];

compiler/src/dmd/errors.d

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -570,8 +570,11 @@ extern (C++) void verrorReportSupplemental(const ref Loc loc, const(char)* forma
570570
goto case ErrorKind.error;
571571
else if (global.params.useDeprecated == DiagnosticReporting.inform && !global.gag)
572572
{
573-
info.headerColor = Classification.deprecation;
574-
verrorPrint(format, ap, info);
573+
if (global.params.v.errorLimit == 0 || global.deprecations <= global.params.v.errorLimit)
574+
{
575+
info.headerColor = Classification.deprecation;
576+
verrorPrint(format, ap, info);
577+
}
575578
}
576579
break;
577580

compiler/src/dmd/expression.d

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -455,7 +455,7 @@ extern (C++) abstract class Expression : ASTNode
455455
dinteger_t toInteger()
456456
{
457457
//printf("Expression %s\n", EXPtoString(op).ptr);
458-
if (!type.isTypeError())
458+
if (!type || !type.isTypeError())
459459
error(loc, "integer constant expression expected instead of `%s`", toChars());
460460
return 0;
461461
}

compiler/src/dmd/expressionsem.d

Lines changed: 26 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -140,16 +140,26 @@ private bool isNeedThisScope(Scope* sc, Declaration d)
140140
* buf = append generated string to buffer
141141
* sc = context
142142
* exps = array of Expressions
143+
* loc = location of the pragma / mixin where this conversion was requested, for supplemental error
144+
* fmt = format string for supplemental error. May contain 1 `%s` which prints the faulty expression
145+
* expandTuples = whether tuples should be expanded rather than printed as tuple syntax
143146
* Returns:
144147
* true on error
145148
*/
146-
bool expressionsToString(ref OutBuffer buf, Scope* sc, Expressions* exps)
149+
bool expressionsToString(ref OutBuffer buf, Scope* sc, Expressions* exps,
150+
Loc loc, const(char)* fmt, bool expandTuples)
147151
{
148152
if (!exps)
149153
return false;
150154

151155
foreach (ex; *exps)
152156
{
157+
bool error()
158+
{
159+
if (loc != Loc.initial && fmt)
160+
errorSupplemental(loc, fmt, ex.toChars());
161+
return true;
162+
}
153163
if (!ex)
154164
continue;
155165
auto sc2 = sc.startCTFE();
@@ -162,15 +172,16 @@ bool expressionsToString(ref OutBuffer buf, Scope* sc, Expressions* exps)
162172
// allowed to contain types as well as expressions
163173
auto e4 = ctfeInterpretForPragmaMsg(e3);
164174
if (!e4 || e4.op == EXP.error)
165-
return true;
175+
return error();
166176

167177
// expand tuple
168-
if (auto te = e4.isTupleExp())
169-
{
170-
if (expressionsToString(buf, sc, te.exps))
171-
return true;
172-
continue;
173-
}
178+
if (expandTuples)
179+
if (auto te = e4.isTupleExp())
180+
{
181+
if (expressionsToString(buf, sc, te.exps, loc, fmt, true))
182+
return error();
183+
continue;
184+
}
174185
// char literals exp `.toStringExp` return `null` but we cant override it
175186
// because in most contexts we don't want the conversion to succeed.
176187
IntegerExp ie = e4.isIntegerExp();
@@ -181,9 +192,11 @@ bool expressionsToString(ref OutBuffer buf, Scope* sc, Expressions* exps)
181192
e4 = new ArrayLiteralExp(ex.loc, tsa, ie);
182193
}
183194

184-
if (StringExp se = e4.toStringExp())
195+
StringExp se = e4.toStringExp();
196+
197+
if (se && se.type.nextOf().ty.isSomeChar)
185198
buf.writestring(se.toUTF8(sc).peekString());
186-
else
199+
else if (!(se && se.len == 0)) // don't print empty array literal `[]`
187200
buf.writestring(e4.toString());
188201
}
189202
return false;
@@ -336,6 +349,7 @@ StringExp toUTF8(StringExp se, Scope* sc)
336349
Expression e = castTo(se, sc, Type.tchar.arrayOf());
337350
e = e.optimize(WANTvalue);
338351
auto result = e.isStringExp();
352+
assert(result);
339353
assert(result.sz == 1);
340354
return result;
341355
}
@@ -7194,17 +7208,7 @@ private extern (C++) final class ExpressionSemanticVisitor : Visitor
71947208
// Handle this in the glue layer
71957209
Expression e = new TypeidExp(exp.loc, ta);
71967210

7197-
bool genObjCode = true;
7198-
7199-
// https://issues.dlang.org/show_bug.cgi?id=23650
7200-
// We generate object code for typeinfo, required
7201-
// by typeid, only if in non-speculative context
7202-
if (sc.traitsCompiles)
7203-
{
7204-
genObjCode = false;
7205-
}
7206-
7207-
e.type = getTypeInfoType(exp.loc, ta, sc, genObjCode);
7211+
e.type = getTypeInfoType(exp.loc, ta, sc);
72087212
semanticTypeInfo(sc, ta);
72097213

72107214
if (ea)
@@ -7704,7 +7708,7 @@ private extern (C++) final class ExpressionSemanticVisitor : Visitor
77047708
private Expression compileIt(MixinExp exp, Scope *sc)
77057709
{
77067710
OutBuffer buf;
7707-
if (expressionsToString(buf, sc, exp.exps))
7711+
if (expressionsToString(buf, sc, exp.exps, exp.loc, null, true))
77087712
return null;
77097713

77107714
uint errors = global.errors;

0 commit comments

Comments
 (0)