]> source.dussan.org Git - rspamd.git/commitdiff
[Feature] Improve base64 usage
authorVsevolod Stakhov <vsevolod@highsecure.ru>
Tue, 12 Nov 2019 16:24:33 +0000 (16:24 +0000)
committerVsevolod Stakhov <vsevolod@highsecure.ru>
Tue, 12 Nov 2019 16:24:33 +0000 (16:24 +0000)
src/libcryptobox/base64/avx2.c
src/libcryptobox/base64/base64.c
src/libcryptobox/base64/sse42.c

index 80f3b9972eb6b2f46ca2cee980bc37ea325f231e..432149a29b25c06554382661627a1020a8b82957 100644 (file)
@@ -144,6 +144,7 @@ dec_reshuffle (__m256i in)
                const __m256i eq_2F       = _mm256_cmpeq_epi8(str, mask_2F); \
                const __m256i roll        = _mm256_shuffle_epi8(lut_roll, _mm256_add_epi8(eq_2F, hi_nibbles)); \
                if (!_mm256_testz_si256(lo, hi)) { \
+                       seen_error = true; \
                        break; \
                } \
                str = _mm256_add_epi8(str, roll); \
@@ -168,12 +169,15 @@ base64_decode_avx2 (const char *in, size_t inlen,
        uint8_t q, carry;
        size_t outl = 0;
        size_t leftover = 0;
+       bool seen_error = false;
 
 repeat:
        switch (leftover) {
                for (;;) {
                case 0:
-                       INNER_LOOP_AVX2
+                       if (G_LIKELY (!seen_error)) {
+                               INNER_LOOP_AVX2
+                       }
 
                        if (inlen-- == 0) {
                                ret = 1;
@@ -267,6 +271,7 @@ repeat:
                }
 
                if (inlen > 0) {
+                       seen_error = false;
                        goto repeat;
                }
        }
index 03ca99786281b425e89a2e4c92f0ee9119eeb759..f3759110b6182c46ce4315c99f5702e5998063b7 100644 (file)
@@ -19,6 +19,7 @@
 #include "base64.h"
 #include "platform_config.h"
 #include "str_util.h"
+#include "util.h"
 #include "contrib/libottery/ottery.h"
 
 extern unsigned long cpu_config;
@@ -116,20 +117,13 @@ gboolean
 rspamd_cryptobox_base64_decode (const gchar *in, gsize inlen,
                guchar *out, gsize *outlen)
 {
-       if (inlen > 256) {
+       if (inlen > 128) {
                /*
                 * For SIMD base64 decoding we need really large inputs with no
                 * garbadge such as newlines
-                * Otherwise, naive version is MUCH faster
+                * Otherwise, naive version is 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);
-               }
+               return base64_opt->decode (in, inlen, out, outlen);
        }
        else {
                /* Small input, use reference version */
@@ -139,12 +133,12 @@ rspamd_cryptobox_base64_decode (const gchar *in, gsize inlen,
        g_assert_not_reached ();
 }
 
-size_t
-base64_test (bool generic, size_t niters, size_t len)
+double
+base64_test (bool generic, size_t niters, size_t len, size_t str_len)
 {
        size_t cycles;
        guchar *in, *out, *tmp;
-       const base64_impl_t *impl;
+       gdouble t1, t2, total = 0;
        gsize outlen;
 
        g_assert (len > 0);
@@ -152,22 +146,35 @@ base64_test (bool generic, size_t niters, size_t len)
        tmp = g_malloc (len);
        ottery_rand_bytes (in, len);
 
-       impl = generic ? &base64_list[0] : base64_opt;
+       out = rspamd_encode_base64_fold (in, len, str_len, &outlen,
+                       RSPAMD_TASK_NEWLINES_CRLF);
 
-       out = rspamd_encode_base64 (in, len, 0, &outlen);
-       impl->decode (out, outlen, tmp, &len);
+       if (generic) {
+               base64_list[0].decode (out, outlen, tmp, &len);
+       }
+       else {
+               rspamd_cryptobox_base64_decode (out, outlen, tmp, &len);
+       }
 
        g_assert (memcmp (in, tmp, len) == 0);
 
        for (cycles = 0; cycles < niters; cycles ++) {
-               impl->decode (out, outlen, in, &len);
+               t1 = rspamd_get_ticks (TRUE);
+               if (generic) {
+                       base64_list[0].decode (out, outlen, tmp, &len);
+               }
+               else {
+                       rspamd_cryptobox_base64_decode (out, outlen, tmp, &len);
+               }
+               t2 = rspamd_get_ticks (TRUE);
+               total += t2 - t1;
        }
 
        g_free (in);
        g_free (tmp);
        g_free (out);
 
-       return cycles;
+       return total;
 }
 
 
index 1d1287ad21101ad17bc33224303f9db7adcfd32c..806dd5298191ca1a7af1e163c3ad16c31550c338 100644 (file)
@@ -118,6 +118,7 @@ static inline __m128i dec_reshuffle (__m128i in)
                        'A','Z', \
                        'a','z'); \
                if (_mm_cmpistrc(range, str, _SIDD_UBYTE_OPS | _SIDD_CMP_RANGES | _SIDD_NEGATIVE_POLARITY)) { \
+                       seen_error = true; \
                        break; \
                } \
                __m128i indices = _mm_subs_epu8(str, _mm_set1_epi8(46)); \
@@ -150,12 +151,15 @@ base64_decode_sse42 (const char *in, size_t inlen,
        uint8_t q, carry;
        size_t outl = 0;
        size_t leftover = 0;
+       bool seen_error = false;
 
 repeat:
        switch (leftover) {
                for (;;) {
                case 0:
-                       INNER_LOOP_SSE42
+                       if (G_LIKELY (!seen_error)) {
+                               INNER_LOOP_SSE42
+                       }
 
                        if (inlen-- == 0) {
                                ret = 1;
@@ -249,6 +253,7 @@ repeat:
                }
 
                if (inlen > 0) {
+                       seen_error = false;
                        goto repeat;
                }
        }