AVR (attiny45) के साथ सिंक्रनाइज़ेशन सिग्नल को कैसे कार्यान्वित करें?

छद्म कोड में मैं निम्नलिखित करना चाहता हूं:

i = 0
state = 0

while (1):

  compareState = readDigitalIn()
  if state == compareState:
    i = i+1
  else:
    i = 0
    state = compareState

  writeDigitalOut(dataVector[i])

अंग्रेजी में, जब भी मैं digitalIn -pin की स्थिति बदलता हूं, तो मैं काउंटर i को रीसेट करना चाहता हूं।

क्या यह उपरोक्त करने का एक अच्छा तरीका है? क्या अटारी के पास ईवेंट श्रोताओं या समान हैं?

अंतिम लक्ष्य विभिन्न चिप्स में एकाधिक पीडब्लूएम नियंत्रकों को सिंक्रनाइज़ करना है (WriteDigitalOut को एडजस्ट PwmFrequency में बदल दिया गया है ...)

Edit: Can I use interrupts for this? How? Can create an interrupt that fires when digitalIn-pin is changed?

2
अगर राज्य जल्दी से नहीं बदलता है, तो i को बड़ा होने और dataVector [] की सीमाओं से बाहर जाने से रोकने के लिए क्या है? क्या आपने writeDigitalOut() के भीतर चेकिंग की जांच की है? यदि नहीं, तो यह एक बहुत ही बुरी स्थिति होगी जिसे आप टालना चाहते हैं। आपके प्रश्न का संक्षिप्त उत्तर हां है, और मैं जल्द ही एक अधिक गहन उत्तर लिखूंगा, लेकिन मैं बस इसे आपके ध्यान में लाना चाहता था।
जोड़ा लेखक kender, स्रोत
वह छद्म पाइथन की तरह दिखता है ...
जोड़ा लेखक Durga Swaroop, स्रोत
@ धोवतपंडिया मान लीजिए मेरी पसंदीदा प्रोग्रामिंग भाषा क्या है;)। बहुत बुरा आप पाइथन के साथ एवीआर प्रोग्राम नहीं कर सकते हैं।
जोड़ा लेखक user7406, स्रोत

1 उत्तर

हां, यह इंटरप्ट्स का उपयोग करने के लिए एक बहुत अच्छा एप्लीकेशन है।

आप में क्या रूचि है बाहरी बाधा है, लेकिन चलो पहले एक बाधा की सामान्य संरचना को तोड़ दें।

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

इस फ़ंक्शन को इंटरप्ट सेवा रूटीन या संक्षिप्त के लिए आईएसआर कहा जाता है। यह एक तरीका है जिसे आपको लिखना चाहिए।

तो आइए पहचान लें कि आप कौन सी बाधा चाहते हैं और आप कौन सी आईएसआर लिखना चाहते हैं। ऐसा करने के लिए, हमें डेटाशीट से परामर्श करने की आवश्यकता है। आप जिस रूचि में रुचि रखते हैं उस प्रकार के इंटरप्ट्स के परिवार में बाहरी इंटरप्ट्स कहा जाता है। ATiny45 डेटाशीट का एक अंश:

<�पी> 9.2 बाहरी इंटरप्ट्स      

बाहरी इंटरप्ट्स INT0 पिन या किसी भी पीसीआईएनटी [5: 0] पिन द्वारा ट्रिगर किए जाते हैं। ध्यान से देखें   यदि, सक्षम है, तो INT0 या पीसीआईएनटी [5: 0] पिन कॉन्फ़िगर किए जाने पर भी इंटरप्ट्स ट्रिगर हो जाएंगे   आउटपुट। यह सुविधा सॉफ़्टवेयर बाधा उत्पन्न करने का एक तरीका प्रदान करती है। पिन परिवर्तन interrupts   यदि कोई सक्षम पीसीआईएनटी [5: 0] पिन टॉगल करता है तो पीसीआई ट्रिगर करेगा। पीसीएमएसके रजिस्टर कौन से पिन नियंत्रित करता है   पिन परिवर्तन interrupts में योगदान। पीसीआईएनटी पर पिन परिवर्तन इंटरप्ट्स [5: 0] अतुल्यकालिक रूप से पता चला है। इसका तात्पर्य यह है कि इन इंटरप्ट्स का उपयोग नींद से भाग को जागने के लिए भी किया जा सकता है   निष्क्रिय मोड के अलावा मोड।

     

