forum.mcontrollers.com - hlavní stránka forum.mcontrollers.com - fórum

 

.: fórum - hlavní stránka :.
Technology Stronghold by Rudolf Vesely
How to build Microsoft System Center hosted cloud series
FAQFAQ HledatHledat Seznam uživatelůSeznam uživatelů Uživatelské skupinyUživatelské skupiny RegistraceRegistrace
ProfilProfil StatistikaStatistika Soukromé zprávySoukromé zprávy PřihlášeníPřihlášení

 
Generátor obdélníku 60kHz

 
Přidat nové téma   Zaslat odpověď    Obsah fóra mcontrollers.com -> AVR
 
vladoxxx
Anonymní





PříspěvekZaslal: 20 březen 2016, 11:39    Předmět: Generátor obdélníku 60kHz Citovat

Ahoj,
potřeboval bych udělat generátor obdélníku 60kHz....

Chtěl jsem na to využít Atmegu16A....ale z nějakýho důvodu to nejde...

Program vypadá takhle:

kód:
#define F_CPU 12000000UL
//includovane knihovny zde

volatile unsigned int tim0; //pomocna promenna - kolikrat pretece TIMER0

int main(void)
{
   sei();//init interrupt
   TIMSK|= (1 << TOIE0);// prerušeni pri pretečení TCNT0
 // TCCR0|= (1 << CS02)| (1 << CS00); // preddelicka 1024
   DDRB |= (1 << PB0); // vystup
   
    while (1)
    {
   
   }
}

//////////////////////////////////////////////////////////////////////////
// TIMER 0
ISR (TIMER0_OVF_vect){ // 8bitu
   tim0++;
   
   switch (tim0)
   {
      case 1:
      PORTB = (1 << PB0);
      break;
      
      case 150:
      PORTB ^= (1 << PB0);
      break;
      
      case 300:
      PORTB ^= (1 << PB0);
      tim0=0;
      break;
   
   }
}


Dá se s tím něco dělat?? ...a nebo to prostě nejde? (jaká je nejjednodušší lepší varianta)
Návrat nahoru
 

 
Balů
Profesionál
Profesionál


Založen: 29.10.2012
Příspěvky: 708

PříspěvekZaslal: 20 březen 2016, 12:27    Předmět: Citovat

1) Máš zakomentované spuštění čítače.
2) Jak jsi to počítal ? 12000000/1024/256 = 45,7763671875 Hz. Jak z toho chceš dalším dělením dostat obdélník 60 kHz ?


A 2 dotazy :
1) opravdu máš u procesoru krystal 12 MHz ?
2) Pokud to bude jenom generátor 60kHz, určitě potřebuješ IO s tolika nožičkama a tak velikou pamětí ?


Úloha má velice jednoduché řešení s minimálním nároky na výkon procesoru. V Cčku jsem shopný se při této konfiguraci dostat na obdélník přes 128khz (v assembleru ještě o kus výše). Samozřejmě s tím, že procesor má ještě čas i na další práci.

Ale domácí úkol tady opravdu řešit nebudu ...


Naposledy upravil Balů dne 20 březen 2016, 13:31, celkově upraveno 1 krát.
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
vladoxxx
Nováček
Nováček


Založen: 20.3.2016
Příspěvky: 9
Bydliště: Brno

PříspěvekZaslal: 20 březen 2016, 13:31    Předmět: Citovat

Balů napsal:
A nebude to tím, že máš zakomentované spuštění čítače ?

A 2 dotazy :
1) opravdu máš u procesoru krystal 12 MHz ?
2) Pokud to bude jenom generátor 60kHz, určitě potřebuješ IO s tolika nožičkama a tak velikou pamětí ?


Mám zakomentovanou jen předděličku (1024)


Udělal jsem změny:

1) Výměna krystalu za 14 745 600Hz
2) tento MCU jsem měl doma i s DPS...tak není co řešít....inak to samozřejmě nepotřebuju

Když odkomentuju předděličku a přepíšu konstanty v časovači, bude to vypadat takhle:

kód:
#define F_CPU 14745600UL

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>
#include <math.h>

volatile unsigned int tim0; //pomocna promenna - kolikrat pretece TIMER0

int main(void)
{
   sei();//init interrupt
   TIMSK|= (1 << TOIE0);// prerušeni pri pretečení TCNT0
   TCCR0|= (1 << CS00)|(1 << CS00); // preddelicka /1024 //datasheet str.73
   DDRB |= (1 << PB0); // LEDka na PB0
   
    while (1)
    {
   
   }
}

