aboutsummaryrefslogtreecommitdiff
path: root/gcc/d/dmd/func.d
diff options
context:
space:
mode:
authorIain Buclaw <ibuclaw@gdcproject.org>2021-12-05 17:11:12 +0100
committerIain Buclaw <ibuclaw@gdcproject.org>2021-12-09 00:58:58 +0100
commit0fb57034770aa20adced4d176f34ca611c2945bf (patch)
tree1f5735c8b4f25aa4a290e5ae8124713c24f98359 /gcc/d/dmd/func.d
parentc15aa46cca0649b68613d3292cf71c7cc57ef78f (diff)
downloadgcc-0fb57034770aa20adced4d176f34ca611c2945bf.zip
gcc-0fb57034770aa20adced4d176f34ca611c2945bf.tar.gz
gcc-0fb57034770aa20adced4d176f34ca611c2945bf.tar.bz2
d: Merge upstream dmd 568496d5b, druntime 178c44ff, phobos 574bf883b.
D front-end changes: - Import dmd v2.098.0 - New ImportC module for compiling preprocessed C11 code into D. - New -ftransition=in switch. - Improved handling of new 'noreturn' type. Druntime changes: - Import druntime v2.098.0 - Fix broken import in core.sys.linux.perf_event module (PR103558). Phobos changes: - Import phobos v2.098.0 - All sources are now compiled with -fpreview=fieldwise. gcc/d/ChangeLog: * dmd/MERGE: Merge upstream dmd 568496d5b. * Make-lang.in (D_FRONTEND_OBJS): Add d/common-file.o, d/common-outbuffer.o, d/common-string.o, d/file_manager.o, d/importc.o. Remove d/root-outbuffer.o. (d/common-%.o): New recipe. * d-builtins.cc (build_frontend_type): Update for new front-end interface. (d_build_d_type_nodes): Set noreturn_type_node. * d-codegen.cc (d_build_call): Don't call function if one of the arguments is type 'noreturn'. (build_vthis_function): Propagate TYPE_QUAL_VOLATILE from original function type. * d-frontend.cc (eval_builtin): Update signature. (getTypeInfoType): Likewise. (toObjFile): New function. * d-gimplify.cc (d_gimplify_call_expr): Always evaluate arguments from left to right. * d-lang.cc (d_handle_option): Handle OPT_ftransition_in. (d_parse_file): Don't generate D main if it is declared in user code. * d-tree.h (CALL_EXPR_ARGS_ORDERED): Remove. (enum d_tree_index): Add DTI_BOTTOM_TYPE. (noreturn_type_node): New. * decl.cc (apply_pragma_crt): Remove. (DeclVisitor::visit): Update for new front-end interface. (DeclVisitor::visit (PragmaDeclaration *)): Don't handle crt_constructor and crt_destructor pragmas. (DeclVisitor::visit (VarDeclaration *)): Don't generate declarations of type 'noreturn'. (DeclVisitor::visit (FuncDeclaration *)): Stop adding parameters when 'noreturn' type has been encountered. (get_symbol_decl): Set DECL_STATIC_CONSTRUCTOR and DECL_STATIC_DESTRUCTOR on decl node if requested. (aggregate_initializer_decl): Update for new front-end interface. * expr.cc (ExprVisitor::visit (CallExp *)): Always use the 'this' object as the result of calling any constructor function. (ExprVisitor::visit): Update for new front-end interface. * gdc.texi (Runtime Options): Document -fmain and -ftransition=in. * lang.opt (ftransition=in): New option. * modules.cc (get_internal_fn): Update for new front-end interface. * types.cc (TypeVisitor::visit): Likewise. (TypeVisitor::visit (TypeNoreturn *)): Return noreturn_type_node. (TypeVisitor::visit (TypeFunction *)): Stop adding parameters when 'notreturn' type has been encountered. Qualify function types that return 'noreturn' as TYPE_QUAL_VOLATILE. libphobos/ChangeLog: PR d/103558 * libdruntime/MERGE: Merge upstream druntime 178c44ff. * libdruntime/Makefile.am (DRUNTIME_DSOURCES_LINUX): Add core/sys/linux/syscalls.d. (DRUNTIME_DSOURCES_OPENBSD): Add core/sys/openbsd/pthread_np.d. * libdruntime/Makefile.in: Regenerate. * src/MERGE: Merge upstream phobos 574bf883b. * src/Makefile.am (D_EXTRA_DFLAGS): Add -fpreview=fieldwise. * src/Makefile.in: Regenerate. * testsuite/libphobos.exceptions/assert_fail.d: Update test. * testsuite/libphobos.betterc/test22336.d: New test.
Diffstat (limited to 'gcc/d/dmd/func.d')
-rw-r--r--gcc/d/dmd/func.d76
1 files changed, 46 insertions, 30 deletions
diff --git a/gcc/d/dmd/func.d b/gcc/d/dmd/func.d
index 7f0b0bb..2d6a756 100644
--- a/gcc/d/dmd/func.d
+++ b/gcc/d/dmd/func.d
@@ -45,7 +45,8 @@ import dmd.identifier;
import dmd.init;
import dmd.mtype;
import dmd.objc;
-import dmd.root.outbuffer;
+import dmd.root.aav;
+import dmd.common.outbuffer;
import dmd.root.rootobject;
import dmd.root.string;
import dmd.root.stringtable;
@@ -261,6 +262,8 @@ extern (C++) class FuncDeclaration : Declaration
VarDeclaration vresult; /// result variable for out contracts
LabelDsymbol returnLabel; /// where the return goes
+ bool[size_t] isTypeIsolatedCache; /// cache for the potentially very expensive isTypeIsolated check
+
// used to prevent symbols in different
// scopes from having the same name
DsymbolTable localsymtab;
@@ -740,7 +743,7 @@ extern (C++) class FuncDeclaration : Declaration
*/
final BaseClass* overrideInterface()
{
- if (ClassDeclaration cd = toParent2().isClassDeclaration())
+ for (ClassDeclaration cd = toParent2().isClassDeclaration(); cd; cd = cd.baseClass)
{
foreach (b; cd.interfaces)
{
@@ -1529,8 +1532,23 @@ extern (C++) class FuncDeclaration : Declaration
extern (D) final bool isTypeIsolated(Type t)
{
StringTable!Type parentTypes;
- parentTypes._init();
- return isTypeIsolated(t, parentTypes);
+ const uniqueTypeID = t.getUniqueID();
+ if (uniqueTypeID)
+ {
+ const cacheResultPtr = uniqueTypeID in isTypeIsolatedCache;
+ if (cacheResultPtr !is null)
+ return *cacheResultPtr;
+
+ parentTypes._init();
+ const isIsolated = isTypeIsolated(t, parentTypes);
+ isTypeIsolatedCache[uniqueTypeID] = isIsolated;
+ return isIsolated;
+ }
+ else
+ {
+ parentTypes._init();
+ return isTypeIsolated(t, parentTypes);
+ }
}
///ditto
@@ -2593,9 +2611,10 @@ extern (C++) class FuncDeclaration : Declaration
}
if (!tf.nextOf())
- error("must return `int` or `void`");
- else if (tf.nextOf().ty != Tint32 && tf.nextOf().ty != Tvoid)
- error("must return `int` or `void`, not `%s`", tf.nextOf().toChars());
+ // auto main(), check after semantic
+ assert(this.inferRetType);
+ else if (tf.nextOf().ty != Tint32 && tf.nextOf().ty != Tvoid && tf.nextOf().ty != Tnoreturn)
+ error("must return `int`, `void` or `noreturn`, not `%s`", tf.nextOf().toChars());
else if (tf.parameterList.varargs || nparams >= 2 || argerr)
error("parameters must be `main()` or `main(string[] args)`");
}
@@ -3054,7 +3073,11 @@ FuncDeclaration resolveFuncCall(const ref Loc loc, Scope* sc, Dsymbol s,
return null;
bool hasOverloads = fd.overnext !is null;
- auto tf = fd.type.toTypeFunction();
+ auto tf = fd.type.isTypeFunction();
+ // if type is an error, the original type should be there for better diagnostics
+ if (!tf)
+ tf = fd.originalType.toTypeFunction();
+
if (tthis && !MODimplicitConv(tthis.mod, tf.mod)) // modifier mismatch
{
OutBuffer thisBuf, funcBuf;
@@ -3253,17 +3276,7 @@ private bool traverseIndirections(Type ta, Type tb)
{
//printf("traverseIndirections(%s, %s)\n", ta.toChars(), tb.toChars());
- /* Threaded list of aggregate types already examined,
- * used to break cycles.
- * Cycles in type graphs can only occur with aggregates.
- */
- static struct Ctxt
- {
- Ctxt* prev;
- Type type; // an aggregate type
- }
-
- static bool traverse(Type ta, Type tb, Ctxt* ctxt, bool reversePass)
+ static bool traverse(Type ta, Type tb, ref scope AssocArray!(const(char)*, bool) table, bool reversePass)
{
//printf("traverse(%s, %s)\n", ta.toChars(), tb.toChars());
ta = ta.baseElemOf();
@@ -3293,28 +3306,27 @@ private bool traverseIndirections(Type ta, Type tb)
if (tb.ty == Tclass || tb.ty == Tstruct)
{
- for (Ctxt* c = ctxt; c; c = c.prev)
- if (tb == c.type)
- return true;
- Ctxt c;
- c.prev = ctxt;
- c.type = tb;
-
/* Traverse the type of each field of the aggregate
*/
+ bool* found = table.getLvalue(tb.deco);
+ if (*found == true)
+ return true; // We have already seen this symbol, break the cycle
+ else
+ *found = true;
+
AggregateDeclaration sym = tb.toDsymbol(null).isAggregateDeclaration();
foreach (v; sym.fields)
{
Type tprmi = v.type.addMod(tb.mod);
//printf("\ttb = %s, tprmi = %s\n", tb.toChars(), tprmi.toChars());
- if (!traverse(ta, tprmi, &c, reversePass))
+ if (!traverse(ta, tprmi, table, reversePass))
return false;
}
}
else if (tb.ty == Tarray || tb.ty == Taarray || tb.ty == Tpointer)
{
Type tind = tb.nextOf();
- if (!traverse(ta, tind, ctxt, reversePass))
+ if (!traverse(ta, tind, table, reversePass))
return false;
}
else if (tb.hasPointers())
@@ -3325,7 +3337,10 @@ private bool traverseIndirections(Type ta, Type tb)
// Still no match, so try breaking up ta if we have not done so yet.
if (!reversePass)
- return traverse(tb, ta, ctxt, true);
+ {
+ scope newTable = AssocArray!(const(char)*, bool)();
+ return traverse(tb, ta, newTable, true);
+ }
return true;
}
@@ -3333,7 +3348,8 @@ private bool traverseIndirections(Type ta, Type tb)
// To handle arbitrary levels of indirections in both parameters, we
// recursively descend into aggregate members/levels of indirection in both
// `ta` and `tb` while avoiding cycles. Start with the original types.
- const result = traverse(ta, tb, null, false);
+ scope table = AssocArray!(const(char)*, bool)();
+ const result = traverse(ta, tb, table, false);
//printf(" returns %d\n", result);
return result;
}