2016-01-14 6 views
1

Используя существующий алгоритм C, я хочу сгенерировать правильный хэш CRC32 для строки в python. Тем не менее, я получаю неверные результаты. Я маскирую результат каждой операции и пытаюсь скопировать логику исходного алгоритма. Код C был предоставлен тем же веб-сайтом, на котором есть инструмент проверки хеш-строки веб-страницы, поэтому он, вероятно, будет правильным.CRC32 хэш строки python

Ниже приведен полный файл Python, включающий код C в своих комментариях, который он пытается имитировать. Вся необходимая информация находится в файле.

P_32 = 0xEDB88320 
init = 0xffffffff 
_ran = True 
tab32 = [] 

def mask32(n): 
    return n & 0xffffffff 

def mask8(n): 
    return n & 0x000000ff 

def mask1(n): 
    return n & 0x00000001 

def init32(): 
    for i in range(256): 
     crc = mask32(i) 
     for j in range(8): 
      if (mask1(crc) == 1): 
       crc = mask32(mask32(crc >> 1)^P_32) 
      else: 
       crc = mask32(crc >> 1) 
     tab32.append(crc) 
    global _ran 
    _ran = False 

def update32(crc, char): 
    char = mask8(char) 
    t = crc^char 
    crc = mask32(mask32(crc >> 8)^tab32[mask8(t)]) 
    return crc 

def run(string): 
    if _ran: 
     init32() 
    crc = init 
    for c in string: 
     crc = update32(crc, ord(c)) 
    print(hex(crc)[2:].upper()) 

check0 = "The CRC32 of this string is 4A1C449B" 
check1 = "123456789" # CBF43926 
run(check0) # Produces B5E3BB64 
run(check1) # Produces 340BC6D9 

# Check CRC-32 on http://www.lammertbies.nl/comm/info/crc-calculation.html#intr 

""" 
/* http://www.lammertbies.nl/download/lib_crc.zip */ 

#define     P_32  0xEDB88320L 
static int    crc_tab32_init   = FALSE; 
static unsigned long crc_tab32[256]; 

    /*******************************************************************\ 
    *                 * 
    * unsigned long update_crc_32(unsigned long crc, char c);  * 
    *                 * 
    * The function update_crc_32 calculates a new CRC-32 value  * 
    * based on the previous value of the CRC and the next byte  * 
    * of the data to be checked.          * 
    *                 * 
    \*******************************************************************/ 

unsigned long update_crc_32(unsigned long crc, char c) { 

    unsigned long tmp, long_c; 

    long_c = 0x000000ffL & (unsigned long) c; 

    if (! crc_tab32_init) init_crc32_tab(); 

    tmp = crc^long_c; 
    crc = (crc >> 8)^crc_tab32[ tmp & 0xff ]; 

    return crc; 

} /* update_crc_32 */ 

    /*******************************************************************\ 
    *                 * 
    * static void init_crc32_tab(void);        * 
    *                 * 
    * The function init_crc32_tab() is used to fill the array  * 
    * for calculation of the CRC-32 with values.      * 
    *                 * 
    \*******************************************************************/ 

static void init_crc32_tab(void) { 

    int i, j; 
    unsigned long crc; 

    for (i=0; i<256; i++) { 

     crc = (unsigned long) i; 

     for (j=0; j<8; j++) { 

      if (crc & 0x00000001L) crc = (crc >> 1)^P_32; 
      else      crc = crc >> 1; 
     } 

     crc_tab32[i] = crc; 
    } 

    crc_tab32_init = TRUE; 

} /* init_crc32_tab */ 
""" 
+2

от zipfile import crc32 не подходит для вас? –

+0

Хорошо, поздравляю; вы точно копировали этот код, потому что код C генерирует точно такой же результат. –

+0

@YoavGlazner Я не могу найти хорошую документацию. –

ответ

1

Там только одна вещь, что случилось с текущей реализации и исправление на самом деле только одна строка кода до конца вашей функции запуска, которая:

crc = crc^init 

Который при добавлении в бега функция выглядеть следующим образом:

def run(string): 
    if _ran: 
     init32() 
    crc = init 
    for c in string: 
     crc = update32(crc, ord(c)) 
    crc = crc^init  
    print(hex(crc)[2:].upper()) 

Это даст вам правильные результаты вы expecting.The причиной того, что это необходимо после того как вы закончите обновление CRC32, то finaliz это XORing с помощью 0xFFFFFFFF. Поскольку у вас были только функции init table и update, а не финализация, вы были в одном шаге от реального crc.

Еще одна возможность, которая немного более проста, - это this one, это немного легче увидеть весь процесс. Единственное, что слегка улавливает, это init poly ~ 0x0 - то же самое (0xFFFFFFFF).

+0

Любопытный. Насколько быстрее выполняется реализация C? Казалось, что мой подход на основе python займет недели, но я думаю, что кто-то сказал, что они нашли собственный хэш с помощью C через пару минут. –

 Смежные вопросы

  • Нет связанных вопросов^_^