//////////////////////////////////////////////////////////////////////////
// TIMER 0
ISR (TIMER0_OVF_vect){ //pocita do 255 - 8bitu
TCNT0 = 111; //Prerusi se po 10ms =>(14745600/1024)/(255-111)
tim0++;
   
   switch (tim0)
   {
      case 1:
      PORTB = (1 << PB0);
      break;
      
      case 2:
      PORTB ^= (1 << PB0);
      tim0=0;
      break;
   
   }
}



FUSES - LOW 0xDF, HIGH 0x D9

Výsledná frekvence by pak měla být 14745600/ 1024/ (255-111)/2
=20ms

Zpoždění MCU je 2us/cyklus....


Takže byl zřejmě špatný krystal...

Teď už jen vymyslet, jak to udělat, aby MCU dával přesně! 60 kHz (nebo 40kHz)


PS: Není to úkol...

Chtěl jsem udělat 12 000 000 bez předděličky, jenom do CASEů napsat 100+100

....bez zpoždění by to vyšlo přesně, byl by prostor na doladění (99+99)



scope_5.bmp
 Komentář:
 Velikost:  394.02 kB
 Zobrazeno:  3846 krát

scope_5.bmp


Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
Balů
Profesionál
Profesionál


Založen: 29.10.2012
Příspěvky: 708

PříspěvekZaslal: 20 březen 2016, 13:57    Předmět: Citovat

Teda teď fakt nevím, co vlastně chceš 50Hz není 60kHz - to jsi o řád jinde...

Výpočet máš pro 50 Hz, osciloskop ukazuje 44,279 kHz - opět o řád jinde.
To mi nějak nesedí.

Řešení je velice jednoduché, ale chci, abys mě přesvědčil, že je to Tvoje práce a není to domácí úkol. S domácím úkolem pomohu (pomůžeme), ale když to za Tebe tady vyřešíme, tak se nic nenaučíš. Jakmile tady vidíme snahu o řešení nebo alespoň se něco naučit pomůžeme (případně i řešení dodáme).

Řešní mám jednoduché (jednodušší a přesnější, než to Tvoje), i když se mi pořád moc nechce věřit, že to není domácí úkol.

Jinak z kmitočtu 14745600 neuděláš 60000 Hz (alespoň ne přesně). Musí to být dělitelný.

12000000/60000=200 => tohle lze.
14745600/60000=245,76 => tohle nepůjde => 14745600/246=59 941,46341 Hz

12000000/40000=300 => tohle lze.
14745600/40000=368,64 => tohle nepůjde => 14745600/367=40 178,746594 Hz

Tady je to řešení - samozřejmě pro krystal 12 MHz:
kód:
#define F_CPU 12000000UL

#include <avr/io.h>
#include <avr/interrupt.h>


ISR(TIMER0_COMP_vect)
{
    PORTB ^= (1<<PB0);
}

int main(void)
{

    DDRB = (1<<PB0);

    OCR0 = 99;// 60 kHz
    //OCR0 = 149;//40 kHz
    TCCR0 = (1<<WGM01)|(1<<CS00);
    TIMSK = (1<<OCIE0);
    sei();

    for(;;)
    {
    }
}
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
vladoxxx
Nováček
Nováček


Založen: 20.3.2016
Příspěvky: 9
Bydliště: Brno

PříspěvekZaslal: 20 březen 2016, 17:07    Předmět: Citovat

Je smutný, že se člověk nemůže jen tak bavit a něco vymýšlet...
Úkol do školy to není...je mi 25 Wink
Každopádně sem asi nechci psát, čeho součástí bude ten generátor...


Tvoje řešení je hodně hezký,
Z datasheetu jsem moc nepochopil,
jakej je rozdíl mezi (1<<OCIE0) a 1 << TOIE0)

A současně nevím, co dělá 1<<WGM01)

...ale to je v tuto chvíli skoro jedno, vyzkouším to a bude to Wink

Díky moc za vřešení problému!!

(...A doufám, že dnes nemá každej malej kluk doma osciloskop jako já ...to bych se nas*al Very Happy
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
Balů
Profesionál
Profesionál


Založen: 29.10.2012
Příspěvky: 708

PříspěvekZaslal: 20 březen 2016, 17:32    Předmět: Citovat

Když ono to zadání bylo tak jednoduchý, že to domácí úlohou opravdu dost zavánělo.

Rozdíl mezi OCIE a TOIE je v tom, kdy přerušení nastává. OCIE nastává v okamžiku, kdy TCNT dosahne OCR. TOIE je přerušení při přetečení TCNT z 0xFF (0xFFFF pro 16-bitový čítač) do 0.

Jinak WGM01 je v tomto případě součástí WGM01:WGM00 a jeho nastavení určuje chování čítače. V tomto případě je čítač nastaven na CTC (Clear Timer on Compare match) neboli čítač čítá 0-OCR a ne 0-0xFF(0xFFFF). V tomto případě TOV nemůže nikdy nastat, protože čítač hodnoty 0xFF (0xFFFF) nidky nedosahne.

Ale tohle je dost dobře v datasheetech popsané.

Na druhou stranu, je dobře, že jsou i takoví jako Ty, kteří ještě něco doma staví a hlavně učí se. Drtivá většina jen koupí arduino, stáhnou uino a pak chodí na fóra s dotazy typu "Už týden hledám knihovnu na rozsvícení LEDky a nemůžu nic najít ...". Jasně, že pokud je tu vidět snaha (i když máš nějaký supertajný projekt o kterým se nesmíš zmínit Smile ), tak tady poradíme a pomůžeme.
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
vladoxxx
Nováček
Nováček


Založen: 20.3.2016
Příspěvky: 9
Bydliště: Brno

PříspěvekZaslal: 20 březen 2016, 18:29    Předmět: Citovat

Balů napsal:
Když ono to zadání bylo tak jednoduchý, že to domácí úlohou opravdu dost zavánělo.

Rozdíl mezi OCIE a TOIE je v tom, kdy přerušení nastává. OCIE nastává v okamžiku, kdy TCNT dosahne OCR. TOIE je přerušení při přetečení TCNT z 0xFF (0xFFFF pro 16-bitový čítač) do 0.

Jinak WGM01 je v tomto případě součástí WGM01:WGM00 a jeho nastavení určuje chování čítače. V tomto případě je čítač nastaven na CTC (Clear Timer on Compare match) neboli čítač čítá 0-OCR a ne 0-0xFF(0xFFFF). V tomto případě TOV nemůže nikdy nastat, protože čítač hodnoty 0xFF (0xFFFF) nidky nedosahne.

Ale tohle je dost dobře v datasheetech popsané.

Na druhou stranu, je dobře, že jsou i takoví jako Ty, kteří ještě něco doma staví a hlavně učí se. Drtivá většina jen koupí arduino, stáhnou uino a pak chodí na fóra s dotazy typu "Už týden hledám knihovnu na rozsvícení LEDky a nemůžu nic najít ...". Jasně, že pokud je tu vidět snaha (i když máš nějaký supertajný projekt o kterým se nesmíš zmínit Smile ), tak tady poradíme a pomůžeme.


Díky moc!
V týdnu skočím pro krystal a dám sem měření z osciloskopu Wink
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
vladoxxx
Nováček
Nováček


Založen: 20.3.2016
Příspěvky: 9
Bydliště: Brno

PříspěvekZaslal: 21 březen 2016, 17:24    Předmět: Citovat

Nakonec jsem vydoloval jenom starej krystal s popisem 16 000kHz
....funguje to, výsledek je takovej:



scope_6.bmp
 Komentář:
 Velikost:  394.02 kB
 Zobrazeno:  3759 krát

scope_6.bmp


Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

 
Balů
Profesionál
Profesionál


Založen: 29.10.2012
Příspěvky: 708

PříspěvekZaslal: 22 březen 2016, 15:58    Předmět: Citovat

Pokud bys netrval na PB0, tak si myslím, že by se dal udělat generátor 60kHz úplně bez účasti programu (vyjma prvotního nastavení čítače, samozřejmě) na pinu PB3, případně PD7, PD5 nebo PD4.
Návrat nahoru
Zobrazit informace o autorovi Odeslat soukromou zprávu
 

Zobrazit příspěvky z předchozích:   
Zobrazit předchozí téma :: Zobrazit následující téma  
Přidat nové téma   Zaslat odpověď    Obsah fóra mcontrollers.com -> AVR Časy uváděny v GMT + 2 hodiny
 
Strana 1 z 1
Přejdi na:  
Můžete přidat nové téma do tohoto fóra.
Můžete odpovídat na témata v tomto fóru.
Nemůžete upravovat své příspěvky v tomto fóru.
Nemůžete mazat své příspěvky v tomto fóru.
Nemůžete hlasovat v tomto fóru.
Můžete k příspěvkům připojovat soubory
Můžete stahovat a prohlížet přiložené soubory
 



Num Lock Holder - app to hold Numlock
Copyright © 2017 Rudolf Veselý, mcontrollers.com.
Je zakázáno používat části tohoto webu bez souhlasu autora. || Powered by phpBB © 2001, 2002 phpBB Group - with RedSquare DoubleJ(Jan Jaap)