klasa CAN – protokol Controller Area Network

CAN je dvožični serijski protokol koji se koristi za pouzdanu isporuku poruka u stvarnom vremenu između jednog ili više čvorova povezanih na zajedničku sabirnicu. CAN 2.0 standardiziran je u ISO-11898 i danas je poznat i kao CAN Classic.

Postoji i noviji, unatrag kompatibilan protokol pod nazivom CAN FD (CAN with Flexible Data-Rate). Upravljački program machine.CAN trenutno ne podržava značajke CAN FD; koristite pyb.CAN na STM32 ako vam je potreban CAN FD.

Podrška za CAN zahtijeva kontroler (često internu periferiju mikrokontrolera) i vanjski primopredajnik za prilagodbu razine signala na CAN sabirnicu.

Dostupno na STM32 OpenMV kamerama (M4 / M7 / H7 / H7 Plus / Pure Thermal / N6, plus inačice s Arduino oznakom koje povezuju primopredajnik). Još nije podržano na OpenMV Cam RT1062 (mimxrt port) ili OpenMV Cam AE3 (alif port).

Sučelje machine.CAN je niskorazinsko osnovno CAN sučelje za razmjenu poruka koje apstrahira CAN kontroler kao izlazni prioritetni red za slanje poruka, ulazni red za primanje poruka i mehanizme za prijavu pogrešaka.

Napomena

Planirani micropython-lib moduli can i aiocan bit će preporučeni način korištenja CAN-a s MicroPythonom.

Konstruktor

class machine.CAN(id: int, *args, **kwargs)

Konstruira objekt CAN kontrolera zadanog id-a:

  • id identificira određeni objekt CAN kontrolera; specifičan je za ploču i port.

  • Svi ostali argumenti prosljeđuju se funkciji CAN.init(). Mora se navesti barem jedan argument (bitrate).

Buduće verzije ove klase ovdje mogu prihvaćati i ključne argumente specifične za port koji konfiguriraju hardver. Trenutno takvi ključni argumenti nisu implementirani.

Primjer

Konstruirajte i inicijalizirajte CAN kontroler 1 s brzinom prijenosa 500kbps:

from machine import CAN
can = CAN(1, 500_000)

Metode

init(bitrate: int, mode: int = CAN.MODE_NORMAL, sample_point: int = 75, sjw: int = 1, tseg1: int | None = None, tseg2: int | None = None) None

Inicijalizira CAN sabirnicu sa zadanim parametrima:

  • bitrate je željena brzina prijenosa sabirnice u bitovima po sekundi.

  • mode je jedna od vrijednosti prikazanih pod Načini rada, koja označava željeni način rada. Zadana vrijednost je „normalan” rad na sabirnici.

Sljedeći parametri su neobavezni i odnose se na CAN vremenske parametre bita. U većini slučajeva ove parametre možete ostaviti na zadanim vrijednostima:

  • sample_point je cjelobrojni postotak vremena podatkovnog bita. Određuje položaj uzorka bita u odnosu na cjelokupno nominalno vrijeme bita. CAN upravljački program u skladu s tim izračunava parametre. Ovaj se parametar zanemaruje ako su postavljeni tseg1 i tseg2.

  • sjw je širina skoka resinkronizacije u jedinicama vremenskih kvanta za nominalne bitove; može biti vrijednost između 1 i 4 uključivo za klasični CAN.

  • tseg1 definira položaj točke uzorkovanja u jedinicama vremenskih kvanta za nominalne bitove; može biti vrijednost između 1 i 16 uključivo za klasični CAN. Ovo je zbroj faza Prop_Seg i Phase_Seg1 kako su definirane u standardu ISO-11898. Ako je ova vrijednost postavljena, tada mora biti postavljen i tseg2, a sample_point se zanemaruje.

  • tseg2 definira položaj točke prijenosa u jedinicama vremenskih kvanta za nominalne bitove; može biti vrijednost između 1 i 8 uključivo za klasični CAN. Ovo odgovara Phase_Seg2 u standardu ISO-11898. Ako je ova vrijednost postavljena, tada mora biti postavljen i tseg1.

Ako su ovi argumenti navedeni, tada je CAN kontroler ispravno konfiguriran za željeni bitrate i navedeni ukupni broj vremenskih kvanta po bitu. Vrijednosti tseg1 i tseg2 nadjačavaju argument sample_point ako su svi navedeni.