INT0 इंटरप्ट्स को गिरने या बढ़ते किनारे या निम्न स्तर से ट्रिगर किया जा सकता है। यह के रूप में स्थापित है   एमसीयू नियंत्रण रजिस्टर के लिए विनिर्देशन में संकेत - एमसीयूसीआर। जब INT0 बाधा होती है   सक्षम और स्तर ट्रिगर के रूप में कॉन्फ़िगर किया गया है, जब तक पिन आयोजित किया जाता है तब तक बाधा ट्रिगर होगी   कम। ध्यान दें कि INT0 पर गिरने या बढ़ते किनारे के बाधाओं की पहचान की उपस्थिति की आवश्यकता है   I/O घड़ी, पृष्ठ 23 पर "क्लॉक सिस्टम और उनके वितरण" में वर्णित है।

So they've mentioned some registers of interest here: PCMSK and MCUCR

PCMSK controls which pins can trigger the interrupt - so you want to wire up your toggling signal to whichever pin(s) you specify here, and MCUCR defines how the pins must change in order to trigger the interrupt. In this case, you would probably be interested in configuring your interrupt for Any logical change on INT0 generates an interrupt request. As outlined in table 9-2 in the document. Continue reading what the registers do in the external interrupt section, they are as follows: MCUCR, GIMSK, GIFR, PCMSK. The information you want to get out of this is

  1. इंटरप्ट को कॉन्फ़िगर कैसे करें ( PCMSK और MCUCR )
  2. इंटरप्ट को सक्षम या अक्षम कैसे करें ( GIMSK )
  3. इसकी वर्तमान स्थिति कैसे जांचें ( GIFR )

अब वास्तविक कोडिंग पर। संरचना इस तरह कुछ दिखाई देगी (छद्म कोड):

volatile int i;//volatile because this gets changed in the ISR, so the compiler will know to NOT optimize this when used in loops

int main(void)
{
     /* set-up your registers here ... */
     /* enable global interrupts */

     i = 0;
     while (1) {
          boundsSafeVectorPrinter(i);
          i++;
     }
}

ISR(PCINT0_ISR)
{
     i = 0;
}

अब जब भी आपके द्वारा निर्दिष्ट पिनों में से एक पिन पर एक पिन परिवर्तन होता है (यह देखते हुए कि आपने सभी रजिस्टरों को सही तरीके से सेट अप किया है), ISR (PCINT0_ISR) दिनचर्या निष्पादित की जाएगी।

तो मुझे ISR (PCINT0_ISR) का उपयोग करने के बारे में कैसे पता चला? आपको यह देखने के लिए कि आप किस कोड परिभाषा फ़ाइल का उपयोग कर रहे हैं, उसे देखने के लिए आपको PCINT0_ISR मैपिंग प्रदान करना होगा, यदि नहीं, तो डेटाशीट से फिर से परामर्श लें और अनुभाग देखें <�कोड> 9.1 ATtiny25/45/8 में इंटरप्ट वेक्टर और इसे स्वयं परिभाषित करें। यदि आप avr-gcc का उपयोग कर रहे हैं, तो ISR() मैक्रो परिभाषित किया गया है यहां

मुझे लगता है कि यह बहुत अधिक कोड देने के बिना मूल बातें शामिल है। गुड लक और मजा करें!

2
जोड़ा
वाह, उत्कृष्ट जवाब। यह वही था जो मैं जानना चाहता था।
जोड़ा लेखक user7406, स्रोत