Obligement - L'Amiga au maximum

Mercredi 23 août 2017 - 19:20  

Translate

En De Nl Nl
Es Pt It Nl


Rubriques

 · Accueil
 · A Propos
 · Articles
 · Galeries
 · Glossaire
 · Hit Parade
 · Liens
 · Liste jeux Amiga
 · Quizz
 · Téléchargements
 · Trucs et astuces


Articles

 · Actualité (récente)
 · Actualité (archive)
 · Comparatifs
 · Dossiers
 · Entrevues
 · Matériel (tests)
 · Matériel (bidouilles)
 · Points de vue
 · En pratique
 · Programmation
 · Reportages
 · Tests de jeux
 · Tests de logiciels
 · Tests de compilations
 · Articles divers

 · Articles in english
 · Articles in other languages


Twitter

Suivez-nous sur Twitter




Liens

 · Sites de téléchargements
 · Associations
 · Pages Personnelles
 · Moteurs de recherche
 · Pages de liens
 · Constructeurs matériels
 · Matériel
 · Autres sites de matériel
 · Réparateurs
 · Revendeurs
 · Presse et médias
 · Programmation
 · Développeurs logiciels
 · Logiciels
 · Développeurs de jeux
 · Jeux
 · Autres sites de jeux
 · Scène démo
 · Divers
 · Informatique générale


Jeux Amiga

0, A, B, C, D, E, F,
G, H, I, J, K, L, M,
N, O, P, Q, R, S, T,
U, V, W, X, Y, Z


Trucs et astuces

0, A, B, C, D, E, F,
G, H, I, J, K, L, M,
N, O, P, Q, R, S, T,
U, V, W, X, Y, Z


Glossaire

0, A, B, C, D, E, F,
G, H, I, J, K, L, M,
N, O, P, Q, R, S, T,
U, V, W, X, Y, Z


Partenaires

Annuaire Amiga

Amedia Computer

Relec

Hit Parade


Contact

David Brunet

Courriel

 


En pratique : Déplombage de Deliverance
(Article écrit par Alpha One et extrait de Flashtro.com - mai 2009)


Note : traduction par Denis Lechevalier.

Prérequis
  • Un Amiga ou l'émulateur WinUAE (configuration : 2 Mo de mémoire Chip !).
  • Une cartouche Action Replay III (ou l'image de sa ROM).
  • Le jeu original de Deliverance ou ses images CAPS (deux disquettes).
  • Un assembleur (ASM-One, Trash-M One, Seka ou similaire).
Déplombage de Deliverance

Eh oui, me voici de retour pour un autre tutoriel sur le déplombage MFM... Deliverance est un jeu sur deux disquettes avec un format de piste spécial de $18A0 octets sur chaque piste. La table de correspondance de fichiers qui contient toutes les informations à propos des positions des fichiers sur ces disquettes est stockée directement dans le bloc d'amorce à l'offset $200.

Regardons vite fait la table de fichiers : on va lire la première piste de la disquette 1 en utilisant notre Action Replay bien-aimée...

Tapez "rt 0 1 50000" et appuyez sur "Entrée"...

Après que la piste ai été chargée, faites comme montré sur l'image ci-dessous pour voir le "dump" en hexa de la table de fichiers.

Déplombage de Deliverance

Comme ça, on peut voir que les positions de fichiers sont stockées comme des positions d'octets normales. Par exemple, le premier fichier commence depuis la position disque $18A0 et finit à la position $A44C, le second fichier commence en $A44C (la fin du premier fichier bien sûr) et finit en $C5CF et ainsi de suite... le dernier fichier se termine en $1EB7A4 qui représente une valeur de plus de 2 Mo, ce qui veut dire que les deux disquettes de jeu sont complètement remplies !

Bon, comment j'ai su où se trouvait la table de fichiers sur la disquette ?! Jetons un oeil dans le code de l'amorce ("bootcode") qui commence en $5000C.

Tapez "d $5000C" et appuyez sur "Entrée". Faites défiler quelques lignes jusqu'à ce que vous voyez ceci :

Déplombage de Deliverance

La première partie du bloc d'amorce vérifie si vous avez au moins 1 Mo de mémoire installé sur votre ordinateur (non montré sur l'image), autrement le code de l'amorce bouclera sans fin.

