Originally Posted by
Hodor
Which bug?
Originally Posted by
awsdert
...unfortunately encountered a bug when converting to a library for other mini-projects to use
Originally Posted by
Hodor
If the very small slowdown in speed is a problem then using the less portable non-loop version of the function might be worth it.
Also, from memory, both the loop and non-loop versions have a bug in them for bases >= 36 which I didn't mention the other day because I forgot and I couldn't work out how to demonstrate the bug anyway. [strike]I don't have the code anymore but a bool used to choose between lower and upper case characters for the conversion is not initialised (I think it was called highashigh or lowaslow or highaslow or something like that)[/strike]. Edit: actually base62.c is in your new archive for the other current question and the unitialised variable is called lowislow
Hmm, given lowislow is a parameter of the function I doubt that it could ever be uninitialised, unless the one I uploaded is different to the version I have now:
Code:
int ubase62(
NEXTC *_nextc, uint_least64_t *dst, int base,
bool lowislow, size_t min_len, size_t max_len )
{
int ret = nextc_validate(_nextc), c;
size_t i = 0, l, h;
uint_least64_t num = 0;
if ( !max_len ) max_len = -2;
if ( ret != EXIT_SUCCESS )
goto ubase62_done;
else if ( base < 2 ) {
ret = ERANGE;
FAIL( stderr, ret, "base is too low!" );
goto ubase62_done;
}
else if ( base <= 36 ) { l = 10; h = 10; }
else if ( base > 62 ) {
ret = ERANGE;
FAIL( stderr, ret, "base is too high!" );
goto ubase62_done;
}
else if ( lowislow ) { l = 10; h = 36; }
else { l = 36; h = 10; }
do {
c = _nextc->c[0];
if ( c >= U'0' && c <= U'9' )
c -= U'0';
else if ( c >= U'A' && c <= U'Z' )
{ c -= U'A'; c += h; }
else if ( c >= U'a' && c <= U'z' )
{ c -= U'a'; c += l; }
else break;
if ( c >= base || i >= max_len ) break;
num *= base;
num += c;
++i;
} while ( (ret = nextc(_nextc)) == EXIT_SUCCESS );
if ( ret != EXIT_SUCCESS )
FAIL( stderr, ret, "" );
if ( i < min_len ) {
ret = ERANGE;
FAIL( stderr, ret, "Not enough digits" );
fprintf( stderr,
"c = '%c', i = %zu, min_len = %zu, max_len = %zu\n",
_nextc->c[0], i, min_len, max_len );
}
ubase62_done:
if ( dst ) *dst = num;
return ret;
}
Btw what kind of bug did you experience above base 36? I never tested that high cause I didn't expect there to be issues when it uses the same handling just with a larger range