Forum: PC-Programmierung shiften im 8086 shr und shl


von Peter B. (funkheld)


Lesenswert?

Hallo, guten Tag.

Ich habe hier ein Programm gefunden für shl.

---------------------------
org 100h
 start:
   mov bx,sp
   mov si,[bx+4] ; Zeiger auf die ZWEITE Variable nach SI
   mov cx,[si]   ; 2. Variable in CX holen
   mov si,[bx+6] ; Zeiger auf die ERSTE Variable nach SI
   mov ax,[si]   ; 1. Variable in AX holen
   mov bx,ax     ; 1. Variable nach BX kopieren
   and bx,8000h  ; Vorzeichen (Bit 15) isolieren, steht in BX
   shl ax,cl     ; hier wird geschoben!
   and ax,7FFFh  ; 15. Bit loeschen (Vorzeichen)
   or ax,bx      ; und altes Vorzeichen wiederherstellen
   mov [si],ax   ; Ergebnis in 1. Variable schreiben
   retf 4       ; Ruecksprung-Unterprogramm verlassen

----------------

Wie sieht bitte das Programm für shr aus.

Oder geht es oben noch anders?

Danke.

von Funkdeppjäger (Gast)


Lesenswert?

Oh Gott  - einen Tag ohne eine saudämliche Frage von Peter B.Löd - sowas 
gibts nicht!
lmgt fy.com/?q=8086+shr

von Dennis H. (c-logic) Benutzerseite


Lesenswert?

das sind atomare Assembler-Befehle.

logisches shift schiebt durch carry-bit raus und shiftet ne 0 rein
arithmetisches shift beachtet das obere sign-bit.
rotate schiebt rund durchs carry.

http://www.c-jump.com/CIS77/ASM/Assembly/A77_0380_shl_shr.htm

das shl ax,cl ist ein Multishift mit Anzahl in cl

mov cl,16
shl ax,cl

ist ein aufwendigeres und zeitraubenderes clear ax

: Bearbeitet durch User
von Ben B. (Firma: Funkenflug Industries) (stromkraft)


Lesenswert?

xor ax,ax braucht nur ein einziges Byte wenn ich mich recht erinnere.

von Peter B. (funkheld)


Lesenswert?

Warum ist denn meins oben so kompliziert?

Ich brauche nicht die Zahlenwerte minus oder plus.
Ich brauche immer nur das 1. Byte vom Integerwert ob rechts oder links 
schieben.
Das wird dann verarbeitet.

Also wird da oben bei mir durch den ganzen Integerwert geschoben?
Das kannte ich gar nicht. Ich dachte das geht nur über 1 Byte.

Danke.
Gruss

: Bearbeitet durch User
von Ben B. (Firma: Funkenflug Industries) (stromkraft)


Lesenswert?

Hä?

Was brauchst Du? Du weißt, daß sich AX problemlos in AH und AL zerlegen 
lässt, je nachdem welches Byte Du brauchst? AX hat zwei Byte, AH ist das 
höherwertige Byte und AL das niedrige.

von Thomas Z. (usbman)


Lesenswert?

das Bespiel ist so komliziert weil die Vars über den Stack übergeben 
werden, weil es eine far function ist und die vars signed.
Wenn du ein byte schieben willst nimm halt byte befehle. Schieben bei 
signed typen ist immer mit Vorsicht zu geniesen.
Ich bin mir sicher das der Code ursprünglich von einem Compiler stammt. 
Niemand würde sowas programmieren.

von Hmm (Gast)


Lesenswert?

Der 8086 sieht mir sehr ungeeignet aus für Low-Level-Programmierung, da 
zu komplex!

Ist der damals vielleicht schon mit Blick auf Hochsprachen mit 
anschliessender Optimierung entwickelt worden ? Natürlich könnte man 
händisch assemblieren wenn etwas besonders schnell sein müsste.

von Ben B. (Firma: Funkenflug Industries) (stromkraft)


Lesenswert?

