# define SRP_RANDOM_SALT_LEN 20
# define MAX_LEN 2500
-static char b64table[] =
- "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz./";
-
-/*
- * the following two conversion routines have been inspired by code from
- * Stanford
- */
-
/*
* Convert a base64 string into raw byte array representation.
*/
-static int t_fromb64(unsigned char *a, const char *src)
+static int t_fromb64(unsigned char *a, size_t alen, const char *src)
{
- char *loc;
- int i, j;
- int size;
-
- while (*src && (*src == ' ' || *src == '\t' || *src == '\n'))
- ++src;
- size = strlen(src);
- i = 0;
- while (i < size) {
- loc = strchr(b64table, src[i]);
- if (loc == (char *)0)
- break;
- else
- a[i] = loc - b64table;
- ++i;
- }
- /* if nothing valid to process we have a zero length response */
- if (i == 0)
- return 0;
- size = i;
- i = size - 1;
- j = size;
- while (1) {
- a[j] = a[i];
- if (--i < 0)
- break;
- a[j] |= (a[i] & 3) << 6;
- --j;
- a[j] = (unsigned char)((a[i] & 0x3c) >> 2);
- if (--i < 0)
- break;
- a[j] |= (a[i] & 0xf) << 4;
- --j;
- a[j] = (unsigned char)((a[i] & 0x30) >> 4);
- if (--i < 0)
- break;
- a[j] |= (a[i] << 2);
-
- a[--j] = 0;
- if (--i < 0)
- break;
- }
- while (a[j] == 0 && j <= size)
- ++j;
- i = 0;
- while (j <= size)
- a[i++] = a[j++];
- return i;
+ size_t size = strlen(src);
+
+ /* Four bytes in src become three bytes output. */
+ if (size > INT_MAX || (size / 4) * 3 > alen)
+ return -1;
+
+ return EVP_DecodeBlock(a, (unsigned char *)src, (int)size);
}
/*
* Convert a raw byte string into a null-terminated base64 ASCII string.
*/
-static char *t_tob64(char *dst, const unsigned char *src, int size)
+static void t_tob64(char *dst, const unsigned char *src, int size)
{
- int c, pos = size % 3;
- unsigned char b0 = 0, b1 = 0, b2 = 0, notleading = 0;
- char *olddst = dst;
-
- switch (pos) {
- case 1:
- b2 = src[0];
- break;
- case 2:
- b1 = src[0];
- b2 = src[1];
- break;
- }
-
- while (1) {
- c = (b0 & 0xfc) >> 2;
- if (notleading || c != 0) {
- *dst++ = b64table[c];
- notleading = 1;
- }
- c = ((b0 & 3) << 4) | ((b1 & 0xf0) >> 4);
- if (notleading || c != 0) {
- *dst++ = b64table[c];
- notleading = 1;
- }
- c = ((b1 & 0xf) << 2) | ((b2 & 0xc0) >> 6);
- if (notleading || c != 0) {
- *dst++ = b64table[c];
- notleading = 1;
- }
- c = b2 & 0x3f;
- if (notleading || c != 0) {
- *dst++ = b64table[c];
- notleading = 1;
- }
- if (pos >= size)
- break;
- else {
- b0 = src[pos++];
- b1 = src[pos++];
- b2 = src[pos++];
- }
- }
-
- *dst++ = '\0';
- return olddst;
+ EVP_EncodeBlock((unsigned char *)dst, src, size);
}
void SRP_user_pwd_free(SRP_user_pwd *user_pwd)
unsigned char tmp[MAX_LEN];
int len;
- if (strlen(s) > MAX_LEN || strlen(v) > MAX_LEN)
+ vinfo->v = NULL;
+ vinfo->s = NULL;
+
+ len = t_fromb64(tmp, sizeof(tmp), v);
+ if (len < 0)
return 0;
- len = t_fromb64(tmp, v);
if (NULL == (vinfo->v = BN_bin2bn(tmp, len, NULL)))
return 0;
- len = t_fromb64(tmp, s);
- return ((vinfo->s = BN_bin2bn(tmp, len, NULL)) != NULL);
+ len = t_fromb64(tmp, sizeof(tmp), s);
+ if (len < 0)
+ goto err;
+ vinfo->s = BN_bin2bn(tmp, len, NULL);
+ if (vinfo->s == NULL)
+ goto err;
+ return 1;
+ err:
+ BN_free(vinfo->v);
+ vinfo->v = NULL;
+ return 0;
}
static int SRP_user_pwd_set_sv_BN(SRP_user_pwd *vinfo, BIGNUM *s, BIGNUM *v)
if (newgN == NULL)
return NULL;
+ len = t_fromb64(tmp, sizeof(tmp), ch);
+ if (len < 0)
+ goto err;
+
if ((newgN->b64_bn = OPENSSL_strdup(ch)) == NULL)
goto err;
- len = t_fromb64(tmp, ch);
if ((newgN->bn = BN_bin2bn(tmp, len, NULL)))
return newgN;
return NULL;
}
- #if OPENSSL_API_COMPAT < 0x10100000L
+# if OPENSSL_API_COMPAT < 0x10100000L
/*
* DEPRECATED: use SRP_VBASE_get1_by_user instead.
* This method ignores the configured seed and fails for an unknown user.
{
return find_user(vb, username);
}
-#endif
+# endif
/*
* Ownership of the returned pointer is released to the caller.
goto err;
if (N) {
- if ((len = t_fromb64(tmp, N)) == 0)
+ if ((len = t_fromb64(tmp, sizeof(tmp), N)) <= 0)
goto err;
N_bn_alloc = BN_bin2bn(tmp, len, NULL);
N_bn = N_bn_alloc;
- if ((len = t_fromb64(tmp, g)) == 0)
+ if ((len = t_fromb64(tmp, sizeof(tmp) ,g)) <= 0)
goto err;
g_bn_alloc = BN_bin2bn(tmp, len, NULL);
g_bn = g_bn_alloc;
s = BN_bin2bn(tmp2, SRP_RANDOM_SALT_LEN, NULL);
} else {
- if ((len = t_fromb64(tmp2, *salt)) == 0)
+ if ((len = t_fromb64(tmp2, sizeof(tmp2), *salt)) <= 0)
goto err;
s = BN_bin2bn(tmp2, len, NULL);
}