;*********************************************
;* Relozierprogramm: Datenblock * ;* Version 2 vom 18.01.1986 - Stefan M. Aust * ;********************************************* ; ;--> Startadresse des Datenblocks ; ORG #A000 ; ;--> Format der Daten: Die Lénge der einzelnen Z80-Befehle ist jeweils ; fèr normale Befehle, ED-Befehle, DD & FD-Befehle ; bitweise in Byte gepackt. ; Fèr den Befehl 'LD HL,(nn)' := 2A steht z.B. an ; #2A. Stelle in der Tabelle % 0011 0111. ; DD & DF-Befehl 3 Byte - - - - ^^^ ; ED-Befehl (undefiniert) 1 Byte - -^^ ; normaler Befehl 3 Byte - - - - - - -^^ ; byttab: DEFB #15,#17,#15,#15,#15,#15,#16,#15 DEFB #15,#15,#15,#15,#15,#15,#16,#15 DEFB #16,#17,#15,#15,#15,#15,#16,#15 DEFB #16,#15,#15,#15,#15,#15,#16,#15 DEFB #16,#37,#37,#15,#15,#15,#16,#15 DEFB #16,#15,#37,#15,#15,#15,#16,#15 DEFB #16,#17,#17,#15,#25,#25,#46,#15 DEFB #16,#15,#17,#15,#15,#15,#16,#15 DEFB #15,#15,#15,#1D,#15,#15,#25,#15 DEFB #15,#15,#15,#1D,#15,#15,#25,#15 DEFB #15,#15,#15,#1D,#15,#15,#25,#15 DEFB #15,#15,#15,#1D,#15,#15,#25,#15 DEFB #15,#15,#15,#1D,#15,#15,#25,#15 DEFB #15,#15,#15,#1D,#15,#15,#25,#15 DEFB #25,#25,#25,#2D,#25,#25,#15,#25 DEFB #15,#15,#15,#1D,#15,#15,#25,#15 DEFB #15,#15,#15,#15,#15,#15,#25,#15 DEFB #15,#15,#15,#15,#15,#15,#25,#15 DEFB #15,#15,#15,#15,#15,#15,#25,#15 DEFB #15,#15,#15,#15,#15,#15,#25,#15 DEFB #15,#15,#15,#15,#15,#15,#25,#15 DEFB #15,#15,#15,#15,#15,#15,#25,#15 DEFB #15,#15,#15,#15,#15,#15,#25,#15 DEFB #15,#15,#15,#15,#15,#15,#25,#15 DEFB #15,#15,#17,#17,#17,#15,#16,#15 DEFB #15,#15,#17,#46,#17,#17,#16,#15 DEFB #15,#15,#17,#16,#17,#15,#16,#15 DEFB #15,#15,#17,#16,#17,#14,#16,#15 DEFB #15,#15,#17,#15,#17,#15,#16,#15 DEFB #15,#15,#17,#15,#17,#14,#16,#15 DEFB #15,#15,#17,#15,#17,#15,#16,#15 DEFB #15,#15,#17,#15,#17,#14,#16,#15 ; ; ;*********************************************** ;* Relozierprogramm: Source-Code * ;* Version 4 vom 18.01.1986 - Stefan M. Aust * ;*********************************************** ; ;Aufruf des Programms: CALL Adresse,Start,Ende,Anfang,Schu~,Offset ; Adresse := Startadresse des Relozierprogramms ; Start := Beginn des zu untersuchenden Bereichs ; Ende := Ende dieses Bereichs ; Anfang := Beginn des Adressbereichs, in dem die ; Adresse liegen mu~, damit sie geéndert wird ; Schlu~ := Ende dieses Bereichs ; Offset := Die Basisadresse fèr den neuen Adressbereich ; ;--> Hier steht das Programm: Startadresse ; Here: EQU $ ;Here mu~ #A100 sein, sonst Fehler in Datenblock ; ;--> Und hier féngt das Programm an ; CP 5 ;wurden 5 Argumente èbergeben? RET NZ ;nein, zurèck LD HL,offset+1 ;Adresse-Speicherbereich LD B,A ;B=Anzahl Argumente (5) loop1: LD A,(IX+1) ;(HL)=(IX+1) LD (HL),A DEC HL LD A,(IX+0) ;(HL-1)=(IX) LD (HL),A DEC HL INC IX INC IX DJNZ loop1 ;weiter bis alle Argumente kopier LD HL,(anfang) ;Startadresse ;--> Hauptschleife: loop2: PUSH HL ;retten LD A,(HL) ;A=zu untersuchendes Byte INC HL ;HL=Adresse néchstes Byte CP #ED ;ED-Befehl? JR NZ,no_ED ;nein,->weiter LD B,1 ;sonst B=ED-Befehl CALL adr1 ;Lénge bestimmen AND 3 LD B,1 JR test ;weiter-> no_ED: CP #DD ;DD-Befehl? JR Z,DD_Bef ;ja,-> CP #FD ;oder FD-Befehl? JR NZ,normal ;nein,->normal DD_Bef: LD B,2 ;sonst B=DD,FD-Befehl CALL adr1 ;Lénge bestimmen AND 7 LD B,1 JR test ;weiter-> normal: LD B,0 ;B=normaler Befehl CALL adr2 ;Lénge bestimmen AND 3 test: CP 3 ;3-Byte-Befehl? JR NZ,unglei ;nein, nicht veréndern PUSH BC ;Register retten LD E,(HL) ;DE=Argument des 3-Byte-Befehls INC HL LD D,(HL) EX DE,HL ;HL=Argument LD BC,(ende) ;BC=Endadresse OR A ;carry lùschen SBC HL,BC ;Argument < Ende ? JR NC,nein ;nein, nicht veréndern ADD HL,BC ;Argument wiederherstellen LD BC,(start) ;BC=Startadresse OR A ;Carry lùschen SBC HL,BC ;Argument > Start ? JR C,nein ;nein, nicht veréndern LD BC,(offset) ;BC=Offset auf neuen Adressbereich ADD HL,BC ;HL=veréndertes Argument EX DE,HL ;DE=Argument, HL=Adress LD (HL),D ;Argument abspeichern DEC HL LD (HL),E nein: POP BC ;Register zurèck unglei: CP 4 ;A = 4 ? ( Spezialbefehl LD (IX+d),n ) JR NZ,weiter ;nein, -> DEC A ;sonst A - 1 weiter: ADD A,B ;Offset B zu A addieren LD D,0 ;DE = A (Lénge des Befehls) LD E,A POP HL ;HL=aktuelle Adresse ADD HL,DE ;HL=neue Adresse LD BC,(schlus) ;BC=Schlu~ OR A ;carry lùschen SBC HL,BC ;schon Schlu~ erreicht? RET NC ;ja, zurèck ADD HL,BC ;sonst HL wiederherstellen JR loop2 ;und weiter ; ;--> Unterprogramm: Lénge des Z80-Befehl feststellen ; In: HL=Adresse des Befehls, B=Befehlstyp (normal,ED,DD & FD) ; Out: A and 3=Lénge, ev. HL=HL+1 ; adr1: LD A,(HL) ;A = Befehlsbyte INC HL ;Adresse + 1 adr2: PUSH HL ;und retten LD HL,byttab ;HL Anfangsadresse Tabelle LD D,0 ;DE=Befehlsbyte (d.h. Offset auf Tabelle) LD E,A ADD HL,DE ;HL=gesuchter Tabelleneintrag LD A,B ;B=0? OR A ;dann Zero=1 LD A,(HL) ;A=Tabelleneintrag JR Z,ok ;B war 0,-> loop3: RRCA ;Eintrag rotieren, solange bis gewènschte RRCA ;Bitposition ins Bit 0 und 1 steht DJNZ loop3 ok: POP HL ;Adresse zurèck nach HL RET ; ;--> Speicherbereich fèr Daten ; anfang: DEFW 0 schlus: DEFW 0 start: DEFW 0 ende: DEFW 0 offset: DEFW 0 END |