2012-03-10 12 views
37

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

दूसरे शब्दों में सर्वर कुछ पथ/tmp/सॉकेट से जुड़ी एक सॉकेट बनाता है। 2 या अधिक ग्राहक/tmp/सॉकेट से कनेक्ट होते हैं। नीचे क्या चल रहा है जो क्लाइंट 1 और क्लाइंट 2 से डेटा का ट्रैक रखता है? मुझे लगता है कि नेटवर्क स्टैक डोमेन सॉकेट में कोई हिस्सा नहीं निभाता है, तो क्या कर्नेल यहां सभी काम कर रहा है?

क्या कोई यूनिक्स डोमेन प्रोटोकॉल प्रारूप है जैसे आईपी प्रोटोकॉल प्रारूप और टीसीपी/यूडीपी प्रारूप है? डोमेन सॉकेट डेटाग्राम प्रोटोकॉल का प्रारूप कहीं प्रकाशित है? क्या प्रत्येक यूनिक्स अलग है या POSIX की तरह कुछ ऐसा करता है?

किसी भी रोशनी के लिए धन्यवाद। मुझे यह जानकारी समझाई गई कोई जानकारी नहीं मिली। प्रत्येक स्रोत सिर्फ डोमेन सॉकेट का उपयोग करने के तरीके पर चमक गया।

+0

यूनिक्स डोमेन प्रोटोकॉल पर बात करना मूल रूप से केवल फ़ाइल I/o है। जब तक कि आप सॉकेट के माध्यम से गुज़रने वाले डेटा में स्रोत पहचान नहीं रखते हैं, तब तक यह बताने का कोई तरीका नहीं है कि किस प्रक्रिया ने एक विशेष स्ट्रिंग को भेजा है। –

+0

@MarcB जो उत्तर होना चाहिए –

+3

क्या यह सच हो सकता है? यदि कोई सर्वर डेटा लिखता है जो पढ़ता है तो पहला क्लाइंट उस डेटा को ध्यान में रखता है चाहे वह उस ग्राहक के लिए था या नहीं? इससे उन्हें लगभग बेकार बना दिया जाता है। –

उत्तर

62

आप प्रकार SOCK_STREAM के PF_UNIX सॉकेट बनाने के लिए, और उस पर कनेक्शन स्वीकार करते हैं, तो हर बार जब आप एक कनेक्शन स्वीकार करते हैं, आप (accept प्रणाली कॉल के रिटर्न मान के रूप में) एक नई फ़ाइल वर्णनकर्ता मिलता है। यह फ़ाइल डिस्क्रिप्टर क्लाइंट प्रक्रिया में फ़ाइल डिस्क्रिप्टर को डेटा से डेटा पढ़ता है और लिखता है। इस प्रकार यह एक टीसीपी/आईपी कनेक्शन की तरह काम करता है।

कोई "यूनिक्स डोमेन प्रोटोकॉल प्रारूप" नहीं है। ऐसा करने की आवश्यकता नहीं है, क्योंकि एक यूनिक्स-डोमेन सॉकेट किसी नेटवर्क कनेक्शन पर एक सहकर्मी से कनेक्ट नहीं किया जा सकता है। कर्नेल में, फाइल डिस्क्रिप्टर SOCK_STREAM यूनिक्स-डोमेन सॉकेट पॉइंट्स के डेटा अंतराल पर आपके अंत का प्रतिनिधित्व करता है जो कर्नेल को बताता है कि फ़ाइल डिस्क्रिप्टर कनेक्शन के दूसरे छोर पर है। जब आप अपनी फ़ाइल डिस्क्रिप्टर को डेटा लिखते हैं, तो कर्नेल कनेक्शन के दूसरे छोर पर फ़ाइल डिस्क्रिप्टर को देखता है और डेटा को उस अन्य फ़ाइल डिस्क्रिप्टर के रीड बफर में जोड़ता है। कर्नेल को अपने डेटा को पैकेट के अंदर अपने गंतव्य का वर्णन करने वाले हेडर के साथ रखने की आवश्यकता नहीं है।

SOCK_DGRAM सॉकेट के लिए, आपको कर्नेल को उस सॉकेट के पथ को बताना होगा जो आपके डेटा को प्राप्त करना चाहिए, और यह उस सॉकेट प्राप्त करने के लिए फ़ाइल डिस्क्रिप्टर को देखने के लिए उपयोग करता है।

आप अपने ग्राहक सॉकेट करने के लिए एक रास्ता बाँध इससे पहले कि आप सर्वर सॉकेट से कनेक्ट (या इससे पहले कि आप अगर आप SOCK_DGRAM उपयोग कर रहे हैं डेटा भेजने), तो सर्वर प्रक्रिया है कि पथ getpeername (SOCK_STREAM के लिए) का उपयोग कर प्राप्त कर सकते हैं। SOCK_DGRAM के लिए, प्राप्त करने वाला पक्ष भेजने की सॉकेट का मार्ग प्राप्त करने के लिए recvfrom का उपयोग कर सकता है।

यदि आप पथ को बांध नहीं पाते हैं, तो प्राप्त करने की प्रक्रिया एक आईडी नहीं मिल सकती है जो विशिष्ट रूप से सहकर्मी की पहचान करती है। कम से कम, लिनक्स कर्नेल पर नहीं चल रहा है (2.6.18-238.19.1.el5)।

+0

एक उत्कृष्ट और पूर्ण उत्तर के लिए धन्यवाद। –

+0

ग्रेट उत्तर। धन्यवाद @rob – nic

+0

लिनक्स में AF_UNIX के लिए SOCK_SEQPACKET भी है जो SOCK_STREAM में कनेक्शन की अनुमति देता है, लेकिन SOCK_DGRAM में संदेश सीमाएं भी संरक्षित करता है। –

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