From: Eric Botcazou Date: Fri, 4 Dec 2015 08:52:24 +0000 (+0000) Subject: c-tree.h (c_build_va_arg): Adjust prototype. X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=f187980b5e132d0b5d36b5ade6a42ef8cfdb5560;p=gcc.git c-tree.h (c_build_va_arg): Adjust prototype. * c-tree.h (c_build_va_arg): Adjust prototype. * c-parser.c (c_parser_postfix_expression): Adjust call to above. * c-typeck.c (c_build_va_arg): Rename LOC parameter to LOC2, add LOC1 parameter, adjust throughout and issue an error if EXPR is a component with reverse storage order. From-SVN: r231250 --- diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 213c407b75e..468ef9398be 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,11 @@ +2015-12-04 Eric Botcazou + + * c-tree.h (c_build_va_arg): Adjust prototype. + * c-parser.c (c_parser_postfix_expression): Adjust call to above. + * c-typeck.c (c_build_va_arg): Rename LOC parameter to LOC2, add LOC1 + parameter, adjust throughout and issue an error if EXPR is a component + with reverse storage order. + 2015-12-02 Jason Merrill * c-fold.c (c_disable_warnings, c_enable_warnings, c_fully_fold) diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index ee0a30517af..c7d15f9fc38 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -7485,7 +7485,7 @@ c_parser_postfix_expression (c_parser *parser) else { tree type_expr = NULL_TREE; - expr.value = c_build_va_arg (loc, e1.value, + expr.value = c_build_va_arg (start_loc, e1.value, loc, groktypename (t1, &type_expr, NULL)); if (type_expr) { diff --git a/gcc/c/c-tree.h b/gcc/c/c-tree.h index 1c07065896a..00e72b115ca 100644 --- a/gcc/c/c-tree.h +++ b/gcc/c/c-tree.h @@ -661,7 +661,7 @@ extern tree c_finish_omp_task (location_t, tree, tree); extern void c_finish_omp_cancel (location_t, tree); extern void c_finish_omp_cancellation_point (location_t, tree); extern tree c_finish_omp_clauses (tree, bool, bool = false); -extern tree c_build_va_arg (location_t, tree, tree); +extern tree c_build_va_arg (location_t, tree, location_t, tree); extern tree c_finish_transaction (location_t, tree, int); extern bool c_tree_equal (tree, tree); extern tree c_build_function_call_vec (location_t, vec, tree, diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 50709729c79..b691072caa9 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -13426,20 +13426,28 @@ c_build_qualified_type (tree type, int type_quals, tree orig_qual_type, /* Build a VA_ARG_EXPR for the C parser. */ tree -c_build_va_arg (location_t loc, tree expr, tree type) +c_build_va_arg (location_t loc1, tree expr, location_t loc2, tree type) { if (error_operand_p (type)) return error_mark_node; + /* VA_ARG_EXPR cannot be used for a scalar va_list with reverse storage + order because it takes the address of the expression. */ + else if (handled_component_p (expr) + && reverse_storage_order_for_component_p (expr)) + { + error_at (loc1, "cannot use % with reverse storage order"); + return error_mark_node; + } else if (!COMPLETE_TYPE_P (type)) { - error_at (loc, "second argument to % is of incomplete " + error_at (loc2, "second argument to % is of incomplete " "type %qT", type); return error_mark_node; } else if (warn_cxx_compat && TREE_CODE (type) == ENUMERAL_TYPE) - warning_at (loc, OPT_Wc___compat, + warning_at (loc2, OPT_Wc___compat, "C++ requires promoted type, not enum type, in %"); - return build_va_arg (loc, expr, type); + return build_va_arg (loc2, expr, type); } /* Return truthvalue of whether T1 is the same tree structure as T2. diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 2e93d1ade2b..ca604d26b4c 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,7 @@ +2015-12-04 Eric Botcazou + + * gcc.dg/sso-9.c: New test. + 2015-12-04 Jakub Jelinek PR target/68655 diff --git a/gcc/testsuite/gcc.dg/sso-9.c b/gcc/testsuite/gcc.dg/sso-9.c new file mode 100644 index 00000000000..6e767462e4d --- /dev/null +++ b/gcc/testsuite/gcc.dg/sso-9.c @@ -0,0 +1,27 @@ +/* Test support of scalar_storage_order attribute */ + +/* { dg-do compile } */ + +#include + +int x; + +#if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__ +struct __attribute__((scalar_storage_order("big-endian"))) Rec +{ + va_list v; +}; +#else +struct __attribute__((scalar_storage_order("little-endian"))) Rec +{ + va_list v; +}; +#endif + +void foo (int i, ...) +{ + struct Rec a; + va_start (a.v, i); + a.v = a.v, x = va_arg (a.v, int); /* { dg-error "array type|reverse storage order" } */ + va_end (a.v); +}