Das Format für den AsmDecoder (*.acf)

 


Der AsmDecoder ist ein Disassembler der für verschiedenste Prozessoren geeignet ist. Die Aufbau der Maschinencodebefehle wird über Formatdateien (*.acf) eingestellt. Der Aufbau dieser Dateien soll im Folgenden beschrieben werden.

Ablauf der Decodierung
Registerabschnitte
flags Variabel
layout Variabel
clips Variabel
Diverse Variablen
Masken
Definitionen
Mikroporgramme


Ablauf der Decodierung

Über die AsmDecode wird die Dekodierung eines CPU-Kommandos gestartet. Es werden zunächst die nächsten 4 Byte aus dem Code-Speicher ausgelesen. Dazu wird in den Maskeneinträgen der am besten passende ausgewählt, und dessen Mikroprogramm ausgeführt. Das Mikroprogramm wird bei einem Maskeneintrag am Ende angefügt. Im Mikroprogramm werden die einzelnen Textabschnitte eingestellt die der Zeile für das CPU-Kommando entsprechen. Eine Zeile enthält folgende Textelemente. 

ADRESSE  DATEN-BYTES    VORTEXTE BEFEHLSTEXTE  REGS , REGS , REGS , REGS ABSCHLUSSTEXT       

oder mehrzeilig:

ADRESSE  DATEN-BYTES    VORTEXTE BEFEHLSTEXTE  REGS , REGS ABSCHLUSSTEXT
                                     LINIENTEXTE                  
 
REGS , REGS 

Adresse Ist die CPU-Adresse an der das Kommando beginnt. Sie wird mit AsmDecode übergeben. Mit AsmSetFormat kann die Breite der Adressangabe eingestellt werden.

Daten-Bytes Ist der Hex-Dump des CPU-Kommandos. Mit AsmSetFormat kann maximale Anzahl der auszugebenden Daten-Bytes eingestellt werden.

Vortexte Mit Vortexten können Texte den Befehlsnamen vorangestellt werden. Vortexte werden mit dem Mikrobefehl TEXT ausgegeben. Das kann beispielsweise beim i386 für den REP Befehl benutzt werden. z.B.  REP MOVS 

Befehlstexte Der Befehlstext bestimmt den Namen eines CPU-Kommandos. Im Normalfall werden Befehlstexte nach einer Maskenangabe angefügt. Es ist aber auch möglich diese mit dem Mikrobefehl TEXT aus zugegeben.

Registerabschnitte In jedem Registerabschnitten können bis zu 8 Register oder Zahleneinträge erstellt werden. Mit dem  Mikrobefehl NEXT kann in den nächsten Registerabschnitt gewechselt werden.

Trennzeichen Zwischen allen Registeranschnitten wird automatisch ein ',' Zeichen eingefügt. In dem man die Variabel cut_sign auf 1 stellt wird das automatische Einfügen abgeschalten, und es kann ein STEXT stattdessen eingefügt werden. Der STEXT wird dann über die Bits 20 bis 23 in flags gewählt. Die Variabel cut_sign wird nach jedem CPU-Kommando wieder auf 0 gesetzt.

Abschlusstexte Am Ende der Ausgabe kann ein Abschlusstext eingefügt werden. Das kann mit dem Mikrobefehl TEXT und dem Flag #N gemacht werden.

Linientexte Falls ein CPU-Befehl mehrere Textzeilen beansprucht, können Linientexte für die nächste Zeile eingefügt werden. Da geschieht mit dem Mikrobefehl TEXT. Eine neue Zeile muss mit dem setzen des NEW_LINE Bits in einem Register-Flag bekannt gegeben werden (Bit 5 in flags). 

Registerabschnitte

Es gibt vier Registerabschnitte jeder Abschnitt hat den gleichen Aufbau. jeder Abschnitt besteht wiederum aus bis zu 8 Einträgen. Wie diese Einträge aussehen wird über die Variabeln flags, layout, clips bestimmt. Die acht Einträge haben fogenden Aufbau:

SEG  [+( LTEXT REG0 LTEXT ) ]       (Eintrag 0)
SEG  [+( LTEXT REG1 LTEXT ) ]      
(Eintrag 1)
SEG  [+( LTEXT REG2 LTEXT ) ]      
(Eintrag 2)
SEG  [+( LTEXT REG3 LTEXT ) ]      
(Eintrag 3)
SEG  [+( LTEXT VAL0 LTEXT ) ]      
(Eintrag 4)
SEG  [+( LTEXT VAL1 LTEXT ) ]      
(Eintrag 5)
SEG  [+( LTEXT REG2 LTEXT ) ]      
(Eintrag 6)
SEG  [+( LTEXT REG3 LTEXT ) ]      
(Eintrag 7) 
 

Seg Ist eine Segmentangabe die vor einen Eintrag gestellt werden kann. Um die Ausgabe der Segmentangabe zu aktivieren muss Bit 4 (0x10) in flags gesetzt werden. Die Segmentangabe kann nur vor einem der acht Einträge stehen. Über die Variabel segment_pos wird bestimmt vor welchem. Bei der Segmentangabe werden immer 3 Texte ausgegeben:

   STEXT[0]   RTEXT[ (flags>>20)&0x0F ]  STEXT[1]

Bits 20 bis 23 wählen einen RTEXT aus. Falls diese vier Bits 0 sind, wird die Segmentangabe nicht ausgegeben. Wird aber die Variabel seg_on auf 1 gesetzt erfolgt die Ausgabe auch bei 0. 

LText Ist ein Präfix- oder Postfixtext der vor bzw. nach einer Register- oder einer Zahlenangabe eingefügt wird. Dazu muss die Angabe über die entsprechenden Bits in flags (8 bis 15) freigegeben sein. Der Eingefügte Text wird mit der LTEXT Definition eingestellt. Über die layout Bits (jeder Eintrag hat 4 Bits) wird ausgewählt welcher LTEXT verwendet wird. Über die Variabel pre_bits kann eingestellt werden, welche Texte als Präfix und welche als Postfix genutzt werden sollen. z.B. wenn LTEXT[3] und LTEXT[6] ein Präfix ist muss Bit 3 und 6 in pre_bits gesetzt sein (0x48).  

