PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : Größer als und kleiner als



Import-Script
01.08.2003, 09:38
Hi, <BR> <BR>gibt es in Assembler einen Befehl der wahr oder falsch zurückgibt, wenn ein Wert in einem Register größer oder kleiner ist, als der Wert eines anderen Registers? Falls nicht, wie würdet ihr das lösen? <BR> <BR>Gruß, <BR>Heiner

Import-Script
01.08.2003, 10:04
So was ähnliches: <BR>CJNE A,dadr,rel &#39;Springe relativ um die Adresse rel, wenn die Inhalte von Akkumulator und dadr ungleich sind. <BR>CJNE A,#konst8,rel <BR>CJNE Rr,#konst8,rel <BR>CJNE @Ri,#konst8,rel <BR> <BR>wobei A = Akku <BR>Rr = Register <BR>@Ri = interne Speicherstelle <BR>#konst8 = 8-Bit-Konstante <BR>dadr = Adresse im internen Datenspeicher <BR>rel = ein Sprung zwischen &#43;127 oder -128 Bytes <BR> <BR>Gruß Winnie <BR> <BR>Ach ja, CJNE = Compare and Jump if Not Equal

Import-Script
01.08.2003, 11:26
Hi, <BR> <BR>bei einigen Vergleichen wird auch das Carry-Bit entsprechend gesetzt. Daran kann man nicht nur sehen, dass es ungleich war, sondern auch ob es größer oder kleiner war. Nach dem Sprung kann man also zusätzlich einen Sprung abhängig vom Carry-Bit machen zur weiteren auswertung. <BR> <BR>gruß <BR>Elmar

Import-Script
01.08.2003, 12:17
Hallo, <BR>Carry kann auch noch zusätzlich ausgewertet werden. <BR> <BR>Beispiel: <BR> <BR>CJNE A,#$FF,Marke_1 ; auf Hex-Zahl FF prüfen <BR> <BR>LJMP .... ; #$FF erekannt <BR> <BR>Marke_1: <BR>CJNE A,#$F0,Marke_2 ; auf Hex-Zahl F0 prüfen <BR> <BR>LJMP ....; #$F0 erkannt <BR> <BR>Marke_2: <BR>JNC Marke_4 ;Carry auswerten <BR> <BR>Durch auswerten des Carry können Werte größer oder kleiner <BR>als #$F0 ausgewertet werden <BR> <BR>Marke_3: Routine <BR>Marke_4: Routine <BR> <BR> <BR>Gruß, Willi

Import-Script
01.08.2003, 13:10
oder beide Werte subtrahieren und schauen was Carry und Zero Flags gemacht haben

Import-Script
01.08.2003, 15:49
Hi, <BR> <BR>@Carsten: <BR> <BR>sehr destruktiv. Der Inhalt des Akkus geht dabei verloren. Ist so wie Glas mit einem Hammer auf Bruchsicherheit prüfen. <img src="http://progshop.com/elektronik/diskussion/clipart/biggrin.gif" border=0> <BR> <BR>Gruß <BR>Elmar

Import-Script
01.08.2003, 17:50
@Heiner <BR>Ein Datum vergleichen ist doch mit das Häufigste, was ein Prozessor so macht. <BR> <BR>Wenn ein Wert in einem Register größer oder kleiner ist, dann ist der Wert schlicht ungleich. Also einfach auf Ungleichheit prüfen. <BR> <BR>In 386er Assembler &#40;16-bit&#41; z.B. würde das in Pseudocode so ausschauen: <BR> <BR>jne Sprungziel &#40;jump if not equal&#41; <BR> &#40;man kann auch jnz verwenden&#41; <BR> <BR>Weil jcc &#40;jump if condition code, mit cc = ne&#41; das Zero Flag auswertet, muß zuvor ein Vergleich erfolgen. <BR> <BR>cmp register1, register2 <BR> <BR>Der Compare Befehl subtrahiert die Register ohne sie zu verändern. Solange jetzt die Register &#40;Speicherzellen&#41; ungleich sind, ist das Zero Flag = 0 und es wird gesprungen &#40;z.B. relativ vor den Vergleich, um den Vergleich erneut zu durchlaufen usw.; Vorsicht vor Endlosschleifen!&#41; <BR> <BR>Ansonsten sitzt der Teufel wie immer im Detail &#40;welcher ASM-Code x86, Microcontroller, DSP usw.&#41;. Vom kommentieren von Codefragmenten halte ich nicht viel, oft zu viele Seiteneffekte, Compiler-Einstellungen, usw. Da hilft oft nur die &#34;Trial- and Error-Methode&#34;. <BR> <BR>Gruß Gerd