Napomena

Pojedinačni hardver kontrolera može imati dodatna ograničenja na valjane vrijednosti za ove parametre i podići će ValueError ako zadana vrijednost nije podržana.

Napomena

Određeni hardver kontrolera može prihvatiti dodatne neobavezne ključne parametre za hardverski specifične značajke poput naduzorkovanja.

set_filters(filters: list | tuple | None) None

Postavlja prijemne filtre u CAN kontroleru. filters može biti:

  • None za prihvaćanje svih dolaznih poruka, ili

  • [] ili () za onemogućavanje primanja svih poruka, ili

  • Iterabilni objekt s jednom ili više stavki koje definiraju kriterije filtriranja. Svaka stavka treba biti tuple ili lista s tri elementa:

    • identifier je CAN identifikator (int).

    • bit_mask je bitna maska za bitove u polju CAN identifikatora (int).

    • flags je cijeli broj s nula ili više postavljenih bitova definiranih u Zastavice poruka. Ovo određuje svojstva kojima dolazna poruka mora odgovarati. Ne podržavaju svi kontroleri filtriranje po svim zastavicama; ValueError se podiže ako se zatraži nepodržana zastavica.

Dolazne poruke se prihvaćaju ako se bitovi maskirani u bit_mask podudaraju između identifikatora poruke i vrijednosti filtra identifier, te ako se zastavice postavljene u filtru podudaraju s dolaznom porukom.

Ako je bit CAN.FLAG_EXT_ID postavljen u zastavicama, filtar se podudara samo s proširenim CAN ID-ovima. Ako bit CAN.FLAG_EXT_ID nije postavljen, filtar se podudara samo sa standardnim CAN ID-ovima.

Svi filtri se u kontroleru spajaju operacijom ILI. Prosljeđivanje prazne liste ili tuplea kao argumenta filters znači da nijedna poruka neće biti primljena.

Neki CAN kontroleri zahtijevaju da svaki filtar bude povezan samo s jednim prijemnim FIFO-om. U tim slučajevima, stavke filtra u argumentu raspoređuju se kružno (round-robin) na dostupne FIFO-ove. Ovaj upravljački program ne razlikuje FIFO-ove u prijemnom IRQ-u.

Napomena

Ako pozivatelj proslijedi iterabilni objekt s više stavki nego što iznosi CAN.FILTERS_MAX, podiže se ValueError.

Napomena

Ako je identifier ili bit_mask izvan raspona za navedeni tip ID-a, podiže se ValueError s razlogom „invalid id”.

Primjeri

Primanje svih dolaznih poruka:

can.set_filters(None)

Primanje poruka samo sa standardnim ID vrijednostima 0x301 i 0x700:

can.set_filters(((0x301, 0x7FF, 0),
                 (0x700, 0x7FF, 0)))

Primanje poruka sa standardnim ID vrijednostima u rasponu 0x300-0x3FF te samo s proširenom ID vrijednošću 0x50700:

can.set_filters(((0x300, 0x700, 0),
                 (0x50700, 0x1FFF_FFFF, CAN.FLAG_EXT_ID)))
FILTERS_MAX: int

Konstantna vrijednost koja vraća maksimalni broj podržanih prijemnih filtara za ovaj hardverski kontroler.

Imajte na umu da neki kontroleri mogu imati složenija hardverska ograničenja na broj filtara u upotrebi (na primjer, neovisno brojanje filtara za standardne i proširene ID-ove). U tim slučajevima CAN.set_filters može podići ValueError čak i kada granica FILTERS_MAX nije premašena.

send(id: int, data: bytes, flags: int = 0) int | None

Kopira novu CAN poruku u hardverski red za prijenos kontrolera kako bi se poslala na sabirnicu. Red za prijenos je prioritetni red sortiran po prioritetu CAN identifikatora (niži numerički identifikatori imaju viši prioritet).

  • id je cjelobrojna vrijednost CAN identifikatora.

  • data je bytes objekt (ili sličan) koji sadrži podatke CAN poruke ili opisuje zahtjev za daljinski prijenos (Remote Transmission Request, vidi ispod).

  • flags je cijeli broj s nula ili više postavljenih bitova definiranih u Zastavice poruka, koji određuje svojstva odlazne CAN poruke (prošireni ID, zahtjev za daljinski prijenos itd.)

