From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-1.web.codeaurora.org [10.30.226.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id AD80A3FADEE for ; Fri, 27 Mar 2026 17:31:58 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1774632718; cv=none; b=QP4O1XSCEjhiGYispd+4WSGvKkg2AAxhGPVPWZLfqYggi8CLUmqo0sKhehMqKSUgOth5n+x1FFd5fvsxACdC9vPPXIG6t9oF9QtgcNgbz9IscVUsq3OdpQKv9atotiZFaNU0xdG148fpgUj7ry/VPopdtJTZEz3CWA4Yosx1AVc= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1774632718; c=relaxed/simple; bh=sYFNi14twGKiJ4CGWabH6I+W5pVnnEKUUvi2J5g6NtY=; h=Date:To:From:Subject:Message-Id; b=q/Sg+Hv1XUPBLkJ77g3f1NwXHBy1WtsDvrwwqhR+rXADNpfHq0YHxrhA3wjBqLI93BYkxzJ2HYGWaj2A3wVO5n52NoqeuSgC9RPcg2cGwncCkDaGO2izhIgkSuC7tjwQa3VUEkIbP5v1tPL4AjMMKUQx5FUPK52YZvZJFaJFCEI= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=linux-foundation.org header.i=@linux-foundation.org header.b=pg9CjG8r; arc=none smtp.client-ip=10.30.226.201 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=linux-foundation.org header.i=@linux-foundation.org header.b="pg9CjG8r" Received: by smtp.kernel.org (Postfix) with ESMTPSA id 24296C19423; Fri, 27 Mar 2026 17:31:58 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=linux-foundation.org; s=korg; t=1774632718; bh=sYFNi14twGKiJ4CGWabH6I+W5pVnnEKUUvi2J5g6NtY=; h=Date:To:From:Subject:From; b=pg9CjG8rswFD4nbOUFl6VcS/spQW8eCMBrfwAkenLA6gi6vn4AnGyT6N497Gu1Ekq PYSDKo4Ct23KEgFeNTFfrafelazMSkjc4++M08D+zq95hRM8JEz0XdXD3FejAk7wio wGjJvDJmn6Qx1D3GNvlpsHNpGFGJtSDBoJpdRqoc= Date: Fri, 27 Mar 2026 10:31:57 -0700 To: mm-commits@vger.kernel.org,hch@lst.de,akpm@linux-foundation.org From: Andrew Morton Subject: [to-be-updated] arm-move-the-xor-code-to-lib-raid.patch removed from -mm tree Message-Id: <20260327173158.24296C19423@smtp.kernel.org> Precedence: bulk X-Mailing-List: mm-commits@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: The quilt patch titled Subject: arm: move the XOR code to lib/raid/ has been removed from the -mm tree. Its filename was arm-move-the-xor-code-to-lib-raid.patch This patch was dropped because an updated version will be issued ------------------------------------------------------ From: Christoph Hellwig Subject: arm: move the XOR code to lib/raid/ Date: Tue, 24 Mar 2026 07:21:47 +0100 Move the optimized XOR into lib/raid and include it it in the main xor.ko instead of building a separate module for it. Link: https://lkml.kernel.org/r/20260324062211.3216301-12-hch@lst.de Signed-off-by: Christoph Hellwig Cc: Albert Ou Cc: Alexander Gordeev Cc: Alexandre Ghiti Cc: Andreas Larsson Cc: Anton Ivanov Cc: Ard Biesheuvel Cc: Arnd Bergmann Cc: "Borislav Petkov (AMD)" Cc: Catalin Marinas Cc: Chris Mason Cc: Christian Borntraeger Cc: Dan Williams Cc: David S. Miller Cc: David Sterba Cc: Heiko Carstens Cc: Herbert Xu Cc: "H. Peter Anvin" Cc: Huacai Chen Cc: Ingo Molnar Cc: Jason A. Donenfeld Cc: Johannes Berg Cc: Li Nan Cc: Madhavan Srinivasan Cc: Magnus Lindholm Cc: Matt Turner Cc: Michael Ellerman Cc: Nicholas Piggin Cc: Palmer Dabbelt Cc: Richard Henderson Cc: Richard Weinberger Cc: Russell King Cc: Song Liu Cc: Sven Schnelle Cc: Ted Ts'o Cc: Vasily Gorbik Cc: WANG Xuerui Cc: Will Deacon Signed-off-by: Andrew Morton --- arch/arm/include/asm/xor.h | 190 ----------------------------- arch/arm/lib/Makefile | 5 arch/arm/lib/xor-neon.c | 39 ----- lib/raid/xor/Makefile | 8 + lib/raid/xor/arm/xor-neon-glue.c | 58 ++++++++ lib/raid/xor/arm/xor-neon.c | 31 ++++ lib/raid/xor/arm/xor.c | 136 ++++++++++++++++++++ 7 files changed, 235 insertions(+), 232 deletions(-) --- a/arch/arm/include/asm/xor.h~arm-move-the-xor-code-to-lib-raid +++ a/arch/arm/include/asm/xor.h @@ -1,198 +1,12 @@ /* SPDX-License-Identifier: GPL-2.0-only */ /* - * arch/arm/include/asm/xor.h - * * Copyright (C) 2001 Russell King */ #include -#include #include -#define __XOR(a1, a2) a1 ^= a2 - -#define GET_BLOCK_2(dst) \ - __asm__("ldmia %0, {%1, %2}" \ - : "=r" (dst), "=r" (a1), "=r" (a2) \ - : "0" (dst)) - -#define GET_BLOCK_4(dst) \ - __asm__("ldmia %0, {%1, %2, %3, %4}" \ - : "=r" (dst), "=r" (a1), "=r" (a2), "=r" (a3), "=r" (a4) \ - : "0" (dst)) - -#define XOR_BLOCK_2(src) \ - __asm__("ldmia %0!, {%1, %2}" \ - : "=r" (src), "=r" (b1), "=r" (b2) \ - : "0" (src)); \ - __XOR(a1, b1); __XOR(a2, b2); - -#define XOR_BLOCK_4(src) \ - __asm__("ldmia %0!, {%1, %2, %3, %4}" \ - : "=r" (src), "=r" (b1), "=r" (b2), "=r" (b3), "=r" (b4) \ - : "0" (src)); \ - __XOR(a1, b1); __XOR(a2, b2); __XOR(a3, b3); __XOR(a4, b4) - -#define PUT_BLOCK_2(dst) \ - __asm__ __volatile__("stmia %0!, {%2, %3}" \ - : "=r" (dst) \ - : "0" (dst), "r" (a1), "r" (a2)) - -#define PUT_BLOCK_4(dst) \ - __asm__ __volatile__("stmia %0!, {%2, %3, %4, %5}" \ - : "=r" (dst) \ - : "0" (dst), "r" (a1), "r" (a2), "r" (a3), "r" (a4)) - -static void -xor_arm4regs_2(unsigned long bytes, unsigned long * __restrict p1, - const unsigned long * __restrict p2) -{ - unsigned int lines = bytes / sizeof(unsigned long) / 4; - register unsigned int a1 __asm__("r4"); - register unsigned int a2 __asm__("r5"); - register unsigned int a3 __asm__("r6"); - register unsigned int a4 __asm__("r10"); - register unsigned int b1 __asm__("r8"); - register unsigned int b2 __asm__("r9"); - register unsigned int b3 __asm__("ip"); - register unsigned int b4 __asm__("lr"); - - do { - GET_BLOCK_4(p1); - XOR_BLOCK_4(p2); - PUT_BLOCK_4(p1); - } while (--lines); -} - -static void -xor_arm4regs_3(unsigned long bytes, unsigned long * __restrict p1, - const unsigned long * __restrict p2, - const unsigned long * __restrict p3) -{ - unsigned int lines = bytes / sizeof(unsigned long) / 4; - register unsigned int a1 __asm__("r4"); - register unsigned int a2 __asm__("r5"); - register unsigned int a3 __asm__("r6"); - register unsigned int a4 __asm__("r10"); - register unsigned int b1 __asm__("r8"); - register unsigned int b2 __asm__("r9"); - register unsigned int b3 __asm__("ip"); - register unsigned int b4 __asm__("lr"); - - do { - GET_BLOCK_4(p1); - XOR_BLOCK_4(p2); - XOR_BLOCK_4(p3); - PUT_BLOCK_4(p1); - } while (--lines); -} - -static void -xor_arm4regs_4(unsigned long bytes, unsigned long * __restrict p1, - const unsigned long * __restrict p2, - const unsigned long * __restrict p3, - const unsigned long * __restrict p4) -{ - unsigned int lines = bytes / sizeof(unsigned long) / 2; - register unsigned int a1 __asm__("r8"); - register unsigned int a2 __asm__("r9"); - register unsigned int b1 __asm__("ip"); - register unsigned int b2 __asm__("lr"); - - do { - GET_BLOCK_2(p1); - XOR_BLOCK_2(p2); - XOR_BLOCK_2(p3); - XOR_BLOCK_2(p4); - PUT_BLOCK_2(p1); - } while (--lines); -} - -static void -xor_arm4regs_5(unsigned long bytes, unsigned long * __restrict p1, - const unsigned long * __restrict p2, - const unsigned long * __restrict p3, - const unsigned long * __restrict p4, - const unsigned long * __restrict p5) -{ - unsigned int lines = bytes / sizeof(unsigned long) / 2; - register unsigned int a1 __asm__("r8"); - register unsigned int a2 __asm__("r9"); - register unsigned int b1 __asm__("ip"); - register unsigned int b2 __asm__("lr"); - - do { - GET_BLOCK_2(p1); - XOR_BLOCK_2(p2); - XOR_BLOCK_2(p3); - XOR_BLOCK_2(p4); - XOR_BLOCK_2(p5); - PUT_BLOCK_2(p1); - } while (--lines); -} - -static struct xor_block_template xor_block_arm4regs = { - .name = "arm4regs", - .do_2 = xor_arm4regs_2, - .do_3 = xor_arm4regs_3, - .do_4 = xor_arm4regs_4, - .do_5 = xor_arm4regs_5, -}; - -#ifdef CONFIG_KERNEL_MODE_NEON - -extern struct xor_block_template const xor_block_neon_inner; - -static void -xor_neon_2(unsigned long bytes, unsigned long * __restrict p1, - const unsigned long * __restrict p2) -{ - kernel_neon_begin(); - xor_block_neon_inner.do_2(bytes, p1, p2); - kernel_neon_end(); -} - -static void -xor_neon_3(unsigned long bytes, unsigned long * __restrict p1, - const unsigned long * __restrict p2, - const unsigned long * __restrict p3) -{ - kernel_neon_begin(); - xor_block_neon_inner.do_3(bytes, p1, p2, p3); - kernel_neon_end(); -} - -static void -xor_neon_4(unsigned long bytes, unsigned long * __restrict p1, - const unsigned long * __restrict p2, - const unsigned long * __restrict p3, - const unsigned long * __restrict p4) -{ - kernel_neon_begin(); - xor_block_neon_inner.do_4(bytes, p1, p2, p3, p4); - kernel_neon_end(); -} - -static void -xor_neon_5(unsigned long bytes, unsigned long * __restrict p1, - const unsigned long * __restrict p2, - const unsigned long * __restrict p3, - const unsigned long * __restrict p4, - const unsigned long * __restrict p5) -{ - kernel_neon_begin(); - xor_block_neon_inner.do_5(bytes, p1, p2, p3, p4, p5); - kernel_neon_end(); -} - -static struct xor_block_template xor_block_neon = { - .name = "neon", - .do_2 = xor_neon_2, - .do_3 = xor_neon_3, - .do_4 = xor_neon_4, - .do_5 = xor_neon_5 -}; - -#endif /* CONFIG_KERNEL_MODE_NEON */ +extern struct xor_block_template xor_block_arm4regs; +extern struct xor_block_template xor_block_neon; #define arch_xor_init arch_xor_init static __always_inline void __init arch_xor_init(void) --- a/arch/arm/lib/Makefile~arm-move-the-xor-code-to-lib-raid +++ a/arch/arm/lib/Makefile @@ -39,9 +39,4 @@ endif $(obj)/csumpartialcopy.o: $(obj)/csumpartialcopygeneric.S $(obj)/csumpartialcopyuser.o: $(obj)/csumpartialcopygeneric.S -ifeq ($(CONFIG_KERNEL_MODE_NEON),y) - CFLAGS_xor-neon.o += $(CC_FLAGS_FPU) - obj-$(CONFIG_XOR_BLOCKS) += xor-neon.o -endif - obj-$(CONFIG_FUNCTION_ERROR_INJECTION) += error-inject.o diff --git a/arch/arm/lib/xor-neon.c a/arch/arm/lib/xor-neon.c deleted file mode 100644 --- a/arch/arm/lib/xor-neon.c +++ /dev/null @@ -1,39 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0-only -/* - * linux/arch/arm/lib/xor-neon.c - * - * Copyright (C) 2013 Linaro Ltd - */ - -#include -#include -#include - -MODULE_DESCRIPTION("NEON accelerated XOR implementation"); -MODULE_LICENSE("GPL"); - -#ifndef __ARM_NEON__ -#error You should compile this file with '-march=armv7-a -mfloat-abi=softfp -mfpu=neon' -#endif - -/* - * Pull in the reference implementations while instructing GCC (through - * -ftree-vectorize) to attempt to exploit implicit parallelism and emit - * NEON instructions. Clang does this by default at O2 so no pragma is - * needed. - */ -#ifdef CONFIG_CC_IS_GCC -#pragma GCC optimize "tree-vectorize" -#endif - -#define NO_TEMPLATE -#include "../../../lib/raid/xor/xor-8regs.c" - -struct xor_block_template const xor_block_neon_inner = { - .name = "__inner_neon__", - .do_2 = xor_8regs_2, - .do_3 = xor_8regs_3, - .do_4 = xor_8regs_4, - .do_5 = xor_8regs_5, -}; -EXPORT_SYMBOL(xor_block_neon_inner); diff --git a/lib/raid/xor/arm/xor.c a/lib/raid/xor/arm/xor.c new file mode 100644 --- /dev/null +++ a/lib/raid/xor/arm/xor.c @@ -0,0 +1,136 @@ +// SPDX-License-Identifier: GPL-2.0-only +/* + * Copyright (C) 2001 Russell King + */ +#include +#include + +#define __XOR(a1, a2) a1 ^= a2 + +#define GET_BLOCK_2(dst) \ + __asm__("ldmia %0, {%1, %2}" \ + : "=r" (dst), "=r" (a1), "=r" (a2) \ + : "0" (dst)) + +#define GET_BLOCK_4(dst) \ + __asm__("ldmia %0, {%1, %2, %3, %4}" \ + : "=r" (dst), "=r" (a1), "=r" (a2), "=r" (a3), "=r" (a4) \ + : "0" (dst)) + +#define XOR_BLOCK_2(src) \ + __asm__("ldmia %0!, {%1, %2}" \ + : "=r" (src), "=r" (b1), "=r" (b2) \ + : "0" (src)); \ + __XOR(a1, b1); __XOR(a2, b2); + +#define XOR_BLOCK_4(src) \ + __asm__("ldmia %0!, {%1, %2, %3, %4}" \ + : "=r" (src), "=r" (b1), "=r" (b2), "=r" (b3), "=r" (b4) \ + : "0" (src)); \ + __XOR(a1, b1); __XOR(a2, b2); __XOR(a3, b3); __XOR(a4, b4) + +#define PUT_BLOCK_2(dst) \ + __asm__ __volatile__("stmia %0!, {%2, %3}" \ + : "=r" (dst) \ + : "0" (dst), "r" (a1), "r" (a2)) + +#define PUT_BLOCK_4(dst) \ + __asm__ __volatile__("stmia %0!, {%2, %3, %4, %5}" \ + : "=r" (dst) \ + : "0" (dst), "r" (a1), "r" (a2), "r" (a3), "r" (a4)) + +static void +xor_arm4regs_2(unsigned long bytes, unsigned long * __restrict p1, + const unsigned long * __restrict p2) +{ + unsigned int lines = bytes / sizeof(unsigned long) / 4; + register unsigned int a1 __asm__("r4"); + register unsigned int a2 __asm__("r5"); + register unsigned int a3 __asm__("r6"); + register unsigned int a4 __asm__("r10"); + register unsigned int b1 __asm__("r8"); + register unsigned int b2 __asm__("r9"); + register unsigned int b3 __asm__("ip"); + register unsigned int b4 __asm__("lr"); + + do { + GET_BLOCK_4(p1); + XOR_BLOCK_4(p2); + PUT_BLOCK_4(p1); + } while (--lines); +} + +static void +xor_arm4regs_3(unsigned long bytes, unsigned long * __restrict p1, + const unsigned long * __restrict p2, + const unsigned long * __restrict p3) +{ + unsigned int lines = bytes / sizeof(unsigned long) / 4; + register unsigned int a1 __asm__("r4"); + register unsigned int a2 __asm__("r5"); + register unsigned int a3 __asm__("r6"); + register unsigned int a4 __asm__("r10"); + register unsigned int b1 __asm__("r8"); + register unsigned int b2 __asm__("r9"); + register unsigned int b3 __asm__("ip"); + register unsigned int b4 __asm__("lr"); + + do { + GET_BLOCK_4(p1); + XOR_BLOCK_4(p2); + XOR_BLOCK_4(p3); + PUT_BLOCK_4(p1); + } while (--lines); +} + +static void +xor_arm4regs_4(unsigned long bytes, unsigned long * __restrict p1, + const unsigned long * __restrict p2, + const unsigned long * __restrict p3, + const unsigned long * __restrict p4) +{ + unsigned int lines = bytes / sizeof(unsigned long) / 2; + register unsigned int a1 __asm__("r8"); + register unsigned int a2 __asm__("r9"); + register unsigned int b1 __asm__("ip"); + register unsigned int b2 __asm__("lr"); + + do { + GET_BLOCK_2(p1); + XOR_BLOCK_2(p2); + XOR_BLOCK_2(p3); + XOR_BLOCK_2(p4); + PUT_BLOCK_2(p1); + } while (--lines); +} + +static void +xor_arm4regs_5(unsigned long bytes, unsigned long * __restrict p1, + const unsigned long * __restrict p2, + const unsigned long * __restrict p3, + const unsigned long * __restrict p4, + const unsigned long * __restrict p5) +{ + unsigned int lines = bytes / sizeof(unsigned long) / 2; + register unsigned int a1 __asm__("r8"); + register unsigned int a2 __asm__("r9"); + register unsigned int b1 __asm__("ip"); + register unsigned int b2 __asm__("lr"); + + do { + GET_BLOCK_2(p1); + XOR_BLOCK_2(p2); + XOR_BLOCK_2(p3); + XOR_BLOCK_2(p4); + XOR_BLOCK_2(p5); + PUT_BLOCK_2(p1); + } while (--lines); +} + +struct xor_block_template xor_block_arm4regs = { + .name = "arm4regs", + .do_2 = xor_arm4regs_2, + .do_3 = xor_arm4regs_3, + .do_4 = xor_arm4regs_4, + .do_5 = xor_arm4regs_5, +}; diff --git a/lib/raid/xor/arm/xor-neon.c a/lib/raid/xor/arm/xor-neon.c new file mode 100664 --- /dev/null +++ a/lib/raid/xor/arm/xor-neon.c @@ -0,0 +1,31 @@ +// SPDX-License-Identifier: GPL-2.0-only +/* + * Copyright (C) 2013 Linaro Ltd + */ + +#include + +#ifndef __ARM_NEON__ +#error You should compile this file with '-march=armv7-a -mfloat-abi=softfp -mfpu=neon' +#endif + +/* + * Pull in the reference implementations while instructing GCC (through + * -ftree-vectorize) to attempt to exploit implicit parallelism and emit + * NEON instructions. Clang does this by default at O2 so no pragma is + * needed. + */ +#ifdef CONFIG_CC_IS_GCC +#pragma GCC optimize "tree-vectorize" +#endif + +#define NO_TEMPLATE +#include "../xor-8regs.c" + +struct xor_block_template const xor_block_neon_inner = { + .name = "__inner_neon__", + .do_2 = xor_8regs_2, + .do_3 = xor_8regs_3, + .do_4 = xor_8regs_4, + .do_5 = xor_8regs_5, +}; diff --git a/lib/raid/xor/arm/xor-neon-glue.c a/lib/raid/xor/arm/xor-neon-glue.c new file mode 100644 --- /dev/null +++ a/lib/raid/xor/arm/xor-neon-glue.c @@ -0,0 +1,58 @@ +// SPDX-License-Identifier: GPL-2.0-only +/* + * Copyright (C) 2001 Russell King + */ +#include +#include + +extern struct xor_block_template const xor_block_neon_inner; + +static void +xor_neon_2(unsigned long bytes, unsigned long * __restrict p1, + const unsigned long * __restrict p2) +{ + kernel_neon_begin(); + xor_block_neon_inner.do_2(bytes, p1, p2); + kernel_neon_end(); +} + +static void +xor_neon_3(unsigned long bytes, unsigned long * __restrict p1, + const unsigned long * __restrict p2, + const unsigned long * __restrict p3) +{ + kernel_neon_begin(); + xor_block_neon_inner.do_3(bytes, p1, p2, p3); + kernel_neon_end(); +} + +static void +xor_neon_4(unsigned long bytes, unsigned long * __restrict p1, + const unsigned long * __restrict p2, + const unsigned long * __restrict p3, + const unsigned long * __restrict p4) +{ + kernel_neon_begin(); + xor_block_neon_inner.do_4(bytes, p1, p2, p3, p4); + kernel_neon_end(); +} + +static void +xor_neon_5(unsigned long bytes, unsigned long * __restrict p1, + const unsigned long * __restrict p2, + const unsigned long * __restrict p3, + const unsigned long * __restrict p4, + const unsigned long * __restrict p5) +{ + kernel_neon_begin(); + xor_block_neon_inner.do_5(bytes, p1, p2, p3, p4, p5); + kernel_neon_end(); +} + +struct xor_block_template xor_block_neon = { + .name = "neon", + .do_2 = xor_neon_2, + .do_3 = xor_neon_3, + .do_4 = xor_neon_4, + .do_5 = xor_neon_5 +}; --- a/lib/raid/xor/Makefile~arm-move-the-xor-code-to-lib-raid +++ a/lib/raid/xor/Makefile @@ -9,3 +9,11 @@ xor-y += xor-8regs-prefetch.o xor-y += xor-32regs-prefetch.o xor-$(CONFIG_ALPHA) += alpha/xor.o +xor-$(CONFIG_ARM) += arm/xor.o +ifeq ($(CONFIG_ARM),y) +xor-$(CONFIG_KERNEL_MODE_NEON) += arm/xor-neon.o arm/xor-neon-glue.o +endif + + +CFLAGS_arm/xor-neon.o += $(CC_FLAGS_FPU) +CFLAGS_REMOVE_arm/xor-neon.o += $(CC_FLAGS_NO_FPU) _ Patches currently in -mm which might be from hch@lst.de are arm64-move-the-xor-code-to-lib-raid.patch loongarch-move-the-xor-code-to-lib-raid.patch powerpc-move-the-xor-code-to-lib-raid.patch riscv-move-the-xor-code-to-lib-raid.patch sparc-move-the-xor-code-to-lib-raid.patch s390-move-the-xor-code-to-lib-raid.patch x86-move-the-xor-code-to-lib-raid.patch xor-avoid-indirect-calls-for-arm64-optimized-ops.patch xor-make-xorko-self-contained-in-lib-raid.patch xor-add-a-better-public-api.patch async_xor-use-xor_gen.patch btrfs-use-xor_gen.patch xor-pass-the-entire-operation-to-the-low-level-ops.patch xor-use-static_call-for-xor_gen.patch xor-add-a-kunit-test-case.patch