एएससीआईआई से उन्नत सीरियल प्रोटोकॉल पर कब स्विच करना चाहिए?


28

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

बुनियादी ASCII संचार कब स्वीकार्य है और मुझे मॉडबस की तरह कुछ और उन्नत पर विचार करना चाहिए? क्या वाणिज्यिक उपकरण ऐसे ASCII का उपयोग करते हैं? औद्योगिक?


3
संक्षिप्त उत्तर: जब आपके आवेदन को इसकी आवश्यकता हो। हां, वाणिज्यिक उपकरण ASCII का उपयोग करते हैं। उदाहरण के तौर पर GPS NMEA को लें। (और फिर से, मैं अपने स्वयं के प्रश्न का उल्लेख यहां करूंगा )
यूजीन श।


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

जवाबों:


28
  1. ASCII और CRC परस्पर अनन्य नहीं हैं। ASCII एक एन्कोडिंग है, और CRC त्रुटि जाँच के लिए है।

  2. कुछ भी ASCII के रूप में भेजा जा सकता है। बूढ़े लोग निश्चित रूप से UUEncoding को याद करते हैं, जो कुछ भी ASCII स्ट्रिंग में बदल जाता है।

  3. ए) मेरे लिए, यह आमतौर पर गति और दक्षता का सवाल है। एएससीआईआई द्वारा एक बड़ी 32-बिट संख्या भेजने में एक लंबा समय लग सकता है, लेकिन इसे सीरियल प्रोटोकॉल के माध्यम से बाइनरी के रूप में भेजने के लिए केवल 4 बाइट्स लगते हैं।

    B) ASCII के माध्यम से NUMBERS भेजने का मतलब है कि आपको नंबर को ASCII में बदलना होगा, जो कि एक स्पष्ट अतिरिक्त कदम है (यह "प्रिंटफ" क्या करता है) का एक हिस्सा है।

  4. यदि आप किसी तरह अपनी जगह खो देते हैं, तो पेंच करें, प्रारूप खो दें, गलत एंडियन प्राप्त करें, आदि, एक बाइनरी संचार प्रोटोकॉल निश्चित रूप से खराब हो सकता है। यदि आप ASCII भेज रहे हैं, तो डेटा स्‍ट्रीम में बस और अंदर जाकर स्क्रूअप से उबरना आसान हो सकता है।


12
"ASCII एक एन्कोडिंग है" के लिए +1। यह एक प्रोटोकॉल नहीं है; प्रोटोकॉल ASCII के शीर्ष पर बनाए जा सकते हैं।
पीट बेकर

8
स्वचालित रूप से एक स्क्रू से पुनर्प्राप्त करना आंतरिक रूप से पाठ-आधारित प्रोटोकॉल के लिए द्विआधारी के रूप में कोई आसान नहीं है, लेकिन निरीक्षण करना और डिबग करना निश्चित रूप से नहीं है।
निक जॉनसन

1
@NickJohnson - बिल्कुल। एक बार जब आप एक हेक्स संपादक में एक फ़ाइल खोलने के बिंदु पर होते हैं, तो आप देख सकते हैं कि आप क्या पुनर्प्राप्त कर सकते हैं, आप पहले से ही फ़ूबर में हैं जब तक एसओपी नहीं जाता है
स्कॉट सेडमन

1
@nickjohnson जो वास्तव में सच नहीं है। ASCII आपको सिंक्रोनाइज़ेशन और रिकवरी में सहायता करने के लिए बहुत सारे बैंड फ्रेमिंग / सीमांकक विकल्प देता है, जिसके लिए यदि चैनल का उपयोग पूर्ण चौड़ाई बाइनरी डेटा के लिए किया जाता है, तो अतिरिक्त पलायन, बिट स्टफिंग, समय अंतराल या अन्य चाल की आवश्यकता होगी।
क्रिस स्ट्रैटन

2
सभी स्पष्ट लाभों (पठनीयता, तर्कशीलता आदि) के लिए प्रोटोकॉल लिखते समय मैं हमेशा ASCII का पक्ष लेता हूं। कर रहे हैं दो मामले हैं जब द्विआधारी बनाता है और अधिक भावना: पहला, गति एक समस्या है और आप धारा में संभव के रूप में ज्यादा डेटा के रूप में रटना द्विआधारी की जरूरत है, और दूसरा, मामूली, अगर आप जानबूझकर अस्पष्ट या यहाँ तक कि डेटा एन्क्रिप्ट करने के प्रयास कर रहे हैं रिवर्स इंजीनियरिंग को रोकने या रोकने के लिए स्ट्रीम। उस समय, मेरे पास रिवर्स इंजीनियर बाइनरी प्रोटोकॉल हैं और इसने मुझे वास्तव में अधिनियम को रोकने की तुलना में अधिक परेशान किया है।
जे ...

10

यहाँ इसके बारे में कुछ विचार दिए गए हैं:

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

7

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

