2008-10-28 11 views
10

में इंजन प्रारंभिकरण को समझना मैं एचएमएसी-एसएचए -256 हैशिंग का मूल परीक्षण स्थापित करने की कोशिश कर रहा हूं लेकिन मुझे इंजन सेटअप में समस्याएं आ रही हैं। आदर्श रूप से मैं केवल एचएमएसी-एसएचए-एल्गोरिदम स्थापित करना चाहता हूं लेकिन अब तक मुझे सामान्य मामला भी नहीं मिला है जहां सभी एल्गोरिदम काम करने के लिए लोड करते हैं। वर्तमान में मुझे पंक्ति पर segfaults मिल रहा है जहां मैं डिफ़ॉल्ट digests सेट करने का प्रयास करें।ओपनएसएसएल

इसके अलावा, मैं नियमित रूप से जावा लड़का हूं, इसलिए कोड में किसी भी गलती को इंगित करने में संकोच न करें।

#include <openssl/hmac.h> 
#include <openssl/evp.h> 
#include <stdio.h> 
#include <string.h> 
#include <stdlib.h> 

int main() { 
    unsigned char* key = (unsigned char*) "0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b"; 
    unsigned char* data = (unsigned char*) "4869205468657265"; 
    unsigned char* expected = (unsigned char*) "b0344c61d8db38535ca8afceaf0bf12b881dc200c9833da726e9376c2e32cff7"; 
    unsigned char* result; 
    HMAC_CTX* ctx; 
    ENGINE* e; 

    ENGINE_load_builtin_engines(); 
    ENGINE_register_all_complete(); 
    ENGINE_set_default_digests(e); 

    HMAC_CTX_init(ctx); 
    HMAC_Init_ex(ctx, key, 40, EVP_sha256(), e); 
    result = HMAC(NULL, NULL, 40, data, 16, NULL, NULL); 
    HMAC_CTX_cleanup(ctx); 

    ENGINE_finish(e); 
    ENGINE_free(e); 

    if (strcmp((char*) result, (char*) expected) == 0) { 
    printf("Test ok\n"); 
    } else { 
    printf("Got %s instead of %s\n", result, expected); 
    } 
} 

संपादित करें: कार्यक्रम अब निम्न के विकसित किया गया है, लेकिन मैं अभी भी HMAC_Init_ex पर segfaulting हूँ:

unsigned char* key = (unsigned char*) "0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b"; 
unsigned char* data = (unsigned char*) "4869205468657265"; 
unsigned char* expected = (unsigned char*) "b0344c61d8db38535ca8afceaf0bf12b881dc200c9833da726e9376c2e32cff7"; 
unsigned char* result; 
unsigned int result_len = 64; 
HMAC_CTX ctx; 
ENGINE* e; 

result = (unsigned char*) malloc(sizeof(char) * result_len); 
e = (ENGINE*) ENGINE_new(); 

ENGINE_load_builtin_engines(); 
ENGINE_register_all_complete(); 
ENGINE_set_default_digests(e); 

HMAC_CTX_init(&ctx); 
HMAC_Init_ex(&ctx, key, 16, EVP_sha256(), e); 
HMAC_Update(&ctx, data, 40); 
HMAC_Final(&ctx, result, &result_len); 
HMAC_CTX_cleanup(&ctx); 

ENGINE_finish(e); 
ENGINE_free(e); 

उत्तर

13

मार्टिन ने कहा कि आपके मूल सुझाव के साथ समस्या यह है कि आपको इंजन शुरू करने की आवश्यकता है। आपके संपादित कोड के साथ समस्या यह थी कि आप ENGINE_new कर रहे थे, जो आपको अपने आप की एक पूरी तरह से नई इंजन प्राप्त कर रहा है, जिसे आपको सिफर विधियों, पचाने के तरीके आदि प्रदान करने की आवश्यकता है। असल में, जो आप चाहते हैं (और क्या लगभग हर कोई चाहता है), बस पूरी तरह से सभी इंजन सामान को अनदेखा करना सही विकल्प है।

