Re: Arduino generování pulzů

Petr Labaj labaj na volny.cz
Neděle Červenec 30 21:51:40 CEST 2023


Mrzí mě, že tomu nerozumím.

Já jsem synek z dědiny, tak všechno dělám jednoduše.
Chci-li generovat stejné pulzy (jak podle mě znělo zadání), tak prostě 
nastavím
časovač a jdu dělat něco jiného. On už si je generuje sám.

Pokud má být každý pulz jinak dlouhý, tak prostě od reloadu čítače udělám
přerušení a naprogramuju do čítače délku následujícího pulzu.

Ale to je jen teorie. V praxi bych použil Blue-pill, který je levnější než
nějaké Arduino s AVR a je nesrovnatelně výkonnější.
Tam bych nastavil DMA, které bude krmit daný čítač.
Podle komunistického hesla "Práci strojům!".

PL

********************

Dne 30.7.2023 v 19:30 Martin Záruba napsal(a):
>
> Ano. A to ten program přesně dělá. Jen fígl je v tom, že to dělá 
> pomocí přerušení, takže procesor přitom může dělat něco jiného. Na 
> opakovací frekvenci cca 20kHz je to už docela honička.
>
> Martin Záruba
> Dne 30.7.2023 v 19:22 Petr Labaj napsal(a):
>> Nejsem žádný velký arduinista.
>> Generování PWM je ale snad principiálně všude stejné, ne?
>> Nastaví se co nejvyšší základní frekvence čítaní, opakovací frekvence 
>> se nastaví
>> v nějakém registru pro reload čítače, a šířka pulzu se nastaví v 
>> nějakém registru
>> pro komparaci s aktuálním stavem čítače.
>>
>> Pokud to ty úplně základní knihovny přímo od Arduina neumí, tak skoro 
>> určitě
>> k nim bude existovat nějaká vylepšená verze.
>> Pokud tedy programátor nechce řešit nastavení čítače sám, což je 
>> nejlepší.
>>
>> I to nejobyčejnější AVR má čítačů víc, takže se nemusí sahat na ten, 
>> který se
>> používá pro generování TIKů.
>>
>> Nebo je tady něco zásadního, co jsem přehlídnul?
>>
>> PL
>>
>> ********************
>>
>> Dne 30.7.2023 v 19:09 Martin Záruba napsal(a):
>>>
>>> Nevyhoví, protože já potřebuji frekvenci okolo 20kHz.
>>>
>>> Ale snad jsem to vyšrachal. Možná by Vás to mohlo zajímat. Zde je 
>>> ukázka programu, který pomocí přerušení od interního časovače 
>>> generuje dva různé nezávislé pulzy na výstupech 9 a 10. Všechny 
>>> normální funkce (externí přerušení, delay) by měly zůstat zachovány.
>>>
>>>
>>> #include <avr/io.h>
>>> #include <avr/interrupt.h>
>>>
>>> // Proměnné pro uchování šířky pulzů
>>> volatile unsigned int pulseWidth1 = 1000; // Výchozí šířka pulzu 1 
>>> na Counter1 - 1000 us (1 ms)
>>> volatile unsigned int pulseWidth2 = 500;  // Výchozí šířka pulzu 2 
>>> na Counter2 - 500 us
>>>
>>> void setup() {
>>>   // Nastavení pinů pro výstup pulzů
>>>   pinMode(9, OUTPUT);
>>>   pinMode(10, OUTPUT);
>>>
>>>   // Nastavení časovače Timer/Counter1
>>>   cli(); // Vypnutí globálních přerušení
>>>   TCCR1A = 0; // Vynulování registru TCCR1A
>>>   TCCR1B = 0; // Vynulování registru TCCR1B
>>>
>>>   // Nastavení režimu Fast PWM (TOP = ICR1)
>>>   TCCR1A |= (1 << WGM11);
>>>   TCCR1B |= (1 << WGM13) | (1 << WGM12);
>>>
>>>   // Nastavení hodinového děliče na 64 (frekvence časovače = 
>>> frekvence CPU / 64)
>>>   TCCR1B |= (1 << CS11) | (1 << CS10);
>>>
>>>   // Nastavení intervalu pro generování přerušení (1 ms) - pro 
>>> frekvenci CPU 16 MHz
>>>   // ICR1 = (F_CPU / (časový interval * hodinový dělič)) - 1
>>>   ICR1 = 249; // 1 ms při frekvenci CPU 16 MHz a hodinovém děliči 64
>>>
>>>   // Povolení přerušení od časovače Timer/Counter1
>>>   TIMSK1 |= (1 << TOIE1);
>>>
>>>   // Nastavení časovače Timer/Counter2
>>>   TCCR2A = 0; // Vynulování registru TCCR2A
>>>   TCCR2B = 0; // Vynulování registru TCCR2B
>>>
>>>   // Nastavení režimu Fast PWM (TOP = 255)
>>>   TCCR2A |= (1 << WGM21) | (1 << WGM20);
>>>   TCCR2B |= (1 << CS22); // Hodinový dělič 64 - frekvence časovače = 
>>> frekvence CPU / 64
>>>
>>>   // Povolení přerušení od časovače Timer/Counter2
>>>   TIMSK2 |= (1 << TOIE2);
>>>
>>>   sei(); // Zapnutí globálních přerušení
>>> }
>>>
>>> void loop() {
>>>   // V hlavní smyčce (loop) můžete provádět další činnosti
>>> }
>>>
>>> // Obsluha přerušení od časovače Timer/Counter1
>>> ISR(TIMER1_OVF_vect) {
>>>   // Generování pulzu 1 na pinu 9 (při logické 1)
>>>   digitalWrite(9, HIGH);
>>>
>>>   // Počkejte na dobu odpovídající šířce pulzu 1
>>>   delayMicroseconds(pulseWidth1);
>>>
>>>   // Ukončení pulzu 1 (nastavení logické 0)
>>>   digitalWrite(9, LOW);
>>> }
>>>
>>> // Obsluha přerušení od časovače Timer/Counter2
>>> ISR(TIMER2_OVF_vect) {
>>>   // Generování pulzu 2 na pinu 10 (při logické 1)
>>>   digitalWrite(10, HIGH);
>>>
>>>   // Počkejte na dobu odpovídající šířce pulzu 2
>>>   delayMicroseconds(pulseWidth2);
>>>
>>>   // Ukončení pulzu 2 (nastavení logické 0)
>>>   digitalWrite(10, LOW);
>>> }
>>>
>>> Martin Záruba
>>> Dne 30.7.2023 v 16:36 Jaroslav Buchta napsal(a):
>>>> To zalezi, jaky mate MCU. Treba ESP32 na generovani prubehu i 
>>>> neperiodickych ma super periferii.
>>>> Jinak nevyhovi obecne PWM? To by mely umet vsechny MCU.
>>>>
>>>> Dne 30.07.2023 v 14:59 Martin Záruba napsal(a):
>>>>> Potřeboval bych přimět Arduino generovat pulzy o frekvenci cca 
>>>>> 20kHz, ale s jinou střídou, než 1:1, jak dělá příkaz tone. Jde to 
>>>>> nějak?
------------- další část ---------------
HTML příloha byla odstraněna...
URL: <http://list.hw.cz/pipermail/hw-list/attachments/20230730/3645cf4c/attachment.htm>


Další informace o konferenci Hw-list