Skip to content

Instantly share code, notes, and snippets.

@mrexodia
Created August 31, 2014 14:34
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save mrexodia/4ed6a40b37628804486b to your computer and use it in GitHub Desktop.
Save mrexodia/4ed6a40b37628804486b to your computer and use it in GitHub Desktop.
#include <stdio.h>
#include <stdint.h>
#include <windows.h>
const char * ALPHABET32 = "ABCDEFGHJKLMNPQRSTUVWXYZ23456789\0";
int MAGIC = 91717;
int g_dwSeed = 0;
int8_t getCharIndex(char c)
{
char *p = (char *)ALPHABET32;
do
{
if ( *p == c )
return p - ALPHABET32;
++p;
}
while ( *p );
return -1;
}
void RandomizeSeed()
{
if ( !g_dwSeed )
g_dwSeed = 0x74D99E;
g_dwSeed = (0x41A7 * g_dwSeed % 0x1F31D) - (0xB14 * g_dwSeed / 0x1F31D);
if ( g_dwSeed <= 0 )
g_dwSeed += 0x7FFFFFFFu;
printf("seed: %.8X\n", g_dwSeed);
}
bool make_bits_array(char bits_array[12], const uint8_t *arKey)
{
memset(bits_array, 0, 12);
int64_t offset = 0;
/* Make the bits array ==> array of 5 bits */
for (int i = 0; i < 18; ++i )
{
uint8_t pos = offset & 7;
uint8_t idx = getCharIndex(arKey[i]);
if ( idx == 255 )
return false;
bits_array[offset / 8] |= idx << pos;
bits_array[offset / 8 + 1] |= idx >> (8 - pos);
offset += 5;
}
return true;
}
void print_bits_array(const char* title, char bits_array[12])
{
puts(title);
for(int i=0; i<12; i++)
printf("%.2X ", (uint8_t)bits_array[i]);
puts("\n");
}
const uint8_t get_expected_checksum(int seed)
{
uint8_t expected_chk = 0;
for (int i = 0; i < 8; ++i )
expected_chk ^= seed >> 4 * i;
expected_chk &= 0x0F;
return expected_chk;
}
void brute(int seed)
{
printf("possible bytes with seed %.8X:\n", seed);
const uint8_t expected_checksum = get_expected_checksum(seed);
for(int i=0,count=0; i<0x100; i++)
for(int j=0; j<0x100; j++)
{
uint8_t computed_chk = (i >> 6) | ((j & 3) << 2);
if(computed_chk == expected_checksum)
{
count++;
if(!(count % 8))
puts("");
printf("%.2X,%.2X=%.2X ", i, j, computed_chk);
}
}
puts("\n");
}
bool KeyCheck(int seed, const uint8_t *arKey)
{
char bits_array[12];
if(!make_bits_array(bits_array, arKey))
{
puts("invalid characters in key!");
return false;
}
print_bits_array("bits_array:", bits_array);
g_dwSeed = seed + 0x2B8ECCB;
for (int i = 0; i < 12; ++i )
{
RandomizeSeed();
g_dwSeed ^= bits_array[i];
bits_array[i] ^= g_dwSeed >> 16;
}
print_bits_array("\nrandomized:", bits_array);
/* Compute the expected checksum */
uint8_t expected_chk = get_expected_checksum(seed);
printf("Expected Checksum=%x\n", expected_chk);
uint8_t computed_chk = (bits_array[10] >> 6) | ((bits_array[11] & 3) << 2);
printf("Computed Checksum=%x\n", computed_chk);
return (computed_chk == expected_chk);
}
int main(int argc, const char *argv[])
{
//brute(MAGIC);
/* entered key: xxxxxx-xxxxxx-xxxxxx and then to upper string */
const uint8_t *szKey = (const uint8_t*)"22222233333344444Z\0";
if(!KeyCheck(MAGIC, szKey))
printf("\n==> Invalid Key (checksum mismatch) !\n");
else
puts("\nyou win!");
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment