← Commit list

53de6e615

Denys Vlasenko
Denys Vlasenko
2025-07-06
SOURCE BUG Duration: 72s

Subject

libbb/yescrypt: use common ascii64 encoding routine

SOURCE BUG

This commit was genuinely broken at the time (not related to our build system): libbb/yescrypt eklenirken (2025-07-06 - 2025-07-07 arasi) once unutulan kaynak dosyalari (pw_encrypt_yes.c, hash_sha256_block.c, pw_ascii64.c), ardindan 64-bit'te derlenmeyen bir 'buflen' degiskeni (alg-yescrypt-kdf.c) vardi - busybox'in kendi kodundaki gercek hatalar (e5d3a8763 ile duzeltildi)

→ Bu hatanin tam hikayesini ve duzeltme diffini gor

Binary

No binary (build failed)

Architecture & Compiler Flags

Architecture: x86_64-linux-gnu Compiler: gcc (Ubuntu 11.4.0-1ubuntu1~22.04.3) 11.4.0

—

Build Log

(log yok)

Commit Diff GitHub →

include/libbb.h+1 -0
@@ -2191,6 +2191,7 @@ void read_base64(FILE *src_stream, FILE *dst_stream, int flags) FAST_FUNC;
int FAST_FUNC i2a64(int i);
int FAST_FUNC a2i64(char c);
+char* FAST_FUNC num2str64_lsb_first(char *s, unsigned v, int n);
typedef struct md5_ctx_t {
uint8_t wbuffer[64]; /* always correctly aligned for uint64_t */
libbb/yescrypt/alg-yescrypt-common.c+34 -64
@@ -19,8 +19,8 @@
*/
/* Not inlining:
- * decode64 fuinctions are only used to read
- * yescrypt_params_t field, and convert salt ti binary -
+ * de/encode64 functions are only used to read
+ * yescrypt_params_t field, and convert salt to binary -
* both of these are negligible compared to main hashing operation
*/
static NOINLINE const uint8_t *decode64_uint32(
@@ -63,56 +63,6 @@ fail:
return NULL;
}
-static uint8_t *encode64_uint32_fixed(
- uint8_t *dst, size_t dstlen,
- uint32_t src, uint32_t srcbits)
-{
- uint32_t bits;
-
- for (bits = 0; bits < srcbits; bits += 6) {
- if (dstlen < 2)
- return NULL;
- *dst++ = i2a64(src);
- dstlen--;
- src >>= 6;
- }
-
- if (src || dstlen < 1)
- return NULL;
-
- *dst = 0; /* NUL terminate just in case */
-
- return dst;
-}
-
-static uint8_t *encode64(
- uint8_t *dst, size_t dstlen,
- const uint8_t *src, size_t srclen)
-{
- size_t i;
-
- for (i = 0; i < srclen; ) {
- uint8_t *dnext;
- uint32_t value = 0, bits = 0;
- do {
- value |= (uint32_t)src[i++] << bits;
- bits += 8;
- } while (bits < 24 && i < srclen);
- dnext = encode64_uint32_fixed(dst, dstlen, value, bits);
- if (!dnext)
- return NULL;
- dstlen -= dnext - dst;
- dst = dnext;
- }
-
- if (dstlen < 1)
- return NULL;
-
- *dst = 0; /* NUL terminate just in case */
-
- return dst;
-}
-
static const uint8_t *decode64(
uint8_t *dst, size_t *dstlen,
const uint8_t *src, size_t srclen)
@@ -156,21 +106,43 @@ static const uint8_t *decode64(
*dstlen = dstpos;
return src;
}
-
fail:
*dstlen = 0;
return NULL;
}
-uint8_t *yescrypt_r(
+static char *encode64(
+ char *dst, size_t dstlen,
+ const uint8_t *src, size_t srclen)
+{
+ while (srclen) {
+ uint32_t value = 0, b = 0;
+ do {
+ value |= (uint32_t)(*src++ << b);
+ b += 8;
+ srclen--;
+ } while (srclen && b < 24);
+
+ b >>= 3; /* number of bits to number of bytes */
+ b++; /* 1, 2 or 3 bytes will become 2, 3 or 4 ascii64 chars */
+ dstlen -= b;
+ if ((ssize_t)dstlen <= 0)
+ return NULL;
+ dst = num2str64_lsb_first(dst, value, b);
+ }
+ *dst = '\0';
+ return dst;
+}
+
+char *yescrypt_r(
const uint8_t *passwd, size_t passwdlen,
const uint8_t *setting,
- uint8_t *buf, size_t buflen)
+ char *buf, size_t buflen)
{
yescrypt_ctx_t yctx[1];
unsigned char hashbin32[32];
+ char *dst;
const uint8_t *src, *saltstr, *saltend;
- uint8_t *dst;
size_t need, prefixlen, saltstrlen;
uint32_t flavor, N_log2;
@@ -241,11 +213,11 @@ uint8_t *yescrypt_r(
goto fail;
yctx->param.NROM = (uint64_t)1 << NROM_log2;
}
+ if (!src)
+ goto fail;
+ if (*src != '$')
+ goto fail;
}
- if (!src)
- goto fail;
- if (*src != '$')
- goto fail;
saltstr = src + 1;
src = (uint8_t *)strchrnul((char *)saltstr, '$');
@@ -268,16 +240,14 @@ uint8_t *yescrypt_r(
dst = mempcpy(buf, setting, prefixlen);
*dst++ = '$';
dst = encode64(dst, buflen - (dst - buf), hashbin32, sizeof(hashbin32));
- if (!dst || dst >= buf + buflen)
+ if (!dst)
goto fail;
-
- *dst = 0; /* NUL termination */
ret:
free_region(yctx->local);
explicit_bzero(yctx, sizeof(yctx));
explicit_bzero(hashbin32, sizeof(hashbin32));
return buf;
-fail:
+ fail:
buf = NULL;
goto ret;
}
libbb/yescrypt/alg-yescrypt.h+2 -2
@@ -151,8 +151,8 @@ typedef struct {
*
* MT-safe as long as local and buf are local to the thread.
*/
-extern uint8_t *yescrypt_r(
+extern char *yescrypt_r(
const uint8_t *passwd, size_t passwdlen,
const uint8_t *setting,
- uint8_t *buf, size_t buflen
+ char *buf, size_t buflen
);