1

I used this BCrypt lib to generate a hash with salt: https://github.com/rg3/libbcrypt

The problem is in bcrypt.c (int bcrypt_gensalt). open("/dev/urandom", O_RDONLY) does not work on Windows. I have tried the following:

int bcrypt_gensalt(int factor, char salt[BCRYPT_HASHSIZE]) {
    int fd;
    unsigned char input[RANDBYTES];
    int workf;
    char *aux;

    HCRYPTPROV hCryptProv;

    if (CryptAcquireContext(
        &hCryptProv,
        NULL,
        (LPCSTR)"Microsoft Base Cryptographic Provider v1.0",
        PROV_RSA_FULL,
        CRYPT_VERIFYCONTEXT)) {
        if (CryptGenRandom(
            hCryptProv,
            RANDBYTES,
            input)) {

            if (CryptReleaseContext(hCryptProv, 0)) {
                return 0;
            }
            else {
                printf("Error during CryptReleaseContext.\n");
            return 4;
            }
        }
        else {
            if (CryptReleaseContext(hCryptProv, 0)) {
                printf("Error during CryptGenRandom.\n");
                return 2;
            }
            else {
                printf("Error during CryptReleaseContext.\n");
                return 3;
            }
        }
    }
    else {
        printf("Error during CryptAcquireContext!\n");
        return 1;
    }

    /* Generate salt. */
    workf = (factor < 4 || factor > 31)?12:factor;
    aux = crypt_gensalt_rn("$2a$", workf, input, RANDBYTES,
                   salt, BCRYPT_HASHSIZE);
    return (aux == NULL)?5:0;
}

But the result is:

Generated salt:
Hashed password: *0
Time taken: 0.000000 seconds
First hash check: OK
Second hash check: OK
First hash check with bcrypt_checkpw: OK
Time taken: 0.060000 seconds
Second hash check with bcrypt_checkpw: OK
Time taken: 0.060000 seconds

The salt will be not generated correctly.

jww
  • 97,681
  • 90
  • 411
  • 885
Zhavok
  • 31
  • 4
  • Maybe https://stackoverflow.com/questions/35590105/authentication-with-bcrypt-hashed-password helps you. – user743414 Aug 08 '18 at 14:20
  • Thx, but no. I spent 5 days with google and forums before I asked here^^ – Zhavok Aug 08 '18 at 14:28
  • your code and your output don't match up at all.... – UKMonkey Aug 08 '18 at 15:08
  • You should probably add the code that **(a)** declares the variable you pass in to receive the salt; **(b)** the call to this function and **(c)** how you are printing the returned salt. If not already doing so, you should be printing the return value of this function. More importantly, unless I'm reading it wrong, it looks like the above function will always have returned before it gets to `/* Generate salt. */`... – TripeHound Aug 08 '18 at 15:16
  • @UKMonkey My code is a part of the lib that i wrote above. But i can't generate a salt with lib on windows. Thats my problem^^ – Zhavok Aug 08 '18 at 15:24
  • Assuming the `Crypt...` functions return true (non-zero) on success, I'm pretty sure the `return 0` shouldn't be there: I'm pretty sure it's causing the function to exit before ever generating the salt. – TripeHound Aug 08 '18 at 19:20
  • I deleted the return under if (CryptReleaseContext(hCryptProv, 0)) {. Now I get an error in bcrypt_hashpw function. So many problems... Maybe it's easier to use PBKDF2. OpenSSL is already included and could use this. What is your opinion? – Zhavok Aug 09 '18 at 02:05
  • Windows does not have `/dev/urandom`; use `CryptGenRandom` instead. – jww Aug 19 '19 at 10:09

1 Answers1

0

In your call to:

aux = crypt_gensalt_rn("$2a$", workf, input, RANDBYTES,
                   salt, BCRYPT_HASHSIZE);

The values of RANDBYTES and BCRYPT_HASHSIZE need one more byte for terminated \0.

Have you tried that (using RANDBYTES-1 and BCRYPT_HASHSIZE-1)?

jww
  • 97,681
  • 90
  • 411
  • 885
Valeca
  • 122
  • 8
  • 1
    **If** they are null-terninated strings, and not just buffers, the correct change would almost certainly be to increase the buffer size available, not reduce the length of the buffer that you use. – TripeHound Aug 08 '18 at 19:24
  • I tried this now, but then it crashes ( assert(ret == 0); ) – Zhavok Aug 08 '18 at 19:36
  • The function takes the length of the buffer. Decreasing or increasing should have same effect. From the code you posted it is not clear where it crashes. Do you have call stack for it? – Valeca Aug 08 '18 at 20:21
  • "_Decreasing or increasing should have same effect_" except that I strongly suspect that the sizes are not arbitrary. Even if the `crypt_gensalt_rn()` routine can work with arbitrary size buffers, the system in which this is a part _probably_ requires hashes of a certain size (e.g. 64/128/256 bits; not 56/120/244 bits). – TripeHound Aug 09 '18 at 15:25
  • @TripeHound I agree, in general. But normally it should parse / verify that values are satisfied to required length. – Valeca Aug 09 '18 at 15:51
  • Thx guys. After so many problem I decided to use PBKDF2. Should I post my PBKDF2 - snippet here as an answer? – Zhavok Aug 10 '18 at 22:07