2010-03-19 14 views
9

मैं सी में शुरुआती हूं, गिट के स्रोत कोड को पढ़ने के दौरान, मुझे यह रैपर फ़ंक्शन malloc पर मिला।रैपिंग मॉलोक - सी

void *xmalloc(size_t size) 
{ 
    void *ret = malloc(size); 
    if (!ret && !size) 
     ret = malloc(1); 
    if (!ret) { 
     release_pack_memory(size, -1); 
     ret = malloc(size); 
     if (!ret && !size) 
      ret = malloc(1); 
     if (!ret) 
      die("Out of memory, malloc failed"); 
    } 
#ifdef XMALLOC_POISON 
    memset(ret, 0xA5, size); 
#endif 
    return ret; 
} 

प्रश्न

  1. मैं नहीं समझ सकता है कि वे क्यों प्रयोग कर रहे हैं malloc(1)?
  2. release_pack_memory क्या करता है और मुझे पूरे स्रोत कोड में यह फ़ंक्शन कार्यान्वयन नहीं मिल रहा है।
  3. #ifdef XMALLOC_POISON memset(ret, 0xA5, size); क्या करता है?

मैं इस परियोजना को अपने प्रोजेक्ट पर पुन: उपयोग करने की योजना बना रहा हूं। क्या यह malloc के आसपास एक अच्छा रैपर है?

कोई भी मदद महान होगी।

मानक malloc(0) के व्यवहार को परिभाषित नहीं करता:

+7

कुडोस के लिए स्मृति रैपर का अच्छा सेट है - मैं चाहता हूँ अधिक डेवलपर्स ने ऐसा ही किया। – Lars

+3

प्रश्न 2 के लिए: इसकी परिभाषा sha1_file.c में है (यह गिट की पैक ऑब्जेक्ट्स के साथ मेमोरी के लिए है, संभवतः) और इसका प्रोटोटाइप गिट-कंपैट-यूटीएच में है। (संकेत: जब तक आप गिट के स्रोत कोड पर देख रहे हों, इसे खोजने के लिए 'git grep release_pack_memory' का उपयोग करें!) – Cascabel

+1

@Lars: धन्यवाद। @ जेफ्रोमी: 'गिट grep' के बारे में अच्छा बिंदु। –

उत्तर

3
  1. malloc (0) सभी प्लेटफार्मों पर काम नहीं करता है, इस मामले में एक-बाइट आवंटन इसके बजाय किया जाता है। 0-लंबाई मेमोरी ब्लॉक के आवंटन को अनुमति देने से कार्यक्रम के उच्च-स्तरीय तर्क को सरल बनाया जाता है।

  2. पता नहीं।

  3. आवंटित स्मृति को गैर-शून्य मान के साथ भरकर, प्रोग्राम में बग को ढूंढना आसान है जहां मेमोरी उचित प्रारंभ के बिना उपयोग की जाती है: प्रोग्राम ऐसे मामलों में लगभग तुरंत क्रैश हो जाएगा। मेमोरी भरने में समय लगता है, यह प्रीप्रोसेसर परिभाषित में लपेटा जाता है, इसलिए इसे वांछित होने पर ही संकलित किया जाता है।

+1

'मॉलोक (0)' का व्यवहार कार्यान्वयन परिभाषित किया गया है। यह या तो डेटा के शून्य बाइट्स के लिए एक नल पॉइंटर या गैर-शून्य सूचक देता है (जो, ज़ाहिर है, आप कभी भी अपमान नहीं कर सकते)। सी 99 §7.20.3 मेमोरी प्रबंधन फ़ंक्शन: "यदि अनुरोधित स्थान का आकार शून्य है, तो व्यवहार कार्यान्वयन कार्यान्वित किया गया है: या तो एक शून्य सूचक वापस आ गया है, या व्यवहार ऐसा है जैसे आकार nonzero मान था, सिवाय इसके कि लौटा सूचक का उपयोग किसी ऑब्जेक्ट तक पहुंचने के लिए नहीं किया जाएगा। " –

2
प्रश्न 1 के लिए

। यह एक वैध सूचक वापस कर सकता है या यह वापस लौट सकता है। अलग-अलग कार्यान्वयन अलग-अलग होते हैं ताकि लगातार व्यवहार प्राप्त करने के लिए कोड malloc(1) पर वापस आ जाए।

प्रश्न 3 के लिए:

यह कुछ 'अजीब' के लिए बफर की सामग्री को निर्धारित करता है। इस तरह, आपका कोड उम्मीद है कि सामग्री पर कुछ निर्भर नहीं है (जो मॉलोक गारंटी नहीं देता है)।

+0

क्या आप इस रैपर का उपयोग करने की सलाह देते हैं? –

+0

@Appu - 0 से 1 को बदलना और मेमसेट करना ठीक है। ओओएम नीति पर मरने पर निर्भर करता है कि आप क्या लिख ​​रहे हैं। नीति कमांड लाइन उपयोगिता के लिए ठीक है जो एक चीज करता है और बाहर निकलती है। पॉलिसी लंबे समय तक रहने वाले सर्वर के लिए ठीक हो सकती है या नहीं भी हो सकती है (क्या आप प्रक्रिया से बाहर निकलना चाहते हैं या आप वर्तमान अनुरोध को साफ करना चाहते हैं और पुनः प्रयास करें)। नीति सामान्य पुस्तकालय के लिए स्वीकार्य नहीं है क्योंकि ओओएम पर नीति मुख्य आवेदन द्वारा तय की जानी चाहिए। –

+0

अच्छा बिंदु। जो कोड मैं लिखूंगा वह पुस्तकालय के लिए है। तो मुझे लगता है कि मुझे 'मरने' से बचना चाहिए। –

1

मैं इस आवरण से परिचित नहीं हूँ, लेकिन यहाँ क्या अपने कर

1 है - अगर आकार = 0 तब निर्दिष्ट किया गया था यह 1 बाइट के बजाय आवंटित अगर अंतर्निहित malloc नहीं किया तो

इस संभवतः है किया ताकि एक फोन करने वाले अभी भी मुक्त उस पर (realloc) की तरह कर सकते हैं

2 मुझे लगता है अपनी स्मृति के लिए कठिन

3 XMALLOC_POISON बलों देखने के लिए अंतर्निहित स्मृति सबसिस्टम मजबूर करने के लिए एक ज्ञात राज्य के लिए बफ़र की कोशिश करने के अनियमित डेटा

दूसरा कारण - आप मॉलोक को लपेटना क्यों चाहते हैं, यह अजीब बग को रोकने और पहचानने के लिए यह सामान्य अभ्यास है। आप जो करना चाहते हैं उसके विचार से शुरू करें और फिर इसे कार्यान्वित करें या कार्यान्वयन की प्रतिलिपि बनाएँ। malloc लपेटकर के लिए कारण

  1. रिसाव का पता लगाना
  2. उपयोग विश्लेषण
  3. पूलिंग
  4. डिबगिंग (XMALLOC_POISON की तरह)
  5. से लागू

जाँच स्मृति इनमें से लगभग सभी के साथ किया जा सकता है valgrind - जो बहुत कुछ करता है।

'ठोस कोड लिखने' पुस्तक मौजूदा जटिल कार्यक्रमों के कोड को पढ़ने के लिए 1,4 और 5

+0

उत्तर के लिए धन्यवाद। ईमानदारी से, मैं सी दुनिया में थोड़ा खो गया हूँ। तो मुझे गलतियों से बचने के लिए, मैं अन्य प्रोग्राम कोड पढ़ रहा हूं और यह पता लगा रहा हूं कि वे कोड कैसे लिखते हैं। –

+2

"यह संभवतः किया जाता है ताकि एक कॉलर अभी भी इस पर मुक्त हो सके" - आप अभी भी एक शून्य सूचक पर मुफ्त या realloc कॉल कर सकते हैं। मुझे गिट के स्रोत को नहीं पता है, लेकिन यह सुनिश्चित करने के लिए यह किया जाता है कि 0 रिटर्न निश्चित रूप से कॉलर द्वारा त्रुटि के रूप में व्यवहार किया जा सकता है, भले ही इनपुट 0 था। या संभवतः यह सुनिश्चित करने के लिए कि पॉइंटर्स अलग-अलग 0- आकार आवंटन अलग तुलना करते हैं ("यह आपका शून्य आकार का बफर नहीं है, इसलिए यह आपका सूटकेस नहीं होना चाहिए!")। –

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