Sida 1 av 1
skillnad på kod? (avr asm)
Postat: 18 september 2004, 17:04:28
av Rymdninja
Hejsan!
Jag bara undrar om det är någon essentiell skillnad på dessa två kod snuttar
charA är addressen till en konstant bara...
Kod: Markera allt
bigLoop:
ldi ZL, low(charA*2)
ldi ZH, high(charA*2)
rcall writeChar
rjmp bigLoop ; now we do this again
writeChar:
lpm
out PORTD, R0 ; send it to the port ;
ret
och
Kod: Markera allt
bigLoop:
ldi ZL, low(charA*2)
ldi ZH, high(charA*2)
lpm
out PORTD, R0 ; send it to the port ;
rjmp bigLoop ; now we do this again
alltså bortsett från exekveringstid och längd på programmet.
Anledningen till att jag frågar är att när jag skickar data till PORTD med andra koden så blir resultatet som jag vill..men med den första snutten så börjar min led-display blinka. Precis som om att PORTD nollställs vid varje rcall eller nåt....
tack o hej
Postat: 18 september 2004, 22:22:17
av Hedis
Dom skall fungera exact likadant.
Skummt att det blinkar med ena.
Du är helt säker på att den inte manipulerar portD ngn annan stans i programmet?
Måste nästan vara så.
Prova annars o lägg in ett fast värde istället för att hämta det med stacken o se om det likadant då.
Postat: 18 september 2004, 23:26:33
av erixon
Du har troligt vis inte stält in stack pekren den som håller reda på retur addressen...
lägg den här coden efter Reset så borde det fungera
Kod: Markera allt
ldi temp,low(RAMEND)
out SPL,temp ;init Stack Pointer
Postat: 19 september 2004, 01:10:49
av Rymdninja
erixon: jag tror inte jag riktigt fattar vad du menar....efter reset?
Du menar alltså att stackpekaren inte initieras by default?
Postat: 19 september 2004, 11:15:00
av Hedis
Ahh det stämmer, Den raden måste du ha med.
Nej den initieras inte som default tyvärr.
Så när du hoppade så skrev den om alltihop o det blev knas.
Såhär någonting borde det se ut (om man använder den init som jag brukar köra med) fast den som föreslogs här kanske funegarr lika bra o är mindre?:
Kod: Markera allt
init:
ldi r16,ramend ;Init stackpointer
out spl,r16
ldi r16,high(ramend)
out sph,r16
ldi temp,$ff
out ddrc,temp ;Init port c to output
bigLoop:
ldi ZL, low(charA*2)
ldi ZH, high(charA*2)
rcall writeChar
rjmp bigLoop ; now we do this again
writeChar:
lpm
out PORTD, R0 ; send it to the port
ret
Senså brukar jag ha med ngt sånthär i toppen på varje projekt
Kod: Markera allt
.include "m32def.inc"
.def temp = r16 ;Temporärt register
.def temp2 = r13 ;Temporärt register
.def count1 = r18 ;Används för timer
.def count2 = r19 ;Används för timer
.CSEG
Postat: 19 september 2004, 14:13:08
av Rymdninja
tack för alla svar...efter en nogrannare titt i databladet så står det juh där med att man måste initiera stackpekaren
ha en bra dag

Postat: 20 september 2004, 01:06:59
av chille
Varför använder alla r16 som temp?

Postat: 20 september 2004, 08:21:01
av karlstedt
Det kommer sig nog av att r16 är det första (lägsta) register som man kan köra "immediate"-instruktioner på.
Postat: 20 september 2004, 18:29:44
av RDX*
Det brukar vara standard att köra r16 som tempregister. Det underlättar att programmera assembler med "standard register" dvs. alla register är förbestämda vad de är till för. Om man tex använder en subrutin som någon annan har skrivigt så är det bra man inte använder ett register som temp när subrutinen har sparat något viktigt i registret. Vilket register som är vilket kan dock variera beroende på processor och programmeringsspråk.