कुछ सहायक समस्याओं:

  • अपने तार हेक्स थे, लेकिन आप चरित्र प्रति एक \ एक्स की जरूरत वास्तव में स्ट्रिंग में उस स्थिति है, जो मुझे लगता है कि तुम क्या चाहते थे पर कि हेक्स बाइट प्राप्त करने के लिए।
  • आप "डेटा" से हैश 40 बाइट्स की कोशिश कर रहे थे, जो कि लंबे समय तक नहीं था (वास्तविक प्रभाव: आप आंशिक रूप से अपने परिणाम स्ट्रिंग को समाप्त कर देंगे)
  • आपका अपेक्षित परिणाम था (जहां तक ​​मैं कह सकता हूं) गलत
  • आप टर्मिनल पर यादृच्छिक वर्ण मुद्रित करेंगे, क्योंकि एचएमएसी फ़ंक्शन यादृच्छिक बाइनरी डेटा के 32 बाइट्स का उत्पादन करेगा, प्रिंट करने योग्य सामान नहीं।

निम्नलिखित कोड संकलित करता है, परीक्षण करता है और परीक्षण पास करता है।

#include <openssl/engine.h> 
#include <openssl/hmac.h> 
#include <openssl/evp.h> 
#include <stdio.h> 
#include <string.h> 
#include <stdlib.h> 


int main(void) 
{ 
     unsigned char* key = (unsigned char*) "\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b"; 
     unsigned char* data = (unsigned char*) "\x48\x69\x20\x54\x68\x65\x72\x65"; 
     unsigned char* expected = (unsigned char*) "\x49\x2c\xe0\x20\xfe\x25\x34\xa5\x78\x9d\xc3\x84\x88\x06\xc7\x8f\x4f\x67\x11\x39\x7f\x08\xe7\xe7\xa1\x2c\xa5\xa4\x48\x3c\x8a\xa6"; 
     unsigned char* result; 
     unsigned int result_len = 32; 
     int i; 
     HMAC_CTX ctx; 

     result = (unsigned char*) malloc(sizeof(char) * result_len); 

     ENGINE_load_builtin_engines(); 
     ENGINE_register_all_complete(); 

     HMAC_CTX_init(&ctx); 
     HMAC_Init_ex(&ctx, key, 16, EVP_sha256(), NULL); 
     HMAC_Update(&ctx, data, 8); 
     HMAC_Final(&ctx, result, &result_len); 
     HMAC_CTX_cleanup(&ctx); 

     for (i=0; i!=result_len; i++) 
     { 
       if (expected[i]!=result[i]) 
       { 
         printf("Got %02X instead of %02X at byte %d!\n", result[i], expected[i], i); 
         break; 
       } 
     } 
     if (i==result_len) 
     { 
       printf("Test ok!\n"); 
     } 
     return 0; 
} 
बेशक

, यह नहीं है: - यह उदाहरण कोड आप पाया (उपयोगी अगर आप HMAC_Update का उपयोग कर थोड़ा करके अपने हैशिंग बिट क्या करना चाहते हैं, क्योंकि यह अभी भी व्यक्तिगत HMAC_ का उपयोग करता है * कार्यों) के लिए थोड़ा अलग है इंजनों को शुरू करने के तरीके के बारे में अपने मूल प्रश्न का उत्तर दें, लेकिन इसके संदर्भ में वास्तव में कोई सही जवाब नहीं है, जो संदर्भ आपके परिस्थिति में प्रासंगिक नहीं है ...

0

ऐसा लगता है कि कुछ भी नहीं है जैसे कि एक इंजन का आवंटन किया गया है, इसलिए e का पहला प्रयोग segfaulting है। मुझे लगता है कि आपको पहले ENGINE *ENGINE_new(void) पर कॉल करने की आवश्यकता है।

(ध्यान दें कि मैं OpenSSL का उपयोग किया है, लेकिन मैं पहले ENGINE कार्यों उपयोग नहीं किया है।)