एप्लिकेशन लेयर वह परत है जो आप सीधे अपने कोड में, और प्रश्न पर केंद्रित करते हैं। जहां तक ​​ट्रांसपोर्ट लेयर की बात है, तो आपने जो बाइट सेंड_डाटा में दी थी, वह सिर्फ एक द्विआधारी पैटर्न है, लेकिन आप इसे अपने एप्लिकेशन कोड में 'ए' अक्षर के रूप में व्याख्या कर सकते हैं। सीआरसी या चेकसम की गणना समान होगी चाहे आप बाइट को 'ए', '0x41, या 0b01000001 मानते हों।

परिवहन परत पैकेट स्तर है, जहां आपके पास अपने संदेश हेडर हैं, और त्रुटि की जांच है, चाहे वह सीआरसी हो या एक बुनियादी चेकसम हो। फर्मवेयर के संदर्भ में, आपके पास send_data जैसे एक फ़ंक्शन हो सकता है, जहां आप इसे भेजने के लिए एक बाइट पास करते हैं। उस फ़ंक्शन के अंदर वह एक पैकेट में डालता है जो कहता है, "अरे यह एक सामान्य संदेश है, एक पावती की आवश्यकता है, और चेकसम 0x47 है, वर्तमान समय एक्स है।" यह पैकेट भौतिक परत पर प्राप्त नोड को भेजा जाता है।

भौतिक परत वह जगह है जहां इलेक्ट्रॉनिक्स और इंटरफ़ेस को परिभाषित किया गया है: कनेक्टर्स, वोल्टेज स्तर, समय, आदि। यह परत एक पीसीबी पर एक बुनियादी UART के लिए TTL संकेतों को चलाने वाले कुछ निशानों से लेकर पूरी तरह से अलग अंतर जोड़ी के रूप में हो सकती है। कार्यान्वयन कर सकते हैं।

प्राप्त नोड पर, पैकेट भौतिक परत पर आता है, परिवहन परत पर अनपैक किया जाता है, और फिर आपका बाइनरी पैटर्न एप्लिकेशन परत पर उपलब्ध होता है। यह पता करने के लिए कि क्या उस पैटर्न को 'ए,' 0x41, या 0b01000001 के रूप में समझा जाना चाहिए और इसके साथ क्या करना है, यह प्राप्त करने के लिए नोड एप्लिकेशन लेयर पर निर्भर है।

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


Ascii प्रोटोकॉल चेकसम को भी शामिल कर सकते हैं। मैंने संख्याओं के असिसी प्रतिनिधित्व का उपयोग करते हुए हेक्स-अस-असीसी विविधताओं का सामना किया है।
यूजीन श।

@EugeneSh। उस बिंदु को स्पष्ट किया
मैट यंग

नाइटपिक के लिए नहीं, लेकिन टीसीपी चार परतें नहीं हैं; इसे OSI मॉडल की परत चार में फिटिंग के रूप में देखा जाता है। सीरियल संचार वास्तव में OSI मॉडल को बहुत अच्छी तरह से फिट नहीं करता है।
बैट्सप्लाटर्स्सन

@batsplatsterson जो कि नाइटपैकिंग है, और मैं जिस बिंदु पर बना रहा हूं, उससे बहुत अच्छी तरह अप्रासंगिक है।
मैट यंग

5

एक बिंदु अभी तक उल्लेख नहीं किया गया है कि क्या कोई ASCII या बाइनरी प्रोटोकॉल का उपयोग कर रहा है, प्रत्येक पैकेट से पहले रगड़-आउट चरित्र भेजना सुनिश्चित करेगा कि भले ही लाइन शोर या फ़्रेमिंग त्रुटियां पैकेट की शुरुआत से पहले दिखाई दें, रगड़ के बाद सभी वर्ण आगे शोर की अनुपस्थिति में सही ढंग से फंसाया जाएगा। अन्यथा, यदि कोई लगातार पैकेट भेजता है और इसमें कोई भी वर्ण शामिल नहीं है जो कि resynchrononization को प्राप्त करने की गारंटी है, तो संभव है कि एक गड़बड़ सब कुछ भ्रष्ट कर सकती है जो ट्रांसमिशन में अगले ठहराव तक चलती है। 0xFF वर्ण अच्छा है क्योंकि यह गारंटी देता है कि कोई भी प्राप्तकर्ता निम्न वर्ण पर पुन: सिंक्रनाइज़ करने में सक्षम होगा।

(*) 0xFF - रुब-आउट कहलाता है क्योंकि कोई व्यक्ति जो एक पेपर टेप पर डेटा टाइप करते समय एक त्रुटिपूर्ण चरित्र टाइप करता है, "स्टेप टेप बैकवर्ड" बटन को धक्का दे सकता है और गलत तरीके से छिद्रित वर्ण को 0xFF के साथ बदलने के लिए रग-आउट कर सकता है, जो होगा अधिकांश प्राप्तकर्ताओं द्वारा अनदेखा किया जाना)।


2

ASCII तार भेजने का एक फायदा यह है कि नियंत्रण कोड का उपयोग संदेश के प्रारंभ / समाप्ति को इंगित करने के लिए किया जा सकता है। उदाहरण के लिए STX (char 2) और ETX (char 3) ट्रांसमिशन और एंड ट्रांसमिशन को सिग्नल दे सकते हैं। वैकल्पिक रूप से आप ट्रांसमिशन के अंत को चिह्नित करने के लिए एक सरल रेखा फ़ीड जोड़ सकते हैं।

बाइनरी डेटा भेजते समय यह अधिक जटिल हो जाता है क्योंकि कोई विशेष बिट पैटर्न नियंत्रण कोड (कुछ अतिरिक्त ओवरहेड या जटिलता के बिना) के लिए आरक्षित नहीं हो सकता है क्योंकि वैध डेटा बाइट में समान पैटर्न हो सकता है।


3
कई बाइनरी प्रोटोकॉल नियंत्रण कोड के रूप में एक या एक से अधिक बिट पैटर्न आरक्षित करते हैं, लेकिन वे डेटा में दिखाई देने पर उन कोड को संभालने के लिए एक एस्केप मैकेनिज्म भी शामिल करते हैं।
डेव ट्वीड

आप किसी भी पैटर्न को बाइनरी में इच्छित किसी भी झंडे के लिए आरक्षित कर सकते हैं। उदाहरण के लिए, मैं एक तेज़ डेटा स्ट्रीम और एक धीमी डेटा स्ट्रीम के साथ एक प्रोजेक्ट पर हूं, जो एक ही uart है। मैंने अपने धीमे डेटा के लिए एक ध्वज के रूप में सबसे बड़ा नकारात्मक int32 आरक्षित किया, और सबसे बड़े नकारात्मक + 1 पर सिर्फ अपने नकारात्मक डेटा को संतृप्त किया
स्कॉट सीडमैन

माना। मैंने इसे संपादित उत्तर में स्पष्ट किया, मुझे आशा है।
ट्रांजिस्टर

2

ASCII बस ठीक है, मैं इसे केवल सभी परियोजनाओं के बारे में उपयोग करता हूं। यह पोर्ट की निगरानी के लिए डिबगिंग को बहुत आसान बनाता है, और यह केवल एक मुद्दा बन जाएगा यदि भेजने के लिए बहुत अधिक डेटा था।

एक और बोनस, मैं arduinos के बीच संदेश प्राप्त करने के लिए धारावाहिक रेडियो उपकरणों का उपयोग करता हूं, और मैं अपने लैपटॉप से ​​जुड़े एक धारावाहिक मॉनिटर का उपयोग कर सकता हूं और कुछ चीजें होने के लिए संदेशों को इंजेक्ट कर सकता हूं। परीक्षण के लिए महान।

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


2

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

मैंने RS-485 नेटवर्क में HDLC का उपयोग बिना किसी समस्या के किया है और पीपीपी भी इसका उपयोग करता है।


2
अच्छा होगा यदि आपने बताया कि आप इसे मोडबस पर क्यों सुझाव देते हैं।
मुझे पता नहीं है कि मैं

1

UART पर ASCII आंशिक रूप से सबसे लोकप्रिय है क्योंकि:

  • यह डीबगिंग के समय मानव पठनीय है (मुझे अभी तक एक तर्क विश्लेषक को देखना है जो ASCII को डिकोड नहीं करता है)।

  • इसे लागू करना बहुत आसान है, आपको त्वरित Google के माध्यम से एक ASCII तालिका मिली है जो अच्छी तरह से मानकीकृत है।

  • यह स्टार्ट / स्टॉप बिट्स के साथ सिंक्रनाइज़ेशन में बनाया गया है।

  • बहुत ज्यादा पूरी हॉबीस्ट दुनिया ने सीरियल के ऊपर ASCII के साथ खुद को स्थापित किया है, इसलिए किसी भी नए तरीके से उस से निपटना होगा, और यह किसी भी तरह से आसान नहीं है।

तब आप ऐसी स्थिति में आ जाते हैं जब आप विशिष्ट एन्कोडिंग भेजना शुरू कर देते हैं, जैसे कि ASCII में फ़्लोट को बदलने की तुलना में फ़्लोट की मेमोरी प्रतिनिधित्व में भेजना, उस सीरियल को भेजें जो 4 बाइट्स से अधिक हो सकता है, और फिर उसे वापस कनवर्ट करें मेजबान पर स्मृति प्रतिनिधित्व में। इसके बजाय, आप बस हर बार 4 बाइट प्रतिनिधित्व भेजते हैं। ज़रूर, आप स्वयं एन्कोडिंग को संभालना शुरू कर सकते हैं, लेकिन फिर आपको स्टार्ट / एंड टैग, ऑर्डर, आदि सेट करने की आवश्यकता है।

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

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.