aboutsummaryrefslogtreecommitdiff
path: root/gcc/d
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/d')
-rw-r--r--gcc/d/ChangeLog74
-rw-r--r--gcc/d/Make-lang.in2
-rw-r--r--gcc/d/d-attribs.cc9
-rw-r--r--gcc/d/d-codegen.cc47
-rw-r--r--gcc/d/d-diagnostic.cc23
-rw-r--r--gcc/d/d-tree.h1
-rw-r--r--gcc/d/decl.cc15
-rw-r--r--gcc/d/dmd/MERGE2
-rw-r--r--gcc/d/dmd/expressionsem.d6
-rw-r--r--gcc/d/expr.cc53
-rw-r--r--gcc/d/imports.cc6
-rw-r--r--gcc/d/toir.cc11
-rw-r--r--gcc/d/types.cc20
13 files changed, 167 insertions, 102 deletions
diff --git a/gcc/d/ChangeLog b/gcc/d/ChangeLog
index b0a4f12..ab6042b 100644
--- a/gcc/d/ChangeLog
+++ b/gcc/d/ChangeLog
@@ -1,3 +1,77 @@
+2025-08-18 Indu Bhagat <indu.bhagat@oracle.com>
+
+ * d-attribs.cc (d_handle_no_sanitize_attribute): Use
+ 'sanitize_code_type' instead of 'unsigned int'.
+
+2025-08-11 Iain Sandoe <iain@sandoe.co.uk>
+
+ * d-codegen.cc (build_filename_from_loc): Use
+ build_string_literal() to build a null-terminated string for
+ the filename.
+
+2025-08-06 Sam James <sam@gentoo.org>
+
+ * Make-lang.in (ALL_DFLAGS): Don't use ALIASING_FLAGS.
+
+2025-07-25 David Malcolm <dmalcolm@redhat.com>
+
+ * d-diagnostic.cc: Likewise.
+
+2025-07-25 David Malcolm <dmalcolm@redhat.com>
+
+ * d-diagnostic.cc: Update for diagnostic_t becoming
+ enum class diagnostics::kind.
+
+2025-07-25 David Malcolm <dmalcolm@redhat.com>
+
+ * d-diagnostic.cc (d_diagnostic_report_diagnostic): Update to add
+ "m_" prefix to fields of diagnostic_info throughout.
+
+2025-07-21 Stefan Schulze Frielinghaus <stefansf@gcc.gnu.org>
+
+ * toir.cc: Pass null pointer to
+ parse_{input,output}_constraint().
+
+2025-04-29 Iain Buclaw <ibuclaw@gdcproject.org>
+
+ PR d/103044
+ * d-tree.h (build_clear_padding_call): New prototype.
+ * d-codegen.cc (build_clear_padding_call): New function.
+ (build_memset_call): Remove generated call to __builtin_memcpy.
+ (build_address): Replace generated call to __builtin_memset with
+ __builtin_clear_padding.
+ (build_array_from_exprs): Likewise.
+ * expr.cc (ExprVisitor::visit (AssignExp *)): Remove generated call to
+ __builtin_memset.
+ (ExprVisitor::visit (ArrayLiteralExp *)): Likewise. Insert call to
+ __builtin_clear_padding after copying array into GC memory.
+ (ExprVisitor::visit (StructLiteralExp *)): Remove generated call to
+ __builtin_memset.
+ * toir.cc (IRVisitor::visit (ReturnStatement *)): Likewise.
+
+2025-04-17 Iain Buclaw <ibuclaw@gdcproject.org>
+
+ * dmd/MERGE: Merge upstream dmd 956e73d64e.
+
+2025-04-15 Iain Buclaw <ibuclaw@gdcproject.org>
+
+ PR d/119826
+ * types.cc (TypeVisitor::visit (TypeEnum *)): Propagate flags of main
+ enum types to all forward-referenced variants.
+
+2025-04-15 Iain Buclaw <ibuclaw@gdcproject.org>
+
+ PR d/119799
+ * decl.cc (DeclVisitor::visit (VarDeclaration *)): Check front-end
+ type size before building the VAR_DECL. Allow C symbols to have a
+ size of `0'.
+
+2025-04-15 Iain Buclaw <ibuclaw@gdcproject.org>
+
+ PR d/119817
+ * imports.cc (ImportVisitor::visit (OverloadSet *)): Don't push
+ NULL_TREE to vector of import symbols.
+
2025-04-12 Iain Buclaw <ibuclaw@gdcproject.org>
PR d/109023
diff --git a/gcc/d/Make-lang.in b/gcc/d/Make-lang.in
index 2d444c9..0ddd524 100644
--- a/gcc/d/Make-lang.in
+++ b/gcc/d/Make-lang.in
@@ -61,7 +61,7 @@ WARN_DFLAGS = -Wall -Wdeprecated
NOEXCEPTION_DFLAGS = $(filter-out -fno-rtti, $(NOEXCEPTION_FLAGS))
ALL_DFLAGS = $(DFLAGS-$@) $(GDCFLAGS) -fversion=IN_GCC $(CHECKING_DFLAGS) \
- $(PICFLAG) $(ALIASING_FLAGS) $(NOEXCEPTION_DFLAGS) $(COVERAGE_FLAGS) \
+ $(PICFLAG) $(NOEXCEPTION_DFLAGS) $(COVERAGE_FLAGS) \
$(WARN_DFLAGS)
DCOMPILE.base = $(GDC) -c $(ALL_DFLAGS) -o $@
diff --git a/gcc/d/d-attribs.cc b/gcc/d/d-attribs.cc
index 77315dc..53aea5e 100644
--- a/gcc/d/d-attribs.cc
+++ b/gcc/d/d-attribs.cc
@@ -1406,7 +1406,7 @@ d_handle_no_sanitize_attribute (tree *node, tree name, tree args, int,
return NULL_TREE;
}
- unsigned int flags = 0;
+ sanitize_code_type flags = 0;
for (; args; args = TREE_CHAIN (args))
{
tree id = TREE_VALUE (args);
@@ -1424,16 +1424,17 @@ d_handle_no_sanitize_attribute (tree *node, tree name, tree args, int,
merge existing flags if no_sanitize was previously handled. */
if (tree attr = lookup_attribute ("no_sanitize", DECL_ATTRIBUTES (*node)))
{
- unsigned int old_value = tree_to_uhwi (TREE_VALUE (attr));
+ sanitize_code_type old_value =
+ tree_to_sanitize_code_type (TREE_VALUE (attr));
flags |= old_value;
if (flags != old_value)
- TREE_VALUE (attr) = build_int_cst (d_uint_type, flags);
+ TREE_VALUE (attr) = build_int_cst (d_ulong_type, flags);
}
else
{
DECL_ATTRIBUTES (*node) = tree_cons (get_identifier ("no_sanitize"),
- build_int_cst (d_uint_type, flags),
+ build_int_cst (d_ulong_type, flags),
DECL_ATTRIBUTES (*node));
}
diff --git a/gcc/d/d-codegen.cc b/gcc/d/d-codegen.cc
index 1a7575a..f3c3e4a 100644
--- a/gcc/d/d-codegen.cc
+++ b/gcc/d/d-codegen.cc
@@ -717,10 +717,11 @@ build_address (tree exp)
if (AGGREGATE_TYPE_P (TREE_TYPE (exp))
&& !aggregate_value_p (TREE_TYPE (exp), exp))
{
- tree tmp = build_local_temp (TREE_TYPE (exp));
- init = compound_expr (init, build_memset_call (tmp));
- init = compound_expr (init, modify_expr (tmp, exp));
- exp = tmp;
+ tree target = force_target_expr (exp);
+ tree ptr = build_address (TARGET_EXPR_SLOT (target));
+ init = compound_expr (init, target);
+ init = compound_expr (init, build_clear_padding_call (ptr));
+ exp = TARGET_EXPR_SLOT (target);
}
else
exp = force_target_expr (exp);
@@ -891,17 +892,13 @@ build_memset_call (tree ptr, tree num)
}
/* Use a zero constant to fill the destination if setting the entire object.
- For CONSTRUCTORs, the memcpy() is lowered to a ref-all pointer assignment,
- which can then be merged with other stores to the object. */
+ For CONSTRUCTORs, also set CONSTRUCTOR_ZERO_PADDING_BITS. */
tree valtype = TREE_TYPE (TREE_TYPE (ptr));
if (tree_int_cst_equal (TYPE_SIZE_UNIT (valtype), num))
{
tree cst = build_zero_cst (valtype);
if (TREE_CODE (cst) == CONSTRUCTOR)
- {
- CONSTRUCTOR_ZERO_PADDING_BITS (cst) = 1;
- return build_memcpy_call (ptr, build_address (cst), num);
- }
+ CONSTRUCTOR_ZERO_PADDING_BITS (cst) = 1;
return modify_expr (build_deref (ptr), cst);
}
@@ -910,6 +907,18 @@ build_memset_call (tree ptr, tree num)
ptr, integer_zero_node, num);
}
+/* Build a call to built-in clear_padding(), clears padding bits inside of the
+ object representation of object pointed by PTR. */
+
+tree
+build_clear_padding_call (tree ptr)
+{
+ gcc_assert (POINTER_TYPE_P (TREE_TYPE (ptr)));
+
+ return build_call_expr (builtin_decl_explicit (BUILT_IN_CLEAR_PADDING), 1,
+ ptr);
+}
+
/* Return TRUE if the struct SD is suitable for comparison using memcmp.
This is because we don't guarantee that padding is zero-initialized for
a stack variable, so we can't use memcmp to compare struct values. */
@@ -1893,15 +1902,13 @@ build_array_from_exprs (Type *type, Expressions *exps, bool const_p)
/* Create a new temporary to store the array. */
tree var = build_local_temp (satype);
- /* Fill any alignment holes with zeroes. */
- TypeStruct *ts = etype->baseElemOf ()->isTypeStruct ();
- tree init = NULL;
- if (ts && (!identity_compare_p (ts->sym) || ts->sym->isUnionDeclaration ()))
- init = build_memset_call (var);
-
/* Initialize the temporary. */
tree assign = modify_expr (var, build_padded_constructor (satype, elms));
- return compound_expr (compound_expr (init, assign), var);
+
+ /* Fill any alignment holes with zeroes. */
+ tree clear_padding = build_clear_padding_call (build_address (var));
+
+ return compound_expr (compound_expr (assign, clear_padding), var);
}
@@ -1932,11 +1939,7 @@ build_filename_from_loc (const Loc &loc)
if (filename == NULL)
filename = d_function_chain->module->srcfile.toChars ();
- unsigned length = strlen (filename);
- tree str = build_string (length, filename);
- TREE_TYPE (str) = make_array_type (Type::tchar, length + 1);
-
- return build_address (str);
+ return build_string_literal (filename);
}
/* Builds a CALL_EXPR at location LOC in the source file to call LIBCALL when
diff --git a/gcc/d/d-diagnostic.cc b/gcc/d/d-diagnostic.cc
index 55cb42e..e666ddf 100644
--- a/gcc/d/d-diagnostic.cc
+++ b/gcc/d/d-diagnostic.cc
@@ -185,7 +185,7 @@ escape_d_format (const char *format)
static void ATTRIBUTE_GCC_DIAG(3,0)
d_diagnostic_report_diagnostic (const SourceLoc &loc, int opt,
const char *format, va_list ap,
- diagnostic_t kind, bool verbatim)
+ enum diagnostics::kind kind, bool verbatim)
{
va_list argp;
va_copy (argp, ap);
@@ -193,13 +193,13 @@ d_diagnostic_report_diagnostic (const SourceLoc &loc, int opt,
if (loc.filename.length != 0 || !verbatim)
{
rich_location rich_loc (line_table, make_location_t (loc));
- diagnostic_info diagnostic;
+ diagnostics::diagnostic_info diagnostic;
char *xformat = expand_d_format (format);
diagnostic_set_info_translated (&diagnostic, xformat, &argp,
&rich_loc, kind);
if (opt != 0)
- diagnostic.option_id = opt;
+ diagnostic.m_option_id = opt;
diagnostic_report_diagnostic (global_dc, &diagnostic);
}
@@ -224,7 +224,7 @@ void D_ATTRIBUTE_FORMAT(2,0) ATTRIBUTE_GCC_DIAG(2,0)
verrorReport (const SourceLoc loc, const char *format, va_list ap,
ErrorKind kind, const char *prefix1, const char *prefix2)
{
- diagnostic_t diag_kind = DK_UNSPECIFIED;
+ enum diagnostics::kind diag_kind = diagnostics::kind::unspecified;
int opt = 0;
bool verbatim = false;
char *xformat;
@@ -238,7 +238,9 @@ verrorReport (const SourceLoc loc, const char *format, va_list ap,
if (global.gag && !global.params.v.showGaggedErrors)
return;
- diag_kind = global.gag ? DK_ANACHRONISM : DK_ERROR;
+ diag_kind = (global.gag
+ ? diagnostics::kind::anachronism
+ : diagnostics::kind::error);
}
else if (kind == ErrorKind::warning)
{
@@ -254,7 +256,7 @@ verrorReport (const SourceLoc loc, const char *format, va_list ap,
if (global.params.useWarnings == DIAGNOSTICerror)
global.warnings++;
- diag_kind = DK_WARNING;
+ diag_kind = diagnostics::kind::warning;
}
else if (kind == ErrorKind::deprecation)
{
@@ -270,11 +272,11 @@ verrorReport (const SourceLoc loc, const char *format, va_list ap,
}
opt = OPT_Wdeprecated;
- diag_kind = DK_WARNING;
+ diag_kind = diagnostics::kind::warning;
}
else if (kind == ErrorKind::message)
{
- diag_kind = DK_NOTE;
+ diag_kind = diagnostics::kind::note;
verbatim = true;
}
else if (kind == ErrorKind::tip)
@@ -282,7 +284,7 @@ verrorReport (const SourceLoc loc, const char *format, va_list ap,
if (global.gag)
return;
- diag_kind = DK_DEBUG;
+ diag_kind = diagnostics::kind::debug;
verbatim = true;
}
else
@@ -328,7 +330,8 @@ verrorReportSupplemental (const SourceLoc loc, const char* format, va_list ap,
else
gcc_unreachable ();
- d_diagnostic_report_diagnostic (loc, 0, format, ap, DK_NOTE, false);
+ d_diagnostic_report_diagnostic (loc, 0, format, ap, diagnostics::kind::note,
+ false);
}
/* Call this after printing out fatal error messages to clean up and
diff --git a/gcc/d/d-tree.h b/gcc/d/d-tree.h
index ebbbe71..9d576e2 100644
--- a/gcc/d/d-tree.h
+++ b/gcc/d/d-tree.h
@@ -568,6 +568,7 @@ extern tree d_mark_read (tree);
extern tree build_memcmp_call (tree, tree, tree);
extern tree build_memcpy_call (tree, tree, tree);
extern tree build_memset_call (tree, tree = NULL_TREE);
+extern tree build_clear_padding_call (tree);
extern bool identity_compare_p (StructDeclaration *);
extern tree build_float_identity (tree_code, tree, tree);
extern tree build_struct_comparison (tree_code, StructDeclaration *,
diff --git a/gcc/d/decl.cc b/gcc/d/decl.cc
index 136f78b..9ddf7cf 100644
--- a/gcc/d/decl.cc
+++ b/gcc/d/decl.cc
@@ -791,6 +791,12 @@ public:
}
else if (d->isDataseg ())
{
+ /* When the front-end type size is invalid, an error has already been
+ given for the declaration or type. */
+ dinteger_t size = dmd::size (d->type, d->loc);
+ if (size == SIZE_INVALID)
+ return;
+
tree decl = get_symbol_decl (d);
/* Only need to build the VAR_DECL for extern declarations. */
@@ -804,9 +810,7 @@ public:
return;
/* How big a symbol can be should depend on back-end. */
- tree size = build_integer_cst (dmd::size (d->type, d->loc),
- build_ctype (Type::tsize_t));
- if (!valid_constant_size_p (size))
+ if (!valid_constant_size_p (build_integer_cst (size, size_type_node)))
{
error_at (make_location_t (d->loc), "size is too large");
return;
@@ -835,8 +839,9 @@ public:
}
/* Frontend should have already caught this. */
- gcc_assert (!integer_zerop (size)
- || d->type->toBasetype ()->isTypeSArray ());
+ gcc_assert ((size != 0 && size != SIZE_INVALID)
+ || d->type->toBasetype ()->isTypeSArray ()
+ || d->isCsymbol ());
d_finish_decl (decl);
diff --git a/gcc/d/dmd/MERGE b/gcc/d/dmd/MERGE
index ee5eb85..58d19b4 100644
--- a/gcc/d/dmd/MERGE
+++ b/gcc/d/dmd/MERGE
@@ -1,4 +1,4 @@
-1b34fea4788136b54ec77c6ed9678754d109fc79
+956e73d64e532a68213970316c2590c572ec03f3
The first line of this file holds the git revision number of the last
merge done from the dlang/dmd repository.
diff --git a/gcc/d/dmd/expressionsem.d b/gcc/d/dmd/expressionsem.d
index 19111e3..b02f6ea 100644
--- a/gcc/d/dmd/expressionsem.d
+++ b/gcc/d/dmd/expressionsem.d
@@ -6978,10 +6978,10 @@ private extern (C++) final class ExpressionSemanticVisitor : Visitor
while (1)
{
AttribDeclaration ad = s.isAttribDeclaration();
- if (!ad)
- break;
- if (ad.decl && ad.decl.length == 1)
+ if (ad && ad.decl && ad.decl.length == 1)
s = (*ad.decl)[0];
+ else
+ break;
}
//printf("inserting '%s' %p into sc = %p\n", s.toChars(), s, sc);
diff --git a/gcc/d/expr.cc b/gcc/d/expr.cc
index 1c1ecf2..268a176 100644
--- a/gcc/d/expr.cc
+++ b/gcc/d/expr.cc
@@ -1026,7 +1026,6 @@ public:
if (tb1->ty == TY::Tstruct)
{
tree t1 = build_expr (e->e1);
- tree t2 = convert_for_assignment (e->e2, e->e1->type, true);
StructDeclaration *sd = tb1->isTypeStruct ()->sym;
/* Look for struct = 0. */
@@ -1051,25 +1050,8 @@ public:
else
{
/* Simple struct literal assignment. */
- tree init = NULL_TREE;
-
- /* Fill any alignment holes in the struct using memset. */
- if ((e->op == EXP::construct
- || (e->e2->op == EXP::structLiteral && e->op == EXP::blit))
- && (sd->isUnionDeclaration () || !identity_compare_p (sd)))
- {
- t1 = stabilize_reference (t1);
- init = build_memset_call (t1);
- }
-
- /* Elide generating assignment if init is all zeroes. */
- if (init != NULL_TREE && initializer_zerop (t2))
- this->result_ = compound_expr (init, t1);
- else
- {
- tree result = build_assign (modifycode, t1, t2);
- this->result_ = compound_expr (init, result);
- }
+ tree t2 = convert_for_assignment (e->e2, e->e1->type, true);
+ this->result_ = build_assign (modifycode, t1, t2);
}
return;
@@ -2685,22 +2667,6 @@ public:
if (constant_p && initializer_constant_valid_p (ctor, TREE_TYPE (ctor)))
TREE_STATIC (ctor) = 1;
- /* Use memset to fill any alignment holes in the array. */
- if (!this->constp_ && !this->literalp_)
- {
- TypeStruct *ts = etype->baseElemOf ()->isTypeStruct ();
-
- if (ts != NULL && (!identity_compare_p (ts->sym)
- || ts->sym->isUnionDeclaration ()))
- {
- tree var = build_local_temp (TREE_TYPE (ctor));
- tree init = build_memset_call (var);
- /* Evaluate memset() first, then any saved elements. */
- saved_elems = compound_expr (init, saved_elems);
- ctor = compound_expr (modify_expr (var, ctor), var);
- }
- }
-
this->result_ = compound_expr (saved_elems, d_convert (type, ctor));
}
else if (e->onstack)
@@ -2726,6 +2692,9 @@ public:
tree result = build_memcpy_call (mem, build_address (ctor), size);
+ /* Fill any alignment holes in the array. */
+ result = compound_expr (result, build_clear_padding_call (mem));
+
/* Return the array pointed to by MEM. */
result = compound_expr (result, mem);
@@ -2899,18 +2868,6 @@ public:
tree var = build_deref (e->sym);
ctor = compound_expr (modify_expr (var, ctor), var);
}
- else if (!this->literalp_)
- {
- /* Use memset to fill any alignment holes in the object. */
- if (!identity_compare_p (e->sd) || e->sd->isUnionDeclaration ())
- {
- tree var = build_local_temp (TREE_TYPE (ctor));
- tree init = build_memset_call (var);
- /* Evaluate memset() first, then any saved element constructors. */
- saved_elems = compound_expr (init, saved_elems);
- ctor = compound_expr (modify_expr (var, ctor), var);
- }
- }
this->result_ = compound_expr (saved_elems, ctor);
}
diff --git a/gcc/d/imports.cc b/gcc/d/imports.cc
index 776caaf..16e4df6 100644
--- a/gcc/d/imports.cc
+++ b/gcc/d/imports.cc
@@ -182,7 +182,11 @@ public:
vec_alloc (tset, d->a.length);
for (size_t i = 0; i < d->a.length; i++)
- vec_safe_push (tset, build_import_decl (d->a[i]));
+ {
+ tree overload = build_import_decl (d->a[i]);
+ if (overload != NULL_TREE)
+ vec_safe_push (tset, overload);
+ }
this->result_ = build_tree_list_vec (tset);
tset->truncate (0);
diff --git a/gcc/d/toir.cc b/gcc/d/toir.cc
index 427a662..554399b 100644
--- a/gcc/d/toir.cc
+++ b/gcc/d/toir.cc
@@ -1058,13 +1058,8 @@ public:
if (sle != NULL)
{
- StructDeclaration *sd = type->baseElemOf ()->isTypeStruct ()->sym;
sle->sym = build_address (this->func_->shidden);
using_rvo_p = true;
-
- /* Fill any alignment holes in the return slot using memset. */
- if (!identity_compare_p (sd) || sd->isUnionDeclaration ())
- add_stmt (build_memset_call (this->func_->shidden));
}
if (using_rvo_p == true)
@@ -1455,7 +1450,8 @@ public:
oconstraints[i] = constraint;
if (parse_output_constraint (&constraint, i, ninputs, noutputs,
- &allows_mem, &allows_reg, &is_inout))
+ &allows_mem, &allows_reg, &is_inout,
+ nullptr))
{
/* If the output argument is going to end up in memory. */
if (!allows_reg)
@@ -1474,7 +1470,8 @@ public:
= TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (t)));
if (parse_input_constraint (&constraint, i, ninputs, noutputs, 0,
- oconstraints, &allows_mem, &allows_reg))
+ oconstraints, &allows_mem, &allows_reg,
+ nullptr))
{
/* If the input argument is going to end up in memory. */
if (!allows_reg && allows_mem)
diff --git a/gcc/d/types.cc b/gcc/d/types.cc
index e43fa88..1c74840 100644
--- a/gcc/d/types.cc
+++ b/gcc/d/types.cc
@@ -1179,6 +1179,26 @@ public:
layout_type (t->ctype);
+ /* Fix up all forward-referenced variants of this enum type. */
+ for (tree v = TYPE_MAIN_VARIANT (t->ctype); v;
+ v = TYPE_NEXT_VARIANT (v))
+ {
+ if (v == t->ctype)
+ continue;
+
+ TYPE_VALUES (v) = TYPE_VALUES (t->ctype);
+ TYPE_LANG_SPECIFIC (v) = TYPE_LANG_SPECIFIC (t->ctype);
+ TYPE_MIN_VALUE (v) = TYPE_MIN_VALUE (t->ctype);
+ TYPE_MAX_VALUE (v) = TYPE_MAX_VALUE (t->ctype);
+ TYPE_UNSIGNED (v) = TYPE_UNSIGNED (t->ctype);
+ TYPE_SIZE (v) = TYPE_SIZE (t->ctype);
+ TYPE_SIZE_UNIT (v) = TYPE_SIZE_UNIT (t->ctype);
+ SET_TYPE_MODE (v, TYPE_MODE (t->ctype));
+ TYPE_PRECISION (v) = TYPE_PRECISION (t->ctype);
+ SET_TYPE_ALIGN (v, TYPE_ALIGN (t->ctype));
+ TYPE_USER_ALIGN (v) = TYPE_USER_ALIGN (t->ctype);
+ }
+
/* Complete forward-referenced fields of this enum type. */
finish_incomplete_fields (t->ctype);
}