[s390x] Use XOR-in-place to zero small fixed-length blocks

The XOR instruction has a storage-and-storage format "xc" that can be
used to zero small blocks of memory without needing to set up the four
registers required for "mvcle".

Signed-off-by: Michael Brown <mcb30@ipxe.org>
This commit is contained in:
Michael Brown
2026-06-16 14:40:36 +01:00
parent 1a0ebb9ba5
commit 73d437859d
+11 -3
View File
@@ -27,15 +27,23 @@ memset ( void *dest, int character, size_t len ) {
struct s390x_pointer_pair dpair = { dest, len };
char ( * dmem ) [ len ] = dest;
if ( __builtin_constant_p ( character ) ) {
/* Constant fill character: use an immediate */
if ( __builtin_constant_p ( len ) && ( len == 0 ) ) {
/* Constant zero length: do nothing */
} else if ( __builtin_constant_p ( character ) && ( character == 0 ) &&
__builtin_constant_p ( len ) && ( len <= 256 ) ) {
/* Constant small length, zeroing: use XOR-in-place */
__asm__ ( "xc %O0(%1, %R0), %0"
: "=Q" ( *dmem )
: "i" ( len ) );
} else if ( __builtin_constant_p ( character ) ) {
/* Constant fill character: use "mvcle" with an immediate */
__asm__ ( "\n1:\n\t"
"mvcle %0, %2, %3\n\t"
"jo 1b\n\t"
: "+r" ( dpair ), "=m" ( *dmem )
: "r" ( spair ), "i" ( character ) );
} else {
/* Variable fill character: use a register */
/* Variable fill character: use "mvcle" with a register */
__asm__ ( "\n1:\n\t"
"mvcle %0, %2, 0(%3)\n\t"
"jo 1b\n\t"