Import-Script
01.08.2003, 22:53
Hi, <BR> <BR>ich bedanke mich für eure Vorschläge. Ziel meines Vorhabens ist, einen beliebigen Wert im Register einer von fünf Stufen zuzuordnen. <BR> <BR>Stufe1 = 0 bis 37 <BR>Stufe2 = 38 bis 71 <BR>Stufe3 = 72 bis 94 <BR>Stufe4 = 95 bis 113 <BR>Stufe5 = 114 bis 255 <BR> <BR>@Winnie, Willi und Gerd <BR>Das mit dem CJNE habe ich noch nicht ganz verstanden. Dieser Befehl kann doch nur unterscheiden ob gleich oder nicht gleich, aber nicht ob größer oder kleiner, oder habe ich da was falsch verstanden? <BR> <BR>Gruß, <BR>Heiner

Import-Script
01.08.2003, 23:30
Oh je, jetzt kommt wieder der 68000er Pseudo Fritze... &#40;aber das geht auf jeder CPU&#41;.. <BR>--&#62; machen wirs in 6805, der hat auch schön brav einen Akku... <BR> <BR>LDA Wert <BR>CMP #&#40;immediate&#41;37 <BR>BLE &#40;lower-equal&#41; Stufe1 <BR>CMP #71 <BR>BLE Stufe2 <BR>CMP #94 <BR>BLE Stufe3 <BR>... usw. <BR> <BR>Labels: <BR> <BR>Stufe1: Tu dies und jenes <BR>BRA Fertig <BR>Stufe2: Tu was anderes <BR>BRA Fertig <BR>...usw <BR> <BR>Fertig: <BR>Tu jetzt was Du willst...<img src="http://progshop.com/elektronik/diskussion/clipart/smile.gif" border=0>

Import-Script
02.08.2003, 00:17
&#62;&#62;Das mit dem CJNE habe ich noch nicht ganz verstanden. Dieser Befehl kann doch nur unterscheiden ob gleich oder nicht gleich, aber nicht ob größer oder kleiner, <BR> <BR>Genau so ist es. <BR>Sieh mal in der Batronix Hilfe der Batronix Software nach. Hier sind einige Basicbefehle integriert die aber auch als Assembler Befehle dargelegt werden wie z. B.: <BR> <BR>If A &#62; #14 Then SETB P1.1 <BR> <BR>Dieser Befehl &#40;und andere&#41; sind dann in Assembler &#39;aufgelöst&#39;: <BR> <BR>Aufbau: <BR> <BR> C0 E0 PUSH E0 &#40;Akku&#41; <BR> C3 CLR C <BR> 94 data&#43;1 SUBB A,#data&#43;1 <BR> D0 E0 POP E0 &#40;Akku&#41; <BR> 40 xx JC xx <BR> <BR>Diese Zeilen habe ich aus der Batronix-Hilfe kopiert. <BR> <BR>Gruß Winnie

Import-Script
02.08.2003, 00:50
@Elmar: <BR>Programmiere viel mit PIC Prozessoren, da geht das nur mit Subtraktion. <BR>Außerdem wozu gibts denn nen Stack? <BR>

Import-Script
02.08.2003, 01:44
@Heiner <BR>Nicht das wir da über zwei verschiedene Dinge sprechen. Ich habe Deine Eingangsfrage so gedeutet, dass Du wissen wolltest, wann ein Wert größer oder kleiner als ein anderer Wert ist, d.h. OB sich ein Wert von einem anderen Unterscheidet. <BR> <BR>Und genau das macht ja die Kombination <BR>cmp register1, register2 <BR>jnz Sprungziel <BR> <BR>Eine andere Fragestellung wäre WIE sich ein Wert von einem anderen Unterscheidet. In deinem Beispiel muss man anders vorgehen. Beispielsweise einfach von oben ausgehend der Reihe nach prüfen, ob der unbekannte Wert größer oder gleich als die jeweilige Stufe ist. <BR> <BR>In Pseudocode, unter der Voraussetzung der beliebige Wert befände sich im Wertebereich, <BR>also 0 &#60;= beliebigerWert &#60;= 255 <BR> <BR>let reg1 = beliebigerWert <BR>if reg1 &#62;= Stufe5 then <BR>__ordne reg1 der Stufe 5 zu <BR>else <BR>__;reg1 muß kleiner als Stufe5 sein <BR>__if reg1 &#62;= Stufe4 then <BR>____ordne reg1 der Stufe4 zu <BR>__else <BR>____;reg1 muß kleiner als Stufe4 sein <BR>____if reg1 &#62;= Stufe3 then <BR>______ordne reg1 der Stufe3 zu <BR>____else <BR>______;reg1 muß kleiner als Stufe3 sein <BR>______if reg1 &#62;= Stufe2 then <BR>________ordne reg1 der Stufe2 zu <BR>______else <BR>________;reg1 muß kleiner als Stufe2 sein <BR>________ordne reg1 der Stufe1 zu <BR>______endif <BR>____endif <BR>__endif <BR>endif <BR> <BR>&#40;Für die Unterstriche sich Leerzeichen denken, die werden hier leider alle entfernt <IMG SRC="http://progshop.com/elektronik/diskussion/clipart/happy.gif" ALT=":-&#41;" BORDER=0>&#41; <BR> <BR>Der Vergleich &#40;&#62;=&#41; lässt sich mit jae &#40;jump above equal&#41; oder jbe &#40;jump not below&#41; durchführen &#40;wohlgemerkt in x86 assembler&#41;. Ob jedesmal vorher der Compare Befehl fällig ist, hängt davon ab inwieweit die Flags &#34;am Leben&#34; bleiben. <BR> <BR>Die Schleife müsste für jeden Wert durchlaufen werden. Das &#34;Zuordnen&#34; hängt davon ab was man erreichen möchte. <BR> <BR>Gruß Gerd

