On 3/2/23 06:20, Jakub Jelinek wrote:
Hi!
On Wed, Mar 01, 2023 at 05:50:47PM -0500, Jason Merrill wrote:
And then there is a question whether we want to emit rtti for
_Float{16,32,64,128}, _Float{32,64,128}x and decltype(0.0bf16) regardless
of whether the target supports them at all or not.
Emitting them always would have an advantage, if say bfloat16_t support
isn't added for aarch64 for GCC 13 (it is still pending review), we wouldn't
need to deal with symbol versioning for it in GCC 14 or later.
On the other side, on some arches some types are very unlikely to be
supported. And e.g. _Float128x isn't supported on any arch right now.
A good point. Incidentally, it seems problematic for embedded users that
all the fundamental type_infos are emitted in the same .o, making it hard to
link in only the ones you care about. And new floating-point variants add
to that problem. So perhaps until that is addressed, it's better to avoid
adding a bunch more on targets that don't support them.
Ok, so here is a variant of the patch which still drops the fallback_* stuff,
but for float*_type_node doesn't do the automatic fallback in generic code
and leaves those to a target hook.
So far lightly tested on x86_64-linux -m32/-m64:
2023-03-02 Jakub Jelinek <ja...@redhat.com>
PR target/108883
gcc/
* target.h (emit_support_tinfos_callback): New typedef.
* targhooks.h (default_emit_support_tinfos): Declare.
* targhooks.cc (default_emit_support_tinfos): New function.
* target.def (emit_support_tinfos): New target hook.
* doc/tm.texi.in (emit_support_tinfos): Document it.
* doc/tm.texi: Regenerated.
* config/i386/i386.cc (ix86_emit_support_tinfos): New function.
(TARGET_EMIT_SUPPORT_TINFOS): Redefine.
gcc/cp/
* cp-tree.h (enum cp_tree_index): Remove CPTI_FALLBACK_DFLOAT*_TYPE
enumerators.
(fallback_dfloat32_type, fallback_dfloat64_type,
fallback_dfloat128_type): Remove.
* rtti.cc (emit_support_tinfo_1): If not emitted already, call
emit_tinfo_decl and remove from unemitted_tinfo_decls right away.
(emit_support_tinfos): Move &dfloat*_type_node from fundamentals array
into new fundamentals_with_fallback array. Call emit_support_tinfo_1
on elements of that array too, with the difference that if
the type is NULL, use a fallback REAL_TYPE for it temporarily.
Drop the !targetm.decimal_float_supported_p () handling. Call
targetm.emit_support_tinfos at the end.
* mangle.cc (write_builtin_type): Remove references to
fallback_dfloat*_type. Handle bfloat16_type_node mangling.
--- gcc/target.h.jj 2023-02-17 12:45:08.056638510 +0100
+++ gcc/target.h 2023-03-02 12:06:59.248146213 +0100
@@ -260,6 +260,8 @@ enum poly_value_estimate_kind
POLY_VALUE_LIKELY
};
+typedef void (*emit_support_tinfos_callback) (tree);
+
extern bool verify_type_context (location_t, type_context_kind, const_tree,
bool = false);
--- gcc/targhooks.h.jj 2023-01-02 09:32:50.422880177 +0100
+++ gcc/targhooks.h 2023-03-02 12:06:22.559686384 +0100
@@ -98,6 +98,8 @@ extern int default_builtin_vectorization
extern tree default_builtin_reciprocal (tree);
+extern void default_emit_support_tinfos (emit_support_tinfos_callback);
+
extern HOST_WIDE_INT default_static_rtx_alignment (machine_mode);
extern HOST_WIDE_INT default_constant_alignment (const_tree, HOST_WIDE_INT);
extern HOST_WIDE_INT constant_alignment_word_strings (const_tree,
--- gcc/targhooks.cc.jj 2023-01-02 09:32:52.591848839 +0100
+++ gcc/targhooks.cc 2023-03-02 12:01:39.576868114 +0100
@@ -752,6 +752,11 @@ default_builtin_reciprocal (tree)
return NULL_TREE;
}
+void
+default_emit_support_tinfos (emit_support_tinfos_callback)
+{
+}
+
bool
hook_bool_CUMULATIVE_ARGS_arg_info_false (cumulative_args_t,
const function_arg_info &)
--- gcc/target.def.jj 2023-02-22 15:58:50.252996452 +0100
+++ gcc/target.def 2023-03-02 12:01:52.002684436 +0100
@@ -2606,6 +2606,19 @@ types.",
const char *, (const_tree type),
hook_constcharptr_const_tree_null)
+/* Temporarily add conditional target specific types for the purpose of
+ emitting C++ fundamental type tinfos. */
+DEFHOOK
+(emit_support_tinfos,
+ "If your target defines any fundamental types which depend on ISA flags,\n\
+they might need C++ tinfo symbols in libsupc++/libstdc++ regardless of\n\
+ISA flags the library is compiled with.\n\
+This hook allows creating tinfo symbols even for those cases, by temporarily\n\
+creating corresponding fundamental type trees, calling the @var{callback}\n\
"each corresponding fundamental type tree"?
OK with that change.
+function on it and setting the type back to @code{nullptr}.",
+ void, (emit_support_tinfos_callback callback),
+ default_emit_support_tinfos)
+
/* Make any adjustments to libfunc names needed for this target. */
DEFHOOK
(init_libfuncs,
--- gcc/doc/tm.texi.in.jj 2023-02-24 09:58:39.963508685 +0100
+++ gcc/doc/tm.texi.in 2023-03-02 11:47:50.044125831 +0100
@@ -1286,6 +1286,8 @@ pattern needs to support both a 32- and
@hook TARGET_MANGLE_TYPE
+@hook TARGET_EMIT_SUPPORT_TINFOS
+
@node Type Layout
@section Layout of Source Language Data Types
--- gcc/doc/tm.texi.jj 2023-02-24 09:58:39.951508859 +0100
+++ gcc/doc/tm.texi 2023-03-02 12:02:18.312295512 +0100
@@ -1525,6 +1525,15 @@ appropriate for a target that does not d
types.
@end deftypefn
+@deftypefn {Target Hook} void TARGET_EMIT_SUPPORT_TINFOS (emit_support_tinfos_callback @var{callback})
+If your target defines any fundamental types which depend on ISA flags,
+they might need C++ tinfo symbols in libsupc++/libstdc++ regardless of
+ISA flags the library is compiled with.
+This hook allows creating tinfo symbols even for those cases, by temporarily
+creating corresponding fundamental type trees, calling the @var{callback}
+function on it and setting the type back to @code{nullptr}.
+@end deftypefn
+
@node Type Layout
@section Layout of Source Language Data Types
--- gcc/config/i386/i386.cc.jj 2023-02-22 15:58:50.109998489 +0100
+++ gcc/config/i386/i386.cc 2023-03-02 12:02:13.193371183 +0100
@@ -22775,6 +22775,27 @@ ix86_mangle_type (const_tree type)
}
}
+/* Create C++ tinfo symbols for only conditionally available fundamental
+ types. */
+
+static void
+ix86_emit_support_tinfos (emit_support_tinfos_callback callback)
+{
+ extern tree ix86_float16_type_node;
+ extern tree ix86_bf16_type_node;
+
+ if (!TARGET_SSE2)
+ {
+ gcc_checking_assert (!float16_type_node && !bfloat16_type_node);
+ float16_type_node = ix86_float16_type_node;
+ bfloat16_type_node = ix86_bf16_type_node;
+ callback (float16_type_node);
+ callback (bfloat16_type_node);
+ float16_type_node = NULL_TREE;
+ bfloat16_type_node = NULL_TREE;
+ }
+}
+
static GTY(()) tree ix86_tls_stack_chk_guard_decl;
static tree
@@ -24954,6 +24975,9 @@ ix86_libgcc_floating_mode_supported_p
#undef TARGET_MANGLE_TYPE
#define TARGET_MANGLE_TYPE ix86_mangle_type
+#undef TARGET_EMIT_SUPPORT_TINFOS
+#define TARGET_EMIT_SUPPORT_TINFOS ix86_emit_support_tinfos
+
#undef TARGET_STACK_PROTECT_GUARD
#define TARGET_STACK_PROTECT_GUARD ix86_stack_protect_guard
--- gcc/cp/cp-tree.h.jj 2023-03-02 08:49:09.569844225 +0100
+++ gcc/cp/cp-tree.h 2023-03-02 11:45:41.972008622 +0100
@@ -235,10 +235,6 @@ enum cp_tree_index
CPTI_PSEUDO_CONTRACT_VIOLATION,
- CPTI_FALLBACK_DFLOAT32_TYPE,
- CPTI_FALLBACK_DFLOAT64_TYPE,
- CPTI_FALLBACK_DFLOAT128_TYPE,
-
CPTI_MAX
};
@@ -397,13 +393,6 @@ extern GTY(()) tree cp_global_trees[CPTI
access nodes in tree.h. */
#define access_default_node null_node
-
-/* Variant of dfloat{32,64,128}_type_node only used for fundamental
- rtti purposes if DFP is disabled. */
-#define fallback_dfloat32_type
cp_global_trees[CPTI_FALLBACK_DFLOAT32_TYPE]
-#define fallback_dfloat64_type
cp_global_trees[CPTI_FALLBACK_DFLOAT64_TYPE]
-#define fallback_dfloat128_type
cp_global_trees[CPTI_FALLBACK_DFLOAT128_TYPE]
-
#include "name-lookup.h"
--- gcc/cp/rtti.cc.jj 2023-02-28 11:28:56.579180090 +0100
+++ gcc/cp/rtti.cc 2023-03-02 11:49:41.380484925 +0100
@@ -1577,6 +1577,15 @@ emit_support_tinfo_1 (tree bltn)
gcc_assert (TREE_PUBLIC (tinfo) && !DECL_COMDAT (tinfo));
DECL_INTERFACE_KNOWN (tinfo) = 1;
}
+
+ /* Emit it right away if not emitted already. */
+ if (DECL_INITIAL (tinfo) == NULL_TREE)
+ {
+ gcc_assert (unemitted_tinfo_decls->last () == tinfo);
+ bool ok = emit_tinfo_decl (tinfo);
+ gcc_assert (ok);
+ unemitted_tinfo_decls->pop ();
+ }
}
}
@@ -1602,12 +1611,18 @@ emit_support_tinfos (void)
&long_integer_type_node, &long_unsigned_type_node,
&long_long_integer_type_node, &long_long_unsigned_type_node,
&float_type_node, &double_type_node, &long_double_type_node,
- &dfloat32_type_node, &dfloat64_type_node, &dfloat128_type_node,
&bfloat16_type_node, &float16_type_node, &float32_type_node,
&float64_type_node, &float128_type_node, &float32x_type_node,
&float64x_type_node, &float128x_type_node, &nullptr_type_node,
0
};
+ /* Similar, but for floating point types only which should get type info
+ regardless whether they are non-NULL or NULL. */
+ static tree *const fundamentals_with_fallback[] =
+ {
+ &dfloat32_type_node, &dfloat64_type_node, &dfloat128_type_node,
+ 0
+ };
int ix;
/* Look for a defined class. */
@@ -1627,8 +1642,20 @@ emit_support_tinfos (void)
location_t saved_loc = input_location;
input_location = BUILTINS_LOCATION;
doing_runtime = 1;
+ tree fallback = NULL_TREE;
for (ix = 0; fundamentals[ix]; ix++)
emit_support_tinfo_1 (*fundamentals[ix]);
+ for (ix = 0; fundamentals_with_fallback[ix]; ix++)
+ if (*fundamentals_with_fallback[ix])
+ emit_support_tinfo_1 (*fundamentals_with_fallback[ix]);
+ else
+ {
+ if (fallback == NULL_TREE)
+ fallback = make_node (REAL_TYPE);
+ *fundamentals_with_fallback[ix] = fallback;
+ emit_support_tinfo_1 (fallback);
+ *fundamentals_with_fallback[ix] = NULL_TREE;
+ }
for (ix = 0; ix < NUM_INT_N_ENTS; ix ++)
if (int_n_enabled_p[ix])
{
@@ -1637,20 +1664,10 @@ emit_support_tinfos (void)
}
for (tree t = registered_builtin_types; t; t = TREE_CHAIN (t))
emit_support_tinfo_1 (TREE_VALUE (t));
- /* For compatibility, emit DFP typeinfos even when DFP isn't enabled,
- because we've emitted that in the past. */
- if (!targetm.decimal_float_supported_p ())
- {
- gcc_assert (dfloat32_type_node == NULL_TREE
- && dfloat64_type_node == NULL_TREE
- && dfloat128_type_node == NULL_TREE);
- fallback_dfloat32_type = make_node (REAL_TYPE);
- fallback_dfloat64_type = make_node (REAL_TYPE);
- fallback_dfloat128_type = make_node (REAL_TYPE);
- emit_support_tinfo_1 (fallback_dfloat32_type);
- emit_support_tinfo_1 (fallback_dfloat64_type);
- emit_support_tinfo_1 (fallback_dfloat128_type);
- }
+
+ /* Emit additional typeinfos as requested by target. */
+ targetm.emit_support_tinfos (emit_support_tinfo_1);
+
input_location = saved_loc;
}
--- gcc/cp/mangle.cc.jj 2023-02-28 11:28:56.532180773 +0100
+++ gcc/cp/mangle.cc 2023-03-02 11:45:41.973008607 +0100
@@ -2732,11 +2732,11 @@ write_builtin_type (tree type)
write_char ('d');
else if (type == long_double_type_node)
write_char ('e');
- else if (type == dfloat32_type_node || type == fallback_dfloat32_type)
+ else if (type == dfloat32_type_node)
write_string ("Df");
- else if (type == dfloat64_type_node || type == fallback_dfloat64_type)
+ else if (type == dfloat64_type_node)
write_string ("Dd");
- else if (type == dfloat128_type_node || type == fallback_dfloat128_type)
+ else if (type == dfloat128_type_node)
write_string ("De");
else if (type == float16_type_node)
write_string ("DF16_");
@@ -2752,6 +2752,8 @@ write_builtin_type (tree type)
write_string ("DF64x");
else if (type == float128x_type_node)
write_string ("DF128x");
+ else if (type == bfloat16_type_node)
+ write_string ("DF16b");
else
gcc_unreachable ();
break;
Jakub