commit 06db5f2: [Feature] Performance: Do not use base64 SIMD version for bad inputs

Vsevolod Stakhov vsevolod at highsecure.ru
Thu Jul 25 14:00:05 UTC 2019


Author: Vsevolod Stakhov
Date: 2019-07-25 14:53:49 +0100
URL: https://github.com/rspamd/rspamd/commit/06db5f2fdab7f04011e5f1c698c28c64ae11c709 (HEAD -> master)

[Feature] Performance: Do not use base64 SIMD version for bad inputs

---
 src/libcryptobox/base64/base64.c | 25 ++++++++++++++++++++++++-
 1 file changed, 24 insertions(+), 1 deletion(-)

diff --git a/src/libcryptobox/base64/base64.c b/src/libcryptobox/base64/base64.c
index eccc89a74..03ca99786 100644
--- a/src/libcryptobox/base64/base64.c
+++ b/src/libcryptobox/base64/base64.c
@@ -43,6 +43,8 @@ base64_table_dec[256] =
 	255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
 };
 
+static const char base64_alphabet[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+/";
+
 typedef struct base64_impl {
 	unsigned long cpu_flags;
 	const char *desc;
@@ -90,6 +92,7 @@ static const base64_impl_t base64_list[] = {
 };
 
 static const base64_impl_t *base64_opt = &base64_list[0];
+static const base64_impl_t *base64_ref = &base64_list[0];
 
 const char *
 base64_load (void)
@@ -113,7 +116,27 @@ gboolean
 rspamd_cryptobox_base64_decode (const gchar *in, gsize inlen,
 		guchar *out, gsize *outlen)
 {
-	return base64_opt->decode (in, inlen, out, outlen);
+	if (inlen > 256) {
+		/*
+		 * For SIMD base64 decoding we need really large inputs with no
+		 * garbadge such as newlines
+		 * Otherwise, naive version is MUCH faster
+		 */
+
+		if (rspamd_memcspn (in, base64_alphabet, 256) == 256) {
+			return base64_opt->decode (in, inlen, out, outlen);
+		}
+		else {
+			/* Garbage found */
+			return base64_ref->decode (in, inlen, out, outlen);
+		}
+	}
+	else {
+		/* Small input, use reference version */
+		return base64_ref->decode (in, inlen, out, outlen);
+	}
+
+	g_assert_not_reached ();
 }
 
 size_t


More information about the Commits mailing list