3.29. Kis fogyasztású és alvó módok¶
Az akkumulátorról működő kameráknak és az időszakosan aktív érzékelőknek nincs szükségük arra, hogy a CPU folyamatosan teljes sebességgel fusson. A machine modul négy, egyre mélyebb energiatakarékos állapotot tesz elérhetővé – active, idle(), lightsleep() és deepsleep(). Minden mélyebb lépés a chip nagyobb részét kapcsolja ki, és több energiát takarít meg, a hosszabb felébredés árán. A megfelelő kiválasztása kompromisszum aközött, hogy mennyi energiát takarít meg a kamera, és milyen gyorsan tud reagálni, amikor történik valami.
3.29.1. Active¶
Az alapértelmezett állapot. A CPU Pythont futtat, minden periféria órajelet kap, és az áramfelvétel a legmagasabb – a kamera logikai tápsínjén több tíz milliamper, plusz amennyit bármely csatlakoztatott tartozék rajta keresztül felvesz.
3.29.2. idle()¶
A machine.idle() leállítja a CPU órajelét, amíg bármilyen megszakítás be nem következik (egy periféria, egy időzítő, egy láb-IRQ). A RAM él, a perifériák bekapcsolva maradnak, az órajelek tovább futnak – csak maga a CPU áll meg, és mikroszekundumok alatt felébred, amikor van tennivaló.
Használd minden olyan szoros lekérdező ciklusban, amely valamilyen külső esemény bekövetkezésére vár:
import machine
while not button_pressed():
machine.idle()
A CPU nem éget el ciklusokat magára a while ellenőrzésre, és természetes módon felébred, amikor a következő esemény megérkezik – egy kis megtakarítás, amely egy milliószor lefutó cikluson keresztül összeadódik.
3.29.3. lightsleep()¶
A machine.lightsleep() a következő lépés lefelé. A CPU teljesen leáll, és a chip belső órajeleinek nagy része kikapcsol, de a RAM és a perifériák állapota megmarad. Amikor az ébresztési forrás bekövetkezik, a szkript pontosan onnan folytatódik, ahol a lightsleep hívást meghívta – a változók, a nyitott leírók és a függőben lévő adatok mind sértetlenül – ezredmásodpercek nagyságrendjével később.
import machine
from machine import Pin
wake_pin = Pin("P0", Pin.IN, Pin.PULL_UP)
wake_pin.irq(lambda _: None, trigger=Pin.IRQ_FALLING, wake=machine.SLEEP)
while True:
do_work()
machine.lightsleep() # wakes on a falling edge on P0
Az ébresztési forrást – itt egy láb-IRQ-t – az alvás hívása előtt kell beállítani. Az áramfelvétel jelentősen csökken az aktív módhoz képest; a pontos érték a kártyától és attól függ, mely perifériák maradnak konfigurálva.
3.29.4. deepsleep()¶
A machine.deepsleep() a legmélyebb állapot. A CPU leáll, a perifériák lekapcsolnak, és a RAM tartalma elveszhet. Az egyetlen, ami még áramot vesz fel, az ébresztő áramkör és egy kis, mindig bekapcsolt logika.
Amikor az ébresztési forrás bekövetkezik, a chip a fő szkript elejéről indul el – a deepsleep nem tér vissza. A szkript a machine.reset_cause() segítségével különbözteti meg a deepsleep-ébresztést a friss bekapcsolástól vagy a hardveres újraindítástól:
import machine
if machine.reset_cause() == machine.DEEPSLEEP_RESET:
# Woke from deepsleep -- restore state from non-volatile storage,
# take a measurement, etc.
pass
else:
# Fresh boot
pass
do_work()
machine.deepsleep(60_000) # arm RTC wake for 60 s, sleep, then restart
A deepsleep() ezredmásodperc argumentuma belsőleg élesíti a chipen lévő RTC-riasztást – az RTC az, ami az ébresztés időzítését átviszi az alváson keresztül, mivel a legtöbb más időzítő ki van kapcsolva. Ha a deepsleep() függvényt argumentum nélkül hívod meg, az ébresztést arra a forrásra bízod, amelyet külön konfiguráltál (egy láb-IRQ-ra, egy külön élesített RTC-riasztásra).
Mivel a szkript újraindul, mindennek, amire a következő iterációnak szüksége van, vagy a main.py tetején újra fel kell épülnie, vagy a flash memóriába (vagy az RTC tartalék regisztereibe, az ilyennel rendelkező alkatrészeken) kell elmentődnie. A deepsleep adja a legnagyobb energiamegtakarítást, de a legtöbb programátstrukturálást igényli – az alkalmazásnak rövid „mérési löketek” sorozataként kell viselkednie, amelyeket alvások választanak el, nem pedig hosszan futó, RAM-ban tárolt állapotú ciklusként.
3.29.5. Állapot kiválasztása¶
A megfelelő állapot attól függ, mire vár a kamera:
Szoros lekérdező ciklus, ezredmásodpercekre várva. Használd a
idle()függvényt. A megtakarítások ciklusonként kicsik, de összességükben nagyok, és az ébredés láthatatlan.Másodpercekig vagy percekig tétlen az események között. Használd a
lightsleep()függvényt. Az állapot megmarad, az ébredés gyors, és az áramfelvétel az aktív mód töredéke.Percekig vagy hosszabb ideig tétlen a rövid munkalöketek között. Használd a
deepsleep()függvényt. A chip gyakorlatilag ki van kapcsolva az események között, és a szkript szerkezete egy ébredés-mérés-alvás ciklusra vált át.
Bármi is az állapot, az ébresztési forrás éppoly fontos, mint maga az állapot – egy deepsleep, amely csak időzítőre ébred, egy munkaciklusos mérési ciklus; egy lightsleep, amely láb-IRQ-ra ébred, egy eseményvezérelt érzékelő. A machine modul alvófüggvényei, a RTC riasztásai és a irq() együtt adják az építőelemeket.