linux-crypto.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] crypto: xor - move __crypto_xor into lib/
@ 2022-07-09 21:54 Eric Biggers
  2022-07-11 15:02 ` Jason A. Donenfeld
  2022-07-15  8:09 ` Herbert Xu
  0 siblings, 2 replies; 3+ messages in thread
From: Eric Biggers @ 2022-07-09 21:54 UTC (permalink / raw)
  To: linux-crypto; +Cc: linux-kernel, Jason A . Donenfeld 

From: Eric Biggers <ebiggers@google.com>

CRYPTO_LIB_CHACHA depends on CRYPTO for __crypto_xor, defined in
crypto/algapi.c.  This is a layering violation because the dependencies
should only go in the other direction (crypto/ => lib/crypto/).  Also
the correct dependency would be CRYPTO_ALGAPI, not CRYPTO.  Fix this by
moving __crypto_xor into lib/xor.c, alongside lib/memneq.c where
__crypto_memneq was recently moved.

Note that CRYPTO_LIB_CHACHA_GENERIC selected XOR_BLOCKS, which is
unrelated and unnecessary.  It was perhaps thought that XOR_BLOCKS was
needed for __crypto_xor, but that's not the case.

Signed-off-by: Eric Biggers <ebiggers@google.com>
---
 crypto/Kconfig     |  1 +
 crypto/algapi.c    | 71 --------------------------------------
 lib/Kconfig        |  3 ++
 lib/Makefile       |  1 +
 lib/crypto/Kconfig |  3 +-
 lib/xor.c          | 85 ++++++++++++++++++++++++++++++++++++++++++++++
 6 files changed, 91 insertions(+), 73 deletions(-)
 create mode 100644 lib/xor.c

diff --git a/crypto/Kconfig b/crypto/Kconfig
index 59489a300cd100..9145fdfa8a5bbd 100644
--- a/crypto/Kconfig
+++ b/crypto/Kconfig
@@ -40,6 +40,7 @@ config CRYPTO_ALGAPI
 	  This option provides the API for cryptographic algorithms.
 
 config CRYPTO_ALGAPI2
+	select LIB_XOR
 	tristate
 
 config CRYPTO_AEAD
diff --git a/crypto/algapi.c b/crypto/algapi.c
index d1c99288af3e0d..5c69ff8e8fa5c1 100644
--- a/crypto/algapi.c
+++ b/crypto/algapi.c
@@ -997,77 +997,6 @@ void crypto_inc(u8 *a, unsigned int size)
 }
 EXPORT_SYMBOL_GPL(crypto_inc);
 
