Tento článek je zrcadlovým článkem o strojovém překladu, klikněte zde pro přechod na původní článek.

Pohled: 9371|Odpověď: 0

Zigbee Journey (9): Několik důležitých základních experimentů CC2430 – systematický spánek a přerušovaná bdělost

[Kopírovat odkaz]
Zveřejněno 30.10.2014 23:24:30 | | | |
1. Propojení horní a dolní úrovně

V tomto článku se budeme věnovat funkci spánku a způsobu probuzení v CC2430. Při skutečném používání je uzel CC2430 obvykle napájen bateriemi, takže kontrola jeho spotřeby energie je zásadní.

Následuje úryvek z čínského manuálu CC2430 pro zavedení 4 režimů spotřeby energie u CC2430:

Jak můžete vidět z tabulky výše, CC2430 má celkem 4 režimy napájení:PM0(plně vzhůru),PM1(trochu ospalý),PM2(napůl vzhůru, napůl spící),PM3(Velmi tvrdě spí). Čím dál vzadu, tím více funkcí se vypne a spotřeba energie je stále nižší. Konverzní vztah mezi nimi je následující:

DátPM1、PM2Vzbuď sePM0, existují tři způsoby: reset, vnější přerušení, přerušení spánkového časovače; Ale dejPM3Vzbuď sePM0, existují pouze dva způsoby: reset, externí přerušení (protože vPM3Všechny oscilátory přestaly fungovat a samozřejmě byl vypnutý i časovač spánku~)

Pojďme si projít malý experiment, který vysvětlí, jak přejít do režimu spánku a jak se probuditPM0stát.

2. Systematický spánek a experimenty s přerušovaným probuzením(1) Úvod do experimentuinicializace systému, vPM0
→ vstupPM1
→ Probudím se podle spánkového časovače po 1 sekunděPM0
→ vstupPM2
→ byl probuzen spánkovým časovačem po 2 sekundáchPM0
→ vstupPM3
→ Počkejte, až se stiskne klávesa S1, spustí se externí přerušení a probudí sePM0
(2) Programový diagram

(Poznámka: Zaoblené pole na obrázku výše ukazuje zdravotní stav systému)