Reg0 Ist ein Registername der eingefügt werden soll. Durch Schreiben auf die Variabel reg0 wird das Register ausgewählt. Die Namen der Register werden mit der RTEXT Definition eingestellt. Um den Registernamen auszugeben ist weiters das Bit 8 in flags zu setzen.  

Reg1 Ist ein Registername der eingefügt werden soll. Durch Schreiben auf die Variabel reg1 wird das Register ausgewählt. Die Namen der Register werden mit der RTEXT Definition eingestellt. Um den Registernamen auszugeben ist weiters das Bit 9 in flags zu setzen.  

Reg2 Ist ein Registername der eingefügt werden soll. Durch Schreiben auf die Variabel reg2 wird das Register ausgewählt. Die Namen der Register werden mit der RTEXT Definition eingestellt. Um den Registernamen auszugeben ist weiters das Bit 10 bzw. 14 (für Eintag 6)in flags zu setzen. 
 
Reg3 Ist ein Registername der eingefügt werden soll. Durch Schreiben auf die Variabel reg3 wird das Register ausgewählt. Die Namen der Register werden mit der RTEXT Definition eingestellt. Um den Registernamen auszugeben ist weiters das Bit 11 bzw. 15 (für Eintag 7) in flags zu setzen.  

Val0 Ist eine Zahlenangabe die eingefügt werden soll. Durch Schreiben auf die Variabel value0 wird die Zahl bestimmt. Über value0_h werden oberen 32 Bit der Zahl bestimmt.  Um die Zahl auszugeben ist das Bit 12 in flags zu setzen. Das Format der Zahl kann über die Bits 24 bis 26 in flags bestimmt werden.

Val1 Ist eine Zahlenangabe die eingefügt werden soll. Durch Schreiben auf die Variabel value1 wird die Zahl bestimmt. Über value1_h werden oberen 32 Bit der Zahl bestimmt.  Um die Zahl auszugeben ist das Bit 13 in flags zu setzen. Das Format der Zahl kann über die Bits 28 bis 30 in flags bestimmt werden.

+ Ein Pluszeichen wird eingefügt wenn in der layout eines der Bits 3,7,11,15,19,23,27,31 (je nach Eintrag) gesetzt ist, und davor kein '[' Klammerzeichen steht.

[()] Über die Variable clips können Klammerzeichen in einem Eintrag aktiviert werden. Bit 0 für '(' , Bit 1 für ')' , Bit 2 für '[' und Bit 3 für ']'. Zu jedem Eintrag ist zu dieser Bitnummer noch n*4 zu addieren.


flags Variable

Über die flags Variabel wird die Ausgabe eines Registerabschnittes bestimmt.

Bits 0..3 Über diese Bits kann die Art des Eintrages angegeben werden, das ist aber nicht zwingend notwendig: 
  0 = Konstante (z.B. mov ax, 1234h )
  1 = Adresse    (z.B. jmp       1234h )
  2 = Referenz   (z.B. mov ax,[1234h] )
  3 = Register    (z.B. mov ax, 1234h )
  4..15 =
frei benutzbar

Bits 4 Die Segmentangabe vor einen Eintrag schreiben. Über die Variabel segment_pos wird bestimmt vor welchem.

Bits 5 Eine neue Zeile beginnen. Damit kann einem CPU-Kommando mehrere Textzeilen zugeordnet werden. Der Registerabschnitt in dem das Flag gesetzt ist ist der erste Abschnitt der neuen Zeile.

Bits 6 Wenn diese Bit gesetzt ist, wird die gesamt Länge des CPU-Kommandos zu value1 addiert.

Bits 7 Wenn diese Bit gesetzt ist, wird die gesamt Länge des CPU-Kommandos und die Länge der Kommandos für die Vortexte, zu value1 addiert.

Bits 8..15 Diese Bits bestimmen in welchen Einträgen, Register bzw. Zahlen ausgegeben werden sollen.
  Bit  8  = Reg0 in Eintrag 0 augeben
  Bit  9  = Reg1 in Eintrag 1 augeben
  Bit 10 = Reg2 in Eintrag 2 augeben
  Bit 11 = Reg3 in Eintrag 3 augeben
  Bit 12 = Val0  in Eintrag 4 augeben
  Bit 13 = Val1  in Eintrag 5 augeben
  Bit 14 = Reg2 in Eintrag 6 augeben
  Bit 15 = Reg3 in Eintrag 7 augeben

Bits 16..17 Diese Bits bestimmen die aktuelle Addressbreite bei einem GET Mikrobefehl (0=8 Bit, 1=16 Bit, 2=32 Bit und 3=64 Bit). Wenn diese Option in GET nicht benötigt wird können die Bits frei verwendet werden. Nach NEXT Mikrobefehl werden diese Bits in den nächsten Registerabschnitt übernommen. Für den ersten Anschnitt werden die Bits aus g_flags geholt.


Bits 18..19 Diese Bits bestimmen die aktuelle Datenbreite bei einem GET Mikrobefehl (0=8 Bit, 1=16 Bit, 2=32 Bit und 3=64 Bit). Wenn diese Option in GET nicht benötigt wird können die Bits frei verwendet werden. Nach NEXT Mikrobefehl werden diese Bits in den nächsten Registerabschnitt übernommen. Für den ersten Anschnitt werden die Bits aus g_flags geholt.

Bits 20..23 Diese Bits bestimmen wie die Segmentangabe aussehnen soll. Sie wählen ein Register aus RTEXT.  (Achtung, auch Bit 4 setzen). 

Eine weitere Verwendung sind spezielle Trennzeichen zwischen den Registerabschnitten. Dazu muss die Variabel cut_sign auf 1 gesetzt werden.  Die Variabel cut_sign wird nach jedem CPU-Kommando wieder auf 0 gesetzt.

Nach NEXT Mikrobefehl werden diese Bits in den nächsten Registerabschnitt übernommen. Für den ersten Anschnitt werden die Bits aus g_flags geholt.

Bits 24..26 Diese Bits bestimmen wie der Zahlenwert Val0 ausgegeben werden soll. 
   0 = 2 Zeichen ausgeben
   1 = 4 Zeichen ausgeben
   2 = 8 Zeichen ausgeben
   3 = 16 Zeichen ausgeben
   4 = variable Länge bis zu '0' Zeichen
   5 = variable Länge bis zu '0' Zeichen mit Vorzeichen
   6 = 2 Zeichen mit Vorzeichen ausgeben
   7 = 4 Zeichen mit Vorzeichen ausgeben
