Timer0 overflow interrupt

PIC, AVR, Arduino, Raspberry Pi, Basic Stamp, PLC mm.
Användarvisningsbild
PaNiC
Inlägg: 2565
Blev medlem: 15 augusti 2003, 22:16:15
Ort: Skånelandet

Timer0 overflow interrupt

Inlägg av PaNiC »

Behöver nyttja detta funktion. För det första hittar jag inte namnet på vektorn utan använder $007. För det andra får jag ett felmeddelande när jag kompilerar som talar om att det finns en overlap i CSEG.

Kod: Markera allt

.include "8515def.inc"

.org $001
	rjmp reset
.org INT0	
	rjmp select
.org INT1
	rjmp doit
.org $007
	rjmp sweep
Hur får jag rätt på detta?

Edit: Hittade namnet på vektorn.
Användarvisningsbild
Melker
Inlägg: 410
Blev medlem: 26 maj 2003, 22:17:34
Ort: Umeå

Inlägg av Melker »

Ska det inte vara två bytes mellan varje vektor, reset på 0x0000, int0 på 0x0002 osv...?

Löste sig overlap-errorn med vektornamnet?
Användarvisningsbild
PaNiC
Inlägg: 2565
Blev medlem: 15 augusti 2003, 22:16:15
Ort: Skånelandet

Inlägg av PaNiC »

Nä där ska inte vara två bytes mellan? Men reset ska mycket riktigt vara på $0000 ;).

Nope. Overlap står kvar. Men om jag kommenterar bort raderna innan så försvinner det.
Användarvisningsbild
chille
Inlägg: 2469
Blev medlem: 25 juni 2003, 20:54:41
Ort: Stockholm
Kontakt:

Inlägg av chille »

Gör något i stil med det här:

.cseg
rjmp reset
reti
rjmp korv
reti
reti
rjmp banan

...osv, då kommer du garanterat få rätt offset plus att du får en kommplett lista på alla interrupts om nån av de skulle behövas i framtiden.
Användarvisningsbild
PaNiC
Inlägg: 2565
Blev medlem: 15 augusti 2003, 22:16:15
Ort: Skånelandet

Inlägg av PaNiC »

Vet inte vad det betyder. Skulle du vilja förklara?

Har stött på ett problem till för övrigt.

Kod: Markera allt

.include "8515def.inc"


.cseg
.org $0000
	rjmp reset
;.org INT0	
;	rjmp select
;.org INT1
;	rjmp doit
.org ovf0ADDR
	rjmp sweep

.def temp=r16
.def eeadr=r17
.def delay=r18
.def baseee=r19
.def temp2=r20
.def temp3=r21
.def teckenh=r22
.def teckenl=r23


Reset:
	ldi r16,high(RAMEND);RAM Stack init
	out	SPH,r16
	ldi	r16,low(RAMEND)
	out	SPL,r16

;Speca outputs
	ser temp
	out ddra, temp
	out ddrb, temp
	out ddrc, temp
	ldi temp, 240 ;fyra övre bitarna ut
	out ddrd, temp

	
;Init UART
	ldi temp, 47
	out UBRR, temp
	sbi UCR, TXEN
	sbi UCR, RXEN

	clr temp
	out portc, temp

	clr eeadr
	out EEARL, eeadr

;Init interrupts
	ldi temp, 192
	out GIMSK, temp

;Init timer0
	ldi temp, 0b00000100
	out TCCR0, temp
	
	ldi temp2, 128
	ldi temp3, 128


	rjmp main
	sei

main:
	sbis pind, 3
	rcall doit
	sbis pind, 2
	rcall select
	in temp, UDR
	cpi temp, 1
-->	breq prog
	rjmp main


sweep:
	mov eeadr, baseee
	clr temp
	out TCNT0, temp
	ldi temp2, 128
	ldi temp3, 128
	rcall loadtecken
	out portc, temp2
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portc, temp2
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portc, temp2
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portc, temp2
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portc, temp2
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portc, temp2
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portc, temp2
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portc, temp2
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	cbi pinc, 0
	out portd, temp3
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portd, temp3
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portd, temp3
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	out portd, temp3
	out porta, teckenh
	out portb, teckenl
	ror temp2
	rcall loadtecken
	reti

prog:
	cli
	in temp, UDR
	cpi temp, 4
-->	breq main
	out EEARL, baseee
	mov eeadr, baseee
	sbi EECR, EEMWE
	out EEDR, temp
	sbi EECR, EEWE
	inc eeadr
	nop
	nop
	nop

	rjmp prog

Select: 
	rcall delay
	sbis pind, 2
	rcall delay
	sbis pind, 2
	rjmp select
	;härunder
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	inc baseee
	ret

Doit:
	rcall delay
	sbis pind, 3
	rjmp doit
	rcall delay
	;härunder
	ret



	
delay: 
	inc delay
	cpi delay, 255
	brne delay
	clr delay
	ret

	

loadtecken:
	sbi EECR, EERE
	in teckenh, EEDR
	inc eeadr
	out EEARL, eeadr
	sbi EECR, EERE
	in teckenl, EEDR
	inc eeadr
	out EEARL, eeadr
	ret
