Commit 36d730e9 authored by Timo Teräs's avatar Timo Teräs

optimize base64 decoding a bit

it's a hot path for decoding checksums in fdb
parent ed94d8ff
...@@ -583,7 +583,7 @@ static unsigned char b64decode[] = { ...@@ -583,7 +583,7 @@ static unsigned char b64decode[] = {
}; };
static inline __attribute__((always_inline)) static inline __attribute__((always_inline))
int pull_b64_chunk(unsigned char *to, const unsigned char *from, int len) int pull_b64_chunk(unsigned char *restrict to, const unsigned char *restrict from, int len)
{ {
unsigned char tmp[4]; unsigned char tmp[4];
int i, r = 0; int i, r = 0;
...@@ -610,21 +610,20 @@ int pull_b64_chunk(unsigned char *to, const unsigned char *from, int len) ...@@ -610,21 +610,20 @@ int pull_b64_chunk(unsigned char *to, const unsigned char *from, int len)
void apk_blob_pull_base64(apk_blob_t *b, apk_blob_t to) void apk_blob_pull_base64(apk_blob_t *b, apk_blob_t to)
{ {
unsigned char tmp[4]; unsigned char tmp[4];
unsigned char *src = (unsigned char *) b->ptr; unsigned char *restrict src = (unsigned char *) b->ptr;
unsigned char *dst = (unsigned char *) to.ptr; unsigned char *restrict dst = (unsigned char *) to.ptr;
int i, r, needed; unsigned char *dend;
int r, needed;
if (unlikely(APK_BLOB_IS_NULL(*b))) if (unlikely(APK_BLOB_IS_NULL(*b)))
return; return;
needed = ((to.len + 2) / 3) * 4; needed = ((to.len + 2) / 3) * 4;
if (unlikely(b->len < needed)) { if (unlikely(b->len < needed)) goto err;
*b = APK_BLOB_NULL;
return;
}
r = 0; r = 0;
for (i = 0; i < to.len / 3; i++, src += 4, dst += 3) { dend = dst + to.len - 2;
for (; dst < dend; src += 4, dst += 3) {
r |= tmp[0] = b64decode[src[0]]; r |= tmp[0] = b64decode[src[0]];
r |= tmp[1] = b64decode[src[1]]; r |= tmp[1] = b64decode[src[1]];
r |= tmp[2] = b64decode[src[2]]; r |= tmp[2] = b64decode[src[2]];
...@@ -633,21 +632,18 @@ void apk_blob_pull_base64(apk_blob_t *b, apk_blob_t to) ...@@ -633,21 +632,18 @@ void apk_blob_pull_base64(apk_blob_t *b, apk_blob_t to)
dst[1] = (tmp[1] << 4 | tmp[2] >> 2); dst[1] = (tmp[1] << 4 | tmp[2] >> 2);
dst[2] = (((tmp[2] << 6) & 0xc0) | tmp[3]); dst[2] = (((tmp[2] << 6) & 0xc0) | tmp[3]);
} }
if (unlikely(r == 0xff)) { if (unlikely(r == 0xff)) goto err;
*b = APK_BLOB_NULL;
return;
}
i = to.len % 3; dend += 2;
if (i != 0) { if (dst != dend &&
if (pull_b64_chunk(dst, src, i) != 0) { pull_b64_chunk(dst, src, dend - dst) != 0)
*b = APK_BLOB_NULL; goto err;
return;
}
}
b->ptr += needed; b->ptr += needed;
b->len -= needed; b->len -= needed;
return;
err:
*b = APK_BLOB_NULL;
} }
static apk_blob_t atom_hash_get_key(apk_hash_item item) static apk_blob_t atom_hash_get_key(apk_hash_item item)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment