ar
लिनक्स में, ar
GNU सामान्य प्रयोजन अभिलेखागार है। ( ar
अन्य यूनिक्स जैसे ओएस में गैर-जीएनयू संस्करण हैं )। विकल्प के साथc
ar c... archive-name file...
यह एक संग्रह बनाता है जिसकी प्रतियां हैं file...
। archive-name
पारंपरिक लेकिन जरूरी नहीं कि एक्सटेंशन है .a
(के लिए संग्रह )। प्रत्येक file...
किसी भी तरह की फाइल हो सकती है, जरूरी नहीं कि वह ऑब्जेक्ट फाइल हो।
जब संग्रहीत फ़ाइलें सभी ऑब्जेक्ट फ़ाइलें होती हैं, तो यह आमतौर पर प्रोग्राम या DSO (डायनेमिक शेयर्ड ऑब्जेक्ट्स) के लिंकेज में ऑब्जेक्ट फ़ाइलों के उस चयन को वितरित करने के लिए संग्रह का उपयोग करने का इरादा होता है। इस मामले archive-name
में भी पारंपरिक रूप से उपसर्ग दिया जाएगा lib
, उदाहरण के लिए
libfoo.a
, ताकि यह लिंक विकल्प के माध्यम से एक उम्मीदवार लिंकर इनपुट फ़ाइल के रूप में खोजा जा सके -lfoo
।
लिंकर इनपुट फ़ाइल के रूप में उपयोग किया libfoo.a
जाता है , जिसे आम तौर पर एक स्थिर पुस्तकालय कहा जाता है । यह उपयोग अनुभवहीन प्रोग्रामरों के लिए भ्रम का एक स्थायी स्रोत है, क्योंकि यह उन्हें सोचने के लिए प्रेरित करता है कि एक संग्रह libfoo.a
एक डीएसओ के रूप में एक ही तरह की चीज है libfoo.so
, जिसे आमतौर पर एक गतिशील / साझा पुस्तकालय कहा जाता है , और इस आधार पर झूठी अपेक्षाओं का निर्माण करना है। वास्तव में एक "स्टैटिक लाइब्रेरी" और एक "डायनेमिक लाइब्रेरी" सभी समान चीजों पर नहीं होती हैं और इनका उपयोग पूरी तरह से अलग-अलग तरीकों से लिंकेज में किया जाता है।
एक विशिष्ट अंतर यह है कि लिंकर द्वारा एक स्थिर पुस्तकालय का उत्पादन नहीं किया जाता है , लेकिन इसके द्वारा ar
। तो कोई जुड़ाव नहीं होता, कोई प्रतीक संकल्प नहीं होता। संग्रहीत ऑब्जेक्ट फ़ाइलें अपरिवर्तित हैं: उन्हें बस एक बैग में रखा गया है।
जब एक संग्रह कुछ है कि के संबंध में इनपुट है है इस तरह के कार्यक्रम या DSO के रूप में - - लिंकर द्वारा उत्पादित बैग में लिंकर दिखता है, तो उसमें किसी भी वस्तु फ़ाइलें जो अनसुलझे प्रतीक संदर्भ एकत्रित कर लेते हैं के लिए परिभाषा प्रदान करते हैं को देखने के लिए इससे पहले लिंकेज में। यदि यह किसी को भी पाता है, तो यह बैग से उन ऑब्जेक्ट फ़ाइलों को निकालता है और उन्हें आउटपुट फाइल में जोड़ता है , ठीक उसी तरह जैसे कि उन्हें लिंकर कमांडलाइन में व्यक्तिगत रूप से नामित किया गया था और संग्रह का उल्लेख नहीं किया गया था। इसलिए लिंकेज में एक संग्रह की पूरी भूमिका वस्तु फ़ाइलों के बैग के रूप में है जिससे लिंकर उन लोगों का चयन कर सकता है जिन्हें लिंकेज पर ले जाने की आवश्यकता है।
डिफ़ॉल्ट रूप से, GNU ar
अपने आउटपुट अभिलेखागार को लिंकर इनपुट के रूप में उपयोग के लिए तैयार करता है। यह एक जादू टोनी फ़ाइलनाम के साथ संग्रह में एक "नोनी" फ़ाइल जोड़ता है, और इस फ़ॉनी फ़ाइल में यह सामग्री लिखता है कि लिंकर वैश्विक प्रतीकों से एक लुकअप तालिका के रूप में पढ़ने में सक्षम है जो संग्रह में किसी भी ऑब्जेक्ट फ़ाइलों द्वारा परिभाषित किया गया है। संग्रह में उन ऑब्जेक्ट फ़ाइलों के नाम और स्थिति। यह लुकअप टेबल वही है जो लिंकर को आर्काइव में देखने और किसी भी ऑब्जेक्ट फाइल की पहचान करने में सक्षम बनाता है जो किसी भी अप्रचलित प्रतीक संदर्भ को परिभाषित करता है जो इसे हाथ में मिला है।
आप q
(=
त्वरित ) विकल्प के साथ इस लुकअप तालिका के निर्माण या अद्यतन को दबा सकते हैं - जो वास्तव में आपने अपने ar
उदाहरण में उपयोग किया है - और (राजधानी) S
(= कोई प्रतीक तालिका ) विकल्प के साथ भी। और यदि आप ar
किसी भी कारण से एक संग्रह (अपटूडेट) प्रतीक तालिका बनाने या अद्यतन करने के लिए आमंत्रित करते हैं, तो आप इसे s
विकल्प के साथ दे सकते हैं ।
ranlib
ranlib
लाइब्रेरी बिल्कुल नहीं बनाता है। लिनक्स में, ranlib
एक विरासत कार्यक्रम है जो एक (uptodate) प्रतीक तालिका को एक ar
संग्रह में जोड़ता है यदि इसमें एक नहीं है। यह प्रभाव ठीक उसी तरह है ar s
, जैसे GNU के साथ होता है ar
। ऐतिहासिक रूप से, इससे पहले ar
कि खुद एक प्रतीक तालिका उत्पन्न करने के लिए सुसज्जित किया ranlib
गया था , वह कीचड़ था जो लिंक से ऑब्जेक्ट फ़ाइलों को लेने में सक्षम करने के लिए मैजिक फॉनी फाइल को एक संग्रह में इंजेक्ट करता था। गैर-जीएनयू यूनिक्स जैसे OSes में, ranlib
इस उद्देश्य के लिए अभी भी आवश्यक हो सकता है। आपका उदाहरण:
ar qc libgraphics.a *.o
ranlib libgraphics.a
कहते हैं:
libgraphics.a
किसी *.o
भी प्रतीक तालिका के साथ, वर्तमान निर्देशिका की सभी फ़ाइलों को संग्रह में जोड़कर बनाएँ ।
- फिर एक प्रतीक तालिका जोड़ें
libgraphics.a
लिनक्स में, इसका समान शुद्ध प्रभाव है:
ar cr libgraphics.a *.o
अपने आप से, ar qc libgraphics.a *.o
एक संग्रह बनाता है जिसे लिंकर उपयोग नहीं कर सकता है, क्योंकि इसमें कोई प्रतीक तालिका नहीं है।
ld
आपका उदाहरण:
ld -r -o libgraphics.a *.o
वास्तव में काफी अपरंपरागत है। यह लिंकर के काफी दुर्लभ उपयोग का चित्रण करता है ,
ld
एक इनपुट ऑब्जेक्ट फाइल को एक आउटपुट आउटपुट फाइल में लिंक करके एक मर्ज किए गए ऑब्जेक्ट फ़ाइल का उत्पादन करने के लिए, जिसमें इनपुट फ़ाइलों को देखते हुए प्रतीक रिज़ॉल्यूशन को यथासंभव संभव किया गया है । -r
(= पुनर्निधारणीय ) विकल्प लिंकर linkaqe विफल अगर अपरिभाषित प्रतीक संदर्भ आउटपुट फ़ाइल में रहते हैं जहाँ तक संभव हो और नहीं आदानों जोड़ने के द्वारा एक वस्तु फ़ाइल लक्ष्य (बजाय एक प्रोग्राम, या DSO) का निर्माण करने के निर्देश देता है। इस उपयोग को आंशिक लिंकिंग कहा जाता है ।
की आउटपुट फ़ाइल ld -r ...
एक ऑब्जेक्ट फ़ाइल है, न कि एक ar
आर्काइव , और एक आउटपुट फ़ाइल नाम निर्दिष्ट करता है, जो दिखता है कि ar
संग्रह एक जैसा नहीं है। तो आपका उदाहरण एक धोखे को दिखाता है। इस:
ld -r -o graphics.o *.o
सत्य होगा। यह मेरे लिए अस्पष्ट है कि इस तरह के धोखे का उद्देश्य क्या हो सकता है, क्योंकि भले ही एक ईएलएफ ऑब्जेक्ट फ़ाइल कहा जाता है libgraphics.a
, और उस नाम से या तो लिंकेज के लिए इनपुट है, या -lgraphics
लिंकर ईएलएफ ऑब्जेक्ट फ़ाइल के रूप में सही पहचान करेगा , एक ar
संग्रह नहीं , और इसे कमांड लाइन में किसी भी ऑब्जेक्ट फ़ाइल का उपभोग करने के तरीके का उपभोग करेगा: यह इसे बिना शर्त के आउटपुट फ़ाइल में जोड़ता है, जबकि एक वास्तविक संग्रह को इनपुट करने का उद्देश्य संग्रह सदस्यों को केवल इस शर्त पर लिंक करना है कि वे संदर्भित हैं । शायद आपके पास यहां पर अनौपचारिक लिंकिंग का एक उदाहरण है।
समेट रहा हु...
हमने वास्तव में केवल कुछ का उत्पादन करने का एक तरीका देखा है जिसे पारंपरिक रूप से एक पुस्तकालय कहा जाता है , और यह कुछ ऑब्जेक्ट फ़ाइलों को संग्रह करके और संग्रह में एक प्रतीक तालिका डालकर, तथाकथित स्थिर पुस्तकालय का उत्पादन है ।
और हमने बिल्कुल नहीं देखा है कि दूसरे और सबसे महत्वपूर्ण तरह की चीज़ का उत्पादन कैसे किया जाता है , जिसे पारंपरिक रूप से एक पुस्तकालय कहा जाता है , जिसका अर्थ है एक गतिशील साझा वस्तु / साझा पुस्तकालय / गतिशील पुस्तकालय।
प्रोग्राम की तरह, लिंकर द्वारा एक डीएसओ का उत्पादन किया जाता है । एक प्रोग्राम और एक DSO ELF बाइनरी के वेरिएंट हैं जिन्हें OS लोडर समझता है और एक रनिंग प्रोसेस को असेंबल करने के लिए उपयोग कर सकता है। आम तौर पर हम एक जीसीसी फ़्रंटएंड्स में से एक (के माध्यम से लिंकर आह्वान gcc
, g++
, gfortran
, आदि):
एक कार्यक्रम को जोड़ना:
gcc -o prog file.o ... -Ldir ... -lfoo ...
एक डीएसओ को जोड़ना:
gcc -shared -o libbar.so file.o ... -Ldir ... -lfoo ...
-lfoo
जब आप किसी अन्य प्रोग्राम या DSO को लिंक कर रहे हों, तब साझा लाइब्रेरी और स्टैटिक लाइब्रेरी दोनों को लिंकर के लिए एक समान प्रोटोकॉल द्वारा पेश किया जा सकता है । यह विकल्प लिंकर को अपने निर्दिष्ट या डिफ़ॉल्ट खोज निर्देश को libfoo.so
या तो खोजने के लिए स्कैन करने का निर्देश देता है
libfoo.a
। डिफ़ॉल्ट रूप से, एक बार जब यह उनमें से किसी एक को खोज लेता है, तो यह उस फ़ाइल को लिंकेज में इनपुट कर देगा, और यदि यह दोनों एक ही खोज निर्देशिका में पाता है, तो यह पसंद करेगा libfoo.so
। यदि libfoo.so
चयनित है, तो लिंकर उस DSO को रनटाइम निर्भरता सूची में जोड़ता है जो भी प्रोग्राम या DSO आप बना रहे हैं। यदि libfoo.a
चुना जाता है, तो लिंकर आउटपुट फ़ाइल में लिंकेज के लिए ऑब्जेक्ट फ़ाइलों के चयन के रूप में संग्रह का उपयोग करता है, यदि आवश्यक हो, तो वहीं और फिर। कोई रनटाइम निर्भरता नहीं
libfoo.a
स्वयं संभव है; इसे एक प्रक्रिया में मैप नहीं किया जा सकता है; इसका मतलब ओएस लोडर से कुछ भी नहीं है।
Https://stackoverflow.com/a/47924864/195787 से कॉपी किया गया ।