Ako je poruka uspješno stavljena u red za prijenos na sabirnicu, funkcija vraća cijeli broj u rasponu od 0 do CAN.TX_QUEUE_LEN (isključivo). Ova vrijednost je indeks međuspremnika za prijenos u kojem je poruka stavljena za slanje i može je koristiti funkcija CAN.cancel_send te u događajima CAN.IRQ_TX.

Ako je red pun, slanje neće uspjeti i vraća se None.

Slanje također može propasti i vratiti None ako navedena vrijednost id ima jednak prioritet kao postojeća poruka u redu za prijenos, a hardver CAN kontrolera ne može jamčiti da će poruke s istim ID-om biti poslane na sabirnicu istim redoslijedom kojim su dodane u red. Da biste poruku ipak stavili u red, proslijedite zastavicu CAN.FLAG_UNORDERED u argumentu flags. Ova zastavica označava da je u redu slati poruke s istim CAN ID-om na sabirnicu bilo kojim redoslijedom.

Ako je kontroler u stanju pogreške „Bus Off” ili onemogućen, tada će poziv ove funkcije podići OSError.

Napomena

Ova namjerno niskorazinska implementacija osmišljena je tako da pozivatelj može uspostaviti softverski red odlaznih poruka.

Važno

CAN „red za prijenos” nije FIFO red, već je poredan po prioritetu, i iako može sadržavati do CAN.TX_QUEUE_LEN stavki, mogu postojati druga hardverska ograničenja na poruke koje se mogu istovremeno staviti u red.

Zahtjevi za daljinski prijenos (Remote Transmission Requests)

Ako je bit CAN.FLAG_RTR postavljen u argumentu flags, tada će kontroler poslati zahtjev za daljinski prijenos umjesto poruke. U tom se slučaju sadržaj argumenta data zanemaruje. Kontroler će poslati zahtjev u kojem je polje duljine DLC jednako duljini argumenta data.

Primjeri

Pokušaj slanja poruke s trobajtnim sadržajem 0a0b0c i standardnim ID-om 0x200:

can.send(0x200, b"\x0a\x0b\x0c", 0)

Pokušaj slanja poruke s praznim sadržajem i proširenim ID-om 0x180008. Naznačite da kontroler može slati poruke s ovim ID-om bilo kojim redoslijedom, u slučaju da su druge poruke već u redu za slanje s istim ID-om:

can.send(0x180008, b"", can.FLAG_EXT_ID | can.FLAG_UNORDERED)

Pokušaj slanja zahtjeva za daljinski prijenos duljine 8 bajtova i standardnog ID-a 0x555:

can.send(0x555, b" " * 8, can.FLAG_RTR)
recv(arg: list | None = None) list | None

Vraća CAN poruku koju je kontroler primio, prema filtrima postavljenima funkcijom CAN.set_filters().

Ova funkcija prima jedan neobavezan argument; ako je naveden, mora biti lista s najmanje 4 elementa gdje je drugi element memoryview objekt koji se odnosi na bytearray ili sličan objekt dovoljnog kapaciteta za pohranu bilo koje primljene CAN poruke (8 bajtova za CAN Classic, 64 bajta za CAN FD). Navedena lista bit će vraćena kao uspješan rezultat i izbjegava alokaciju memorije unutar funkcije.

Ako CAN kontroler nije primio nijednu poruku, ova funkcija vraća None.

Napomena

CAN.set_filters mora se pozvati prije nego što kontroler može primiti bilo koju poruku. Za primanje svih poruka pozovite set_filters(None).

Ako je CAN kontroler primio poruku, ova funkcija vraća listu s 4 elementa:

  • Indeks 0 je CAN ID primljene poruke, kao cijeli broj.

  • Indeks 1 je memoryview koji omogućuje pristup podacima primljene poruke.

    • Ako arg nije naveden, tada je ovo memoryview koji sadrži bajtove koji su primljeni. Ovaj memoryview se oslanja na novo alocirani bytearray dovoljno velik za pohranu bilo koje primljene CAN poruke. To omogućuje da se rezultat sigurno ponovno koristi kao budući arg, čime se štedi na alokacijama memorije.

    • Ako je arg naveden, tada će navedeni memoryview biti promijenjene veličine kako bi sadržavao točno bajtove koji su primljeni. Pozivatelj je odgovoran osigurati da pozadinski objekt za memoryview može pohraniti CAN poruku bilo koje duljine.

  • Indeks 2 je cijeli broj s nula ili više postavljenih bitova definiranih u Zastavice poruka. Označava metapodatke o primljenoj poruci.

  • Indeks 3 je cijeli broj s nula ili više postavljenih bitova definiranih u Zastavice pogrešaka pri primanju. Bilo koja vrijednost različita od nule označava potencijalne probleme pri primanju CAN poruka. Ove zastavice se unutar kontrolera resetiraju svaki put kada ova funkcija završi.