Anmerkung im Init-Programm, das von AsmInit ausgeführt wird, ist es über m0 und m1 möglich die Formate 6 und 7 zu ändern. Wird Bit 7 in m0/m1 gesetzt, so wird das Vorzeichen berücksichtigt. Die Bits 0..6 geben die Ausgabebreite an. Null bedeutet dabei variabel.  

Bits 27 Dieses Bit kann frei verwendet werden. Nach NEXT Mikrobefehl wird dises Bits in den nächsten Registerabschnitt übernommen. Für den ersten Anschnitt wird das Bit aus g_flags geholt.

Bits 28..30 Diese Bits bestimmen wie der Zahlenwert Val1 ausgegeben werden soll. 
   0 = 2 Zeichen ausgeben
   1 = 4 Zeichen ausgeben
   2 = 8 Zeichen ausgeben
   3 = 16 Zeichen ausgeben
   4 = variable Länge bis zu '0' Zeichen
   5 = variable Länge bis zu '0' Zeichen mit Vorzeichen
   6 = 2 Zeichen mit Vorzeichen ausgeben
   7 = 4 Zeichen mit Vorzeichen ausgeben
Anmerkung im Init-Programm, das von AsmInit ausgeführt wird, ist es über m0 und m1 möglich die Formate 6 und 7 zu ändern. Wird Bit 7 in m0/m1 gesetzt, so wird das Vorzeichen berücksichtigt. Die Bits 0..6 geben die Ausgabebreite an. Null bedeutet dabei variabel. 
 

Bits 31 Dieses Bit kann frei verwendet werden. Nach einem NEXT Mikrobefehl wird dieses Bits in den nächsten Registerabschnitt übernommen. Für den ersten Anschnitt wird das Bit aus g_flags geholt.

 


layout Variable

Über die layout Variabel können Prefixe und Postfixe in den Einträgen eingestellt werden. Über die Variable mono_lt können die LTexte auch ausgegeben werden wenn der entsprechente Eintrag nicht aktiviert wurde.

Bits 0..3 Ist die Nummer des Präfix- bzw. Postfixtextes der vor bzw. nach der Reg0 Angabe eingefügt wird. Dazu muss die Angabe über das Bit 8 in flags freigegeben sein. Der eingefügte Text wird mit der LTEXT Definition eingestellt. 

Bits 4..7 Ist die Nummer des Präfix- bzw. Postfixtextes der vor bzw. nach der Reg1 Angabe eingefügt wird. Dazu muss die Angabe über das Bit 9 in flags freigegeben sein. Der eingefügte Text wird mit der LTEXT Definition eingestellt. 

Bits 8..11 Ist die Nummer des Präfix- bzw. Postfixtextes der vor bzw. nach der Reg2 Angabe eingefügt wird. Dazu muss die Angabe über das Bit 10 in flags freigegeben sein. Der eingefügte Text wird mit der LTEXT Definition eingestellt. 

Bits 12..15 Ist die Nummer des Präfix- bzw. Postfixtextes der vor bzw. nach der Reg3 Angabe eingefügt wird. Dazu muss die Angabe über das Bit 11 in flags freigegeben sein. Der eingefügte Text wird mit der LTEXT Definition eingestellt. 

Bits 16..19 Ist die Nummer des Präfix- bzw. Postfixtextes der vor bzw. nach der Val0 Angabe eingefügt wird. Dazu muss die Angabe über das Bit 12 in flags freigegeben sein. Der eingefügte Text wird mit der LTEXT Definition eingestellt. 

Bits 20..23 Ist die Nummer des Präfix- bzw. Postfixtextes der vor bzw. nach der Val0 Angabe eingefügt wird. Dazu muss die Angabe über das Bit 13 in flags freigegeben sein. Der eingefügte Text wird mit der LTEXT Definition eingestellt. 

Bits 24..27 Ist die Nummer des Präfix- bzw. Postfixtextes der vor bzw. nach der Reg2 Angabe eingefügt wird. Dazu muss die Angabe über das Bit 14 in flags freigegeben sein. Der eingefügte Text wird mit der LTEXT Definition eingestellt. 

Bits 28..31 Ist die Nummer des Präfix- bzw. Postfixtextes der vor bzw. nach der Reg3 Angabe eingefügt wird. Dazu muss die Angabe über das Bit 15 in flags freigegeben sein. Der eingefügte Text wird mit der LTEXT Definition eingestellt. 



clips Variable

Über die clips Variabel können Klammern in den Einträgen eingestellt werden.

Bits 0 Klammerzeichen '(' vor der Reg0 Angabe einfügen. 

Bits 1 Klammerzeichen ')' vor der Reg0 Angabe einfügen. 

Bits 2 Klammerzeichen '[' vor der Reg0 Angabe einfügen. 

Bits 3 Klammerzeichen ']' vor der Reg0 Angabe einfügen. 

Bits 4-7 Wie Bits 0 bis 3 nur für Reg1. 

Bits 8-11 Wie Bits 0 bis 3 nur für Reg2. 

Bits 12-15 Wie Bits 0 bis 3 nur für Reg3. 

Bits 16-19 Wie Bits 0 bis 3 nur für Val0. 

Bits 20-23 Wie Bits 0 bis 3 nur für Val1. 

Bits 24-27 Wie Bits 0 bis 3 nur für Reg2 im 6. Eintrag. 

Bits 28-31 Wie Bits 0 bis 3 nur für Reg3 im 7. Eintrag. 



Diverse Variablen

Dieser Abschnitt beinhaltet eine Beschreibung zu verschiedenen Variabeln.

g_param0 Über diese Variable stellt man den ersten Standartübergabeparameter, für Mikroprogramm ein. Falls ein Mikroprogramm ohne Parameter angegeben ist, wird  mit g_param0 übergeben. 

g_param1 Über diese Variable stellt man den zweiten Standartübergabeparameter, für Mikroprogramm ein. Falls ein Mikroprogramm ohne oder mit nur einem Parameter angegeben ist, wird g_param1 mit übergeben. 