Mais si vous êtes l'heureux propriétaire d'une extension mémoire dépassant les 512 ko, le jeu allouera $1200 octets de mémoire pour le reste de la piste 0 ($400 octets du bloc d'amorce, $1200 octets d'autre code = $1600 octets de la longueur d'une piste DOS normale) et puis lire ces $1200 octets en utilisant le trackdisk.device.

Vous pouvez voir l'appel AllocMem() en $50076 et l'appel DoIO() pour lire les $1200 octets en $50098. Enfin, en $5009C, il copie la table de fichiers depuis la position de l'amorce $200 jusqu'en mémoire haute.

Si vous regardez de plus près à l'adresse $5007A, juste après l'appel AllocMem(), vous reconnaîtrez que le résultat de cet appel, qui est en fait l'adresse des $1200 octets du bloc mémoire, est poussé sur la pile ! En $500AC, après que la table de fichiers ai été copiée, l'instruction RTS qui suit amène la dernière adresse depuis la pile et continue l'exécution à cette position. Donc en fait, c'est notre JMP vers le bloc mémoire alloué !

Donc la partie importante de la piste 0 commencera sûrement à l'offset $400. Désassemblons cet endroit en tapant "d $50400", suivi de "Entrée"...

Déplombage de Deliverance

Bon, ça a l'air très familier tout ça, hein ?! Un numéro de fichier est donné en D0, l'adresse de chargement en A0 et puis une routine est appelée qui charge sûrement le numéro de fichier spécifié dans son emplacement mémoire.

Comme je l'ai découvert, le numéro de fichier #3 est une sorte de code de jeu principal qui inclut également un autre chargeur de piste qui marche de la même façon que celui-ci.

Pour continuer le désassemblage du code où le "JMP $8(A4)" en $5044A nous emmènera alors, on va écraser cette instruction avec une boucle de branchement. Donc, si on démarre le jeu, le programme s'arrêtera à cet endroit, comme ça on peut trouver ou pointe a4+8...

Insérez l'instruction branche et écrivez la piste 0 modifiée sur la disquette de jeu comme montré ci-dessous sur l'image :

Déplombage de Deliverance

Important : si vous utilisez une autre configuration mémoire que 2 Mo de mémoire Chip, les adresses qui sont montrées à partir de maintenant diffèreront !

Réinitialisez votre machine maintenant et laissez le jeu démarrer jusqu'à ce que notre boucle de branchement soit lancée... vous remarquerez ceci si vraiment rien ne se passe ! ;-D

Maintenant, activez votre Action Replay à nouveau et jetez un oeil sur les registres en tapant "r" puis "Entrée"...

Si la configuration mémoire ci-dessus est celle utilisée, alors A4 pointera vers l'adresse $86800, ainsi notre saut continuera vers le code en $86808 !

Désassemblons le code avec "d $86808" suivi de "Entrée"...

Vous devrez aller descendre quelques pages plus bas jusqu'à ce que vous voyez enfin ce code :

Déplombage de Deliverance

On peut voir les fichiers #6, #0 et #5 qui sont chargés en utilisant un chargeur de piste à l'adresse $8D334.

Maintenant, pour choper le contenu des disquettes, on va regarder ce que fait le chargeur de pistes... désassemblons le code du chargeur de pistes avec "d $8D334".

Déplombage de Deliverance

Maintenant, on va se servir de ce chargeur de pistes pour choper toutes les données des disques.

On va mettre un point d'arrêt ("breakpoint") de suite en $8D352, comme ça l'Action Replay s'active avant que le chargeur de piste soit appelé. Puis on va changer les paramètres du chargeur et avant de continuer l'exécution, on va mettre un autre point d'arrêt en $8D356, l'instruction juste après le retour du chargeur de piste. Ainsi, on est prévenu quand le chargeur de piste a terminé et on peut choper les pistes avant que le jeu les décompresse !

On ne sauvera aucun fichier sur disquette cette fois et on ne va même pas coder une nouvelle image de disquette aujourd'hui... ;). On va choper les pistes et les écrire directement depuis la mémoire sur nos disquettes fraîchement formatées !

Comme je l'ai dit quelques lignes auparavant, les deux disquettes de jeu sont complètement remplies avec des données, donc on devra utiliser une troisième disquette pour faire tenir toutes les données du jeu sur notre déplombage. Maintenant, réfléchissons à la façon dont on va répartir les données sur ces trois disquettes...

Revenez à la table de fichiers, j'ai décidé de diviser les données comme suit :

Disquette 1 : $000000 à $0B7976
Disquette 2 : $0B7976 à $182E7E
Disquette 3 : $182E7E à $1EB7A4

Déplombage de Deliverance

Ainsi, pour notre nouveau chargeur, on va d'abord vérifier que la position des fichiers sur disque est par exemple plus petite que $B7976 parce que si c'est vrai, le fichier appartient à la disquette 1. Si la position de fichier est plus petite que $182E7E, le fichier appartient à la disquette 2, autrement, c'est sur la disquette 3.

Bon d'accord, commençons à créer la disquette déplombée #1.

On ne peut pas sortir de l'Action Replay avec la commande "x" de suite parce qu'on est bloqué dans notre boucle. Pour continuer dans le code du jeu, on doit sauter à l'adresse stockée en a4 + 8 !

Étant donné que A4 pointe vers $86800, on va quitter l'Action Replay en faisant "g $86808" suivi de "Entrée"...

Maintenant, le jeu commence à lire les pistes (ce qui se fait dans la foulée), entrez dans l'Action Replay à nouveau pour mettre notre point d'arrêt obligatoire comme ceci : "bs $8D352" suivi de "Entrée".

Sortez de l'Action Replay à nouveau et attendez jusqu'à ce que l'Action Replay s'affiche... si cela se produit, regardons les "regs" pour voir que le chargeur de pistes veut faire... hum... charger. :-)