Zahtjevi za daljinski prijenos (Remote Transmission Requests)

Ako je primljen zahtjev za daljinski prijenos, tada će bit CAN.FLAG_RTR biti postavljen u Indeksu 2, a memoryview u Indeksu 1 sadržavat će sve nule, s duljinom jednakom polju DLC primljenog zahtjeva.

Primjer
can.set_filters(None)   # receive all
while True:
    res = can.recv()
    if res:
        can_id, data, flags, errs = res
        print("Received", hex(can_id), data.hex(), hex(flags), hex(errs))
    else:
        time.sleep_ms(1)  # not a good pattern, use the irq instead!
irq(handler: Callable[[CAN], None] | None = None, trigger: int = 0, hard: bool = False) None

Postavlja funkciju rukovatelja prekidom handler koja se poziva kada se dogodi jedan ili više događaja označenih u trigger.

  • handler je funkcija koja se poziva kada se aktivira događaj prekida. Rukovatelj mora primati točno jedan argument, a to je instanca CAN.

  • trigger konfigurira događaj(e) koji mogu generirati prekid. Moguće vrijednosti su maska jednog ili više od sljedećeg:

    • Događaj CAN.IRQ_RX nastupa nakon što je CAN kontroler primio barem jednu poruku u svoj RX FIFO (što znači da će CAN.recv() uspješno vratiti rezultat).

    • Događaj CAN.IRQ_TX nastupa nakon što je CAN kontroler ili uspješno poslao poruku na CAN sabirnicu ili nije uspio poslati poruku. Ovaj okidač ima dodatne zahtjeve za rukovatelja, vidi IRQ zastavice za pojedinosti.

    • Događaj CAN.IRQ_STATE nastupa kada je CAN kontroler prešao u ozbiljnije stanje pogreške. Pozovite CAN.state() kako biste dobili ažurirano stanje.

  • hard ako je True, koristi se tvrdi prekid. Time se smanjuje kašnjenje između događaja CAN kontrolera i poziva rukovatelja. Rukovatelji tvrdim prekidom ne smiju alocirati memoriju; vidi Pisanje rukovatelja prekidima.

Vraća irq objekt. Ako se pozove bez argumenata, vraća se prethodno konfigurirani irq objekt.

Pogledajte IRQ zastavice za primjer.

cancel_send(index: int) bool

Zahtijeva od CAN kontrolera da otkaže slanje poruke na sabirnicu.

Argument index identificira jedan međuspremnik za prijenos. Treba biti cijeli broj u rasponu od 0 do CAN.TX_QUEUE_LEN (isključivo). Općenito će to biti vrijednost koju je prethodno vratila CAN.send().

Rezultat je True ako je poruka čekala na prijenos u ovom međuspremniku i prijenos je otkazan.

Rezultat je inače False (ili nijedna poruka nije čekala na prijenos u ovom međuspremniku, ili je prijenos već uspio).

IRQ događaj CAN.IRQ_TX treba se koristiti za utvrđivanje je li poruka definitivno poslana ili ne, ali imajte na umu da postoje potencijalna stanja utrke ako se prijenos otkaže, a zatim se isti međuspremnik upotrijebi za slanje druge poruke (osobito ako CAN kontrolerov IRQ nije „tvrd”).

state() int

Vraća cjelobrojnu vrijednost koja označava trenutno stanje kontrolera. Vrijednost će biti jedna od vrijednosti definiranih u Stanja.

Stanja pogreške niže ozbiljnosti mogu se automatski očistiti ako se sabirnica oporavi, ali stanje CAN.STATE_BUS_OFF može se oporaviti samo pozivom CAN.restart().