Import-Script
02.08.2003, 11:49
Hi, <BR> <BR>das mit dem größer und kleiner ist auch in assembler möglich. Irgendwie muss der Basic-Befehl das ja auch übersetzen. <BR> <BR>Im Befehlssatz steht da über den Befehl CJNE: <BR> <BR><blockquote><hr size=0><!-quote-!><font size=1><b>quote:</b></font><p><b>CJNE &#60;dest-byte&#62;, &#60;src-byte&#62;, rel</b> <BR>Function: Compare and jump if not equal <BR>Description: CJNE compares the magnitudes of the tirst two operands, and branches if their <BR>values are not equal. The branch destination is computed by adding the signed <BR>relative displacement in the last instruction byte to the PC, after incrementing the <BR>PC to the start of the next instruction. The carry flag is set if the unsigned integer <BR>value of &#60;dest-byte&#62; is less than the unsigned integer value of &#60;src-byte&#62;; <BR>otherwise, the carry is cleared. Neither operand is affected. <BR>The first two operands allow four addressing mode combinations: the accumulator <BR>may be compared with any directly addressed byte or immediate data, and any <BR>indirect RAM location or working register can be compared with an immediate <BR>constant. <BR>Example: The accumulator contains 34 H . Register 7 contains 56 H . The first instruction in the <BR>sequence <BR>CJNE R7, # 60 H , NOT_EQ <BR>; . . . . . . . . ; R7 = 60 H <BR>NOT_EQ JC REQ_LOW ; If R7 &#60; 60 H <BR>; . . . . . . . . ; R7 &#62; 60 H <BR>sets the carry flag and branches to the instruction at label NOT_EQ. By testing the <BR>carry flag, this instruction determines whether R7 is greater or less than 60 H . <BR>If the data being presented to port 1 is also 34 H , then the instruction <BR>WAIT: CJNE A,P1,WAIT <BR>clears the carry flag and continues with the next instruction in sequence, since the <BR>accumulator does equal the data read from P1. &#40;If some other value was input on <BR>P1, the program will loop at this point until the P1 data changes to 34 H &#41;.<!-/quote-!><hr size=0></blockquote> <BR> <BR>Soll heißen: <BR> <BR>Bei Ungleichheit springen. <BR>Nach dem Sprung ist das Carry-Bit gesetzt, wenn der Wert &#60;dest&#62; kleiner ist als die Quelle &#60;src-byte&#62; und gelöscht, wenn der Wert größer ist. <BR> <BR>Nach dem Sprung muss man das einfach nur prüfen. Also mit JC bzw. JNC. <BR>Möchte man nicht irgendwo hinspringen, und z.B. nur auf kleiner prüfen, so gibt man bei CJNE als &#60;rel&#62; einfach nur 0 an. So wird in jedem Fall bei dem nächsten Befehl weitergemacht und das Carry-Bit ist gesetzt, wenn der Wert kleiner ist. Vorher ist das Carry natürlich zu löschen, damit bei gleichheit &#40;Kein Sprung lässt Carry in Ruhe&#41; das Carry ebenfalls gelöscht bleibt. So Prüft man ausschließlich auf &#34;Kleiner als&#34; <BR> <BR>CLR C <BR>CJNE &#60;dest-byte&#62;,&#60;src-Byte,0 <BR>JC Go_To_Kleiner_als <BR> <BR>Wenn Dest-Byte kleiner als src-Byte ist, so wird nach Go_To_Kleiner_als gesprungen. <BR> <BR>In 5 Schritten á 3 Befehlern kannst Du so Deinen Vergleich durchführen. <BR> <BR> <BR> <BR>Eine andere hübsche Möglichkeit ist es, den Eingangswert durch die Anzahl der Sprünge zu teilen und dann steht im Akku direkt die Nummer des Einsprunggs. Das Ganze dann mal 2 nehmen &#40;oder um eine Stelle nach links shiften, was ebenfalls einer multiplikation mit 2 entspricht&#41; und Du kannst mt JMP @A&#43; DPTR auf eine Sprungtabelle gehen, die aus AJMPs zu Deinen Einsprungadressen geht. Mal zwei nehmen deshalb, weil Die Einsprungtabelle immer zwei Byte je Eintrag hat. <BR> <BR>Gruß <BR>Elmar