Déplombage de Deliverance

On sait, grâce au code désassemblé du chargeur de piste, que D1 pointe vers le début du fichier sur la disquette. Comme on peut le voir, le jeu veut charger le fichier #0 de suite parce qu'il commence en $18A0 ! On n'a pas besoin de toucher cette valeur alors, le fichier #0 est la bonne position de départ pour la mise en oeuvre de notre "rippe" !

La valeur stockée en D0 est la taille du fichier, $8BAC dans le cas de notre fichier #0. Maintenant, étant donné que l'on veut ripper plus que simplement le fichier #0, on va changer la valeur en D0 de manière à ce que le chargeur de piste lise tout les octets que l'on veut stocker sur notre disquette déplombée #1 ($B7976 octets).

Pour faire en sorte que le chargeur lise tout depuis $18A0 à $B7976, on définit la valeur en D0 en $B7976-$18A0 (toutes les étapes sont montrées dans l'image ci-dessous). Enfin, on va changer l'adresse de chargement du fichier (stocké en A0) en $918A0...

Maintenant, vous pouvez vous demander, mais pourquoi charger les données en $918A0 et pas en $90000 ? Comme on le sait, le fichier #0 commence sur la disquette de jeu à la position $18A0. Je vais donc sauver les pistes sur notre disquette déplombée à partir de $90000 plus tard pour être sûr que le fichier #0 a aussi la bonne position de départ sur notre disquette déplombée !

Donc... si vous changez les "regs" comme décrit, vous pouvez enfin définir le point d'arrêt à l'adresse juste après le renvoi du chargeur de piste avec bs $8D356, suivi par entrée...

Quittez l'Action Replay maintenant et attendez que le chargeur de piste ait fini le boulot... vous serez prévenu par l'activation de l'Action Replay. ;-)

Déplombage de Deliverance

Maintenant que le chargement de piste est terminé, vous pouvez vérifier que tout s'est bien déroulé en examinant la mémoire à l'adresse $918A0 à l'identique de l'image ci-dessus.

Après ça, je continue en lisant la piste 0 en $90000 de manière à ce que l'on ait un "dump" complet de la disquette de jeu 1 allant de $0 à $B7976 en mémoire.

Maintenant, avant de sauver cela sur notre disquette déplombée #1, on va devoir écraser notre boucle de branchement que l'on a mise sur la disquette originale parce qu'on ne veut pas que notre déplombage boucle ! Faites comme ce qui est montré dans l'image ci-dessous...

Et enfin... insérez une disquette déplombée formatée #1 dans le lecteur df0: et sauvez tout ça en faisant : "wt 0 !134 90000".

On sauve 134 pistes parce que... !134 * !5632 (taille de piste dos) = !754688 ($B8400). Ainsi, c'est OK pour notre plage allant de $0 à $B7976 !

A présent, la création des disquettes déplombées #2 et #3 est même encore plus facile... revenez dans la partie de ce tutoriel où l'on démarre la disquette de jeu originale #1 et suivez à nouveau toutes les étapes de manière à ce que votre Action Replay s'active juste avant que le chargeur de piste soit appelé...

Pour créer la disquette déplombée #2, changez les paramètres de chargement comme ceci :

Déplombage de Deliverance

Quittez l'Action Replay et si le chargement de piste est terminé, sauvez les pistes sur la seconde disquette déplombée comme ceci : "wt 0 !148 90000" suivi de "Entrée"...

Pour créer la disquette déplombée #3, changez les paramètres de chargement comme ceci :

Déplombage de Deliverance

Sortez de l'Action Replay et si le chargement de piste est terminé, sauvez les pistes sur notre troisième disquette déplombée comme ceci : "wt 0 !77 90000" suivi de "Entrée"...

On est enfin arrivés au moment où les disquettes originales ne sont plus nécessaires.

Maintenant, la seule chose qui reste à faire, c'est d'insérer notre propre chargeur de piste qui gère les pistes DOS normales. Pour faire cela, réinitialisez votre machine et démarrez votre assembleur favori, en espérant que ce soit ASM-One. ;-D

Pour rendre la chose plus simple pour vous, j'ai inclus le code source tout entier dans l'archive Zip avec le binaire du chargement de piste (NDLR : vous devez être enregistré au site Flashtro pour pouvoir le télécharger).

Donc... réservez quelques kilo-octets de mémoire Chip et lisez le source (en utilisant la commande "r") fourni avec ce tutoriel. Appuyez sur "Esc" pour basculer en mode éditeur, vous devriez vous quelque chose comme ceci :

Déplombage de Deliverance

A présent, voilà ce que je fais dans le source : avant que l'on lance ce code source, on va lire la première piste de notre disquette déplombée manuellement en mémoire au label piste0:. Après que l'on puisse exécuter le code qui ne fait qu'écraser le premier chargeur de piste du jeu avec notre nouveau chargeur à partir du label "Nouveauchargeur:" au label "Nouveauchargeurfin:".

Maintenant, ce chargeur vérifie lui-même si le jeu veut charger le fichier #4. Si c'est le cas, le code principal du jeu inclut le second chargeur de piste (stocké dans le fichier #3) se trouve déjà décompressé en mémoire. Puis notre chargeur se copie lui-même en mémoire en $7FC00, une région mémoire qui n'est pas utilisée par le jeu et met un JMP $7FC00 sur la première instruction de la deuxième routine de chargement de piste. Comme ça, on n'a pas besoin de toucher le second chargeur compressé sur la disquette.

Le code source avec les commentaires est ci-dessous :

LEA Nouveauchargeur(PC),A0    ; pas d'explications ici, copie simplement le nouveau chargeur !
LEA piste0+$566,A1
MOVE.L #(Nouveauchargeurfin-Nouveauchargeur)-1,D0
REmPLACEchargeur:
MOVE.B (A0)+,(A1)+
DBF D0,REmPLACEchargeur
RTS

; si notre nouveau chargeur est appelé par le jeu, ces valeurs
; sont stockées dans les registres ci-après :
; D0 = Longueur du fichier
; D1 = position en octet sur le(s) Disquette(s)
; A0 = adresse de chargement de fichier
; A1 = tampon MFM

Nouveauchargeur :

MOVEM.L D0-A6,-(A7)            ; Sauve les registres sur la pile
LEA $DFF000,A6                 ; base des puces propriétaires en A6
MOVE.L A1,A2                   ; notre chargeur de pistes a besoin d'une adresse MFM en A2
CMP.L #$313,D0                 ; Fichier #4 à charger (le fichier #4 a une longueur de $313 octets)
BNE.B NO                       ; pas encore...
LEA Nouveauchargeur(PC),A3     ; autrement copiez le chargeur en $7FC00, Ptr vers Nouveauchargeur en A3
LEA $7FC00,A5                  ; Pointeur vers $7FC00 en A5
MOVE.L #(Nouveauchargeurfin-Nouveauchargeur)-1,D7 ; taille de notre chargeur en octets
COPierchargeur:
MOVE.B (A3)+,(A5)+             ; Copier le chargeur
DBF D7,COPierchargeur
MOVE.W #$4EF9,$7082(A4)        ; Place le "JMP $7FC00" ...
MOVE.L #$7FC00,$7084(A4)       ; ... dans le code du second chargeur de piste

NumerO :

LEA etatdisque(PC),A5      ; le numéro du disque actuel dans le lecteur est stocké ici (1/2/3)
CMP.L #$B7976,D1           ; position de fichier sur le disque ci-dessous $B7976 ?
BLT.B DISque1              ; ouais, le fichier est sur le disque #1 !
CMP.L #$182E7E,D1          ; position de fichier sur le disque ci-dessous $182E7E ?
BLT.B DISque2              ; ouais, le fichier est sur le disque #2 !

DISque3 : ; autrement il est sur le disque #3 ! ;-)

CMP.B #3,(A5)              ; Disque 3 inséré ?
BEQ.B DISque3IN            ; ouais, on continue...
MOVE.W #$00F,D7            ; autrement met le code de couleur *bleu* en d7
BSR.W FLASHe               ; l'écran flashe et attend le clic de souris !
MOVE.B #3,(A5)             ; le Disque #3 est dans le lecteur, sauver l'état

DISque3IN :

SUB.L #$182E7E,D1          ; Fichier en $182E7E démarre en $0 sur le disque 3... soustrait la valeur !
BRA.W lecture              ; lire le fichier !

; pas d'explications supplémentaires pour la gestion du disque 1 et 2, tous pareil que pour le disque 3...

DISque2 :

CMP.B #2,(A5)
BEQ.B DISque2IN
MOVE.W #$0F0,D7
BSR.W FLASHe

DISque2IN :

MOVE.B #2,(A5)
SUB.L #$B7976,D1
BRA.W lecture

DISque1 :

CMP.B #1,(A5)
BEQ.B lecture
MOVE.W #$F00,D7
BSR.W FLASHe
MOVE.B #1,(A5)

Lecture :

DIVS.W #$1600,D1           ; obtenir le n° de piste où démarre le fichier actuel
SWAP D1                    ; permutter d1 pour obtenir le reste de notre division...
MOVE.W D1,D2               ; ... lequel est la position en octet sur la piste !
EXT.L D2                   ; élargir d2 en un mot long
CLR.W D1                   ; effacer la valeur restante en d1
SWAP D1                    ; permutter encore d1 pour avoir encore le numérodepiste.l
BSR.B chargeurpiste        ; saut vers le chargeur de piste
MOVEM.L (A7)+,D0-A6        ; restaurer les registres
RTS                        ; retour au code du jeu

FLASHe :

MOVE.W D7,$180(A6)
BTST #6,$BFE001
BNE.B FLASHe
RTS

etatdisque :

DC.B 1,0

Chargeurpiste :

INCBIN "chargeur^piste.BIN"   ; notre chargeur de piste ! ;-)

Nouveauchargeurfin :

piste0 :

BLK.B $1600,0              ; espace pour une piste DOS !

Maintenant, faites comme dans l'image ci-dessous. Assemblez le tout en faisant "a", insérez votre disquette déplombée #1 et lisez la piste 0 en tapant "rt".

Enfin, exécutez le source en utilisant "j" et écrivez la piste 0 avec "wt".

Déplombage de Deliverance

Maintenant que notre déplombage est terminé, réinitialisez votre Amiga et faites une partie...

Déplombage de Deliverance

Ce jeu déchire (ou pas) ! ;-D

Note : salutations spéciales à Musashi9 pour avoir mis en ligne le (presque) meilleur site Web dans le monde entier et bien sûr à Rob.


[Retour en haut] / [Retour aux articles]