get_counters(list: list | None = None, /) list

Vraća vrijednosti brojača pogrešaka kontrolera. Rezultat je lista od osam vrijednosti. Ako je naveden neobavezni parametar list, tada se navedeni objekt liste ažurira i vraća kao rezultat, kako bi se izbjegla alokacija.

Stavke liste su:

  • TEC (Transmit Error Counter) vrijednost

  • REC (Receive Error Counter) vrijednost

  • Broj puta koliko je kontroler ušao u stanje upozorenja iz aktivnog stanja.

  • Broj puta koliko je kontroler ušao u stanje Error Passive iz stanja upozorenja.

  • Broj puta koliko je kontroler ušao u stanje Bus Off iz stanja Error Passive.

  • Ukupan broj TX poruka koje čekaju u hardverskom redu.

  • Ukupan broj RX poruka koje čekaju u hardverskom redu.

  • Broj puta koliko se dogodilo prekoračenje RX-a (overrun).

Napomena

Ovisno o kontroleru, ove vrijednosti mogu se preliti natrag na 0 nakon određene vrijednosti.

Napomena

Ako kontroler ne podržava određeni brojač, za taj element liste vratit će None.

get_timings(list: list | None = None, /) list

Vraća listu elemenata koji označavaju trenutne vremenske parametre konfigurirane u CAN kontroleru. Ovo se može koristiti za provjeru vremenskih parametara u svrhe otklanjanja pogrešaka. Rezultat je lista od šest vrijednosti. Ako je naveden neobavezni parametar list, tada se navedeni objekt liste ažurira i vraća kao rezultat, kako bi se izbjegla alokacija.

Stavke liste su:

  • Točna brzina prijenosa koju koristi kontroler. Može se razlikovati od argumenta bitrate proslijeđenog funkciji CAN.init() zbog kvantizacije radi zadovoljavanja hardverskih ograničenja.

  • Širina skoka resinkronizacije (SJW) u jedinicama vremenskih kvanta za nominalne bitove. Ima isto značenje kao parametar sjw funkcije CAN.init().

  • Položaj točke uzorkovanja u jedinicama vremenskih kvanta za nominalne bitove. Ima isto značenje kao parametar tseg1 funkcije CAN.init().

  • Položaj točke prijenosa u jedinicama vremenskih kvanta za nominalne bitove. Ima isto značenje kao parametar tseg2 funkcije CAN.init().

  • Informacije o CAN FD vremenskim parametrima. None za kontrolere koji ne podržavaju CAN FD, ili ako CAN FD nije inicijaliziran. Inače, ugniježđena lista od četiri elementa koja odgovara gornjim stavkama, ali primjenjiva na CAN FD BRS značajku.

  • Neobavezne informacije o vremenskim parametrima specifične za kontroler. Ovisno o kontroleru, ovo će biti ili None ako kontroler ne prijavljuje nijednu, ili će biti lista konstantne duljine čiji su elementi specifični za određeni hardverski kontroler.

Napomena

Ako CAN.init() nije pozvana, ova funkcija i dalje vraća rezultat, ali rezultat ovisi o unutrašnjosti kontrolera i možda neće biti točan.

restart() None

Uzrokuje da kontroler izađe iz STATE_BUS_OFF bez čišćenja bilo kojeg drugog internog stanja. Također čisti neke od brojača pogrešaka (uvijek broj puta koliko je svako stanje pogreške bilo ulazno, eventualno TEC i REC ovisno o kontroleru).

Poziv ove funkcije također otkazuje sve poruke koje čekaju slanje. Za te poruke se ne isporučuju prekidi IRQ_TX.

Imajte na umu da ova funkcija može, ali i ne mora uzrokovati izlazak kontrolera iz stanja „Error Passive”, ovisno o tome poništava li hardver kontrolera TEC i REC ili ne.

deinit() None

De-inicijalizira prethodno aktivnu CAN instancu. Sve poruke na čekanju (za prijenos i primanje) se odbacuju i kontroler prestaje s interakcijom na sabirnici. Za ponovno korištenje ove instance pozovite CAN.init().

Kao odgovor na poziv ove funkcije ne pozivaju se prekidi IRQ_TX ni IRQ_RX.

Pogledajte i CAN.restart().

Konstante

TX_QUEUE_LEN: int