> Ich bin mir sicher das der Code ursprünglich von einem Compiler stammt.
Das war eine gängige Praxis, wenn man keine eigene gute Idee für eine 
Assembler-Lösung hatte. Dann wurde das mal schnell in C oder so 
hingeklatscht und geschaut wie der Compiler das Problem löst, ggf. wurde 
der Disassembler-Schnipsel dann mal eben in den eigenen Quelltext 
reingeguttenbergt.

> Niemand würde sowas programmieren.
Doch, die Variablen auf dem Stack übergeben hat einige Vorteile, vor 
allem wenn man Funktionen rekursiv verwenden möchte. Die maximale Tiefe 
wird dann nur von der maximalen Stackgröße bestimmt.

> Der 8086 sieht mir sehr ungeeignet aus für Low-Level-Programmierung,
> da zu komplex!
So ein Quatsch. Der ist doch nicht komplex. Außerdem sind komplexe 
Befehle und Funktionen für die Assembler-Programmierung eher gut, weil 
man sich nicht so viel selbst zusammenstricken braucht wenn der 
Prozessor das in Hardware kann.

Ich bin bei den Mikrocontrollern z.B. von den PICs zu den AVRs 
gewechselt, aus genau diesem Grund. Die PICs hatte ich zuerst in den 
Fingern und hab deswegen mit denen angefangen mich in das Thema 
einzuarbeiten. Aber deren minimalistische Ausstattung mit 
Assembler-Befehlen nervt. Ich glaube die hatten nicht mal einen echten 
Registersatz, sondern nur einen Akkumulator und das wars. Die Dinger 
sind viel eher für eine Hochsprache entwickelt, die wesentlich 
komplexeren AVRs lassen sich viel einfacher in Assembler programmieren.

von Melder (Gast)


Lesenswert?

> nicht mal einen echten Registersatz, sondern nur einen Akkumulator

Da gibt es welche, die sind so beschraenkt, dass sie selbst die
einfache Architektur nicht begreifen. Vermutlich begreift
er den AVR auch nicht und stuempert lieber in C herum.

Das was wie ein Akkumulator aussieht, ist nur ein 
Operandenhilfsregister.
Und das was nicht wie echte Register aussieht, sind Akkumulatoren.
Davon gibt es genau so viele wie es Register gibt.
Und viel hin- und herspeichern muss man deswegen auch nicht.
Was im jeweiligen Akkumulator/Register ausgerechnet wurde,
kann dort einfach liegen bleiben...

von Thomas Z. (usbman)


Lesenswert?

Ben B. schrieb:
>> Niemand würde sowas programmieren.
> Doch, die Variablen auf dem Stack übergeben hat einige Vorteile, vor
> allem wenn man Funktionen rekursiv verwenden möchte. Die maximale Tiefe
> wird dann nur von der maximalen Stackgröße bestimmt.

das ist bekannt und auch üblch das weis ich schon.

schau noch mal genau hin:
da wird was auf dem stack übergeben und verwurstelt und dann das 
Ergebnis auf dem Stack zurückgegeben soweit noch ok.
ABER dann wird mit RETF 4 der stack abgebaut. Also entweder überseh ich 
gerade was oder das Ergebnis ist weg. Das ist entweder besonders clever 
oder aber grober Unsinn.
Kanns leider nicht durchsteppen.

Wie immer zeigt der TO ein Fragment total aus dem Kontext gerissen. Dazu 
passt auch das org 100. was wohl nur bei com Programmen anzutreffen ist.

Edit:
ich seh gerade das Ergebnis ist ja auch in AX
ok dann gibt es doch einen Rückgabewert dann ist der letzte MOV vor dem 
RETF unnötig.

: Bearbeitet durch User
von Ben B. (Firma: Funkenflug Industries) (stromkraft)


Lesenswert?

Wenns danach geht, hat der Code so einige Sachen, die schwer 
verständlich sind. CX z.B. wird mit 16 Bit geladen, aber nur die unteren 
8 Bit verwendet. Das Ergebnis zurückzuspeichern könnte dagegen recht 
sinnvoll sein, wenn der Programmdurchlauf eine Tabelle modifizieren soll 
oder was auch immer. Das geht aus dem kurzen Schnipsel nicht hervor.

