From: "H.J. Lu" <hjl.tools@gmail.com>
To: Joseph Myers <joseph@codesourcery.com>
Cc: Martin Sebor <msebor@gmail.com>, Jason Merrill <jason@redhat.com>,
GCC Patches <gcc-patches@gcc.gnu.org>
Subject: Re: RFC: [PATCH] Add warn_if_not_aligned attribute
Date: Fri, 16 Jun 2017 11:55:00 -0000 [thread overview]
Message-ID: <20170616115455.GA3457@gmail.com> (raw)
In-Reply-To: <alpine.DEB.2.20.1706151728020.3768@digraph.polyomino.org.uk>
On Thu, Jun 15, 2017 at 05:31:34PM +0000, Joseph Myers wrote:
> On Thu, 15 Jun 2017, H.J. Lu wrote:
>
> > On Thu, Jun 15, 2017 at 8:38 AM, Martin Sebor <msebor@gmail.com> wrote:
> > >>
> > >> Where do we go from here?
> > >
> > >
> > > Other than the C and C++ maintainers needing to approve the patch
> > > I can't think of anything else.
> >
> > Hi Joseph, Jason,
> >
> > The complete patch is at
> >
> > https://gcc.gnu.org/ml/gcc-patches/2017-06/msg00541.html
> >
> > Is this OK for trunk?
>
> I'd expect the warning calls to include OPT_Wif_not_aligned or
> OPT_Wpacked_not_aligned (as appropriate, depending on what triggered the
> warning / would disable it), so the warning output includes an option
> name.
>
Done.
> As the attribute is specific to fields I'd expect testcases that use of it
Done.
> on non-fields is diagnosed. And I think the diagnostic for that should
> include quotes, %<warn_if_not_aligned%>.
>
Done.
Here is the updated patch. OK for trunk?
Thanks.
H.J.
---
Add warn_if_not_aligned attribute as well as command line options:
-Wif-not-aligned and -Wpacked-not-aligned.
__attribute__((warn_if_not_aligned(N))) causes compiler to issue a
warning if the field in a struct or union is not aligned to N:
typedef unsigned long long __u64
__attribute__((aligned(4),warn_if_not_aligned(8)));
struct foo
{
int i1;
int i2;
__u64 x;
};
__u64 is aligned to 4 bytes. But inside struct foo, __u64 should be
aligned at 8 bytes. It is used to define struct foo in such a way that
struct foo has the same layout and x has the same alignment when __u64
is aligned at either 4 or 8 bytes.
Since struct foo is normally aligned to 4 bytes, a warning will be issued:
warning: alignment 4 of 'struct foo' is less than 8
Align struct foo to 8 bytes:
struct foo
{
int i1;
int i2;
__u64 x;
} __attribute__((aligned(8)));
silences the warning. It also warns the field with misaligned offset:
struct foo
{
int i1;
int i2;
int i3;
__u64 x;
} __attribute__((aligned(8)));
warning: 'x' offset 12 in 'struct foo' isn't aligned to 8
This warning is controlled by -Wif-not-aligned and is enabled by default.
When -Wpacked-not-aligned is used, the same warning is also issued for
the field with explicitly specified alignment in a packed struct or union:
struct __attribute__ ((aligned (8))) S8 { char a[8]; };
struct __attribute__ ((packed)) S {
struct S8 s8;
};
warning: alignment 1 of 'struct S' is less than 8
This warning is disabled by default and enabled by -Wall.
gcc/
PR c/53037
* print-tree.c (print_node): Support DECL_WARN_IF_NOT_ALIGN
and TYPE_WARN_IF_NOT_ALIGN.
* stor-layout.c (do_type_align): Merge DECL_WARN_IF_NOT_ALIGN.
(handle_warn_if_not_align): New.
(place_union_field): Call handle_warn_if_not_align.
(place_field): Call handle_warn_if_not_align. Copy
TYPE_WARN_IF_NOT_ALIGN.
(finish_builtin_struct): Copy TYPE_WARN_IF_NOT_ALIGN.
(layout_type): Likewise.
* tree-core.h (tree_type_common): Add warn_if_not_align. Set
spare to 18.
(tree_decl_common): Add warn_if_not_align.
* tree.c (build_range_type_1): Copy TYPE_WARN_IF_NOT_ALIGN.
* tree.h (TYPE_WARN_IF_NOT_ALIGN): New.
(SET_TYPE_WARN_IF_NOT_ALIGN): Likewise.
(DECL_WARN_IF_NOT_ALIGN): Likewise.
(SET_DECL_WARN_IF_NOT_ALIGN): Likewise.
* doc/extend.texi: Document warn_if_not_aligned attribute.
* doc/invoke.texi: Document -Wif-not-aligned and
-Wpacked-not-aligned.
gcc/c-family/
PR c/53037
* c-attribs.c (handle_warn_if_not_aligned_attribute): New.
(c_common_attribute_table): Add warn_if_not_aligned.
(handle_aligned_attribute): Renamed to ...
(common_handle_aligned_attribute): Remove argument, name, and add
argument, warn_if_not_aligned. Handle warn_if_not_aligned.
(handle_aligned_attribute): New.
* c.opt: Add -Wif-not-aligned and -Wpacked-not-aligned.
gcc/c/
PR c/53037
* c-decl.c (merge_decls): Also merge DECL_WARN_IF_NOT_ALIGN.
gcc/cp/
PR c/53037
* decl.c (duplicate_decls): Also merge DECL_WARN_IF_NOT_ALIGN.
gcc/testsuite/
PR c/53037
* c-c++-common/pr53037-5.c: New test.
* g++.dg/pr53037-1.C: Likewise.
* g++.dg/pr53037-2.C: Likewise.
* g++.dg/pr53037-3.C: Likewise.
* g++.dg/pr53037-4.C: Likewise.
* gcc.dg/pr53037-1.c: Likewise.
* gcc.dg/pr53037-2.c: Likewise.
* gcc.dg/pr53037-3.c: Likewise.
* gcc.dg/pr53037-4.c: Likewise.
---
gcc/c-family/c-attribs.c | 68 ++++++++++++++++++++++----
gcc/c-family/c.opt | 8 ++++
gcc/c/c-decl.c | 4 ++
gcc/cp/decl.c | 4 ++
gcc/doc/extend.texi | 87 ++++++++++++++++++++++++++++++++++
gcc/doc/invoke.texi | 29 +++++++++++-
gcc/print-tree.c | 9 ++--
gcc/stor-layout.c | 63 ++++++++++++++++++++++++
gcc/testsuite/c-c++-common/pr53037-5.c | 81 +++++++++++++++++++++++++++++++
gcc/testsuite/g++.dg/pr53037-1.C | 81 +++++++++++++++++++++++++++++++
gcc/testsuite/g++.dg/pr53037-2.C | 37 +++++++++++++++
gcc/testsuite/g++.dg/pr53037-3.C | 37 +++++++++++++++
gcc/testsuite/g++.dg/pr53037-4.C | 11 +++++
gcc/testsuite/gcc.dg/pr53037-1.c | 81 +++++++++++++++++++++++++++++++
gcc/testsuite/gcc.dg/pr53037-2.c | 37 +++++++++++++++
gcc/testsuite/gcc.dg/pr53037-3.c | 37 +++++++++++++++
gcc/testsuite/gcc.dg/pr53037-4.c | 11 +++++
gcc/tree-core.h | 9 +++-
gcc/tree.c | 1 +
gcc/tree.h | 20 ++++++++
20 files changed, 701 insertions(+), 14 deletions(-)
create mode 100644 gcc/testsuite/c-c++-common/pr53037-5.c
create mode 100644 gcc/testsuite/g++.dg/pr53037-1.C
create mode 100644 gcc/testsuite/g++.dg/pr53037-2.C
create mode 100644 gcc/testsuite/g++.dg/pr53037-3.C
create mode 100644 gcc/testsuite/g++.dg/pr53037-4.C
create mode 100644 gcc/testsuite/gcc.dg/pr53037-1.c
create mode 100644 gcc/testsuite/gcc.dg/pr53037-2.c
create mode 100644 gcc/testsuite/gcc.dg/pr53037-3.c
create mode 100644 gcc/testsuite/gcc.dg/pr53037-4.c
diff --git a/gcc/c-family/c-attribs.c b/gcc/c-family/c-attribs.c
index 2b6845f..d01f623 100644
--- a/gcc/c-family/c-attribs.c
+++ b/gcc/c-family/c-attribs.c
@@ -88,6 +88,8 @@ static tree handle_destructor_attribute (tree *, tree, tree, int, bool *);
static tree handle_mode_attribute (tree *, tree, tree, int, bool *);
static tree handle_section_attribute (tree *, tree, tree, int, bool *);
static tree handle_aligned_attribute (tree *, tree, tree, int, bool *);
+static tree handle_warn_if_not_aligned_attribute (tree *, tree, tree,
+ int, bool *);
static tree handle_weak_attribute (tree *, tree, tree, int, bool *) ;
static tree handle_noplt_attribute (tree *, tree, tree, int, bool *) ;
static tree handle_alias_ifunc_attribute (bool, tree *, tree, tree, bool *);
@@ -211,6 +213,9 @@ const struct attribute_spec c_common_attribute_table[] =
handle_section_attribute, false },
{ "aligned", 0, 1, false, false, false,
handle_aligned_attribute, false },
+ { "warn_if_not_aligned", 0, 1, false, false, false,
+ handle_warn_if_not_aligned_attribute,
+ false },
{ "weak", 0, 0, true, false, false,
handle_weak_attribute, false },
{ "noplt", 0, 0, true, false, false,
@@ -1640,12 +1645,13 @@ check_cxx_fundamental_alignment_constraints (tree node,
return !alignment_too_large_p;
}
-/* Handle a "aligned" attribute; arguments as in
- struct attribute_spec.handler. */
+/* Common codes shared by handle_warn_if_not_aligned_attribute and
+ handle_aligned_attribute. */
static tree
-handle_aligned_attribute (tree *node, tree ARG_UNUSED (name), tree args,
- int flags, bool *no_add_attrs)
+common_handle_aligned_attribute (tree *node, tree args, int flags,
+ bool *no_add_attrs,
+ bool warn_if_not_aligned_p)
{
tree decl = NULL_TREE;
tree *type = NULL;
@@ -1694,8 +1700,16 @@ handle_aligned_attribute (tree *node, tree ARG_UNUSED (name), tree args,
else
*type = build_variant_type_copy (*type);
- SET_TYPE_ALIGN (*type, (1U << i) * BITS_PER_UNIT);
- TYPE_USER_ALIGN (*type) = 1;
+ if (warn_if_not_aligned_p)
+ {
+ SET_TYPE_WARN_IF_NOT_ALIGN (*type, (1U << i) * BITS_PER_UNIT);
+ warn_if_not_aligned_p = false;
+ }
+ else
+ {
+ SET_TYPE_ALIGN (*type, (1U << i) * BITS_PER_UNIT);
+ TYPE_USER_ALIGN (*type) = 1;
+ }
}
else if (! VAR_OR_FUNCTION_DECL_P (decl)
&& TREE_CODE (decl) != FIELD_DECL)
@@ -1728,13 +1742,51 @@ handle_aligned_attribute (tree *node, tree ARG_UNUSED (name), tree args,
}
else
{
- SET_DECL_ALIGN (decl, (1U << i) * BITS_PER_UNIT);
- DECL_USER_ALIGN (decl) = 1;
+ if (warn_if_not_aligned_p && TREE_CODE (decl) == FIELD_DECL)
+ {
+ SET_DECL_WARN_IF_NOT_ALIGN (decl, (1U << i) * BITS_PER_UNIT);
+ warn_if_not_aligned_p = false;
+ }
+ else
+ {
+ SET_DECL_ALIGN (decl, (1U << i) * BITS_PER_UNIT);
+ DECL_USER_ALIGN (decl) = 1;
+ }
+ }
+
+ if (warn_if_not_aligned_p)
+ {
+ error ("%<warn_if_not_aligned%> may not be specified for %q+D",
+ decl);
+ *no_add_attrs = true;
}
return NULL_TREE;
}
+/* Handle a "aligned" attribute; arguments as in
+ struct attribute_spec.handler. */
+
+static tree
+handle_aligned_attribute (tree *node, tree ARG_UNUSED (name), tree args,
+ int flags, bool *no_add_attrs)
+{
+ return common_handle_aligned_attribute (node, args, flags,
+ no_add_attrs, false);
+}
+
+/* Handle a "warn_if_not_aligned" attribute; arguments as in
+ struct attribute_spec.handler. */
+
+static tree
+handle_warn_if_not_aligned_attribute (tree *node, tree ARG_UNUSED (name),
+ tree args, int flags,
+ bool *no_add_attrs)
+{
+ return common_handle_aligned_attribute (node, args, flags,
+ no_add_attrs, true);
+}
+
/* Handle a "weak" attribute; arguments as in
struct attribute_spec.handler. */
diff --git a/gcc/c-family/c.opt b/gcc/c-family/c.opt
index 37bb236..b324666 100644
--- a/gcc/c-family/c.opt
+++ b/gcc/c-family/c.opt
@@ -579,6 +579,10 @@ Wformat-truncation=
C ObjC C++ ObjC++ Joined RejectNegative UInteger Var(warn_format_trunc) Warning LangEnabledBy(C ObjC C++ ObjC++,Wformat=, warn_format >= 1, 0)
Warn about calls to snprintf and similar functions that truncate output.
+Wif-not-aligned
+C ObjC C++ ObjC++ Var(warn_if_not_aligned) Init(1) Warning
+Warn when the field in a struct is not aligned.
+
Wignored-qualifiers
C C++ Var(warn_ignored_qualifiers) Warning EnabledBy(Wextra)
Warn whenever type qualifiers are ignored.
@@ -706,6 +710,10 @@ Wnamespaces
C++ ObjC++ Var(warn_namespaces) Warning
Warn on namespace definition.
+Wpacked-not-aligned
+C ObjC C++ ObjC++ Var(warn_packed_not_aligned) Warning LangEnabledBy(C ObjC C++ ObjC++,Wall)
+Warn when fields in a struct with the packed attribute are misaligned.
+
Wsized-deallocation
C++ ObjC++ Var(warn_sized_deallocation) Warning EnabledBy(Wextra)
Warn about missing sized deallocation functions.
diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c
index 317d5cd..144174e 100644
--- a/gcc/c/c-decl.c
+++ b/gcc/c/c-decl.c
@@ -2384,6 +2384,10 @@ merge_decls (tree newdecl, tree olddecl, tree newtype, tree oldtype)
SET_DECL_ALIGN (newdecl, DECL_ALIGN (olddecl));
DECL_USER_ALIGN (newdecl) |= DECL_USER_ALIGN (olddecl);
}
+ if (DECL_WARN_IF_NOT_ALIGN (olddecl)
+ > DECL_WARN_IF_NOT_ALIGN (newdecl))
+ SET_DECL_WARN_IF_NOT_ALIGN (newdecl,
+ DECL_WARN_IF_NOT_ALIGN (olddecl));
}
/* Keep the old rtl since we can safely use it. */
diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c
index 3711476..ab22f98 100644
--- a/gcc/cp/decl.c
+++ b/gcc/cp/decl.c
@@ -2527,6 +2527,10 @@ duplicate_decls (tree newdecl, tree olddecl, bool newdecl_is_friend)
DECL_USER_ALIGN (newdecl) |= DECL_USER_ALIGN (olddecl);
}
DECL_USER_ALIGN (olddecl) = DECL_USER_ALIGN (newdecl);
+ if (DECL_WARN_IF_NOT_ALIGN (olddecl)
+ > DECL_WARN_IF_NOT_ALIGN (newdecl))
+ SET_DECL_WARN_IF_NOT_ALIGN (newdecl,
+ DECL_WARN_IF_NOT_ALIGN (olddecl));
if (TREE_CODE (newdecl) == FIELD_DECL)
DECL_PACKED (olddecl) = DECL_PACKED (newdecl);
diff --git a/gcc/doc/extend.texi b/gcc/doc/extend.texi
index 1de17b4..d5abe35 100644
--- a/gcc/doc/extend.texi
+++ b/gcc/doc/extend.texi
@@ -5707,6 +5707,41 @@ alignment. See your linker documentation for further information.
The @code{aligned} attribute can also be used for functions
(@pxref{Common Function Attributes}.)
+@cindex @code{warn_if_not_aligned} variable attribute
+@item warn_if_not_aligned (@var{alignment})
+This attribute specifies a threshold for the structure field, measured
+in bytes. If the structure field is aligned below the threshold, a
+warning will be issued. For example, the declaration:
+
+@smallexample
+struct foo
+@{
+ int i1;
+ int i2;
+ unsigned long long x __attribute__((warn_if_not_aligned(16)));
+@};
+@end smallexample
+
+@noindent
+causes the compiler to issue an warning on @code{struct foo}, like
+@code{warning: alignment 8 of 'struct foo' is less than 16}.
+The compiler also issues a warning, like @code{warning: 'x' offset
+8 in 'struct foo' isn't aligned to 16}, when the structure field has
+the misaligned offset:
+
+@smallexample
+struct foo
+@{
+ int i1;
+ int i2;
+ unsigned long long x __attribute__((warn_if_not_aligned(16)));
+@} __attribute__((aligned(16)));
+@end smallexample
+
+This warning can be disabled by @option{-Wno-if-not-aligned}.
+The @code{warn_if_not_aligned } attribute can also be used for types
+(@pxref{Common Type Attributes}.)
+
@item cleanup (@var{cleanup_function})
@cindex @code{cleanup} variable attribute
The @code{cleanup} attribute runs a function when the variable goes
@@ -6560,6 +6595,58 @@ alignment. See your linker documentation for further information.
The @code{aligned} attribute can only increase alignment. Alignment
can be decreased by specifying the @code{packed} attribute. See below.
+@cindex @code{warn_if_not_aligned} type attribute
+@item warn_if_not_aligned (@var{alignment})
+This attribute specifies a threshold for the structure field, measured
+in bytes. If the structure field is aligned below the threshold, a
+warning will be issued. For example, the declaration:
+
+@smallexample
+typedef unsigned long long __u64
+ __attribute__((aligned(4),warn_if_not_aligned(8)));
+
+struct foo
+@{
+ int i1;
+ int i2;
+ __u64 x;
+@};
+@end smallexample
+
+@noindent
+causes the compiler to issue an warning on @code{struct foo}, like
+@code{warning: alignment 4 of 'struct foo' is less than 8}.
+It is used to define @code{struct foo} in such a way that
+@code{struct foo} has the same layout and the structure field @code{x}
+has the same alignment when @code{__u64} is aligned at either 4 or
+8 bytes. Align @code{struct foo} to 8 bytes:
+
+@smallexample
+struct foo
+@{
+ int i1;
+ int i2;
+ __u64 x;
+@} __attribute__((aligned(8)));
+@end smallexample
+
+@noindent
+silences the warning. The compiler also issues a warning, like
+@code{warning: 'x' offset 12 in 'struct foo' isn't aligned to 8},
+when the structure field has the misaligned offset:
+
+@smallexample
+struct foo
+@{
+ int i1;
+ int i2;
+ int i3;
+ __u64 x;
+@} __attribute__((aligned(8)));
+@end smallexample
+
+This warning can be disabled by @option{-Wno-if-not-aligned}.
+
@item bnd_variable_size
@cindex @code{bnd_variable_size} type attribute
@cindex Pointer Bounds Checker attributes
diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi
index 653bc07..5bf2a2d 100644
--- a/gcc/doc/invoke.texi
+++ b/gcc/doc/invoke.texi
@@ -283,6 +283,7 @@ Objective-C and Objective-C++ Dialects}.
-Wformat-security -Wformat-signedness -Wformat-truncation=@var{n} @gol
-Wformat-y2k -Wframe-address @gol
-Wframe-larger-than=@var{len} -Wno-free-nonheap-object -Wjump-misses-init @gol
+-Wif-not-aligned @gol
-Wignored-qualifiers -Wignored-attributes -Wincompatible-pointer-types @gol
-Wimplicit -Wimplicit-fallthrough -Wimplicit-fallthrough=@var{n} @gol
-Wimplicit-function-declaration -Wimplicit-int @gol
@@ -297,7 +298,7 @@ Objective-C and Objective-C++ Dialects}.
-Wnormalized=@r{[}none@r{|}id@r{|}nfc@r{|}nfkc@r{]} @gol
-Wnull-dereference -Wodr -Wno-overflow -Wopenmp-simd @gol
-Woverride-init-side-effects -Woverlength-strings @gol
--Wpacked -Wpacked-bitfield-compat -Wpadded @gol
+-Wpacked -Wpacked-bitfield-compat -Wpacked-not-aligned -Wpadded @gol
-Wparentheses -Wno-pedantic-ms-format @gol
-Wplacement-new -Wplacement-new=@var{n} @gol
-Wpointer-arith -Wpointer-compare -Wno-pointer-to-int-cast @gol
@@ -4407,6 +4408,13 @@ switch (cond)
The @option{-Wimplicit-fallthrough=3} warning is enabled by @option{-Wextra}.
+@item -Wif-not-aligned @r{(C, C++, Objective-C and Objective-C++ only)}
+@opindex Wif-not-aligned
+@opindex Wno-if-not-aligned
+Control if warning triggered by the @code{warn_if_not_aligned} attribute
+should be issued. This is is enabled by default.
+Use @option{-Wno-if-not-aligned} to disable it.
+
@item -Wignored-qualifiers @r{(C and C++ only)}
@opindex Wignored-qualifiers
@opindex Wno-ignored-qualifiers
@@ -6474,6 +6482,25 @@ struct foo
This warning is enabled by default. Use
@option{-Wno-packed-bitfield-compat} to disable this warning.
+@item -Wpacked-not-aligned @r{(C, C++, Objective-C and Objective-C++ only)}
+@opindex Wpacked-not-aligned
+@opindex Wno-packed-not-aligned
+Warn if a structure field with explicitly specified alignment in a
+packed struct or union is misaligned. For example, a warning will
+be issued on @code{struct S}, like, @code{warning: alignment 1 of
+'struct S' is less than 8}, in this code:
+
+@smallexample
+@group
+struct __attribute__ ((aligned (8))) S8 @{ char a[8]; @};
+struct __attribute__ ((packed)) S @{
+ struct S8 s8;
+@};
+@end group
+@end smallexample
+
+This warning is enabled by @option{-Wall}.
+
@item -Wpadded
@opindex Wpadded
@opindex Wno-padded
diff --git a/gcc/print-tree.c b/gcc/print-tree.c
index ea26a0b..7fdff8f 100644
--- a/gcc/print-tree.c
+++ b/gcc/print-tree.c
@@ -458,7 +458,8 @@ print_node (FILE *file, const char *prefix, tree node, int indent,
if (DECL_USER_ALIGN (node))
fprintf (file, " user");
- fprintf (file, " align %d", DECL_ALIGN (node));
+ fprintf (file, " align %d warn_if_not_align %d",
+ DECL_ALIGN (node), DECL_WARN_IF_NOT_ALIGN (node));
if (code == FIELD_DECL)
fprintf (file, " offset_align " HOST_WIDE_INT_PRINT_UNSIGNED,
DECL_OFFSET_ALIGN (node));
@@ -603,8 +604,10 @@ print_node (FILE *file, const char *prefix, tree node, int indent,
if (TYPE_USER_ALIGN (node))
fprintf (file, " user");
- fprintf (file, " align %d symtab %d alias set " HOST_WIDE_INT_PRINT_DEC,
- TYPE_ALIGN (node), TYPE_SYMTAB_ADDRESS (node),
+ fprintf (file, " align %d warn_if_not_align %d symtab %d alias set "
+ HOST_WIDE_INT_PRINT_DEC,
+ TYPE_ALIGN (node), TYPE_WARN_IF_NOT_ALIGN (node),
+ TYPE_SYMTAB_ADDRESS (node),
(HOST_WIDE_INT) TYPE_ALIAS_SET (node));
if (TYPE_STRUCTURAL_EQUALITY_P (node))
diff --git a/gcc/stor-layout.c b/gcc/stor-layout.c
index 1574e43..ae6f981 100644
--- a/gcc/stor-layout.c
+++ b/gcc/stor-layout.c
@@ -570,6 +570,8 @@ do_type_align (tree type, tree decl)
if (TREE_CODE (decl) == FIELD_DECL)
DECL_USER_ALIGN (decl) = TYPE_USER_ALIGN (type);
}
+ if (TYPE_WARN_IF_NOT_ALIGN (type) > DECL_WARN_IF_NOT_ALIGN (decl))
+ SET_DECL_WARN_IF_NOT_ALIGN (decl, TYPE_WARN_IF_NOT_ALIGN (type));
}
/* Set the size, mode and alignment of a ..._DECL node.
@@ -1074,6 +1076,54 @@ update_alignment_for_field (record_layout_info rli, tree field,
return desired_align;
}
+static void
+handle_warn_if_not_align (tree field, unsigned int record_align)
+{
+ tree type = TREE_TYPE (field);
+
+ if (type == error_mark_node)
+ return;
+
+ unsigned int warn_if_not_align = 0;
+
+ int opt_w = 0;
+
+ if (warn_if_not_aligned)
+ {
+ warn_if_not_align = DECL_WARN_IF_NOT_ALIGN (field);
+ if (!warn_if_not_align)
+ warn_if_not_align = TYPE_WARN_IF_NOT_ALIGN (type);
+ if (warn_if_not_align)
+ opt_w = OPT_Wif_not_aligned;
+ }
+
+ if (!warn_if_not_align
+ && warn_packed_not_aligned
+ && TYPE_USER_ALIGN (type))
+ {
+ warn_if_not_align = TYPE_ALIGN (type);
+ opt_w = OPT_Wpacked_not_aligned;
+ }
+
+ if (!warn_if_not_align)
+ return;
+
+ tree context = DECL_CONTEXT (field);
+
+ warn_if_not_align /= BITS_PER_UNIT;
+ record_align /= BITS_PER_UNIT;
+ if ((record_align % warn_if_not_align) != 0)
+ warning (opt_w, "alignment %d of %qT is less than %d",
+ record_align, context, warn_if_not_align);
+
+ unsigned int off
+ = (tree_to_uhwi (DECL_FIELD_OFFSET (field))
+ + tree_to_uhwi (DECL_FIELD_BIT_OFFSET (field)) / BITS_PER_UNIT);
+ if ((off % warn_if_not_align) != 0)
+ warning (opt_w, "%q+D offset %d in %qT isn't aligned to %d",
+ field, off, context, warn_if_not_align);
+}
+
/* Called from place_field to handle unions. */
static void
@@ -1084,6 +1134,7 @@ place_union_field (record_layout_info rli, tree field)
DECL_FIELD_OFFSET (field) = size_zero_node;
DECL_FIELD_BIT_OFFSET (field) = bitsize_zero_node;
SET_DECL_OFFSET_ALIGN (field, BIGGEST_ALIGNMENT);
+ handle_warn_if_not_align (field, rli->record_align);
/* If this is an ERROR_MARK return *after* having set the
field at the start of the union. This helps when parsing
@@ -1169,6 +1220,7 @@ place_field (record_layout_info rli, tree field)
DECL_FIELD_OFFSET (field) = rli->offset;
DECL_FIELD_BIT_OFFSET (field) = rli->bitpos;
SET_DECL_OFFSET_ALIGN (field, rli->offset_align);
+ handle_warn_if_not_align (field, rli->record_align);
return;
}
@@ -1290,6 +1342,9 @@ place_field (record_layout_info rli, tree field)
if (! DECL_PACKED (field))
TYPE_USER_ALIGN (rli->t) |= TYPE_USER_ALIGN (type);
+
+ SET_TYPE_WARN_IF_NOT_ALIGN (rli->t,
+ TYPE_WARN_IF_NOT_ALIGN (type));
}
#ifdef BITFIELD_NBYTES_LIMITED
@@ -1328,6 +1383,8 @@ place_field (record_layout_info rli, tree field)
rli->bitpos = round_up (rli->bitpos, type_align);
TYPE_USER_ALIGN (rli->t) |= TYPE_USER_ALIGN (type);
+ SET_TYPE_WARN_IF_NOT_ALIGN (rli->t,
+ TYPE_WARN_IF_NOT_ALIGN (type));
}
#endif
@@ -1478,6 +1535,7 @@ place_field (record_layout_info rli, tree field)
DECL_FIELD_OFFSET (field) = rli->offset;
DECL_FIELD_BIT_OFFSET (field) = rli->bitpos;
SET_DECL_OFFSET_ALIGN (field, rli->offset_align);
+ handle_warn_if_not_align (field, rli->record_align);
/* Evaluate nonconstant offsets only once, either now or as soon as safe. */
if (TREE_CODE (DECL_FIELD_OFFSET (field)) != INTEGER_CST)
@@ -2088,6 +2146,8 @@ finish_builtin_struct (tree type, const char *name, tree fields,
{
SET_TYPE_ALIGN (type, TYPE_ALIGN (align_type));
TYPE_USER_ALIGN (type) = TYPE_USER_ALIGN (align_type);
+ SET_TYPE_WARN_IF_NOT_ALIGN (type,
+ TYPE_WARN_IF_NOT_ALIGN (align_type));
}
layout_type (type);
@@ -2324,6 +2384,9 @@ layout_type (tree type)
align = MAX (align, TYPE_ALIGN (type));
else
TYPE_USER_ALIGN (type) = TYPE_USER_ALIGN (element);
+ if (!TYPE_WARN_IF_NOT_ALIGN (type))
+ SET_TYPE_WARN_IF_NOT_ALIGN (type,
+ TYPE_WARN_IF_NOT_ALIGN (element));
#ifdef ROUND_TYPE_ALIGN
align = ROUND_TYPE_ALIGN (type, align, BITS_PER_UNIT);
#else
diff --git a/gcc/testsuite/c-c++-common/pr53037-5.c b/gcc/testsuite/c-c++-common/pr53037-5.c
new file mode 100644
index 0000000..97d54b1
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/pr53037-5.c
@@ -0,0 +1,81 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0 -Wno-if-not-aligned" } */
+
+typedef unsigned long long __u64
+ __attribute__((aligned(4),warn_if_not_aligned(8)));
+
+struct foo1
+{
+ int i1;
+ int i2;
+ int i3;
+ __u64 x;
+};
+
+struct foo2
+{
+ int i1;
+ int i2;
+ int i3;
+ __u64 x;
+} __attribute__((aligned(8)));
+
+struct foo3
+{
+ int i1;
+ int i3;
+ __u64 x;
+};
+
+struct foo4
+{
+ int i1;
+ int i2;
+ __u64 x;
+} __attribute__((aligned(8)));
+
+struct foo5
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16)));
+};
+
+struct foo6
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16)));
+} __attribute__((aligned(16)));
+
+struct foo7
+{
+ int i1;
+ int i2;
+ int i3;
+ int i4;
+ int x __attribute__((warn_if_not_aligned(16)));
+} __attribute__((aligned(16)));
+
+union bar1
+{
+ int i1;
+ __u64 x;
+};
+
+union bar2
+{
+ int i1;
+ __u64 x;
+} __attribute__((aligned(8)));
+
+union bar3
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16)));
+};
+
+union bar4
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16)));
+} __attribute__((aligned(16)));
diff --git a/gcc/testsuite/g++.dg/pr53037-1.C b/gcc/testsuite/g++.dg/pr53037-1.C
new file mode 100644
index 0000000..a3d8f99
--- /dev/null
+++ b/gcc/testsuite/g++.dg/pr53037-1.C
@@ -0,0 +1,81 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0" } */
+
+typedef unsigned long long __u64
+ __attribute__((aligned(4),warn_if_not_aligned(8)));
+
+struct foo1 /* { dg-warning "alignment 4 of 'foo1' is less than 8" } */
+{
+ int i1;
+ int i2;
+ int i3;
+ __u64 x; /* { dg-warning "'foo1::x' offset 12 in 'foo1' isn't aligned to 8" } */
+};
+
+struct foo2
+{
+ int i1;
+ int i2;
+ int i3;
+ __u64 x; /* { dg-warning "'foo2::x' offset 12 in 'foo2' isn't aligned to 8" } */
+} __attribute__((aligned(8)));
+
+struct foo3 /* { dg-warning "alignment 4 of 'foo3' is less than 8" } */
+{
+ int i1;
+ int i3;
+ __u64 x;
+};
+
+struct foo4
+{
+ int i1;
+ int i2;
+ __u64 x;
+} __attribute__((aligned(8)));
+
+struct foo5 /* { dg-warning "alignment 4 of 'foo5' is less than 16" } */
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16))); /* { dg-warning "'foo5::x' offset 4 in 'foo5' isn't aligned to 16" } */
+};
+
+struct foo6
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16))); /* { dg-warning "'foo6::x' offset 4 in 'foo6' isn't aligned to 16" } */
+} __attribute__((aligned(16)));
+
+struct foo7
+{
+ int i1;
+ int i2;
+ int i3;
+ int i4;
+ int x __attribute__((warn_if_not_aligned(16)));
+} __attribute__((aligned(16)));
+
+union bar1 /* { dg-warning "alignment 4 of 'bar1' is less than 8" } */
+{
+ int i1;
+ __u64 x;
+};
+
+union bar2
+{
+ int i1;
+ __u64 x;
+} __attribute__((aligned(8)));
+
+union bar3 /* { dg-warning "alignment 4 of 'bar3' is less than 16" } */
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16)));
+};
+
+union bar4
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16)));
+} __attribute__((aligned(16)));
diff --git a/gcc/testsuite/g++.dg/pr53037-2.C b/gcc/testsuite/g++.dg/pr53037-2.C
new file mode 100644
index 0000000..e617f90
--- /dev/null
+++ b/gcc/testsuite/g++.dg/pr53037-2.C
@@ -0,0 +1,37 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0 -Wpacked-not-aligned" } */
+
+struct __attribute__ ((aligned (8))) S8 { char a[8]; };
+struct __attribute__ ((packed)) S1 { /* { dg-warning "alignment 1 of 'S1' is less than 8" } */
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed, aligned (8))) S2 {
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed, aligned (8))) S3 {
+ int i1;
+ struct S8 s8; /* { dg-warning "'S3::s8' offset 4 in 'S3' isn't aligned to 8" } */
+};
+
+struct __attribute__ ((packed, aligned (8))) S4 {
+ int i1;
+ int i2;
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed)) S5 {
+ long long ll;
+};
+
+union __attribute__ ((packed)) U1 { /* { dg-warning "alignment 1 of 'U1' is less than 8" } */
+ int i1;
+ struct S8 s8;
+};
+
+union __attribute__ ((packed, aligned (8))) U2 {
+ int i1;
+ struct S8 s8;
+};
diff --git a/gcc/testsuite/g++.dg/pr53037-3.C b/gcc/testsuite/g++.dg/pr53037-3.C
new file mode 100644
index 0000000..1ed6354
--- /dev/null
+++ b/gcc/testsuite/g++.dg/pr53037-3.C
@@ -0,0 +1,37 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0 -Wall" } */
+
+struct __attribute__ ((aligned (8))) S8 { char a[8]; };
+struct __attribute__ ((packed)) S1 { /* { dg-warning "alignment 1 of 'S1' is less than 8" } */
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed, aligned (8))) S2 {
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed, aligned (8))) S3 {
+ int i1;
+ struct S8 s8; /* { dg-warning "'S3::s8' offset 4 in 'S3' isn't aligned to 8" } */
+};
+
+struct __attribute__ ((packed, aligned (8))) S4 {
+ int i1;
+ int i2;
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed)) S5 {
+ long long ll;
+};
+
+union __attribute__ ((packed)) U1 { /* { dg-warning "alignment 1 of 'U1' is less than 8" } */
+ int i1;
+ struct S8 s8;
+};
+
+union __attribute__ ((packed, aligned (8))) U2 {
+ int i1;
+ struct S8 s8;
+};
diff --git a/gcc/testsuite/g++.dg/pr53037-4.C b/gcc/testsuite/g++.dg/pr53037-4.C
new file mode 100644
index 0000000..525483d
--- /dev/null
+++ b/gcc/testsuite/g++.dg/pr53037-4.C
@@ -0,0 +1,11 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0" } */
+
+int foo __attribute__((warn_if_not_aligned(8))); /* { dg-error "'warn_if_not_aligned' may not be specified for 'foo'" } */
+
+__attribute__((warn_if_not_aligned(8)))
+void
+bar (void) /* { dg-error "'warn_if_not_aligned' may not be specified for 'void bar\\(\\)'" } */
+{
+}
diff --git a/gcc/testsuite/gcc.dg/pr53037-1.c b/gcc/testsuite/gcc.dg/pr53037-1.c
new file mode 100644
index 0000000..93af0a5
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr53037-1.c
@@ -0,0 +1,81 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0" } */
+
+typedef unsigned long long __u64
+ __attribute__((aligned(4),warn_if_not_aligned(8)));
+
+struct foo1
+{
+ int i1;
+ int i2;
+ int i3;
+ __u64 x; /* { dg-warning "'x' offset 12 in 'struct foo1' isn't aligned to 8" } */
+}; /* { dg-warning "alignment 4 of 'struct foo1' is less than 8" } */
+
+struct foo2
+{
+ int i1;
+ int i2;
+ int i3;
+ __u64 x; /* { dg-warning "'x' offset 12 in 'struct foo2' isn't aligned to 8" } */
+} __attribute__((aligned(8)));
+
+struct foo3
+{
+ int i1;
+ int i3;
+ __u64 x;
+}; /* { dg-warning "alignment 4 of 'struct foo3' is less than 8" } */
+
+struct foo4
+{
+ int i1;
+ int i2;
+ __u64 x;
+} __attribute__((aligned(8)));
+
+struct foo5
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16))); /* { dg-warning "'x' offset 4 in 'struct foo5' isn't aligned to 16" } */
+}; /* { dg-warning "alignment 4 of 'struct foo5' is less than 16" } */
+
+struct foo6
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16))); /* { dg-warning "'x' offset 4 in 'struct foo6' isn't aligned to 16" } */
+} __attribute__((aligned(16)));
+
+struct foo7
+{
+ int i1;
+ int i2;
+ int i3;
+ int i4;
+ int x __attribute__((warn_if_not_aligned(16)));
+} __attribute__((aligned(16)));
+
+union bar1
+{
+ int i1;
+ __u64 x;
+}; /* { dg-warning "alignment 4 of 'union bar1' is less than 8" } */
+
+union bar2
+{
+ int i1;
+ __u64 x;
+} __attribute__((aligned(8)));
+
+union bar3
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16)));
+}; /* { dg-warning "alignment 4 of 'union bar3' is less than 16" } */
+
+union bar4
+{
+ int i1;
+ int x __attribute__((warn_if_not_aligned(16)));
+} __attribute__((aligned(16)));
diff --git a/gcc/testsuite/gcc.dg/pr53037-2.c b/gcc/testsuite/gcc.dg/pr53037-2.c
new file mode 100644
index 0000000..f9934a6
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr53037-2.c
@@ -0,0 +1,37 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0 -Wpacked-not-aligned" } */
+
+struct __attribute__ ((aligned (8))) S8 { char a[8]; };
+struct __attribute__ ((packed)) S1 {
+ struct S8 s8;
+}; /* { dg-warning "alignment 1 of 'struct S1' is less than 8" } */
+
+struct __attribute__ ((packed, aligned (8))) S2 {
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed, aligned (8))) S3 {
+ int i1;
+ struct S8 s8; /* { dg-warning "'s8' offset 4 in 'struct S3' isn't aligned to 8" } */
+};
+
+struct __attribute__ ((packed, aligned (8))) S4 {
+ int i1;
+ int i2;
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed)) S5 {
+ long long ll;
+};
+
+union __attribute__ ((packed)) U1 {
+ int i1;
+ struct S8 s8;
+}; /* { dg-warning "alignment 1 of 'union U1' is less than 8" } */
+
+union __attribute__ ((packed, aligned (8))) U2 {
+ int i1;
+ struct S8 s8;
+};
diff --git a/gcc/testsuite/gcc.dg/pr53037-3.c b/gcc/testsuite/gcc.dg/pr53037-3.c
new file mode 100644
index 0000000..fc69ae8
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr53037-3.c
@@ -0,0 +1,37 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0 -Wall" } */
+
+struct __attribute__ ((aligned (8))) S8 { char a[8]; };
+struct __attribute__ ((packed)) S1 {
+ struct S8 s8;
+}; /* { dg-warning "alignment 1 of 'struct S1' is less than 8" } */
+
+struct __attribute__ ((packed, aligned (8))) S2 {
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed, aligned (8))) S3 {
+ int i1;
+ struct S8 s8; /* { dg-warning "'s8' offset 4 in 'struct S3' isn't aligned to 8" } */
+};
+
+struct __attribute__ ((packed, aligned (8))) S4 {
+ int i1;
+ int i2;
+ struct S8 s8;
+};
+
+struct __attribute__ ((packed)) S5 {
+ long long ll;
+};
+
+union __attribute__ ((packed)) U1 {
+ int i1;
+ struct S8 s8;
+}; /* { dg-warning "alignment 1 of 'union U1' is less than 8" } */
+
+union __attribute__ ((packed, aligned (8))) U2 {
+ int i1;
+ struct S8 s8;
+};
diff --git a/gcc/testsuite/gcc.dg/pr53037-4.c b/gcc/testsuite/gcc.dg/pr53037-4.c
new file mode 100644
index 0000000..665f828
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr53037-4.c
@@ -0,0 +1,11 @@
+/* PR c/53037. */
+/* { dg-do compile } */
+/* { dg-options "-O0" } */
+
+int foo __attribute__((warn_if_not_aligned(8))); /* { dg-error "'warn_if_not_aligned' may not be specified for 'foo'" } */
+
+__attribute__((warn_if_not_aligned(8)))
+void
+bar (void) /* { dg-error "'warn_if_not_aligned' may not be specified for 'bar'" } */
+{
+}
diff --git a/gcc/tree-core.h b/gcc/tree-core.h
index 34e5c17..a31d4e6 100644
--- a/gcc/tree-core.h
+++ b/gcc/tree-core.h
@@ -1519,8 +1519,9 @@ struct GTY(()) tree_type_common {
so we need to store the value 32 (not 31, as we need the zero
as well), hence six bits. */
unsigned align : 6;
+ unsigned warn_if_not_align : 6;
unsigned typeless_storage : 1;
- unsigned spare : 24;
+ unsigned spare : 18;
alias_set_type alias_set;
tree pointer_to;
@@ -1627,7 +1628,11 @@ struct GTY(()) tree_decl_common {
/* DECL_ALIGN. It should have the same size as TYPE_ALIGN. */
unsigned int align : 6;
- /* 20 bits unused. */
+ /* DECL_WARN_IF_NOT_ALIGN. It should have the same size as
+ TYPE_WARN_IF_NOT_ALIGN. */
+ unsigned int warn_if_not_align : 6;
+
+ /* 14 bits unused. */
/* UID for points-to sets, stable over copying from inlining. */
unsigned int pt_uid;
diff --git a/gcc/tree.c b/gcc/tree.c
index 2602803..e4b5892 100644
--- a/gcc/tree.c
+++ b/gcc/tree.c
@@ -8303,6 +8303,7 @@ build_range_type_1 (tree type, tree lowval, tree highval, bool shared)
TYPE_SIZE_UNIT (itype) = TYPE_SIZE_UNIT (type);
SET_TYPE_ALIGN (itype, TYPE_ALIGN (type));
TYPE_USER_ALIGN (itype) = TYPE_USER_ALIGN (type);
+ SET_TYPE_WARN_IF_NOT_ALIGN (itype, TYPE_WARN_IF_NOT_ALIGN (type));
if (!shared)
return itype;
diff --git a/gcc/tree.h b/gcc/tree.h
index bfe83f7..bb8d927 100644
--- a/gcc/tree.h
+++ b/gcc/tree.h
@@ -1922,6 +1922,16 @@ extern machine_mode element_mode (const_tree t);
/* The alignment for NODE, in bytes. */
#define TYPE_ALIGN_UNIT(NODE) (TYPE_ALIGN (NODE) / BITS_PER_UNIT)
+/* The minimum alignment necessary for objects of this type without
+ warning. The value is an int, measured in bits. */
+#define TYPE_WARN_IF_NOT_ALIGN(NODE) \
+ (TYPE_CHECK (NODE)->type_common.warn_if_not_align \
+ ? ((unsigned)1) << ((NODE)->type_common.warn_if_not_align - 1) : 0)
+
+/* Specify that TYPE_WARN_IF_NOT_ALIGN(NODE) is X. */
+#define SET_TYPE_WARN_IF_NOT_ALIGN(NODE, X) \
+ (TYPE_CHECK (NODE)->type_common.warn_if_not_align = ffs_hwi (X))
+
/* If your language allows you to declare types, and you want debug info
for them, then you need to generate corresponding TYPE_DECL nodes.
These "stub" TYPE_DECL nodes have no name, and simply point at the
@@ -2377,6 +2387,16 @@ extern machine_mode element_mode (const_tree t);
#define SET_DECL_ALIGN(NODE, X) \
(DECL_COMMON_CHECK (NODE)->decl_common.align = ffs_hwi (X))
+/* The minimum alignment necessary for the datum, in bits, without
+ warning. */
+#define DECL_WARN_IF_NOT_ALIGN(NODE) \
+ (DECL_COMMON_CHECK (NODE)->decl_common.warn_if_not_align \
+ ? ((unsigned)1) << ((NODE)->decl_common.warn_if_not_align - 1) : 0)
+
+/* Specify that DECL_WARN_IF_NOT_ALIGN(NODE) is X. */
+#define SET_DECL_WARN_IF_NOT_ALIGN(NODE, X) \
+ (DECL_COMMON_CHECK (NODE)->decl_common.warn_if_not_align = ffs_hwi (X))
+
/* The alignment of NODE, in bytes. */
#define DECL_ALIGN_UNIT(NODE) (DECL_ALIGN (NODE) / BITS_PER_UNIT)
/* Set if the alignment of this DECL has been set by the user, for
--
2.9.4
next prev parent reply other threads:[~2017-06-16 11:55 UTC|newest]
Thread overview: 24+ messages / expand[flat|nested] mbox.gz Atom feed top
2017-06-04 15:52 H.J. Lu
2017-06-05 15:11 ` Joseph Myers
2017-06-05 17:45 ` H.J. Lu
2017-06-06 16:07 ` Martin Sebor
2017-06-06 16:11 ` Martin Sebor
2017-06-06 16:59 ` H.J. Lu
2017-06-06 17:35 ` Martin Sebor
2017-06-06 22:57 ` H.J. Lu
2017-06-07 0:11 ` Martin Sebor
2017-06-07 13:30 ` H.J. Lu
2017-06-08 17:00 ` H.J. Lu
2017-06-08 19:13 ` Martin Sebor
2017-06-09 13:31 ` H.J. Lu
2017-06-15 15:38 ` Martin Sebor
2017-06-15 15:47 ` H.J. Lu
2017-06-15 17:31 ` Joseph Myers
2017-06-16 11:55 ` H.J. Lu [this message]
2017-07-06 15:45 ` Joseph Myers
2017-07-08 13:45 ` H.J. Lu
2017-08-17 14:19 ` Joseph Myers
2017-08-17 16:23 ` H.J. Lu
2017-08-18 1:40 ` Jason Merrill
2017-08-21 12:02 ` Szabolcs Nagy
2017-08-21 12:57 ` H.J. Lu
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20170616115455.GA3457@gmail.com \
--to=hjl.tools@gmail.com \
--cc=gcc-patches@gcc.gnu.org \
--cc=jason@redhat.com \
--cc=joseph@codesourcery.com \
--cc=msebor@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).