diff options
author | Eric Botcazou <ebotcazou@adacore.com> | 2013-08-13 10:26:40 +0000 |
---|---|---|
committer | Eric Botcazou <ebotcazou@gcc.gnu.org> | 2013-08-13 10:26:40 +0000 |
commit | 537e035c48955b3ea88dcb3a4b0ff03ef4bb2e31 (patch) | |
tree | fb3c96501d1d6d6055e09aec228353590a1c90e7 /gcc | |
parent | 3944d88d35e71f0aaf58c2c82bc7cf34414cb6ac (diff) | |
download | gcc-537e035c48955b3ea88dcb3a4b0ff03ef4bb2e31.zip gcc-537e035c48955b3ea88dcb3a4b0ff03ef4bb2e31.tar.gz gcc-537e035c48955b3ea88dcb3a4b0ff03ef4bb2e31.tar.bz2 |
utils2.c (build_atomic_load): Do a mere view-conversion to the original type before converting to the result type.
* gcc-interface/utils2.c (build_atomic_load): Do a mere view-conversion
to the original type before converting to the result type.
(build_atomic_store): First do a conversion to the original type before
view-converting to the effective type, but deal with a padded type
specially.
From-SVN: r201682
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ada/ChangeLog | 8 | ||||
-rw-r--r-- | gcc/ada/gcc-interface/utils2.c | 32 |
2 files changed, 31 insertions, 9 deletions
diff --git a/gcc/ada/ChangeLog b/gcc/ada/ChangeLog index fe062d8..e8d5389 100644 --- a/gcc/ada/ChangeLog +++ b/gcc/ada/ChangeLog @@ -1,3 +1,11 @@ +2013-08-13 Eric Botcazou <ebotcazou@adacore.com> + + * gcc-interface/utils2.c (build_atomic_load): Do a mere view-conversion + to the original type before converting to the result type. + (build_atomic_store): First do a conversion to the original type before + view-converting to the effective type, but deal with a padded type + specially. + 2013-08-08 Eric Botcazou <ebotcazou@adacore.com> * gcc-interface/Makefile.in (TOOLS_LIBS): Pick C object files from the diff --git a/gcc/ada/gcc-interface/utils2.c b/gcc/ada/gcc-interface/utils2.c index 7f7f6af..64f7564 100644 --- a/gcc/ada/gcc-interface/utils2.c +++ b/gcc/ada/gcc-interface/utils2.c @@ -648,11 +648,11 @@ build_atomic_load (tree src) (build_qualified_type (void_type_node, TYPE_QUAL_VOLATILE)); tree mem_model = build_int_cst (integer_type_node, MEMMODEL_SEQ_CST); tree orig_src = src; - tree type = TREE_TYPE (src); - tree t, val; + tree t, addr, val; unsigned int size; int fncode; + /* Remove conversions to get the address of the underlying object. */ src = remove_conversions (src, false); size = resolve_atomic_size (TREE_TYPE (src)); if (size == 0) @@ -661,10 +661,13 @@ build_atomic_load (tree src) fncode = (int) BUILT_IN_ATOMIC_LOAD_N + exact_log2 (size) + 1; t = builtin_decl_implicit ((enum built_in_function) fncode); - src = build_unary_op (ADDR_EXPR, ptr_type, src); - val = build_call_expr (t, 2, src, mem_model); + addr = build_unary_op (ADDR_EXPR, ptr_type, src); + val = build_call_expr (t, 2, addr, mem_model); - return unchecked_convert (type, val, true); + /* First reinterpret the loaded bits in the original type of the load, + then convert to the expected result type. */ + t = fold_build1 (VIEW_CONVERT_EXPR, TREE_TYPE (src), val); + return convert (TREE_TYPE (orig_src), t); } /* Build an atomic store from SRC to the underlying atomic object in DEST. */ @@ -677,10 +680,11 @@ build_atomic_store (tree dest, tree src) (build_qualified_type (void_type_node, TYPE_QUAL_VOLATILE)); tree mem_model = build_int_cst (integer_type_node, MEMMODEL_SEQ_CST); tree orig_dest = dest; - tree t, int_type; + tree t, int_type, addr; unsigned int size; int fncode; + /* Remove conversions to get the address of the underlying object. */ dest = remove_conversions (dest, false); size = resolve_atomic_size (TREE_TYPE (dest)); if (size == 0) @@ -690,10 +694,20 @@ build_atomic_store (tree dest, tree src) t = builtin_decl_implicit ((enum built_in_function) fncode); int_type = gnat_type_for_size (BITS_PER_UNIT * size, 1); - dest = build_unary_op (ADDR_EXPR, ptr_type, dest); - src = unchecked_convert (int_type, src, true); + /* First convert the bits to be stored to the original type of the store, + then reinterpret them in the effective type. But if the original type + is a padded type with the same size, convert to the inner type instead, + as we don't want to artificially introduce a CONSTRUCTOR here. */ + if (TYPE_IS_PADDING_P (TREE_TYPE (dest)) + && TYPE_SIZE (TREE_TYPE (dest)) + == TYPE_SIZE (TREE_TYPE (TYPE_FIELDS (TREE_TYPE (dest))))) + src = convert (TREE_TYPE (TYPE_FIELDS (TREE_TYPE (dest))), src); + else + src = convert (TREE_TYPE (dest), src); + src = fold_build1 (VIEW_CONVERT_EXPR, int_type, src); + addr = build_unary_op (ADDR_EXPR, ptr_type, dest); - return build_call_expr (t, 3, dest, src, mem_model); + return build_call_expr (t, 3, addr, src, mem_model); } /* Make a binary operation of kind OP_CODE. RESULT_TYPE is the type |