param0 In dieser Variable wird der erste Übergabeparameter für ein Mikroprogramm gespeichert.

param1 In dieser Variable wird der zweite Übergabeparameter für ein Mikroprogramm gespeichert.

seg_on Wird seg_on auf 1 gesetzt so wird eine Segmentangabe auch ausgegeben wenn die Bits 20..23 in flags auf 0 sind. 

g_flags Über diese Variable werden die Bits für die flags Variabel eingestellt, die beim Mikrobefehl NEXT und am Beginn gesetzt werden sollen. Die Ausnahme sind die Bits 16..23,27 und 31. Sie werden am Anfang auf Null gesetzt, und dann in vom vorherigen Registerabschnitt übernommen. 

g_layout  Über diese Variable werden die Bits für die layout Variabel eingestellt, die beim Mikrobefehl NEXT und am Beginn gesetzt werden sollen.

g_clips Über diese Variable werden die Bits für die clips Variabel eingestellt, die beim Mikrobefehl NEXT und am Beginn gesetzt werden sollen. 

g_type Über diese Variable wird der Wert für die type Variabel eingestellt, der beim Mikrobefehl NEXT und am Beginn gesetzt werden sollen. 

g_reg0..3 Über diese Variable wird der Wert für die reg0..3 Variabel eingestellt, der beim Mikrobefehl NEXT und am Beginn gesetzt werden sollen. 

g_value0..1 Über diese Variable wird der Wert für die value0..1 Variabel eingestellt, der beim Mikrobefehl NEXT und am Beginn gesetzt werden sollen. 

flags Siehe flags

layout Siehe layout

clips Siehe clips

type In jedem Registerabschnitt gibt es eine type Variable. Sie kann frei verwendet werden um Informationen über die Abschnitte zu speichern. z.B. die Art eines Sprungbefehls oder Returnbefehl (siehe entry[?].type)
 
 
reg0..3 Über diese Variabeln kann eingestellt werden welcher Registertext in einem Eintrag eines Registerabschnittes dargestellt werden soll.

 
reg2n..3n Über diese Variabeln kann eingestellt werden welcher Registertext in den Einträgen 6 und 7 eines Registerabschnittes dargestellt werden soll.

 
value0..1
value0_h..1_h
Über diese Variabeln kann eingestellt werden welcher Zahlenwerte in den Einträgen 4 und 5 eines Registerabschnittes dargestellt werden soll. Über value?..1 werden die oberen 32 Bit bestimmt. 

 
m0..7 Sind globale Speicherstellen zur freien Verwendung.

 
select Mit select kann man bei Auswahlbefehlsnamen (z.B. ..."ADD:SUB"...) den Befehl wählen. Auswahlbefehlsnamen werden in den Masken definiert, in dem die einzelnen Namen durch einen Doppelpunkt getrennt werden.

 
pre_plus Über die Bits diese Wertes kann bestimmt werden vor welche TLEXT Pre/Postfixe ein '+' Zeigen gesetzt werden darf. Bei gesetztem Bit ist das nicht mehr möglich. Die Variable wird auf 0xFF00 initialisiert.

 
cut_sign In Wenn dieser Wert auf 1 gesetzt wird dann werden statt "," die Trennzeichen STEXT[n] nach jedem Eintrag gespeichert. cut_sign wird bei jedem Aufruf von AsmDecode automatisch auf 0 gesetzt. Das Trennzeichen wird in flags mit den Bits 20 bis 23 eingestellt.

 
code_addres
code_addres_h
In code_addres ist die aktuelle Anzeigeadresse des CPU-Kommandos gespeichert, die mit AsmDecode übergeben wird. code_addres_h sind die oberen 32 Bit der Adresse.

no_end Setzt man no_end auf 1 so wird automatisch der nächste Befehl geladen, wenn die Dekodierung des aktuellen CPU-Kommandos abgeschlossen ist. Das kann z.B. verwendet werden für Befehlsvorsätze wie REP oder ES:. 

pre_bits Mit diesen Bits wird bestimmt ob die LTEXT Texte vor oder nach einem Eintrag eingefügt werden. In AsmInit wird der Wert auf 0xF1F1 voreingestellt. Jeder der 16 Bits steht für einen LTEXT. Ein gesetztes Bit bedeutet das der Text vor dem Eintrag eingefügt wird.

mono_lt Wenn dieser Wert auf 1 gesetzt wird, werden LTEXTE auch ausgegeben wenn sie größer 0 sind und der zugehörige Eintrag nicht aktiviert ist (siehe flags 8..15).

byte_order Mit byte_order kann die Byte-Order für den Maskenvergleich umgedreht werden. Auf das Laden der Bits über den GET Befehl  hat das keinen Einfluss.

bit_direction Gibt an wie beim Mikrobefehl GET die Bits vom nächsten 8 Bit Block eingelesen werden:
   0 : Von Bit 0 bis 7
   1 : Von Bit 7 bis 0

z.B. Die nächste Bytefolge ist 4A 33 ... , Wenn GET 4 Bits holt würde bei bit_direction=0 der Wert 0x0A eingelesen, bei bit_direction=1 der Wert 0x04 eingelesen.

 
segment_pos Gibt an vor welchem Eintrag eine Segmentangabe ausgegeben werden soll:
   0 : Vor reg0
   1 : Vor reg1
   2 : Vor reg2
   3 : Vor reg3
   4 : Vor value0
   5 : Vor value1
   6 : Vor reg0 in Eintrag 6
   7 : Vor reg1 in Eintrag 7
   8 : Keine Ausgabe

flags_take Gibt an welche Bits beim NEXT Mikrobefehl mit genommen werden. Normalerweise ist dieser Wert auf 0x88FF0000 gesetzt.


Masken

Mit Maskeneinträgen wird bestimmt welches Mikroprogramm zu für ein bestimmtes Bitmuster beim Dekodieren ausgeführt werden muss, um einen bestimmten Befehl zu dekodieren. Jeder Maskeneintrag besteht aus drei Teilen:

Die Maskeneinträge müssen immer am Ende der Formatdatei stehen. Sie werden mit der MASK Definition eingeleitet:

MASK                           ; Kommentar

A0           "MOV"  Br:0:0 e   ; Kommentar
:01000???    "INC"  Xv:5r      ; Kommentar
D9:11010000  "FNOP"            ; Kommentar

