Hallo an alle,
seit etwas über ein Jahr verfolge ich hin und wieder dieses Forum und
heute habe ich mich dann doch noch angemeldet :)
Habe heute die ersten Gehversuche mit meinem SKT500-Board und Assembler
gemacht.
Mein erster Code sollte diese Funktion haben:
Betätigung Taster 0 -> LED3 ein
Betätigung Taster 7 -> LED4 ein
beide Taster betätigt -> beide LEDs ein
würde mich freuen wenn ihr meinen Code mal anschaut und
verbesserungsvorschläge hättet :)
Beim Testen am STK500 kommt selten dieser Fehler:
Ist einer der beiden Taster betätigt und wir der andere auch betätigt,
sind beide LEDs kurz aus oder solange aus, bis ich die Taster (oder nur
einen von beiden) loslasse und wieder betätige. Dann funktioniert es
wieder einige male problemlos.
Vielen Dank schon mal für eure Hilfe, Tips und Tricks :)
Juke Box schrieb:> Betätigung Taster 0 -> LED3 ein> Betätigung Taster 7 -> LED4 ein> beide Taster betätigt -> beide LEDs ein
Für so etwas einen µC verwenden, ist wie mit Kanonen auf Spatzen
schiessen.
Umständlicher geht es wohl nicht mehr?
Was willst du Kevin?
Ich versuche mir Assembler beizubringen und du versuchst am Sonntagabend
einen auf dicke Hose zu machen!!?
WIESO meldest du dich wenn du zu meinem Anliegen absolut nichts
beitragen willst oder kannst???
Ich wollte einfach nur mal anfangen zu coden. Aller Anfang ist schwer.
Bin froh dass ich mein Ziel gar nicht so schlecht erreicht habe.
Hätte ich mir ein Ziel gesetzt, das für einen µc zugeschnitten ist,
hätte ich heute sicher kein Code zustande gebracht, das funktioniert.
Hat hier irgendwer noch Lust mein Prog anzuschauen und zu beurteilen,
was man einfacher machen kann oder oder oder...???
Und du Kevin... lass die Hände schön über der Bettdecke wenn du gleich
schlafen gehst!
Man kann auch einzelne Bits testen, bzw setzen und löschen.
Beitrag "sbr,cbr.sbrs,sbrc"
cpi r16, 0b11111110;vergleiche Tasterkombination mit NUR Taster 0
gedrückt
Da gibt es einen Befehl:
sbrs (Skip if bit in Register is set)
analog dazu
sbrc (Skip if bit in Register is clear)
Da wird der jeweils nächste Befehl übersprungen (skip).
Das würde ich hier eher verwenden.
Ansonsten passt das wohl schon, ohne es jetzt genau ausprobiert zu
haben. Aber es gilt: Viele Wege führen nach Rom.
Danke Norbert!
Werd ich mir anschauen. Kennst du dich sehr gut mit Assembler aus?
Was kann ich im Code besser machen? Abgesehen jetzt von der Tatsache,
dass hier mit Kanonen auf spatzen geschossen wird^^
Auch eine Lösung wäre.
Käme ohne Vergleiche etc. aus.
loop:
IN r16,PINB ;einlesen
AND r16,0b10000001 ;wichtige Bit Maskieren
CLC ;Carrybit löschen
ROR r16 ;Rollen durchs Carrybit 5 mal
ROR r16
ROR r16
ROR r16
ROR r16
IN r17,PORTB ;Outport lesen
AND r16,0b11100111 ;beeinflußte Bits löschen
EOR r17,r16 ;XOR-Verknüpfen
OUT PORTB,r17 ;Outport ausgeben
RJMP loop
oder
loop:
IN r16,PIND ;lade Tasterkombination in r16
IN r17,PORTB
OR r17,0b00011000
SBRS r16,0 ;Überspringen des nächst.Befehls bei gesetzem Bit 0
CBR r17,3 ;Clear Bit 3 in Reg r17
SBRS r16,7 ;Überspringen des nächst.Befehls bei gesetzem Bit 7
CBR r17, 4
OUT PORTB, r17
RJMP loop
Was sich dafür noch empfiehlt zu lesen ist
http://www.atmel.com/images/doc0856.pdf
Dieses Dokumemt zeigt eine Übersicht über die Assembler-Befehle und
deren Wirkung.
oookay... danke schon mal Dennis
ich sehe schon... es gibt sehr viel zu lernen :)
werd morgen gleich mal eure vorschläge genauer anschauen und hoffentlich
auch einen guten tag haben wie heute
MoinMoin,
ich hätte da ein paar Vorschläge =).
1. Lass dich von solchen Beiträgen wie dem vor mir nicht davon abhalten
weiterzumachen, jeder fängt mal klein an, und natürlich ist simple LEDs
an und aus machen nicht DAAAAS Metier wo man unbedingt nen µC braucht,
aber wie gesagt, irgendwomit muss man ja anfangen.
und nun zu deinem Code.
Ich würde in deiner Loop direkt abfragen, ob auch beide Tasten gedrückt
sind. Also quasi so:
1
loop: in r16, PIND ; lade Tasterkombination in r16
2
3
cpi r16, 0b11111110 ; vergleiche Tasterkombination mit NUR Taster 0 gedrückt
4
breq LED3_on ; Springe zu LED3_on
5
cpi r16, 0b01111111 ; verlgeiche Tasterkombination mit NUR Taster 7 gedrückt
6
breq LED4_on ; Springe zu LED4_on
7
cpi r16,0b011111110
8
breq LED34_on
9
rjmp loop
dann kannst du dir nämlich in deiner LED3_on und LED4_on die Abfrage
sparen.
Als nächstes ist mir aufgefallen, das du deine LEDs genaugenommen nicht
einschaltest, wenn du die Taste drückst, sondern (wenn auch sehr
schnell) blinken lässt.
Evtl kann man das in eine LED_on und eine LEDoff splitten, die dann je
nachdem was gedrückt ist, aufgerufen werden. Dann müsstest du aber davon
abrücken, jeweils den ganzen PortD abzufragen, welche Tasten gedrückt
sind, sondern maskierst dir deine Bits für den jeweiligen schalter aus.
also quasi so:
1
StartLED:
2
3
in r16,PortD
4
andi r16,0b00000001 (evtl auch nur and und den binären Wert in nen Register laden, bin grad unsicher obs andi gibt *gg.)
5
sbrc r16,1 (kann auch sbrc r16,0 sein, bin grad unsicher ob bei sbrc das bit oder die Wertigkeit angegeben wird,
6
lange nix mehr mit assembler gemacht)
7
rcall LED3_off
8
sbrs r16,1
9
rcall LED3_on
10
11
in r16,PortD
12
andi r16,0b10000000
13
sbrc r16,128
14
rcall LED4_off
15
sbrs r16,128
16
rcall LED4_on
17
18
in r16,PortD
19
andi r16,0b10000001
20
sbrc r16,129
21
rcall LED34_on
22
sbrs r16,129
23
rcall LED34_on
24
25
rjmp Start_LED
26
27
LED3_on:
28
ldi r16,0b11111110
29
out PortB,r16
30
ret
andi (and imediate) macht eine bitweise Verknüpfung des Registerwertes
mit dem Wert der da steht. Damit maskierst du dir deine Bits aus, um die
es dir geht.
sbrc (skip if bit in register is cleared) überspringt den nächsten
Befehl, wenn die ausmaskierten Bits null sind. Also wenn dein Taster
gedrückt ist, liefert er dir ne 0, also wird der Befehl zum LED
auschalten übersprungen. sbrs macht das gleiche nur andersrum.
rcall springt zu der entsprechenden Sprungmarke, also ähnlich wie dein
breq, mit dem Unterschied, das er sich beim call/rcall merkt, von wo er
gesprungen ist, und kehrt danach wieder dorthin zurück. Deshalb musst du
auch den Stackpointer initialisieren, dort "merkt" sich dein µC nämlich,
wo er herkam. Mit ret in LED3_on springst du dann zurück. Damit umgehst
du dann auch das Problem, das sich dir wahrscheinlich gestellt hat, als
du die Abfrage ob beide gedrückt sind, in deine LED3/LED4_on getan hast.
Nämlich wenn Taster0 gedrückt, würde er bei dir ja nicht weiter nach den
anderen Tasten fragen. Und mit rcall umgehst du das Problem ganz
einfach, indem du einfach dort weitermachst, wo du herkamst.
Wichtig, wenn du mit rcall arbeiten möchtest, ist den Stackpointer zu
initialisieren
;stackpointer initialisieren
ldi r16,low(ramend)
out spl,r16
ldi r16,high(ramend)
out sph,r16.
Ich hoffe, damit ist dir erstmal ein wenig geholfen und wünsch dir viel
Spass beim Basteln
MfG Chaos
Da war ich schon etwas umnachtet.
SBRS muß SBRC sind.
loop:
IN r16,PIND ;lade Tasterkombination in r16
IN r17,PORTB
OR r17,0b00011000
SBRC r16,0 ;Überspringen des nächst.Befehls bei gelöschtem Bit 0
CBR r17,3 ;Clear Bit 3 in Reg r17
SBRC r16,7 ;Überspringen des nächst.Befehls bei gelöschtem Bit 7
CBR r17, 4
OUT PORTB, r17
RJMP loop
Gruß Dennis
Hi
Ich hätte da noch eine Quelle für dich, die dir zusätzlich zum Tutorial,
welches du hier findest, ein wenig weiterhelfen könnte. Schau mal bei
AVR-Praxis-Forum rein. Dort findest du unter der Rubrik FAQ einen
Beitrag: Keine Angst vor Assembler. Da steht so ein bischen was drin.
Gruß oldmax