Import-Script
02.08.2003, 12:07
Anbei mal 2 Beispiele, einmal, mit dem ADD-Befehl und dann mit CJNE. Den ADD-Befehl deswegen, weil ma da nicht vorher das Carry-Flag löschen muß. Und es ist ja egal, ob ich <BR> <BR>CLC C <BR>SUBB A, #50 <BR> <BR>oder <BR> <BR>ADD a, #-50 <BR> <BR>schreibe, denn: A - B = A &#43; &#40;-B&#41; <BR> <BR> <BR> <BR><!--attachment: Vergleic-8298.txt*mime_txt.gif*text/plain*0.7*5%2dBereich%2dVergleich*Vergleic%2ea51 --><center><table border=1><tr><td><img src="http://progshop.com/elektronik/diskussion/icons/mime_txt.gif" align=left alt="text/plain">5-Bereich-Vergleich<br><a href="http://progshop.com/elektronik/diskussion/messages/4982/Vergleic-8298.txt" target="_blank"><b>Vergleic.a51</b></a> (0.7 k)</td></tr></table></center><!--/attachment--> <BR> <BR> <BR>@Elmar, <BR> <BR>daß eine Operation den ACCU benutzt, ist kein Problem. Der ACCU ist eben nicht der richtige Platz, um Variablen länger zu speichern, das geht bequemer in den Registern. <BR> <BR>Ich hab schon Programme gesehen, wo sich die Leute tot-gepusht/-gepopt haben, d.h. der größte Teil des Programms war PUSH/POP. <BR>Da ist es wesentlich effektiver davon auszugehen, daß der ACCU eben nur ein Arbeitsregister ist. <BR> <BR> <BR>Peter

Import-Script
06.08.2003, 16:45
wie wäs mit folgender Routine ? Habs zwar nicht getestet, müsste aber gehen. Wenn ich was vom Akku mit SUBB subtrakiere, wird doch das Carry-Bit gesetzt, wenn ein Unterlauf stattfindet. <BR> <BR>mov A, Wert <BR>clr C <BR>SUBB A, #37 <BR>JC Stufe1 <BR>SUBB A, #71-37 <BR>JC Stufe2 <BR>SUBB A, #94-71 <BR>JC Stufe3 <BR>SUBB A, 113-94 <BR>JC Stufe4 <BR>; hier weiter für Stufe 5 <BR>.... <BR>Stufe4: <BR>; hier weiter für Stufe 4 <BR>.... <BR>Stufe3: <BR>; hier weiter für Stufe 3 <BR>.... <BR>Stufe2: <BR>; hier weiter für Stufe 2 <BR>.... <BR>Stufe1: <BR>; hier weiter für Stufe 1 <BR>.... <BR> <BR>einfacher gehts wohl kaum ! <BR>Grüessli <BR>Thedy <BR> <BR>

Import-Script
06.08.2003, 17:23
@Thedy, <BR> <BR>auf das &#34;Vergleic.a51&#34; kann man auch klicken. <BR> <BR>Peter <BR>

Import-Script
15.08.2003, 11:40
Hi, <BR> <BR>ich wollte nur eben eine Rückmeldung zum Thema abgeben. Die Routine funktioniert nun. Ich habe sie von Peter übernommen. <BR> <BR>Danke an alle für eure Inspirationen! <BR> <BR>Gruß, <BR>Heiner

Import-Script
15.08.2003, 12:01
Jaaa, geht doch, endlich mal eine Rückmeldung. Das wünschen sich doch alle hier. Schneiden wir uns doch alle gleich eine Scheibe davon ab. <BR> <BR>Gruß Winnie

Import-Script
16.08.2003, 00:55
Das finde ich auch, bin auch schon sehr oft entäuscht worden in dieser Beziehung. Manchmal verliert man dann halt die Lust, dem nächsten zu helfen! Und ein paar Worte hier zu schreiben ist genau nicht schwieriger als eine frage hier zu stellen!<img src="http://progshop.com/elektronik/diskussion/clipart/talker.gif" border=0>

Import-Script
16.08.2003, 02:23
Da kann ich Holger und Winnie nur zustimmen. <BR> <BR>Gruß Gerd