Maksimalni broj CAN poruka koje se mogu staviti u odlazni hardverski red poruka kontrolera. „Indeksi međuspremnika za prijenos” koje koriste CAN.send(), CAN.cancel_send() i IRQ zastavice bit će u ovom rasponu.

Načini rada

Ove vrijednosti predstavljaju načine rada kontrolera, kako se prosljeđuju funkciji CAN.init(). Ne podržavaju svi kontroleri sve načine rada.

Promjena načina rada pokrenutog kontrolera zahtijeva poziv CAN.deinit() i zatim ponovni poziv CAN.init() s novim načinom rada.

MODE_NORMAL: int

Kontroler je aktivan kao standardni čvor CAN mreže (potvrđivat će valjane poruke i može prenositi pogreške ovisno o svom trenutnom Stanju).

MODE_SLEEP: int

CAN kontroler spava u načinu rada s niskom potrošnjom. Ovisno o kontroleru, ovo može podržavati buđenje kontrolera i prijelaz u CAN.MODE_NORMAL ako se primi CAN promet.

MODE_LOOPBACK: int

Testni način rada. CAN kontroler je i dalje povezan s vanjskom sabirnicom, ali će također primati vlastite poslane poruke i zanemarivati sve ACK pogreške.

MODE_SILENT: int

CAN kontroler prima poruke, ali ne stupa u interakciju s CAN sabirnicom (uključujući slanje ACK-ova, pogrešaka itd.)

MODE_SILENT_LOOPBACK: int

Testni način rada koji uopće ne zahtijeva povezan CAN primopredajnik. CAN kontroler prima vlastite poslane poruke bez ikakve interakcije s CAN sabirnicom. CAN TX i RX pinovi ostaju u mirovanju.

Stanja

Ove vrijednosti vraća CAN.state() i odražavaju stanje pogreške CAN kontrolera:

STATE_STOPPED: int

Kontroler nije inicijaliziran.

STATE_ACTIVE: int

Kontroler je aktivan i brojači pogrešaka TEC i REC su oba ispod praga upozorenja od 96. Pogledajte CAN.get_counters().

STATE_WARNING: int

Kontroler je aktivan, ali je barem jedan od brojača pogrešaka TEC i REC između 96 i 127. Pogledajte CAN.get_counters().

STATE_PASSIVE: int

Kontroler je u stanju „Error Passive”, što znači da više ne prenosi aktivne pogreške na sabirnicu, ali je inače funkcionalan. U ovo stanje se ulazi kada je barem jedan od brojača pogrešaka TEC i REC 128 ili veći, ali TEC je manji od 255. Pogledajte CAN.get_counters().

STATE_BUS_OFF: int

Kontroler je u stanju Bus-Off, što znači da je brojač pogrešaka TEC veći od 255. CAN kontroler u ovom stanju neće stupati u interakciju sa sabirnicom i treba ga ponovno pokrenuti putem CAN.restart() za nastavak.

Zastavice poruka

Ove vrijednosti predstavljaju metapodatke o CAN poruci. Funkcije CAN.send(), CAN.recv() i CAN.set_filters() ili prihvaćaju ili vraćaju cjelobrojnu vrijednost sastavljenu od nula ili više ovih zastavica spojenih bitovnom operacijom ILI.

FLAG_RTR: int

Označava da je poruka zahtjev za daljinski prijenos.

FLAG_EXT_ID: int

Ako je postavljeno, označava da je identifikator poruke prošireni (29-bitni). Ako nije postavljeno, označava da je identifikator poruke standardni (11-bitni).

FLAG_UNORDERED: int

Ako je postavljeno u argumentu flags funkcije CAN.send(), označava da je u redu ako se poruke s istim CAN ID-om šalju bilo kojim redoslijedom na sabirnicu.

Inače pokušaj stavljanja u red više poruka s istim ID-om može rezultirati neuspjehom CAN.send() ako hardver kontrolera ne može osigurati poredak.

Ova zastavica nikada nije postavljena na primljenim porukama i zanemaruje ju CAN.set_filters().

Zastavice pogrešaka pri primanju

Rezultat CAN.recv() uključuje cjelobrojnu vrijednost sastavljenu od nula ili više ovih zastavica spojenih bitovnom operacijom ILI. Ako su postavljene, ove zastavice označavaju potencijalne opće probleme pri primanju CAN poruka.

