2012-12-01 19 views
5

सी ++ के साथ गेम बनाने के लिए राज्यों का अध्ययन करते समय मैं कॉलिंग सम्मेलनों में आया हूं।सादा और सरल, हम _stdcall का उपयोग क्यों करते हैं?

पिछले प्रश्न में किसी ने कहा था कि एमएसडीएन _stdcall को अच्छी तरह से समझा नहीं है - मैं सहमत हूं।

_stdcall जैसे सम्मेलनों को कॉल करने के प्राथमिक उद्देश्य क्या हैं? क्या इससे कोई फर्क पड़ता है कि स्टैक पर तर्क किस क्रम में रखा गया है? यह X86 में कोड के आकार को कैसे कम करता है (जैसा कि किसी और ने कहा है)?

+3

यदि किसी फ़ंक्शन में कई तर्क और कई कॉलर हैं, तो कैली के लिए कई जगहों पर प्रत्येक कॉलर की बजाय स्टैक को साफ करने के लिए यह समझ में आता है। – ildjarn

+0

क्या आप इस बारे में पूछ रहे हैं कि विभिन्न कॉलिंग सम्मेलनों के डिजाइन ने क्या किया है, या उन्हें निर्दिष्ट करने की आवश्यकता क्यों है? – StoryTeller

+0

अधिकतर लोग वास्तव में क्यों उपयोग किए जाते हैं, सरल लोगों की बात करते हैं: पी एमएसडीएन काफी जटिल था और ऐसा लगता है कि बहुत से लोग उलझन में हैं! – Dezachu

उत्तर

8

रखने का कारण कुछ कॉलिंग सम्मेलन बहुत आसान है: ताकि कॉलर और कैली सहमत हों कि चीजें कैसे काम करती हैं। इसके बिना, कॉलर को यह नहीं पता कि जब यह किसी विशेष फ़ंक्शन को कॉल कर रहा है तो तर्क कहां रखना है।

माइक्रोसॉफ्ट ने _stdcall के विशिष्ट विवरणों पर क्यों निर्णय लिया, यह है जो ऐतिहासिक है। एमएस-डॉस पर, सभी कॉल पंजीकृत थे, इसलिए सभी ओएस कॉलों को असेंबली भाषा, या अधिकतर उच्च-स्तरीय भाषाओं में अजीब एक्सटेंशन की आवश्यकता होती है।

जब उन्होंने पहली बार विंडोज किया, तो उन्होंने cdecl कॉलिंग सम्मेलन का उपयोग किया, क्योंकि ज्यादातर संकलक डिफ़ॉल्ट रूप से करते थे। कम से कम अफवाह के मुताबिक, विंडोज 1.0 जारी करने के लिए तैयार होने से कुछ समय पहले, वे पास्कल कॉलिंग कन्वेंशन में चले गए क्योंकि यह काफी कुशल था कि (अन्य चीजों के साथ) यह विंडोज को एक छोटी फ्लॉपी डिस्क पर फिट करने की इजाजत देता था। सटीक विवरणों के बावजूद, पास्कल कॉलिंग सम्मेलन ने कोड को थोड़ा छोटा बना दिया, क्योंकि बुलाए गए फ़ंक्शन को हर जगह इसे साफ़ करने की आवश्यकता के बजाय स्टैक से तर्कों को साफ कर दिया गया था। किसी भी समारोह के लिए जिसे कम से कम 2 अलग-अलग स्थानों से बुलाया गया था, यह एक जीत है (और यदि यह कहीं और बांधती है)।

फिर उन्होंने ओएस/2 पर काम करना शुरू किया, और अभी तक एक और कॉलिंग सम्मेलन (syscall) का आविष्कार किया।

फिर, निश्चित रूप से, Win32 आया। तकनीकी दृष्टिकोण से सिस्कल के साथ वास्तव में बहुत कुछ गलत नहीं था, लेकिन (मुझे लगता है) ओएस/2 से जुड़े सबकुछ को दंडित माना जाता था, इसलिए सिस्कल को जाना पड़ा। परिणाम एक नया नाम औचित्य देने के लिए बस कुछ अलग था। निष्पक्षता में, यह एक असाधारणता का एक छोटा सा हिस्सा है: उन्होंने एक वास्तव में उपयोगी जोड़ जोड़ा है: उन्होंने प्रत्येक फ़ंक्शन नाम में तर्कों के बाइट्स की संख्या को एन्कोड किया है, इसलिए यदि (उदाहरण के लिए) आपने फ़ंक्शन के लिए गलत प्रोटोटाइप प्रदान किया है, तो कोड होगा कॉलर और कैली के बीच एक विसंगति के साथ समाप्त होने के बजाय लिंक नहीं है जो अधिक गंभीर समस्याओं का कारण बन सकता है।

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

+0

अहह, यह बताता है कि 5 क्यों पहले स्थान पर मौजूद हैं; मैंने सोचा होगा कि वे उस व्यक्ति को बनाए रखेंगे जो सबसे कुशल और अद्यतन और शेष स्क्रैप करता है! चीयर्स। यह अभी भी स्पष्ट नहीं है कि हमें एक का उपयोग करने की आवश्यकता क्यों है? क्या यह पूरी तरह से है क्योंकि विभिन्न कंपाइलर्स अलग-अलग डिफ़ॉल्ट कॉलिंग सम्मेलनों का उपयोग करते हैं, इसलिए एक निर्दिष्ट करके हम सभी कंपाइलर्स/ओएस में एक समान कॉल विधि का उपयोग करते हैं? यदि हां, तो क्या यह मेरे लिए उपयोग करने के लिए एक अच्छा अभ्यास है? या मुझे अपनी शिक्षा के दौरान उनके बारे में चिंता नहीं करनी चाहिए? – Dezachu

+0

कॉलिंग सम्मेलन उन चीजों में से एक हैं जो कंपाइलर लेखकों पर बहस करते हैं ताकि वे ऊब जाएंगे :) यह एक निम्न स्तर का विवरण है जिसे आप लंबे समय तक सुरक्षित रूप से अनदेखा कर सकते हैं। –

+0

भी, कुछ कॉलिंग सम्मेलन अतिरिक्त "विशेषताओं" प्रदान करने में सहायता करते हैं कि अन्य कॉलिंग सम्मेलन प्रदान करने के लिए कठिन नहीं हो सकते हैं या नहीं मिल सकते हैं। उदाहरण के लिए, 'cdecl' कॉलर के बजाय कॉलर पर स्टैक क्लीनअप रखता है। यह आसानी से परिवर्तनीय लंबाई तर्कों को सुविधाजनक बनाता है क्योंकि केवल कॉलर जानता है कि ढेर कितना बड़ा होगा। इस मामले में कॉलर एकमात्र ऐसा व्यक्ति है जो जानता है कि ढेर को कैसे साफ किया जाए और इसके लिए भी जिम्मेदार है। 'Stdcall' के लिए, यह काम करने का एकमात्र तरीका यह है कि अगर कॉलर ने 'कैली' को अधिसूचित किया कि कितना बड़ा ढेर होगा, लेकिन मैंने इसे इस तरह से लागू नहीं देखा है। –