]> git.ipfire.org Git - thirdparty/gcc.git/commit
Introduce -finline-stringops
authorAlexandre Oliva <oliva@adacore.com>
Wed, 29 Nov 2023 07:00:24 +0000 (04:00 -0300)
committerAlexandre Oliva <oliva@gnu.org>
Wed, 29 Nov 2023 07:00:24 +0000 (04:00 -0300)
commit1ff6d9f7428b0668cd8ab0b3e3ab94f1d733124d
tree0c3efcba4d588c5014b1b25365e9021c97c4ee4b
parent25a51e98fdd504826a40775a5e5b9ffb336b5aa1
Introduce -finline-stringops

try_store_by_multiple_pieces was added not long ago, enabling
variable-sized memset to be expanded inline when the worst-case
in-range constant length would, using conditional blocks with powers
of two to cover all possibilities of length and alignment.

This patch introduces -finline-stringops[=fn] to request expansions to
start with a loop, so as to still take advantage of known alignment
even with long lengths, but without necessarily adding store blocks
for every power of two.

This makes it possible for the supported stringops (memset, memcpy,
memmove, memset) to be expanded, even if storing a single byte per
iteration.  Surely efficient implementations can run faster, with a
pre-loop to increase alignment, but that would likely be excessive for
inline expansions.

Still, in some cases, such as in freestanding environments, users
prefer to inline such stringops, especially those that the compiler
may introduce itself, even if the expansion is not as performant as a
highly optimized C library implementation could be, to avoid
depending on a C runtime library.

for  gcc/ChangeLog

* expr.cc (emit_block_move_hints): Take ctz of len.  Obey
-finline-stringops.  Use oriented or sized loop.
(emit_block_move): Take ctz of len, and pass it on.
(emit_block_move_via_sized_loop): New.
(emit_block_move_via_oriented_loop): New.
(emit_block_move_via_loop): Take incr.  Move an incr-sized
block per iteration.
(emit_block_cmp_via_cmpmem): Take ctz of len.  Obey
-finline-stringops.
(emit_block_cmp_via_loop): New.
* expr.h (emit_block_move): Add ctz of len defaulting to zero.
(emit_block_move_hints): Likewise.
(emit_block_cmp_hints): Likewise.
* builtins.cc (expand_builtin_memory_copy_args): Pass ctz of
len to emit_block_move_hints.
(try_store_by_multiple_pieces): Support starting with a loop.
(expand_builtin_memcmp): Pass ctz of len to
emit_block_cmp_hints.
(expand_builtin): Allow inline expansion of memset, memcpy,
memmove and memcmp if requested.
* common.opt (finline-stringops): New.
(ilsop_fn): New enum.
* flag-types.h (enum ilsop_fn): New.
* doc/invoke.texi (-finline-stringops): Add.

for  gcc/testsuite/ChangeLog

* gcc.dg/torture/inline-mem-cmp-1.c: New.
* gcc.dg/torture/inline-mem-cpy-1.c: New.
* gcc.dg/torture/inline-mem-cpy-cmp-1.c: New.
* gcc.dg/torture/inline-mem-move-1.c: New.
* gcc.dg/torture/inline-mem-set-1.c: New.
gcc/builtins.cc
gcc/common.opt
gcc/doc/invoke.texi
gcc/expr.cc
gcc/expr.h
gcc/flag-types.h
gcc/testsuite/gcc.dg/torture/inline-mem-cmp-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/torture/inline-mem-cpy-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/torture/inline-mem-cpy-cmp-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/torture/inline-mem-move-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/torture/inline-mem-set-1.c [new file with mode: 0644]