अद्यतन: मैं अपने खुद के जवाब के साथ वास्तव में खुश नहीं हूँ (मैं करने के लिए दूर भागना पड़ा चाय, पहले)। तो मेरी आगे नोट कर रहे हैं:

  1. मैं man pageENGINE कार्यों के लिए (लंबी) पर एक नज़र का एक सा लिया है, और मैं काफी यकीन है कि फोन करने के लिए पर्याप्त है ENGINE_new नहीं हूँ।

  2. मुझे नहीं पता था कि HMAC_CTX_* फ़ंक्शंस को कॉल आवंटित संरचना के सूचक के बजाय एक प्रारंभिक सूचक ले रहे थे। HMAC_CTX_init इसकी ctx पैरामीटर द्वारा इंगित स्मृति को लिखने का प्रयास करेगा, जो segfault होगा। आप घोषित करने और इस तरह ctx उपयोग करने की आवश्यकता:

    HMAC_CTX ctx; 
    HMAC_CTX_init(&ctx); 
    HMAC_Init_ex(&ctx, key, 40, EVP_sha256(), e); 
    ... 
    

    इस तरह आप ढेर पर संरचना का आवंटन कर रहे हैं, और फिर इसे करने के लिए एक सूचक गुजर।

  3. HMAC समारोह नहीं वैश्विक या धागे की स्थानीय भंडारण से इतना अलग सब पर एक CTX के लिए सूचक ले करता है, मुझे यकीन है कि क्या यह CTX के लिए कनेक्शन है है नहीं कर रहा हूँ। मुझे लगता है कि परिणाम प्राप्त करने के लिए HMAC_Final के बाद HMAC_Update एक या अधिक बार कॉल करके आप इसे बाईपास कर सकते हैं। आपको लगता है कि परिणाम के लिए जगह आवंटित करने के लिए आवश्यकता होगी, तो निम्नलिखित की तरह कुछ है कि के लिए काम करेगा:

    unsigned int len; 
    HMAC_Final(&ctx, result, &len); 
    
+0

सुझाव मार्टिन के लिए धन्यवाद, मैंने कोशिश की है उन्हें बाहर लेकिन मैं अभी भी अटक गया हूँ। मैं इस बारे में इंजन टिप्पणी के बारे में उत्सुक हूं कि आपने इसका उपयोग नहीं किया है। क्या इंजन के बिना ओपनएसएसएल का उपयोग करना संभव है? – Fylke

1

ठीक है, पता चला है कि आप एक इंजन का उपयोग करने की जरूरत नहीं है कि लेकिन मैं गलत समझा था एक स्पष्ट इंजन का उपयोग कैसे नहीं करें। मैंने यह भी गलत समझा कि टेस्ट वैक्टर को सही तरीके से कैसे प्रारूपित किया जाए। अंत में मैंने hmactest.c को देखा जो मैं बहुत कुछ करना चाहता हूं, मुझे कोड को समझ में नहीं आया।

मुझे क्या करना है कोशिश कर रहा था करने के लिए अंतिम समाधान इस तरह दिखता है:

int main() { 
    unsigned char* key = (unsigned char*) "Jefe"; 
    unsigned char* data = (unsigned char*) "what do ya want for nothing?"; 
    unsigned char* expected = (unsigned char*) "5bdcc146bf60754e6a042426089575c75a003f089d2739839dec58b964ec3843"; 
    unsigned char* result; 
    unsigned int result_len = 32; 
    int i; 
    static char res_hexstring[32]; 

    result = HMAC(EVP_sha256(), key, 4, data, 28, NULL, NULL); 
    for (i = 0; i < result_len; i++) { 
    sprintf(&(res_hexstring[i * 2]), "%02x", result[i]); 
    } 

    if (strcmp((char*) res_hexstring, (char*) expected) == 0) { 
    printf("Test ok, result length %d\n", result_len); 
    } else { 
    printf("Got %s instead of %s\n", res_hexstring, expected); 
    } 
} 

लेकिन चूंकि मैं कुछ पूरी तरह से अलग के बारे में पूछ रहा था, मैं क्या मूल प्रश्न से कोई लेना देना के बारे में अनिश्चित हूँ। सुझाव?

+0

न्यूल। नोट: स्थिर सरणी का उपयोग करने के लिए एमडी के लिए एक पूर्ण मान पास करना धागा सुरक्षित नहीं है। https://www.openssl.org/docs/man1.0.2/crypto/hmac.html – codenamezero

संबंधित मुद्दे