Question

I'm trying to implement PBKDF2 and I keep getting the wrong result, not sure what the problem is...

I'm using the common crypto implementation to check my results

here is my test function

#include <stdio.h>
#include "PBKDF2.h"
#include <CommonCrypto/CommonKeyDerivation.h>

int main (int argc, const char * argv[])
{

    const char *P = "password";
    const char *S = "salt";
    uint8_t *dk = PBKFD2(P, (uint8_t *)S, strlen(S), 1, 32);
    printf("mine: ");
    for(int i = 0; i < 32; i++) {
        printf("%02X ", dk[i]);
    }
    printf("\n");
    uint8_t *dk2 = malloc(32);

    CCKeyDerivationPBKDF(kCCPBKDF2, P, strlen(P), (uint8_t *)S, strlen(S), kCCHmacAlgSHA256, 1, dk2, 32);
    printf("aapl: ");
    for(int i = 0; i < 32; i++) {
        printf("%02X ", dk2[i]);
    }
    printf("\n");
    free(dk);
    free(dk2);
    return 0;
}

and here is my actual code

#include "PBKDF2.h"
#include <CommonCrypto/CommonHMAC.h>
#include <math.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
uint8_t *F(const char *, const uint8_t*, size_t, uint32_t, uint32_t);
uint8_t *F(const char *P, const uint8_t *S, size_t saltLen, uint32_t c, uint32_t i) {
    uint8_t *T = malloc(CC_SHA256_DIGEST_LENGTH);
    memset(T, 0, CC_SHA256_DIGEST_LENGTH);
    for(int k = 0; k < c; k++) {
        uint8_t salt[8];
        uint8_t U[CC_SHA256_DIGEST_LENGTH] = {0};
        if(k == 0) {
            memcpy(salt, S, saltLen);
            salt[saltLen] = i & 0xFF;
            salt[saltLen + 1] = (i>>8)&0xFF;
            salt[saltLen + 2] = (i>>16)&0xFF;
            salt[saltLen + 3] = (i>>24)&0xFF;
            CCHmac(kCCHmacAlgSHA256, salt, saltLen+4, P, strlen(P), U);
        } else {
            CCHmac(kCCHmacAlgSHA256, S, saltLen, P, strlen(P), U);
        }
        for(int j = 0; j < CC_SHA256_DIGEST_LENGTH; j++) {
            T[j] ^= U[j];
        }
    }
    return T;
}

uint8_t* PBKFD2(const char *P, const uint8_t *S, size_t saltLen, uint32_t c, uint32_t dkLen) {
    uint32_t hLen = 32;
    uint32_t l = (uint32_t)(ceil(((double)dkLen)/((double)hLen)));
    uint32_t r = dkLen - (l - 1) * hLen;

    uint8_t **T = malloc(sizeof(uint8_t *) * l);
    for(int i = 1; i <= l; i++) {
        T[i-1] = F(P, S, saltLen, c, i);
    }

    uint8_t *dk = malloc(sizeof(uint8_t) * dkLen);
    for(int i = 0; i < l; i++){
        if(i < l-1)
        {
            memcpy(dk+(hLen*i), T[i], hLen);
        } else {
            memcpy(dk+(hLen*i), T[i], r);
        }
        free(T[i]);
    }
    free(T);
    return dk;
}
Était-ce utile?

La solution

CommonCrypto is open source, so you can check Apple's implementation against your own. The file you want is CommonKeyDerivation.c.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top