-void __crypto_xor(u8 *dst, const u8 *src1, const u8 *src2, unsigned int len)
-{
-	int relalign = 0;
-
-	if (!IS_ENABLED(CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS)) {
-		int size = sizeof(unsigned long);
-		int d = (((unsigned long)dst ^ (unsigned long)src1) |
-			 ((unsigned long)dst ^ (unsigned long)src2)) &
-			(size - 1);
-
-		relalign = d ? 1 << __ffs(d) : size;
-
-		/*
-		 * If we care about alignment, process as many bytes as
-		 * needed to advance dst and src to values whose alignments
-		 * equal their relative alignment. This will allow us to
-		 * process the remainder of the input using optimal strides.
-		 */
-		while (((unsigned long)dst & (relalign - 1)) && len > 0) {
-			*dst++ = *src1++ ^ *src2++;
-			len--;
-		}
-	}
-
-	while (IS_ENABLED(CONFIG_64BIT) && len >= 8 && !(relalign & 7)) {
-		if (IS_ENABLED(CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS)) {
-			u64 l = get_unaligned((u64 *)src1) ^
-				get_unaligned((u64 *)src2);
-			put_unaligned(l, (u64 *)dst);
-		} else {
-			*(u64 *)dst = *(u64 *)src1 ^ *(u64 *)src2;
-		}
-		dst += 8;
-		src1 += 8;
-		src2 += 8;
-		len -= 8;
-	}
-
-	while (len >= 4 && !(relalign & 3)) {
-		if (IS_ENABLED(CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS)) {
-			u32 l = get_unaligned((u32 *)src1) ^
-				get_unaligned((u32 *)src2);
-			put_unaligned(l, (u32 *)dst);
-		} else {
-			*(u32 *)dst = *(u32 *)src1 ^ *(u32 *)src2;
-		}
-		dst += 4;
-		src1 += 4;
-		src2 += 4;
-		len -= 4;
-	}
-
-	while (len >= 2 && !(relalign & 1)) {
-		if (IS_ENABLED(CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS)) {
-			u16 l = get_unaligned((u16 *)src1) ^
-				get_unaligned((u16 *)src2);
-			put_unaligned(l, (u16 *)dst);
-		} else {
-			*(u16 *)dst = *(u16 *)src1 ^ *(u16 *)src2;
-		}
-		dst += 2;
-		src1 += 2;
-		src2 += 2;
-		len -= 2;
-	}
-
-	while (len--)
-		*dst++ = *src1++ ^ *src2++;
-}
-EXPORT_SYMBOL_GPL(__crypto_xor);
-
 unsigned int crypto_alg_extsize(struct crypto_alg *alg)
 {
 	return alg->cra_ctxsize +
diff --git a/lib/Kconfig b/lib/Kconfig
index eaaad4d85bf24b..4d2b09487442ea 100644
--- a/lib/Kconfig
+++ b/lib/Kconfig
@@ -123,6 +123,9 @@ source "lib/crypto/Kconfig"
 config LIB_MEMNEQ
 	bool
 
+config LIB_XOR
+	bool
+
 config CRC_CCITT
 	tristate "CRC-CCITT functions"
 	help
diff --git a/lib/Makefile b/lib/Makefile
index f99bf61f8bbc67..ceeb3f913f1b57 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -252,6 +252,7 @@ obj-$(CONFIG_SIGNATURE) += digsig.o
 
 lib-$(CONFIG_CLZ_TAB) += clz_tab.o
 lib-$(CONFIG_LIB_MEMNEQ) += memneq.o
+lib-$(CONFIG_LIB_XOR) += xor.o
 
 obj-$(CONFIG_GENERIC_STRNCPY_FROM_USER) += strncpy_from_user.o
 obj-$(CONFIG_GENERIC_STRNLEN_USER) += strnlen_user.o
diff --git a/lib/crypto/Kconfig b/lib/crypto/Kconfig
index 2082af43d51fbe..8432e0e2a9ee0d 100644
--- a/lib/crypto/Kconfig
+++ b/lib/crypto/Kconfig
@@ -33,7 +33,7 @@ config CRYPTO_ARCH_HAVE_LIB_CHACHA
 
 config CRYPTO_LIB_CHACHA_GENERIC
 	tristate
-	select XOR_BLOCKS
+	select LIB_XOR
 	help
 	  This symbol can be depended upon by arch implementations of the
 	  ChaCha library interface that require the generic code as a
@@ -43,7 +43,6 @@ config CRYPTO_LIB_CHACHA_GENERIC
 
 config CRYPTO_LIB_CHACHA
 	tristate "ChaCha library interface"
-	depends on CRYPTO
 	depends on CRYPTO_ARCH_HAVE_LIB_CHACHA || !CRYPTO_ARCH_HAVE_LIB_CHACHA
 	select CRYPTO_LIB_CHACHA_GENERIC if CRYPTO_ARCH_HAVE_LIB_CHACHA=n
 	help
diff --git a/lib/xor.c b/lib/xor.c
new file mode 100644
index 00000000000000..5f8f7765a48d5f
--- /dev/null
+++ b/lib/xor.c
@@ -0,0 +1,85 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+/*
+ * The __crypto_xor library function
+ *
+ * Copyright (c) 2006 Herbert Xu <herbert@gondor.apana.org.au>
+ */
+
+#include <crypto/algapi.h>
+#include <asm/unaligned.h>
+
+/*
+ * XOR @len bytes from @src1 and @src2 together, writing the result to @dst
+ * (which may alias one of the sources).  Don't call this directly; call
+ * crypto_xor() or crypto_xor_cpy() instead.
+ */
+void __crypto_xor(u8 *dst, const u8 *src1, const u8 *src2, unsigned int len)
+{
+	int relalign = 0;
+
+	if (!IS_ENABLED(CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS)) {
+		int size = sizeof(unsigned long);
+		int d = (((unsigned long)dst ^ (unsigned long)src1) |
+			 ((unsigned long)dst ^ (unsigned long)src2)) &
+			(size - 1);
+
+		relalign = d ? 1 << __ffs(d) : size;
+
+		/*
+		 * If we care about alignment, process as many bytes as
+		 * needed to advance dst and src to values whose alignments
+		 * equal their relative alignment. This will allow us to
+		 * process the remainder of the input using optimal strides.
+		 */
+		while (((unsigned long)dst & (relalign - 1)) && len > 0) {
+			*dst++ = *src1++ ^ *src2++;
+			len--;
+		}
+	}
+
+	while (IS_ENABLED(CONFIG_64BIT) && len >= 8 && !(relalign & 7)) {
+		if (IS_ENABLED(CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS)) {
+			u64 l = get_unaligned((u64 *)src1) ^
+				get_unaligned((u64 *)src2);
+			put_unaligned(l, (u64 *)dst);
+		} else {
+			*(u64 *)dst = *(u64 *)src1 ^ *(u64 *)src2;
+		}
+		dst += 8;
+		src1 += 8;
+		src2 += 8;
+		len -= 8;
+	}
+
+	while (len >= 4 && !(relalign & 3)) {
+		if (IS_ENABLED(CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS)) {
+			u32 l = get_unaligned((u32 *)src1) ^
+				get_unaligned((u32 *)src2);
+			put_unaligned(l, (u32 *)dst);
+		} else {
+			*(u32 *)dst = *(u32 *)src1 ^ *(u32 *)src2;
+		}
+		dst += 4;
+		src1 += 4;
+		src2 += 4;
+		len -= 4;
+	}
+
+	while (len >= 2 && !(relalign & 1)) {
+		if (IS_ENABLED(CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS)) {
+			u16 l = get_unaligned((u16 *)src1) ^
+				get_unaligned((u16 *)src2);
+			put_unaligned(l, (u16 *)dst);
+		} else {
+			*(u16 *)dst = *(u16 *)src1 ^ *(u16 *)src2;
+		}
+		dst += 2;
+		src1 += 2;
+		src2 += 2;
+		len -= 2;
+	}
+
+	while (len--)
+		*dst++ = *src1++ ^ *src2++;
+}
+EXPORT_SYMBOL_GPL(__crypto_xor);

base-commit: 79e6e2f3f3ff345947075341781e900e4f70db81
-- 
2.37.0


^ permalink raw reply related	[flat|nested] 3+ messages in thread

* Re: [PATCH] crypto: xor - move __crypto_xor into lib/
  2022-07-09 21:54 [PATCH] crypto: xor - move __crypto_xor into lib/ Eric Biggers
@ 2022-07-11 15:02 ` Jason A. Donenfeld
  2022-07-15  8:09 ` Herbert Xu
  1 sibling, 0 replies; 3+ messages in thread
From: Jason A. Donenfeld @ 2022-07-11 15:02 UTC (permalink / raw)
  To: Eric Biggers; +Cc: linux-crypto, linux-kernel

Hi Eric,

On Sat, Jul 09, 2022 at 02:54:53PM -0700, Eric Biggers wrote:
> From: Eric Biggers <ebiggers@google.com>
> 
> CRYPTO_LIB_CHACHA depends on CRYPTO for __crypto_xor, defined in
> crypto/algapi.c.  This is a layering violation because the dependencies
> should only go in the other direction (crypto/ => lib/crypto/).  Also
> the correct dependency would be CRYPTO_ALGAPI, not CRYPTO.  Fix this by
> moving __crypto_xor into lib/xor.c, alongside lib/memneq.c where
> __crypto_memneq was recently moved.
> 
> Note that CRYPTO_LIB_CHACHA_GENERIC selected XOR_BLOCKS, which is
> unrelated and unnecessary.  It was perhaps thought that XOR_BLOCKS was
> needed for __crypto_xor, but that's not the case.

Oh thank goodness. Excellent! Indeed untangling this knot will be a
large improvement.

Reviewed-by: Jason A. Donenfeld <Jason@zx2c4.com>

Jason

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: [PATCH] crypto: xor - move __crypto_xor into lib/
  2022-07-09 21:54 [PATCH] crypto: xor - move __crypto_xor into lib/ Eric Biggers
  2022-07-11 15:02 ` Jason A. Donenfeld
@ 2022-07-15  8:09 ` Herbert Xu
  1 sibling, 0 replies; 3+ messages in thread
From: Herbert Xu @ 2022-07-15  8:09 UTC (permalink / raw)
  To: Eric Biggers; +Cc: linux-crypto, linux-kernel, Jason

Eric Biggers <ebiggers@kernel.org> wrote:
> From: Eric Biggers <ebiggers@google.com>
> 
> CRYPTO_LIB_CHACHA depends on CRYPTO for __crypto_xor, defined in
> crypto/algapi.c.  This is a layering violation because the dependencies
> should only go in the other direction (crypto/ => lib/crypto/).  Also
> the correct dependency would be CRYPTO_ALGAPI, not CRYPTO.  Fix this by
> moving __crypto_xor into lib/xor.c, alongside lib/memneq.c where
> __crypto_memneq was recently moved.
> 
> Note that CRYPTO_LIB_CHACHA_GENERIC selected XOR_BLOCKS, which is
> unrelated and unnecessary.  It was perhaps thought that XOR_BLOCKS was
> needed for __crypto_xor, but that's not the case.
> 
> Signed-off-by: Eric Biggers <ebiggers@google.com>
> ---
> crypto/Kconfig     |  1 +
> crypto/algapi.c    | 71 --------------------------------------
> lib/Kconfig        |  3 ++
> lib/Makefile       |  1 +
> lib/crypto/Kconfig |  3 +-
> lib/xor.c          | 85 ++++++++++++++++++++++++++++++++++++++++++++++
> 6 files changed, 91 insertions(+), 73 deletions(-)
> create mode 100644 lib/xor.c

Now that there are two of these things (xor and memneq), please
aggregate them into a module (either as separate files linked
together or as a single file) and turn it into a tristate.

They should also be moved into lib/crypto together with their
main users as lib is way too crowded as it is.

We could then revisit that simd variable and move it in too.

Thanks,
-- 
Email: Herbert Xu <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2022-07-15  8:09 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-07-09 21:54 [PATCH] crypto: xor - move __crypto_xor into lib/ Eric Biggers
2022-07-11 15:02 ` Jason A. Donenfeld
2022-07-15  8:09 ` Herbert Xu

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).