/** * Double-hashes the given password using the given * server and client tokens. * * outBuffer MUST be at least 20 bytes long. */ MEXP(void) doubleHashPassword(const char* password, uint32_t clientToken, uint32_t serverToken, char* outBuffer) { char intermediate[28]; uint32_t* lp; calcHashBuf(password, std::strlen(password), intermediate + 8); lp = (uint32_t*) &intermediate; lp[0] = clientToken; lp[1] = serverToken; calcHashBuf(intermediate, 28, outBuffer); #if DEBUG bncsutil_debug_message_a("doubleHashPassword(\"%s\", 0x%08X, 0x%08X) =", password, clientToken, serverToken); bncsutil_debug_dump(outBuffer, 20); #endif }
/** * Single-hashes the password for account creation and password changes. * * outBuffer MUST be at least 20 bytes long. */ MEXP(void) hashPassword(const char* password, char* outBuffer) { calcHashBuf(password, std::strlen(password), outBuffer); #if DEBUG bncsutil_debug_message_a("hashPassword(\"%s\") =", password); bncsutil_debug_dump(outBuffer, 20); #endif }
/** * Calculates the CD-Key hash for use in SID_AUTH_CHECK (0x51) * Returns the length of the generated hash; call getHash and pass * it a character array that is at least this size. Returns 0 on failure. * * Note that clientToken and serverToken will be added to the buffer and * hashed as-is, regardless of system endianness. It is assumed that * the program's extraction of the server token does not change its * endianness, and since the client token is generated by the client, * endianness is not a factor. */ size_t CDKeyDecoder::calculateHash(uint32_t clientToken, uint32_t serverToken) { struct CDKEYHASH kh; SHA1Context sha; if (!initialized || !keyOK) return 0; hashLen = 0; kh.clientToken = clientToken; kh.serverToken = serverToken; switch (keyType) { case KEY_STARCRAFT: case KEY_WARCRAFT2: kh.product = (uint32_t) LSB4(product); kh.value1 = (uint32_t) LSB4(value1); kh.value2.s.zero = 0; kh.value2.s.v = (uint32_t) LSB4(value2); keyHash = new char[20]; calcHashBuf((char*) &kh, 24, keyHash); hashLen = 20; #if DEBUG bncsutil_debug_message_a("%s: Hash calculated.", cdkey); bncsutil_debug_dump(keyHash, 20); #endif return 20; case KEY_WARCRAFT3: kh.product = (uint32_t) MSB4(product); kh.value1 = (uint32_t) MSB4(value1); memcpy(kh.value2.l.v, w3value2, 10); if (SHA1Reset(&sha)) return 0; if (SHA1Input(&sha, (const unsigned char*) &kh, 26)) return 0; keyHash = new char[20]; if (SHA1Result(&sha, (unsigned char*) keyHash)) { SHA1Reset(&sha); return 0; } SHA1Reset(&sha); hashLen = 20; #if DEBUG bncsutil_debug_message_a("%s: Hash calculated.", cdkey); bncsutil_debug_dump(keyHash, 20); #endif return 20; default: return 0; } }