(3) Experimentální zdrojový kód a analýza (Následující políčka lze kliknout~Definice hlavičkového souboru a makra[url=] [/url]
/*
    Experimentální popis: Experiment s přerušovaným probuzením spánku, který zavádí bdělost ve třech režimech spánku
*/

#include
#define LED_ON 0
#define LED_OFF 1#defineLED1 P1_0         
#defineLED2 P1_1         
#defineLED3 P1_2         
#defineLED4 P1_3   [url=] [/url]

Podfunkce[url=] [/url]
/*Inicializace systémových hodin
-------------------------------------------------------
*/
prázdnotaxtal_init(prázdnota)
{
  SPÁT &= ~0x04;            //Všechny jsou napájené
  zatímco(! (SPÁT &0x40));     //Krystalový oscilátor je zapnutý a stabilní
  CLKCON &= ~0x47;         //Vyberte krystalový oscilátor s frekvencí 32 MHz
  SPÁT |=0x04;
}


/*Inicializace LED
-------------------------------------------------------
*/
prázdnotaled_init(prázdnota)
{
  P1SEL =0x00;         //P1 je běžný I/O port
  P1DIR |=0x0F;         //P1.0 P1.1 P1.1 P1.2 P1.3 výstup
  
  led1 = LED_OFF;         //Vypněte všechny LED diody
  led2 = LED_OFF;
  led3 = LED_OFF;
  led4 = LED_OFF;
}


/*Inicializace externího přerušení
-------------------------------------------------------
*/
prázdnotaio_init(prázdnota)
{
    P0INP &= ~0X02;   //P0.1 má shyb a stahování dolů

    EA =1;           //Úplné přerušení povoleno
   
    IEN1 |=  0X20;   //P0IE = 1, P0 přerušení je povoleno
   
    PICTL |=  0X09;   //P0.1 umožňuje přerušení, spouštění na okraji
   
    P0IFG &= ~0x02;   //P0.1 Značka přerušení clear00
}


/*Inicializace přerušení spánkového časovače
-------------------------------------------------------
*/
prázdnotasleepTimer_init(prázdnota)
{
  STIF=0;   //Značka přerušení spánku je čistá 0
   
  STIE=1;   //Zapnutí spánkového časovače přerušeno
   
  EA=1;     //Otevřete úplné přerušení
}


/*Nastavte si plánovaný interval pro spánkový časovač
-------------------------------------------------------
*/
prázdnotasetSleepTimer(nepodepsané)intsec)
{
  nepodepsánodlouhýsleepTimer =0;
  
  sleepTimer |= ST0;                     //Získejte hodnotu počtu aktuálního spánkového časovače
  sleepTimer |= (nepodeptánodlouhý)ST1 <<8;
  sleepTimer |= (nepodeptánodlouhý)ST2 <<16;
  
  sleepTimer += ((unsigneddlouhý)sec* (nepodepsánodlouhý)32768);   //Plus požadovaná časová doba trvání
  
  ST2 = (nepodepsánochar(SleepTimer >>16);   //Nastavte srovnávací hodnotu spánkového časovače
  ST1 = (nepodepsánochar(SleepTimer >>8);
  ST0 = (nepodepsánochar)sleepTimer;
}


/*Vyber režim napájení
-------------------------------------------------------
*/
prázdnotaPowerMode(nepodepsané(nepodepsáno)charrežim)
{
  pokud(mód <4)
  {
    SPÁT &=0xfc;      //Zrušte režim spánku na 0
    SLEEP |= režim;      //Vyber režim napájení
    PCON |=0x01;        //Zapněte tento režim napájení
  }
}


/*Zpožďovací funkce
-------------------------------------------------------
*/
prázdnotaZpoždění (nepodepsané)intn)
{
  nepodepsánointi,j;
  pro(i=0; i<n; i++)
    pro(j=0; j <1000; j++);
}
[url=] [/url]

Hlavní funkce[url=] [/url]
/*Hlavní funkce
-------------------------------------------------------
*/
prázdnotamain(prázdnota)
{
  xtal_init();         
  led_init();         
  
  //Stav PM0, rozsvícení a zpoždění
  led1 = LED_ON;         //Jas LED1 indikuje, že systém pracuje v režimu PM0
  Delay(10);


  //PM1 stát, světla zhasnutá
  setSleepTimer(1);      //Nastavte časový interval spánkového časovače na 1 s
  sleepTimer_init();     //Zapnutí spánkového časovače přerušeno
  led1 = LED_OFF;
  PowerMode(1);         //Nastavte režim napájení na PM1
  
  
//Po 1 sekundě PM1 vstupuje do PM0, rozsvítí se a zpožďuje
  led1 = LED_ON;
  Delay(50);
  
  //PM2, světla zhasnout
  setSleepTimer(2);      //Nastavte časový interval pro spánkový časovač na 2 sekundy
  led1 = LED_OFF;
  PowerMode(2);         //Nastavte režim napájení na PM2


  
//Po dvou sekundách PM2 vstupuje do PM0, rozsvítí se a zpožďuje
  led1=0;
  Delay(50);
  
  //PM3, zhasnutí  
  io_init();            //Inicializace externích přerušení
  led1 = LED_OFF;
  PowerMode(3);         //Nastavte režim napájení na PM3
  
  
//Když dojde k externímu přerušení, PM3 vstoupí do PM0 a rozsvítí se
  led1 = LED_ON;

  zatímco(1);
}
[url=] [/url]

Postupy pro přerušení[url=] [/url]
/*Program pro externí přerušení
-------------------------------------------------------
*/
#pragmavektor = P0INT_VECTOR
__interruptprázdnotaP0_ISR(prázdnota)
{
  EA =0;                        //Brána je přerušena
  
  Delay(50);

  pokud((P0IFG &0x02) >0)         //Klávesy jsou přerušeny
  {
    P0IFG &= ~0x02;               //P0.1 Značka přerušení clear00
  }
  P0IF =0;                       //P0 přerušovací značka clear00


  EA =1;                        //Otevřené přerušení
}


/*Časovač spánku přerušuje servisní programy
-------------------------------------------------------
*/
#pragmavektor= ST_VECTOR
__interruptprázdnotasleepTimer_IRQ(prázdnota)
{
  EA=0;     //Brána je přerušena
   
  STIF=0;   //Značka přerušení spánku je čistá 0
  
  EA=1;     //Otevřené přerušení
}
[url=] [/url]

Jak použít časovač spánku k probuzení systému lze shrnout následovně:Otevřete přerušení časovače spánku → nastavte časový interval spánku → nastavte režim napájení

(Poznámka: Krok "Nastavit interval spánku časovače" musí být před "Nastavit režim napájení", protože systém po přechodu do spánku program nedokončí)

Dále se zaměřme na podfunkci, která nastavuje interval spánkového časovače:setSleepTimer

Nejprve krátké představení spánkového časovače: běží dál32,768 kHzz24. místoČasovač, když systém běžíKromě PM3Ve všech režimech napájení bude časovač spánkuNepřerušený provoz

Registry používané spánkovými časovači jsou:ST0ST1ST2。 Následuje podrobný úvod do jeho funkcí z čínského manuálu CC2430:

Je vidět, že jejich funkce zahrnují dva aspekty:ČístNapsat

  Číst: Používá se k přečtení hodnoty počtu aktuálního časovače, pořadí, ve kterém je třeba měření dodržovat:Čti ST0 → Čti ST1 → Čti ST2

  Napsat: Používá se k nastavení hodnoty porovnání časovače (když hodnota počtu časovače = hodnota porovnání, dojde k přerušení), pořadí zápisu musí následovat:Zapisujte ST2 → zapisujte ST1 → zapisujte ST0

Dobře, vysvětlíme to v kombinaci se zdrojovým kódem:

(1) Nejprve definujte neposigned long variable (32bit) sleepTimer, který přijímá aktuální hodnotu počtu sleepTimerů:

  nepodepsánodlouhýsleepTimer =0;
  
  sleepTimer |= ST0;                     //Získejte hodnotu počtu aktuálního spánkového časovače
  sleepTimer |= (nepodeptánodlouhý)ST1 <<8;
  sleepTimer |= (nepodeptánodlouhý)ST2 <<16;

(2) Pak přičtěte požadovaný časový interval:

  sleepTimer += ((unsigneddlouhý)sec* (nepodepsánodlouhý)32768);   //Plus požadovaná časová doba trvání

Tady je malé vysvětlení:

Proč jednička představuje 32768? Protože časovač pracuje pod 32,768 kHz, trvá 1/32768 s za každou přidanou 1 sekundu; Přidejte 32768 a budete potřebovat jedničky;

(3) Nakonec se hodnota sleepTimer používá jako srovnávací hodnota časovače:

  ST2 = (nepodepsánochar(SleepTimer >>16);   //Nastavte srovnávací hodnotu spánkového časovače
  ST1 = (nepodepsánochar(SleepTimer >>8);
  ST0 = (nepodepsánochar)sleepTimer;

Tímto způsobem můžete úspěšně nastavit časovou dobu časovače~

(Poznámka: Co se týče ostatních částí zdrojového kódu, věřím, že v kombinaci s podrobnými poznámkami to snadno pochopíte, a nebudu to zde opakovat)

(4) Experimentální výsledky
Při spuštění programu, pozorování LED1, je tento jev:LED1 bliká (tj. zapnuto-> vypnuto 1krát), znovu bliká po 1 sekundě, znovu bliká po 2 sekundách, pak zůstává vypnutá a pak stiskne S1, LED1 se rozsvítí.
Experimentální jev je zcela v souladu s očekáváním, Konec ~

3. Závěr

Oh~ Po dvou dnech volného času jsem konečně dostal tento záznam. Opravdu jsem zjistil, že psaní blogu, zvlášť "čtenáři přívětivého" blogového příspěvku, je skutečně fyzická práce: přísnost, estetika, logika... Je to všechno o ohleduplnosti.

Pokaždé, když kód zveřejním, přijde mi příliš dlouhý, ale nerad používám skládací nástroj, který je součástí blogové zahrady. Proto autor v tomto blogovém příspěvku předběžně přidal některé prvky JQuery, aby dosáhl hladkého skládání kódu, a přesto je tu malý pocit úspěchu, hehe (JQuery nováčku, nesměj se mistrovi~). Ale nevím, jestli to opravdu zlepšuje čitelnost článku, a čtenáři a přátelé jsou vítáni, aby komentovali :)

Tento měsíc se autor opravdu rozhodl zakořenit v blogové zahradě, takže jsem strávil spoustu volného času psaním blogových příspěvků. Když jsem poprvé psal blog, i když bylo málo komentářů, většina záznamů měla míru prokliků přes 500, což pro mě bylo malé povzbuzení! Chce to odvahu publikovat obsah o mikrokontrolérech v blogové zahradě, ale já u toho zůstanu~

Devět blogových příspěvků od začátku až do současnosti se zaměřuje na použití základních hardwarových modulů na čipu CC2430. Zatím jsme v podstatě prošli většinu periferií na CC2430, ale stále jsou tu věci jako přístup k Flashi, generátor náhodných čísel, AES koprocesor, RF komunikace atd., které jsme neřešily. Cesta se Zigbee však ještě neskončila a autor hodlá tyto opomenutí selektivně doplnit v dalším tématu (implementaci protokolu Z-Stack).

V příštím blogovém příspěvku plánuji zakončit první cestu Zigbee o něco komplexnějším a rozšířenějším experimentem – "systémem měření teploty" a vysvětlit, jak komplexně aplikovat poznatky získané dříve.

Ve skutečnosti není kvalifikovaný k tomu, aby byl nazýván "VysvětleníJako začátečník si autor přeje jen to, že se navzájem povzbuzí a společně pokročí v procesu psaní doktorátu!


</n; i++)




Předchozí:Zigbee Journey (8): Několik důležitých základních experimentů CC2430 – hlídací psi
Další:Zigbee Journey (10): Komplexní experiment – systém měření teploty založený na CC2430
Zřeknutí se:
Veškerý software, programovací materiály nebo články publikované organizací Code Farmer Network slouží pouze k učení a výzkumu; Výše uvedený obsah nesmí být používán pro komerční ani nelegální účely, jinak nesou všechny důsledky uživatelé. Informace na tomto webu pocházejí z internetu a spory o autorská práva s tímto webem nesouvisí. Musíte výše uvedený obsah ze svého počítače zcela smazat do 24 hodin od stažení. Pokud se vám program líbí, podporujte prosím originální software, kupte si registraci a získejte lepší skutečné služby. Pokud dojde k jakémukoli porušení, kontaktujte nás prosím e-mailem.

Mail To:help@itsvse.com