Die Syntax für Maskeneinträge sieht wie folgt aus:

Bitmaske  "Befehlstext"  Mikroprogramm  [;Kommentar]

Eine Bitmaske hat folgenden Aufbau:

[>]{Hex-Digits}{:Bin-Digits:}{?-Digits}{_-Digits

Wenn die Maske mit einem '>' Zeichen anfängt heißt das die Maske im Motorolaformat angegeben ist. Achtung, die Maske muss dann immer 32-Bit lang sein. Anschließend folgt eine beliebige Reihenfolge von Zeichen wie 0..9,A..F,?,_ . Mit dem ':' Zeichen wird vom Hex-Modus in den binär Modus umgeschalten. Ab hier wird dann die Maske bitweise eingelesen. Ein weiteres ':' Zeichen schaltet wieder in den Hex-Modus um. Mit '?'-Zeichen werden Bits definiert die beim Maskenvergleich nicht berücksichtigt werden sollen. Die '_' Zeichen dienen nur als Platzhalte für eine Bessere Formatierung. Das Ende der Bitmaske wird mit einem Leerzeichen definiert. Die maximale Länge einer Bitmaske beträgt 32 Bit. z.B.:

A0            Maske=0x000000FF Wert=0x000000A0
A?            Maske=0x000000F0 Wert=0x000000A0
>A0           Maske=0xFF000000 Wert=0xA0000000
A_0           Maske=0x000000FF Wert=0x000000A0
A0:11??0??0   Maske=0x0000C9FF Wert=0x0000C0A0
:11??_0??0    Maske=0x000000C9 Wert=0x000000C0
:11??0??0:55  Maske=0x000055C9 Wert=0x000055C0

Wenn die Maske einer Bitmaske mit 0xFF anfängt dann wird beim Dekodieren mit AsmDecode sofort ein Byte aus dem Code-Speicher gelöscht und die Code-Länge um Eins erhöht. Die Bits die dann mit dem Mikrobefehl GET geholt werden, beginnen dann beim zweiten Code-Byte. Sollten auch die nächsten Bytes der Maske auf 0xFF sein, wird dieser Vorgang wieder holt.

Eine Befehlstext hat folgenden Aufbau:

"Name{:Name}" 

Der Befehlsname muss zwischen Anführungszeichen stehen. Dur einen Doppelpunkt im Text können weiter Unterbefehlstexte definiert werden. Die Auswahl des Befehlsnamens erfolg dann im Mikroprogramm durch beschreiben der select Variable. z.B.: 

"MOV"
"ROL:ROR:RCL:RCR:SHL:SHR:???:SAR"

Eine Mikroprogramm hat folgenden Aufbau:

{[Programmkey[:Parameter[:Parameter]]]}

Ein Mikroprogramm beginnt immer mit einem Buchstaben der den Programmkey darstellt. Durch Doppelpunke getrennt können zwei Zahlenparameter für das Mikroprogramm definiert werden. Die Zahle müssen kleiner 48 sein. Die Parameter werden in den Variabeln param0 und  param1 an das Mikroprogramm übergeben. Es kann eine beliebige Anzahl an Mikroprogrammen aneinander gereiht werden. Es dürfen auch Leerzeichen zwischen den Mikroprogrammen stehen. Sollte in einem Maskeneintrag kein Mikroprogramm vorhanden sein, wird der Befehlsname direkt übernommen. Die Code-Länge wird über die Anzahl der 0xFF Bytes am Anfang der Maske ermittelt. Daher sollten kein '?' Zeichen in der Maske sein. z.B.:

Br:1:0 d:0
Xr:0:0 d:0
Xormx

In einem Mikroprogramm werden mit dem GET Mikrobefehl weite Bits aus dem Code-Speicher geholt. Die Bits werden dann ausgewertet und die Registerabschnitte dementsprechend gesetzt. So kann das Aussehen eine Textzeile für ein CPU-Kommando bestimmt werden. 

     
Für Masken ist es möglich ein 8 Bit Fenster einzustellen in dem die Suche in den Maskeneinträgen optimiert wird. Dieses Fenster sollte auf einen Bereich in der Maskeneinträge geschoben werden in dem bei möglichst vielen Masken alle 8 Bits auf eins sind. Über die Definition SETMATCH kann die Position dieses Fensters eingestellt werden. Weiters können mit SETMATCH auch die Bits eingestellt werden, die im 8 Bitfenster ausgewertet werden. Bei der Maskenerstellung ist darauf zu achten das keine Maskeneinträge doppelt vorhanden sind.

Sollte eine CPU mehrere Befehlssätze besitzen, ist es auch möglich mehrere Masken hintereinander zu definieren. Die Auswahl der Maskenseite erfolgt mit dem uPage Parameter für AsmDecode.


Definitionen

Definitionen sind Anweisungen die beim Laden der *.acf Datei ausgeführt werden. Mit ihnen kann Alles definiert werden, was zur Laufzeit nicht geändert werden muss. Es gibt folgende Definitionen: 

RTEXT Über diese Definition wird einem RText eine Zeichenfolge zugewiesen. Über RTexte werden hauptsächlich Registernamen definiert. Über die Textnummer wird der Speicherplatz bestimmt. Es sind die Nummern 0 bis 511 erlaubt. Syntax:
   RTEXT "Zeichenfolge" ,Textnummer

LTEXT Über diese Definition wird einem LText eine Zeichenfolge zugewiesen. LTexte werden für die Prefixe und Postfixe bei Registereinträgen benutzt.  Über die Textnummer wird der Speicherplatz bestimmt. Es sind die Nummern 0 bis 15 erlaubt. Syntax:
   LTEXT "Zeichenfolge" ,Textnummer

STEXT Über diese Definition wird einem SText eine Zeichenfolge zugewiesen. Die ersten beiden STexte werden für bei Segmentangaben vor Registereinträgen, als Präfix und Postfix für das Segment benutzt, außerdem Finden sie Verwendung wenn spezielle Trennzeichen benutzt werden (siehe cut_sign). Über die Textnummer wird der Speicherplatz bestimmt. Es sind die Nummern 0 bis 15 erlaubt. Syntax:
   STEXT "Zeichenfolge" ,Textnummer

BFIELD Mit dieser Definition kann ein Bitfeld angelegt werden. Das Bitfeld kann in den Mikroprogrammen mit dem Mikrobefehl BIT ausgelesen werden. Der Hex-Dump bestimmt welche Bits im Feld gesetzt werden sollen (z.B.: "11 22 33"), er kann bis zu 32 Byte lang werden. Über die Feldnummer wird der Speicherplatz für das Feld bestimmt. Es sind die Nummern 0 bis 3 erlaubt. Syntax:
   BFEILD "Hex-Dump" Feldnummer

ALIAS Über die ALIAS Definition wird einem Befehlsnamen ein Aliasname zugewiesen. Das ist nützlich für die AsmEncode Funktion, wenn es für einen Befehl mehrere Bezeichnungen gibt, dann kann über den Aliasnamen der richtige Befehlsname ermittelt werden. Syntax:
   ALIAS "Befehlsname" "Aliasname" 

SETMATCH Über SETMACHT wird einer Maskenseite das 8-Bit-Fenster für die Schnellsuche zugewiesen. Beim laden der Masken wird eine Hashtabelle mit 256 Einträgen erstellt. Um die Suche nach dem richtigen Maskeneintrag zu beschleunigen, werden 8-Bits aus der Maske über die Hashtabelle vor gefiltert. Dazu müssen die 8 Bits im Maskeneintrag beim Fenster eindeutig sein (keine ? Angaben). Das Fenster kann im 32-Bit Maskeneintrag frei verschoben werden. Weiters ist es möglich die Fensterbits beliebig zu wählen. Die Fensterangabe berechnet sich folgender maßen: Fensterposition+Fensterbits*256, wobei wenn alle Fensterbits auf eins sind (0xFF) die Addition der Fensterbits entfallen kann. Über die Maskennummer wird die Nummer der Maskenseite bestimmt (von 0 bis 3). Syntax:
   SETMATCH Fensterangabe [Maskennummer]

CONST Über die CONST Definition, ist es möglich eine Zuweisungskonstante zu definieren. Wenn eine solchen Konstante ein wert zugewiesen wird, werden den Variabel flags, layout und clips automatisch Zahlenwerte über Und- und Oderverknüpfungen zugewiesen. Syntax: 

   CONST "Konstante" [Variabel] [&fAND] [|fOR] [*lAND] [/lOR] [$cAND] [!cOR]

Die Zuweisung erfolgt wie folgt. Wenn ein Mikrobefehl auf die definierte Konstante einen Wert schreibt, werden zuerst folgende Berechnungen gemacht:

  1. flags   &= fAND
  2. flags   |=  fOR
  3. layout &= lAND
  4. layout |=  lOR
  5. clips   &=  cAND
  6. clips   |=  cOR 

Durch Einfügen eine  '~' Zeichens vor die Konstanten, ist es möglich diese zu invertieren. Anschließend wird der angegeben Variable der eigentliche Zuweisungswert übergeben. Falls keine Variabel angegeben ist entfällt die Variablezuweisung. 

MASK Über die MASK Definition wird der Beginn einer neuen Maskenseite bekannt gegeben. Es können bis zu vier Maskenseiten definiert werden. Nähere Information gibt es im Punkt Masken.Syntax: 

    MASK 

MACRO Über die MACRO kann ein Makro definiert werden. Über Makros ist es möglich Zeilen der *.acf Datei vom Laden auszuschließen (siehe #Macroname). Ein Makro besteh aus einem Makronamen und einem Rechenausdruck. Wenn der Rechenausdruck ungleich 0 ist werden Zeilen mit diesem Makro geladen. Syntax: 

   MACRO  "Makroname" "Rechenausdruck"

Die im Rechenausdruck können alle möglichen Zahlen und Integer-Rechenoperationen stehen. Außerdem ist es möglich die Parameter param0 und param1 zu verwenden. Diese Parameter entsprechen den Übergabeparametern von AsmInit. z.B.:

   MACRO  "ABC" "param0 == 5"
  
MACRO  "xyz" "param0 & 0x80"
  
MACRO  "m"   "(param1 - 19) *3 + 47 >= param0"

  
@xyz   ....  

#Macroname Über diese Definition via Makro bestimmt werden ob eine Zeile der *.acf Datei geladen werden soll. Wenn das zu vor definierte Makro ungleich Null war, so wird die folgende Zeile geladen. Syntax: 

   @Macroname ...Zeile...


Mikroprogramme 

Mikroprogramme sind eine Folge von Mikrobefehlen die abgearbeitet werden um eine Textzeile für ein CPU-Kommando zu erstellen. Der Beginn eines Mikroprogramms wird mit einer Sprungmarke definiert deren Namen nur ein Zeichen lang sein darf. Mikroprogramme werden aufgerufen in dem die Sprungmarkenzeichen am Ende eines Maskeneintages angehängt werden. Wird ein CPU-Kommando dekodiert das zu diesem Maskeneintrag passt, so werden diese Mikroprogramme ausgeführt. z.B.:

:A

   OR   flags  0x0100
   SET  reg0   13
   NEXT
   END

Dieses Mikroprogramm füllt einen Registerabschnitt. In flags wird der Eintrag 0 aktiviert, dieser soll das Register mit dem Namen RTEXT[13] darstellen (reg0=13). Am Ende des Programms wird auf den nächsten Registerabschnitt weitergeschalten. END markiert das Ende des Mikroprogramms.

Die Sprungmarke :Init hat eine spezielle Bedeutung. Wenn eine *.acf Datei über AsmInit geladen wurde, dann wird dieses Mikroprogramm ausgeführt. Die Übergabeparameter von AsmInit werden in den Variablen param0 und param1 ans Programm übergeben. Im Init Programm können globale Einstellungen für die Dekodierung vorgenommen werden. 

Folgende Mikrobefehle sind möglich: 

GET Dieser Befehl holt die nächsten Bits aus den Code-Daten vom der aktuellen Bitposition. Die Richtung mit der die Bits aus dem nächsten Byte geholt werden kann in der Variable bit_direction bestimmt werden. Syntax:
   GET out = [zahl|var] [Term] [#Flags]

out        : Ist die Variabel in der die Bits gespeichert 
              werden. out kann auch eine Konstante sein.
              In diesem Fall werden auch die Variablen 
              flags, layout und clips beschrieben wie bei
              der CONST Definition beschrieben.
zahl/var : Bestimmt den Bit-Offset ab dem die Bits aus 
              den Code-Daten genommen werden.
              Dieser Offset kann eine konstante Zahl oder
              der Wert einer Variable sein.
Term     : Wenn ein Term angegeben ist werden die 
              eingelesenen Bits entsprechend dem Term 
              umgerechnet. (siehe Terme weiter unten)
#A        : Aktuelle Datenbreite als Bitanzahl benutzen. 
              (siehe flags Bits 18-19)
#B         : Aktuelle Adressbreite als Bitanzahl benutzen. 
              (siehe flags Bits 16-17)
#N        : Bitposition nicht erhöhen nach dem Einlesen. 
#S        : Als Bitposition den Maskenanfang benutzen.
#D        : Als Bitposition das Maskenende benutzen.
#G        : Byte-Order nach dem Einlesen drehen.
#M        : Die Angabe zahl/var als Bitanzahl benutzen.
              Der Bit-Offset ist in diesem Fall 0.
#U        : Die eingelesenen Bits aus auf 32-Bit erweitern. 
              Sollte das oberste Bit 1 sein wird auf eine 
              negative Zahl erweitert.
#0-32    : Ist Anzahl die geholt werden soll wird, falls die 
              Anzahl nicht über andere Flags bestimmt wird.
SET Dieser Befehl speichert einen Wert in einer Variable ab. Syntax:
   SET out = [zahl|var] [Term]

out        : Ist die Variabel in der der Wert gespeichert 
              wird. out kann auch eine Konstante sein.
              In diesem Fall werden auch die Variablen 
              flags, layout und clips beschrieben wie bei
              der CONST Definition beschrieben.
zahl/var : Bestimmt den Wert der nach out geschrieben  
              werden soll. Dieser Wert kann eine konstante 
              Zahl oder der Wert einer Variable sein.
              den Code-Daten genommen werden.
Term     : Wenn ein Term angegeben ist wird der Wert
              entsprechend dem Term umgerechnet. 
              (siehe Terme weiter unten)
AND Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, mit out und verknüpft wird. 

   out &= wert

Syntax:
   AND out = [zahl|var] [Term]
OR Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, mit out oder verknüpft wird. 

   out |= wert

Syntax:
   OR out = [zahl|var] [Term]
XOR Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, mit out xor verknüpft wird. 

   out ^= wert

Syntax:
   XOR out = [zahl|var] [Term]
ADD Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, zu out addiert wird. 

   out += wert

Syntax:
   ADD out = [zahl|var] [Term]
SUB Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, von out suptrahiert wird. 

   out -= wert

Syntax:
   SUB out = [zahl|var] [Term]
MUL Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, mit out multipliziert wird. 

   out *= wert

Syntax:
   MUL out = [zahl|var] [Term]
DIV Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, bei out als Divisor dient. 

   out /= wert

Syntax:
   DIV out = [zahl|var] [Term]
MOD Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, bei out als Modulo-Divisor dient. 

   out %= wert

Syntax:
   MOD out = [zahl|var] [Term]
SHIFT Dieser Befehl funktioniert gleich wie der SET-Befehl, mit dem Unterschied das der Wert nach dem er geholt und mit dem Term umgerechnet wurde, bei out als Shift-Operator dient. Bei negativen Werten wird nach rechts geschoben, bei positive nach links.  

   if(wert<0)
        
out >>= wert
   else  out <<= wert



Syntax:
   SHIFT out = [zahl|var] [Term]
SET64
AND64
OR64
XOR64
ADD64
SUB64
MUL64
DIV64
MOD64
SHIFT64
Dieser Befehls funktioniert gleich wie die entsprechenden 32-Bitbefehle, mit dem Unterschied das out eine 64-Bit Variabel darstellt. Das Berechnen des Wertes erfolgt weiter mit 32 Bit, die Zuweisung erfolgt aber auf eine 64-Bit out Variabel:

     value0 / value0_h 
     value1 / value1_h 
     g_value0 / g_value0_h
     g_value1 / g_value1_h
     code_addres / code_addres_h
     m0 / m1 
     m2 / m3

     ... 

Syntax:
   ???64 out = [zahl|var] [Term]
BIT Dieser Befehl kann ein Bit aus einem Bitfeld geladen werden. Es wird dann in out gespeichert. Syntax:
   BIT out = [zahl|var] [Term] [#Bitfeld]

out        : Ist die Variabel in der das Bit gespeichert 
              wird. out kann auch eine Konstante sein.
              In diesem Fall werden auch die Variablen 
              flags, layout und clips beschrieben wie bei
              der CONST Definition beschrieben.
zahl/var : Bestimmt den Bit-Offset bei dem das Bit aus 
              dem Feld genommen wird. Dieser Offset 
              kann eine konstante Zahl oder der Wert 
              einer Variable sein.
Term     : Wenn ein Term angegeben ist wird der Offset 
              entsprechend dem Term umgerechnet. 
              (siehe Terme weiter unten)
#0-3      : Ist die Nummer des Bitfeldes aus dem das Bit
              geholt werden soll.
NEXT Mit dem NEXT Befehl kann in den nächsten Registerabschnitt gesprungen werden. Der nächste Abschnitt wird mit den Werten aus g_flags, g_layout, g_clips, g_type, g_reg0..3 und g_value0..1 initialisiert. Bei den flags werden die Bits 16..23,27 und 31 vom vorherigen Abschnitt übernommen. Maximal können bis zu 4 Abschnitte erstellt werden. Syntax:
   NEXT 

END Mit dem END Befehl wird das Ende eines Mikroprogramms definiert. Syntax:
   END 

XCHG Mit dem XCHG Befehl können zwei Registerabschnitte mit einander getauscht werden. Damit verändert sicht ihre Ausgabereihenfolge. Zum Zeitpunkt des XCHG Befehls müssen die Abschnitte noch nicht existieren. Syntax:
   XCHG [zahl1|var1] [zahl2|var2]

zahl1/var1 : Bestimmt die Nummer des ersten  
                 Registerabschnittes. Dieser Wert 
                 kann eine konstante Zahl oder der  
                 Wert einer Variable sein.
zahl2/var2 : Bestimmt die Nummer des zweiten  
                 Registerabschnittes. Dieser Wert 
                 kann eine konstante Zahl oder der  
                 Wert einer Variable sein.
GOTO Mit GOTO kann ein unbedingter Spring in einem Mikroprogramm gemacht werden. Syntax:
   GOTO Marke

Marke       : Ist die Marke zu der gesprungen werden 
                 soll. 
IF Mit IF kann ein bedingter Spring in einem Mikroprogramm gemacht werden. Syntax:
   IF [zahl1|var1] == [zahl2|var2] [Term] GOTO Marke
   IF [zahl1|var1] != [zahl2|var2] [Term] GOTO Marke
   IF [zahl1|var1] >= [zahl2|var2] [Term] GOTO Marke
   IF [zahl1|var1] <= [zahl2|var2] [Term] GOTO Marke
   IF [zahl1|var1] >  [zahl2|var2] [Term] GOTO Marke
   IF [zahl1|var1] <  [zahl2|var2] [Term] GOTO Marke

zahl1/var1 : Bestimmt den Wert für den ersten  
                 Vergleichswert. Dieser Wert kann 
                 eine konstante Zahl oder der Wert  
                 einer Variable sein.
zahl2/var2 : Bestimmt den Wert für den zweiten  
                 Vergleichswert. Dieser Wert kann 
                 eine konstante Zahl oder der Wert 
                 Wert einer Variable sein.
Term        : Wenn ein Term angegeben ist wird der 
                 zweite Vergleichswert entsprechend 
                 dem Term umgerechnet.
                 (siehe Terme weiter unten)
Marke       : Ist die Marke zu der gesprungen werden 
                 soll wenn der Vergleich wahr ist. 
TEXT Über diesen Befehl kann ein in die Assemblerzeile geschrieben werden. Syntax:
   TEXT "text" [#Flags]

text       : Ist der Text die der In die Zeile geschrieben  
              werden soll. Über die Flags am Ende des .
              TEXT Befehls, wird bestimm wo der in der
              Zeile der Text eingefügt werden soll.
              Wenn kein Flag angegeben ist wird der 
              Text als Vortext ausgegeben.
#A         : Den Text als Befehlstext für die nächste 
              Zeile ausgeben.
#N         : Den Text als weitern Abschlusstext an den
              aktuellen Registerabschnitt anhängen.
#B         : Den Text als weitern Befehlstext anhängen.
RLIST Über diesen Befehl kann eine Registerliste in der Form {R1,R3-R5,R9} erzeugt werden. Syntax:
   RLIST zahl1 [zahl2|var2] [#Flags]

zahl1          : Bestimmt ab welchem Offset die Register-  
                  namen werden, aus den RTEXT'en geholt
                  werden sollen.
zahl2/var2   :Ist eine Bitliste. Bits die auf 1 sind, be-
                  wirken dass das Register in die Liste  
                  eingefügt wird.
#A             : Die Liste als Befehlstext für die nächste 
                  Zeile ausgeben.
#N             : Die Liste als weitern Abschlusstext an den
                  aktuellen Registerabschnitt anhängen.
#B             : Die Liste als weitern Befehlstext anhängen.
PRINT Über diesen Befehl kann eine Zahl oder ein Formatierter Text in die Assemblerzeile geschrieben werden. Wenn kein Flag angegeben ist wird der Text als Vortext ausgegeben. Syntax:
   PRINT          [zahl1|var1] [zahl2|var2] [#Flags]
   PRINT "format" [zahl3|var4] [zahl4|var4] [#Flags]


zahl1/var1 : Bestimmt die Zahl die ausgegeben   
                 werden soll. Dieser Wert 
                 kann eine konstante Zahl oder der  
                 Wert einer Variable sein.
zahl2/var2 : Bestimmt Anzahl der Zeichen der  
                 mit dem die Zahl ausgegeben werden
                 soll. Null steht für Variabel.		 
format      : Dieser Text bestimmt das Ausgabe-  
                 format des Textes. 
	    ( siehe printf(format,zahl3,zahl4) )
zahl4/var4 : Ist der erste Parameter der an die   
                 printf Funktion übergeben wird. Dieser 
                 Wert kann eine konstante Zahl oder der  
                 Wert einer Variable sein.
zahl4/var4 : Ist der zweite Parameter der an die   
                 printf Funktion übergeben wird. Dieser 
                 Wert kann eine konstante Zahl oder der  
                 Wert einer Variable sein.
#A            : Den Text als Befehlstext für die nächste 
                 Zeile ausgeben.
#N            : Den Text als weitern Abschlusstext an den
                 aktuellen Registerabschnitt anhängen.
#B            : Den Text als weitern Befehlstext anhängen.

Terme haben folgende Funktion:

[zahl|var] [&zahl1] [|zahl2|^zahl2] [<<zahl3|>>zahl3|+zahl3|-zahl3]

Durch Einfügen eine  '~' Zeichens vor die konstanten Zahlen, ist es möglich diese zu invertieren.Terme ergeben einen Wert der mit einer Zahl bzw. Variabel verarbeitet wird. Ein Term kann aus bis zu drei Zahlen bestehen:

zahl1  : Macht eine UND-Verknüpfung mit dem Wert.
zahl2  : Macht eine ODER bzw. XOR-Verknüpfung mit dem Wert.
zahl3  : Macht eine Addition, Subtraktion oder eine Schiebeoperation 
           mit dem Wert.

Der Term wird je nach Angabe so ausgerechnet:
wert  =  (( [zahl|var] & zahl1 ) | zahl2 ) +  zahl3
wert  =  (( [zahl|var] & zahl1 ) ^ zahl2 ) +  zahl3
wert  =  (( [zahl|var] & zahl1 ) | zahl2 ) -  zahl3
wert  =  (( [zahl|var] & zahl1 ) ^ zahl2 ) -  zahl3
wert  =  (( [zahl|var] & zahl1 ) | zahl2 ) << zahl3
wert  =  (( [zahl|var] & zahl1 ) ^ zahl2 ) << zahl3
wert  =  (( [zahl|var] & zahl1 ) | zahl2 ) >> zahl3
wert  =  (( [zahl|var] & zahl1 ) ^ zahl2 ) >> zahl3