RECV_ERR_FULL: int

Hardverski FIFO u kojem je ova poruka primljena je pun i dodatne dolazne poruke mogu se izgubiti.

RECV_ERR_OVERRUN: int

Hardverski FIFO u kojem je ova poruka primljena je pun i jedna ili više dolaznih poruka je izgubljena.

IRQ vrijednosti

IRQ_RX: int

Proslijedite argumentu trigger metode irq() kako bi se rukovatelj aktivirao svaki put kada CAN kontroler primi cijelu poruku u RX FIFO. Unutar rukovatelja pročitajte poruku s recv().

IRQ_TX: int

Proslijedite argumentu trigger metode irq() kako bi se rukovatelj aktivirao svaki put kada CAN kontroler završi pokušaj prijenosa (uspjeh ili neuspjeh). Unutar rukovatelja koristite dodatne bitove ispod kako biste saznali koji je sandučić (mailbox) dovršen i je li propao – vidi IRQ zastavice.

IRQ_STATE: int

Proslijedite argumentu trigger metode irq() kako bi se rukovatelj aktivirao svaki put kada kontroler prijeđe između vrijednosti STATE_* (aktivno / upozorenje / pasivno / bus-off). Koristite state() unutar rukovatelja za čitanje novog stanja.

IRQ_TX_FAILED: int

Statusna zastavica koja može biti postavljena u irq().flags() kada nastupi događaj IRQ_TX. Označava da pokušaj prijenosa nije uspio (obično jer je pozvana cancel_send(), ili je kontroler ušao u stanje pogreške).

IRQ_TX_IDX_SHIFT: int

Položaj bita polja indeksa sandučića za prijenos unutar vrijednosti irq().flags() tijekom događaja IRQ_TX. Indeks sandučića se izdvaja kao (flags >> IRQ_TX_IDX_SHIFT) & IRQ_TX_IDX_MASK.

IRQ_TX_IDX_MASK: int

Bitna maska polja indeksa sandučića za prijenos unutar vrijednosti irq().flags() tijekom događaja IRQ_TX. Izdvojeni indeks odgovara cijelom broju koji vraća odgovarajući poziv send() (int u rasponu od 0 do TX_QUEUE_LEN).

IRQ zastavice

Poziv CAN.irq() registrira rukovatelja prekidom s jednim ili više okidača CAN.IRQ_RX, CAN.IRQ_TX i CAN.IRQ_STATE.

Funkcija vraća IRQ objekt, a poziv funkcije flags() na ovom objektu vraća cijeli broj koji označava koji su događaj(i) okidača aktivirali prekid. CAN IRQ rukovatelj treba pozivati funkciju flags() opetovano sve dok ne vrati 0.

Kada funkcija flags() vrati postavljen bit CAN.IRQ_TX, rukovatelj može također provjeriti sljedeće bitove zastavica u rezultatu za dodatne informacije o TX događaju:

  • Bit CAN.IRQ_TX_FAILED je postavljen ako prijenos nije uspio. Obično se to događa samo ako je pozvana CAN.cancel_send(), iako se može dogoditi i ako kontroler uđe u stanje pogreške.

  • CAN.IRQ_TX_IDX_MASK << CAN.IRQ_TX_IDX_SHIFT je bitovno maskirano područje vrijednosti zastavica koje sadrži indeks međuspremnika za prijenos koji je generirao događaj. Ovo će biti cijeli broj u rasponu od 0 do CAN.TX_QUEUE_LEN (isključivo) i odgovarat će rezultatu prethodnog poziva CAN.send().

IRQ_TX primjer

from machine import CAN

def irq_send(can):
    while flags := can.irq().flags():
        if flags & can.IRQ_TX:
            idx = (flags >> can.IRQ_TX_IDX_SHIFT) & can.IRQ_TX_IDX_MASK
            success = not (flags & can.IRQ_TX_FAILED)
            print("irq_send", idx, success)

can = CAN(1, 500_000)
can.irq(irq_send, trigger=can.IRQ_TX, hard=True)

Važno

Ako je postavljen okidač CAN.IRQ_TX, tada rukovatelj mora pozivati flags() opetovano sve dok ne vrati 0, kao što je prikazano u ovom primjeru. Inače, CAN prekidi možda neće biti ispravno ponovno omogućeni.