Koden är väl inte så snygg nej. Klaga inte på hur jag adderar 32 till ett register :D. Är just nu inte i stånd att förstå hur jag ska göra annars.
Men iallafall. Där jag har satt pilar får jag felet "Relative branch out of reach". Misstänker att det är något med stackpekaren. Vad betyder det och hur ska jag åtgärda det?
Användarvisningsbild
erixon
Inlägg: 380
Blev medlem: 27 augusti 2003, 10:21:58

Inlägg av erixon »

Tja det beror på att breq kan bara hoppa -64 till 63 i förhålande till PC (Program conter)

Kod: Markera allt

-->breq prog
rjmp main

kan bytas ut mot 

brne main
rjmp prog
som exempel
Istället för att inc typ 32 gånger så använd subi
subi baseee, -32 exempel
Användarvisningsbild
PaNiC
Inlägg: 2565
Blev medlem: 15 augusti 2003, 22:16:15
Ort: Skånelandet

Inlägg av PaNiC »

Åfan. Hade jag ingen aning om. Jaja, de felen är avhjälpta nu iaf. Tackar :).
Användarvisningsbild
chille
Inlägg: 2469
Blev medlem: 25 juni 2003, 20:54:41
Ort: Stockholm
Kontakt:

Inlägg av chille »

Kod: Markera allt

delay: 
   inc delay 
   cpi delay, 255 
   brne delay 
   clr delay 
   ret
kan ändras till

Kod: Markera allt

delay:
   dec delay
   brne delay
   ret
Ladda delay med valfritt värde och den kommer räkna ner till 0 och sedan returnera. Dock kommer den köras ganska mycket snabbare så du får köra högre värden. Vill du alltid köra samma delay kan du göra såhär:

Kod: Markera allt

delay:
   ser delay ; 255
dly:
   dec delay
   brne dly
   ret
Sen är det nästan lite onödigt med en egen variabel som heter delay. Bättre i de flesta fall att köra en som heter temp som används nästan överallt. Akta dig bara så du inte först skriver temp, sen kör delay, och efter det vill läsa första värdet du skrev till den, sen kommer alltid bli 0 då :D
Användarvisningsbild
PaNiC
Inlägg: 2565
Blev medlem: 15 augusti 2003, 22:16:15
Ort: Skånelandet

Inlägg av PaNiC »

Nu har jag lite kod till ett annat projekt. Problemet här är att den hoppar till fel ställe när timer0 gör overflow.

Kod: Markera allt

.include "8515def.inc"

.def temp=r16
.def rtcdat=r17
.def cnt=r18
.def temp2=r19


.CSEG
.org ovf0ADDR
	rcall sweep



reset:

;initiera stackpekaren
	ldi temp, HIGH(RAMEND)
	out SPH, temp
	ldi temp, LOW(RAMEND)
	out SPL, temp

;Sätt upp portar
	ser temp
	out ddra, temp
	out ddrb, temp
	out ddrc, temp
	ldi temp, 0b11111000
	out ddrd, temp
	
;Init interrupts
	ldi temp, 0b00000010
	out timsk, temp
	sei
;Init timer0
	ldi temp, 0b00000100
	out TCCR0, temp

rjmp main



main:
	nop
	rjmp main


sweep:
	push temp
	in temp, sreg
	push temp
	inc temp2
	out porta, temp
	pop temp
	out sreg, temp
	pop temp
	reti
Den börjar om från början i programmet istället för att kalla på sweep-funktionen.

Något annat som är jävligt irriterande är att disassembler-fönstret hoppar fram hela tiden när jag kör koden i simulatorn. Hur stänga av?
Senast redigerad av PaNiC 28 oktober 2004, 14:54:43, redigerad totalt 1 gång.
Användarvisningsbild
Melker
Inlägg: 410
Blev medlem: 26 maj 2003, 22:17:34
Ort: Umeå

Inlägg av Melker »

.org ovf0ADDR
rcall sweep
Byt rcall mot rjmp, så ska det nog funka, annars läggs adressen av "rcall sweep"-raden på stacken, och när reti körs så hoppar den dit isället för där den fick interruptet.
Användarvisningsbild
PaNiC
Inlägg: 2565
Blev medlem: 15 augusti 2003, 22:16:15
Ort: Skånelandet

Inlägg av PaNiC »

Aj.. Givetvis. Så dumt det kan bli :).
Man stirrar sig blind emellanåt.
Tackar.
Användarvisningsbild
erixon
Inlägg: 380
Blev medlem: 27 augusti 2003, 10:21:58

Inlägg av erixon »

Jag ser två fel....
1. Du startar inte genom att hoppa till reset
det gör du genom
.org 0x0000
rjmp Reset
2. du använder Rcall detta gör att du push:ar på en tillbaka hoppnings address vilket i sin tur gör att när du gör reti så kommer den ta den address som du har push:at och inte där intreuptet intrefade, så använd rjmp istället, för just nu har du mines läckars


Hoppas det klar gjorde en del saker :)
Användarvisningsbild
PaNiC
Inlägg: 2565
Blev medlem: 15 augusti 2003, 22:16:15
Ort: Skånelandet

Inlägg av PaNiC »

Jo nu fungerar det.
Lyckas fortfarande inte kommunicera med DS1302n (som en annan del av detta programmet ska göra) men det ska väl lösa sig. Antingen innan eller efter jag har gått i taket.
Skriv svar