Adesea, în programele microcontrolerului trebuie să creați întârzieri în coordonarea acțiunilor sau să așteptați ca acestea să se termine. În mod teoretic, cel mai simplu mod de a întrerupe activitatea microcontrolerului este să-i supraîncărcați procesorul cu alte acțiuni, de exemplu, pentru al forța să numere numere mari. Prin frecvența ciclurilor procesorului, puteți calcula cât timp este nevoie să numărați numerele pentru a crea o anumită întârziere. Citirea oricărui număr de la zero la frecvența ceasului procesorului în hertz ar crea teoretic o întârziere de o secundă. În practică, din anumite motive, nu este atât de simplu.
Dacă microcontrolerul găsește procesor prin intermediul numerelor, forma binară care este la fel de lată ca și magistrala internă (în cazul AVR - 8 biți), apoi acțiune un arifmiticheskoe, cum ar fi adăugarea la numărul de unități, este nevoie de timp într-un singur ciclu de lucru al procesorului. Pentru a funcționa în mii sau milioane, numărul trebuie să fie 16 sau 32 de biți, iar pentru a le calcula, procesorul pe 8 biți petrece mai mult de un ciclu de ceas. Pentru numerele mari, trebuie să cunoașteți dispozitivul intern al procesorului sau mai degrabă sistemul de comenzi.
Deoarece limbajele de programare de nivel înalt (de exemplu limbajul C), programul nu este scris direct pe sistemele bazate pe comandă, este necesar să se creeze un program de întârziere, pentru a ști compilator care convertește un program în cod mașină. Depinde de câte instrucțiuni (și, în consecință, câte bare) sunt necesare pentru a efectua operația aritmetică. O altă complicație este faptul că compilatorul poate converti un program în codul mașinii în mai multe moduri - de exemplu, făcând codul mașinii cât mai economic posibil sau rapid executat. Astfel de capacități de compilare se numesc optimizare. Cu diferite moduri de optimizare, codul mașinii pentru întârzierea programului și durata sa de timp sunt diferite.
Aici, aceeași secțiune a programului C este dată numai după compilare. Două numere hexazecimale cu stânga sunt codul mașinii, iar în partea dreaptă este o instrucțiune pentru limba de asamblare împreună cu operandul (operanții). Codul mașinii și limba de asamblare sunt interdependente, iar asamblorul reprezintă pur și simplu reprezentarea codului mașinii într-o formă ușor de citit. La compilare, se utilizează optimizarea lungimii programului (opțiunea compilatorului -O).
În forma compilată, este clar ce se întâmplă de fapt în ciclul limbajului C și pe baza acesteia, este posibil să se calculeze câte cicluri este necesar pentru a umple o perioadă de ciclu. Informațiile despre acțiunile instrucțiunilor și orele de lucru se află pe pagina de date a sistemului de comandă AVR. În acest exemplu, pentru o perioadă de ciclu, sunt necesare 4 cicluri pentru a completa 4 instrucțiuni, deoarece toate instrucțiunile cer un ciclu de ceas. În plus, înainte de începerea ciclului, se utilizează 1 ciclu pentru instrucțiunea de încărcare și 1 ciclu pentru ieșirea din ciclu. Presupunând că ceasul de funcționare al controlerului este de 14,7456 MHz. atunci este posibil să se calculeze întârzierea de timp a întregului segment de software:
(1 + 100 ⋅ 4 + 1) / 14745600 = 27,26 μs
Întârzierea creată în exemplu este în microsecunde și variabila folosită este de 8 biți, prin urmare codul mașinii este, de asemenea, simplu. Pentru a crea o pauză în milisecunde, trebuie să citiți numere mult mai mari și apoi codul mașinii va deveni mai lung. Puteți utiliza bucle care funcționează în interiorul celuilalt, dar în cazul acestei metode întreaga întârziere nu este liniară în funcție de numărul de cicluri, deoarece la fiecare nivel de ciclu există mici întârzieri suplimentare.
Scopul acestei sarcini nu este acela de a crea o întârziere exactă a programului la nivelul codului mașinii, deoarece aceasta este o lucrare destul de delicată și, pe lângă funcțiile pentru crearea întârzierilor, sunt deja disponibile în avr-libc și în biblioteca Home Lab. Ele sunt, de asemenea, utilizate în următoarele exemple.
Pe întârzierea software-ului, este important să știm că, spre deosebire de simplitatea sa fundamentală, este o metodă extrem de ineficientă în ceea ce privește consumul de energie. Toate aceste cicluri consumă energie atunci când microcontrolerul este implicat într-o contabilitate în van. Atunci când utilizați baterii, nu este recomandabil să creați întârzieri lungi în program, dar trebuie să utilizați cronometre care funcționează independent și să trezi procesorul de la somn dacă trebuie să continuați să lucrați.
Următorul cod de program se referă la funcția de întârziere software sw_delay_ms. care creează un număr specificat în milisecunde. Funcția, la rândul său, folosește funcția _delay_ms a bibliotecii avr-libc, care este scrisă în limbajul de asamblare. Motivul pentru care _delay_ms nu este folosit în activități simultan este că pot apărea probleme cu întârzieri lungi cu _delay_ms. Funcția sw_delay_ms face posibilă crearea de întârzieri de până la 65535 ms fără probleme.
Pentru a utiliza această funcție, există următorul program, care creează două întârzieri într-o buclă infinită: 100 ms și 900 ms. În timpul unei scurte întârzieri, LED-ul este aprins și pentru o lungă perioadă de timp - se stinge și, ca urmare, clipește periodic.
În ciuda faptului că se pare că LED-ul clipește după 1 secundă, timpul real este puțin mai lung, deoarece apelurile pentru funcțiile LED și întârzierile ceasului microcontrolerului necesită ceva timp.