Der Programmanfang ist in der Form sowieso Schrott, das ORG 100h gehört 
zwar zu .COM-Dateien und man könnte das so assemblieren, allerdings 
arbeitet man dann mit einem uninitialisierten Stack oder Stackpointer. 
Der Schuss geht also an eine ziemlich beliebige Stelle im eigenen 
Segment und spätestens nach dem RETF schmiert die Kiste ab. Da fehlt 
definitiv der Programmteil, der diese Funktion aufruft. RETF ist auch 
untypisch für .COM-Programme, da diese mit DOS-Bordmitteln nur aus 
64k-100h Bytes Code bestehen können und dafür braucht man keine far 
calls. Bei mehr Code (was schon ein verdammt großes Assemblerprogramm 
ist) nimmt man entweder .EXE-Dateien oder man muß einen eigenen Loader 
schreiben, um den Code nachzuladen.

Ich weiß nicht mehr so extrem genau wie DOS .COM-Dateien lädt. 
Wahrscheinlich wird das komplette 64K-Segment an Speicher zugewiesen und 
der Stackpointer mit 0FFFFh initialisiert.

von Rolf M. (rmagnus)


Lesenswert?

Hmm schrieb:
> Der 8086 sieht mir sehr ungeeignet aus für Low-Level-Programmierung, da
> zu komplex!
>
> Ist der damals vielleicht schon mit Blick auf Hochsprachen mit
> anschliessender Optimierung entwickelt worden ? Natürlich könnte man
> händisch assemblieren wenn etwas besonders schnell sein müsste.

Der 8086 war mit Blick darauf entwickelt worden, dass man sehr einfach 
und ohne manuelle Arbeit Code für den 8085 auf diesen portieren kann, 
der wiederum zum 8080 kompatibel war und der wiederum zum 8008, welcher 
Anfang der Siebziger auf den Markt kam und damals sicherlich so gut wie 
ausschließlich in Assembler programmiert wurde.

: Bearbeitet durch User
von rbx (Gast)


Lesenswert?

Ben B. schrieb:
> RETF ist auch
> untypisch für .COM-Programme, da diese mit DOS-Bordmitteln nur aus
> 64k-100h Bytes Code bestehen können und dafür braucht man keine far
> calls.

Das sieht wirklich etwas merkwürdig aus, weil normalerweise Hochsprachen 
(C, Pascal z.B.) das mit der Stackübergabe so handhaben, um (für ein 
schnelles Rechenprogramm, einen bestimmten Hardwarezugriff o.ä.) auf die 
Assemblerebene zu gehen.

Diese machen aber (vermutlich) Retf, weil (Segmentmanagement) schon 
fortschrittlich intus habend -  der tatsächlich nicht in so ein kleines 
Unterprogramm gehört, außer eben als Hochsprachen-Assemblerunterteil.

Selbst sollte man auch die Finger von so einem Befehl lassen, wenn man 
nicht genau weiß, was dahinter steckt. Was bleibt, sind Schablonen der 
Hochsprachenpraxis (wie mache ich ein Assembler-Unterprogramm in Sprache 
x) - Da kann man sich hier zumindest über den fehlenden Hinweis 
beschweren, diese Übergaben sind nicht einheitlich.

Letztlich: Das stiftet hier nur unnötig Verwirrung. In dem Buch 
Digitaltechnik von Klaus Beuth ist noch ein 4-Bit Intel-cpu beschrieben 
(ob die neue aktuelle Ausgabe das auch noch macht, weiß ich nicht). Die 
Schaltungen werden sehr kompliziert bzw. die Segment-Lösung für 
20Bit-Anpassung beim 8086 ist recht schwierig.

Die Programmierung selber in Assember bzw. Hex (z.B. 7C für JL oder 5A 
für Pushall usw. ist aber sehr gut gemacht und macht viel Spaß. Gerade 
auch wegen dem einfachen .com-Format im Dos. Das beste an der Geschichte 
ist, dass man im Virtual-Mode die aktuellen Features der Intelcpus 
nutzen kann. Wie weit das heute geht, weiß ich nicht - weil der 
Virtual-Modus für Dos-Programme/bzw. 16Bit-Programme bei 64Bit nicht 
mehr geht. Man müsste zumindest ein 32Bit Windows zum Testen nehmen.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.