Problém s PIC 16F876
Moderátor: Moderátoři
Problém s PIC 16F876
Už strácam nervy pri jednom vlastnom projekte, kde pomocou PIC16F876 ovládam LCD display, I2C zbernicu /pomocou vlastnej rutiny, nie pomocou intrených I2C/ atď.
Celý projekt mi funguje, akurát som sa rozhodol, že posielanie sériových dát z RB7 /funkčné pomocou vlastných rutín/ vyriešim pomocou prerušení.
A tu mi vznikol problém.
Keď som nakonfiguroval TMR0 /nikde nieje využívaný, len ako počítadlo na prerušenie/ a následne povolil prerušenie, celý program mi zblbne a stratí "niť". Mám pocit že PIC je rušený z portu B, pretože keď som dal 20nF kondík na RB4 -je to E signál do LCD tak sa to zlepšilo, ale aj tak sa program časom zauzlí.
Dokonca mi program zblbne aj keď do prerušenia nenapíšem nič.
To znamená len toto:
;prerušenie
prerus
bcf INTCON,T0IF
retfie
Aj napriek nič nevykonávajúcemu prerušeniu procesor blbne.
Keď prerušenie od TMR0 zakážem, všetko ide perfektne.
Myslím tým BCF INCON,T0IE.
Neexistuje na to nejaká finta? Už som pár vlastných projektov urobil, ale toto ma teda dostalo.
Ďakujem vám za akúkoľvek radu.
Celá chyba sa prejavuje ako problém zo stránkovaním pamäte, alebo zlým nastavením PCLATH. Jednoducho... zrazu to skočí úplne mimo.
David
Ako máš riešené uloženie a návrat programových charakteristík
Kód: Vybrat vše
;
;
itvector ORG 0x004 ; interrupt vector location
movwf w_temp ; save off current W register
swapf STATUS,W ; STATUS save to W
clrf STATUS ; banky do 0
movwf status_temp ; save off contents of STATUS register
movfw PCLATH
movwf pclath_temp
clrf PCLATH
....
a ešte je dobré w_temp a status_temp ukladať na adresy do RAM od 0x70....0x7F
a návrat z isr
Kód: Vybrat vše
RetItRout100
movfw pclath_temp
movwf PCLATH
swapf status_temp,w
movwf STATUS
swapf w_temp,f
swapf w_temp,w ; restore pre-isr W register contents
returnorg 0x0000
. goto Init ; skočí na nastavenie procesoru
org 0x0004
. goto prerus ; skočí na prerušenie
A teraz prerušenie - pôvodné:
prerus
. movwf W_temp ;adresa je 0x72 - prístupná zo všetkých BANK
. swapf STATUS,w
. clrf STATUS
. movwf ST_temp ;adresa RAM je 0x70 - prístupná zo všetkých Bank
. movf PCLATH,w
. movwf PCL_temp ;adresa RAM 0x71 - prístupná zo všetkých BANK
;;;;;
;rutina prerušenia
;;;;;
end_prerus
. movf PCL_temp,w
. movwf PCLATH
. swapf ST_temp,w
. movwf STATUS
. swapf W_temp,f
. swapf W_temp,w
. retfie
;*********************************************************
Po laborovaní som zálohovanie odstránil a celé prerušenie zmenil na:
prerus
. BCF INTCON,T0IF
. retfie
Tie bodky som doložil aby boli dodržané odstavce tak ako v zdrojáku.
Keď prerušenie vypnem, všetko funguje ako má.
Neviem si vysvetliť ako môže bezvýznamné prerušenie ktoré nič neobsahuje ovplyvniť niečo v registroch.
Ale neviem samozrejme urobiť ďalšie veci na ktoré to prerušenie potrebujem.
Keďže adresujem aj PCLATH, asi som urobil chybu v tomto:
org 0x0004
. goto prerus!!!!
Ak nie je PCLATH v nule, tak to asi zblbne tam!
Že ano?
Viem to urobiť aj takto?
org 0x0004
.. movf PCLATH,w
.. movwf PCL_temp ;0x71RAM
.. CLRF PCLATH
.. goto prerus
asi to by malo byť takto že?
A potom návrat registra pri ukončovaní prerušenia tak ako to bolo v predošlom príspevku...
Ďakujem
Len tomu retfie som nepochopil.
Ty nepoužívaš retfie na návrat z prerušenia?
Potom sa čím vraciaš?
Return-om?
Ešte niečo.
Pokiaľ v isr nemáš nič čo by ti pomiešalo registre STATUS, W a PCLATH, tak ich nemusíš zálohovať. Alebo sa mýlim?
Podľa mňa keď chceš vytvoriť nič nerobiace isr, tak stačí len
BCF INTCON,7
retfie
či....
To je dôvodom toho zmätku v chode programu.
------------------------------------------------------
Do toho end_prerus to už nevojde a neobnoví sa to čo sa má obnoviť.
INTCON,7 je GIE (general interrupt enable bit)- stačí na to retfie.
Ten sa nahodí s tou poslednou inštrukciou v end_prerus....... retfie.
Re: Problém s PIC 16F876
Dike píše:;prerušenie
prerus
bcf INTCON,T0IF
retfie
TU NESMIE BYŤ retfie...... MUSÍ TAM BYŤ GOTO end_prerus,
preto ti to blbne
Ten tvůj pic má totiž 8K paměti programu, ale pomocí instrukce goto lze adresovat pouze 2K, tedy 11 bitů. Zbylé dva bity se berou právě z PCLATH. Takže, pokud máš tu rutinu "prerus" hned na začátku, tak v PCLATH musí být opravdu nula. Pak je ale také možné, že ji máš až někde dál (přes 2K) a pak musíš do PCLATH dát tu správnou hodnotu, jinak to skočí jinam. Podle mě je nejlepší začít tu přerušovací rutinu rovnou na té adrese 4 a neskákat na ni tím goto.
Kód: Vybrat vše
0004 goto prerus
.
.
prerus
bcf INTCON,T0IF
retfie
Ako sa zaistí správne vykonanie toho GOTO?
Bez nastavenia PCLATH program BUDE POKRAĆOVAŤ v stránke kde sa program nachádzal v okamihu prerušenia.
V prípade, že program má vtesnaný v nultej stránke to bude fungovať. Inak sa to bude chovať nepredvidateľne.
Aj v tej časti, kde odkladá W,STATUS, PCLATH mu chýba nastavenie PCLATH do stránky, kde bude ISR. Samozrejme ak je celý program iba v stráke 0 to bude fungovať.