266
Jein, in unserem Fall ist es ein Schaltnetz. Es gibt allerdings ALU's die mit einem Mikroprogramm rechnen FPU's Floating Point Units..
Nerven behalten, wir haben praktisch 32 Akkus! Tipp: Nehmt einfach das Register R16 als temp als "Ersatz-Akku". Die Lösung zu der µC-Aufgabe muss ich sowieso selber erstellen, bzw. besprechen, daher zählen funktionierende sinnvolle Lösungen mit "unserem" System...
Man sollte, wenn es nicht klar ist kommentieren, besonders wenn man keine aussagekräftigen Bezeichner verwendet hat!
Ich tendiere dazu "schlampige" Lösungen schlechter zu bewerten als klare ordentliche saubere einfach lesbare ;-)
BRCC k Branch if Carry Cleared If (C=0) THEN PC:=PC+k+1 None 1/2
BRSH k Branch if Same or Higher If (C=0) THEN PC:=PC+k+1 None 1/2
BRCS k Branch if Carry Set If (C=1) THEN PC:=PC+k+1 None 1/2
BRLO k Branch if Lower If (C=1) THEN PC:=PC+k+1 None 1/2
Bei AT90S2313 wird jeweils der selbe OP-Code erzeugt somit ist BRCC gleich BRSH und BRCS gleich BRLO. Warum zwei Bezeichnungen für die selbe Sache verwendet werden ist mir noch schleierhaft..
Was passiert bei
.def temp = R16 ldi temp, 0b00000111 cp temp, 0b00000111 BREQ 1 RJMP foo RJMP bar foo: ... bar: ...
springt er zu foo oder bar?
Also da z = 1 wird er wohl zu bar springen, bedenke wir zählen Wörter = 2 Byte im Programmspeicher.
Keine Panik, das macht man nicht von Hand, man springt auf Marken und das Ausrechnen von k übernimmt der Assembler!
Ist es dann alleine mir überlassen wie ich ihn verarbeite, also z.B. zur schnelleren Umsetzung einfach negiere?
Würde in meinem Programmcode dann so aussehen:
ldi c,13 cp c,a brpl spring ;wenn das N flag nicht gesetzt ist, also a = c || a < c, dann spring ldi a,13 spring:
Die andere Möglichkeit hierbei wäre dann, anstatt brpl zwei Befehle zu nehmen und das ganze etwas anders aufzubauen:
cpi a,13 brmi spring ; wenn a - 13 < 0, also 13 > a breq spring ; wenn a = 13, nötig um Negation von a>13 zu vervollständigen ldi a,13 spring:
Welche der zwei Möglichkeiten ist besser geeignet, und welche passt eher zur Aufgabenstellung? ( die zwei Möglichkeiten geben sich nicht viel in Hinsicht der Programmlänge, aber die erste Möglichkeit hat nur 2 unterschiedliche Ausführungslängen, die andere 3, wobei 2 davon die gleiche Länge haben.
Antwort: Bei Lösung1 wird ein Register c benötigt, würde ich vermeiden, unterschiedliche Ausführungslängen sind aber manchmal auch unerwünscht.. Wenn es so gut kommentiert ist wie hier hab ich mit beiden Lösungen kein Problem!
setze ich das am besten so um:
ldi b,3 cpi a,2 brne spring ; wenn sie nicht gleich sind springe ldi b,7 spring:
Ist das so OK, oder muss ich mich stärker nach der Vorgabe richten, auch wenn das Ergebnis das gleiche ist?
Antwort: Ist so bestens! Lösung soll kurz, einfach, gut verständlich und schnell sein. Trifft hier alles zu.
Ich würde es nun so lösen:
ldi c,10 ldi i,0 schleife: mov a,i inc i cpi c,i brpl schleife ; solange c>=i ist, also N=0, gehe zu schleife
würde diese Lösung vom Aufbau her passen?
Antwort: Nein, es sind Fehler enthalten: cpi c,i und die Schleife ist fuß-gesteuert, For-Schleifen sind aber Kopf-gesteuert. Hier eine richtige Lösung:
ldi i,0 ;i initalisieren schleife: cpi i,11 ;i-11 testen, für 0 bis 10 ist es negativ (N = 1) brpl ende;wenn Ergebnis positiv, ist Bedingung falsch mov a,i ;den Rumpf ausführen inc i ;i++ rjmp schleife ende:
Indirektes Adressieren von Speicher, haben wir noch nicht behandelt.
anfang: in R16, PINB andi R16, 0b001 1111 (<- fehlt da bei dir nicht ne Null?) stimmt es fehlt eine! 0b0001 1111 umcodieren: ... anzeigen: ... sbis PINB, 7 rjmp anfang speichern: ... ruecksetzen: ... rjmp anfang
Klar geht das, es kommt nur darauf an, dass die Befehle in der richtigen Reihenfolge abgearbeitet werden ;-)
Bei rjmp bla wird einfach der PC mit neuem Wert belegt somit dumm zur Stelle bla gesprungen. Bei rcall blub passiert etwas mehr: Es wird auch zur stelle blub gesprungen, zusätzlich wurde aber die die Adresse des Befehls der auf das rcall blub folgt auf einen Stapel (engl. Stack) gelegt. Am Ende des Unterprogramms steht ein ret, das bewirkt, dass mit der obersten Adresse auf dem Stack weiter gemacht wird, also zurückgesprungen wird.
http://mezdata.de/avr/200_schnelleinstieg/
Bei der Zeichnung eines Pins (Anschluss) zu sehen: Es gibt eine Möglichkeit den Eingang abzufragen die Adresse lautet PIN.. Und zu jedem Pin (Anschluss) gibt es ein D-FF (Adresse PORT) das den Wert des Ausgangs speichern kann. Der Wert des D-FF wird zum Ausgang durchgeschaltet wenn ein Richtungs D-FF (Adresse DD) eine 1 gespeichert hat.
Auf http://mezdata.de/avr/120_indirektes-adr/ wurde ersten Bild beim SRAM geschrieben, dass er 128 Byte groß ist. Weiter unten (bei den 4 Beispielen zur direkten Adressierung) hast im 4. Bsp geschrieben, dass der SRAM ne 16 Bit Adresse hat. Handelt es sich hier um den gleichen µContoller oder gilt für des Beispiel das was in den Klammern dahinter steht und ist somit für uns nicht relevant? denn für die 128 Byte würden doch 7 Bit zur Adressierung reichen, da er wortweise organisiert ist die indirekte Adressierung, braucht man doch nur wenn man was Zusammenhängendes (Liste, ...) in den RAM schreiben/lesen will oder?
Unser Controller hat 128 Byte somit würden 7 Bit reichen, aber man will ja Programme universeller schreiben und den Quelltext auch mühelos auf fettere Teile anwenden können z.B. auf den Mega32... Da sind 8Bit zu wenig, somit noch ein Register somit 16 Bit!
Jein, mir sind klare Zuweisungen lieber, aber hier wird auch klar beschrieben was gemacht wird, somit ist es akzeptabel.. Allerdings welches Register wird konkret gemeint?? Konkrete Lösung ist immer besser als nebulöse Gedanken!
0 0 Input No Tri-State (Hochohmig)
0 1 Input Yes Der Ausgang liefert einen Strom für z.B. Taster auf GND
das PORTB setzen brauch ich wenn ich den eingangswert definieren will ... d.h. bei taster -> PORTB auf 1 damit eingangszustand definiert ist?
Also DDBn ist 0 damit ein Eingang. PORTBn ist 1 damit ist der PullUp Transistor geschaltet und liefert einen PullUp-Strom. D.h. der Pin hängt auf Log 1 ohne Beschaltung -> wenn wir den auf 0, Ground (GND) mit nem Taster ziehen, dann ist da 0 zu lesen via PINBn, wenn Taster gedrückt.
© Oliver Mezger 08.03.2007 MezData.de Den Kontakt herstellen...