COURS205.TXT/fr

From Atari Wiki
Revision as of 14:07, 23 November 2023 by Exxos (talk | contribs)
Jump to navigation Jump to search
   ******************************************************************
   *                                                                *
   *             COURS D'ASSEMBLEUR 68000 SUR ATARI ST              *
   *                                                                *
   *                 par Le F�roce Lapin (from 44E)                 *
   *                                                                *
   *                         Seconde s�rie                          *
   *                                                                *
   *                         Cours num�ro 5                         *
   ******************************************************************

   Apr�s  ce cours sur les macros,  nous allons passer � l'usage  des
   tableaux   en  assembleur.   J'esp�re qu'apr�s chaque  cours  vous
   effectuez  vous-m�me des recherches et des exercices,  et que vous
   ne  vous pr�cipitez pas tout de suite sur le cours  suivant.  M�me
   si   les cours vous semblent maintenant courts par rapport �  ceux
   de  la premi�re s�rie, il n'en soul�vent pas moins le voile sur de
   nombreux   sujets.  Vous   avez  maintenant  le  niveau  pour  les
   approfondir et j'esp�re que vous le faites!

   LES TABLEAUX
   L'usage   des  tableaux n'est pas tr�s r�pandu  en  assembleur  au
   niveau   des  programmeurs d�butants.  En effet  le  syst�me  peut
   sembler  assez p�rilleux � manipuler mais s'av�re par contre  tr�s
   puissant et tr�s commode!

   Tout  comme le principe de la pile,  celui des tableaux est simple
   mais   demande  beaucoup  de  logique  pour  pouvoir   fonctionner
   convenablement.  Prenons   tout d'abord un  exemple  simple:  nous
   allons   appuyer sur les touches de fonctions F1 jusqu'� F10 et  �
   chaque   fois nous allons afficher une lettre.  Commen�ons par  un
   exemple sans tableau.

   Voir le listing num�ro 2.

   Au  d�part INCLUDE de la routine de d�marrage de programme �tudi�e
   au  d�but de la seconde s�rie. Pr�sentation avec un petit message,
   puis  attente d'un appui sur une touche. Comme nous voulons tester
   les   touches  de  fonctions et que celles-ci n'ont  pas  de  code
   ASCII,  nous  profitons du fait que la fonction Gemdos 7  retourne
   dans  le poids faible de D0 le code ASCII mais aussi dans le poids
   fort le scan code. Il n'y a d'ailleurs pas que �a de retourn�, car
   si   vous consultez la bible ST ou simplement la  description  des
   fonctions  dans les derni�res pages de la doc du GFA 3.00,  vous y
   apprenez  que  Gemdos  7 renvoi  dans  les bits 0-7 le code ASCI, 
   16-23 le  code clavier et 24-31 l'�tat des touches de commutations
   du clavier.

   Petit   rappel  sur les codes ASCII et les scan  code.  Les  codes
   ASCII  (American Standard Code for Information  Interchange)  sont
   des   codes  sur 7 bits,  qui  suivent  l'ordre  alphab�tique.  Ce
   standard   est  aussi  appelle  Code  t�l�graphique  international
   num�ro  5. Le 8 �me bit est un bit de parit� c'est � dire qu'il ne
   sert  qu'� la v�rification de la bonne transmission  du  code.  De
   part   le fait que ce syst�me est Am�ricain,  le codage  ASCII  ne
   prend   pas  en  compte les accents ni les caract�res  du  type  c
   c�dille.  Cependant   notre  ordinateur n'ayant pas besoin  de  ce
   huiti�me   bit  pour  v�rifier  les  transmissions,  celui-ci  est
   utilis�  pour augmenter le nombre de combinaison possible.  Retour
   au  cours 2 de la s�rie 1,  sur les chiffres magiques: avec 7 bits
   nous   pouvons compter de 0 � 127,  un bit de plus nous permet  de
   compter  de 0 � 255.  Consulter un tableau des codes ASCII (bible,
   livre  du d�veloppeur, doc GFA etc...) et vous vous rendrez compte
   que  tous  les  signes 'bizarres' sont cod�s sur 8bits et ont donc
   des codes sup�rieurs � 127.

   Cependant  les codes ASCII ne suffisent pas.  Imaginez que je tape
   sur   la touche A de mon clavier.  En code ASCII je vais  recevoir
   65. Mais  si  un Anglais tape sur la m�me touche, pour lui ce sera
   un  Q et il recevra le code ASCII 81. Le code ASCII ne d�pend donc
   pas  de la touche, m�caniquement parlant, mais plut�t de la lettre
   de  cette touche. Il existe un autre codage qui lui correspond aux
   touches  d'un point de vue m�canique. C'est ce que l'on appelle le
   scan-code.

   Pour   le  scan-code,  une touche poss�de  un  num�ro,  totalement
   ind�pendant  de la lettre qui sera affect�e � cette touche.  Ainsi
   la   touche A de votre clavier renvoi le scan-code $10,  et il  en
   est   de  m�me pour tous les ST du monde,  que cette  touche  soit
   marqu�e   "A",  ou  "Q".  C'est l'emplacement sur le  clavier  qui
   compte. 

   Nous   testons  donc le scan-code de la touche sur  laquelle  nous
   avons   appuy�.  Si  c'est  Escape,  nous  sortons  du  programme.
   Autrement,   nous  allons  tester  s'il  s'agit  d'une  touche  de
   fonction.  La  touche F1 a pour scan-code  $3B,  F2->$3C,  F3->$3D
   etc...  jusqu'�  F10->$44. Les scan-codes se suivant, nous testons
   donc   notre  r�sultat par rapport au scan-code de  F1,  si  c'est
   inf�rieur  ce  n'est  donc  pas  valable, de  m�me  par rapport au
   scan-code   de  F10:  si c'est sup�rieur ce n'est pas valable non 
   plus. 

   Ces tests �tant faits, nous sommes donc en pr�sence d'un scan-code
   situ�  entre $3B et $44,  ces 2 nombres compris. $3B, cela fait 59
   en  d�cimal.  Pour avoir 65 (code ASCII de A) il suffit  d'ajouter
   6.  C'est   que nous faisons ensuite.  Nous obtenons donc le  code
   ASCII  de A,  B,  C etc... suivant la touche de fonction qui a �t�
   enfonc�e. Il ne reste plus qu'� afficher cette lettre!

   Imaginons   maintenant  que  nous voulions  afficher  "touche  F1"
   lorsque   nous appuyons sur cette  touche,  "touche  F2",  etc....
   Plusieurs solutions s'offrent � nous. En voici une premi�re qui me
   vient  � l'esprit et que je vais juste vous d�voiler car elle  n'a
   pas  de rapport avec les tableaux.  Pour ne pas  compliquer,  nous
   n'afficherons   pas  "touche F10",  en fait nous ne  prendrons  en
   compte  que les touches F1-F9.  Souvenez vous d'un des listing  de
   la  s�rie 1.  Celui qui affichait une phrase en faisant appara�tre
   les   lettres   comme   sur   les  affichages  des  gares  ou  des
   a�roports.Reprenez   donc   un   peu   ce  listing   (c'�tait  le 
   num�ro   3)  et  souvenez-vous   de   ce  qui se passait pour  la 
   phrase   situ�e   �  l'adresse  TXT.  Nous affichions cette phrase
   mais  auparavant  elle  �tait  modifi�e  �  l'adresse colonne et �
   l'adresse lettre.

   Dans  la cas pr�sent il suffit de faire � peu pr�s la m�me  chose.
   Pr�parons une phrase ainsi:

   TXT     DC.B    "TOUCHE F"
   NUMERO  DC.B    "  ",13,10,0

   A  chaque appui sur une touche de fonction,  nous retirons 10  (en
   d�cimal)  au  scan-code,  et nous mettons le r�sultat �  l'adresse
   NUMERO.  Ainsi   le  scan-code  de la touche F1 ($3B  donc  59  en
   d�cimal)  deviendra   49 qui est le code ASCII de la  lettre  '1'.
   Nous verrons donc s'afficher 'TOUCHE F1'.

   R�alisez  ce  programme avant de passer � la suite, cela vous fera
   un excellent exercice!!!!

   Passons maintenant au tableau, en modifiant un peu l'affichage.

   Un appui sur:                   affichera:
   F1                      A
   F2                      Z
   F2                      E
   F4                      R
   F5                      T
   F6                      Y
   F7                      U
   F8                      I
   F9                      O
   F10                     P

   Premi�re   constatation:  si les scan-code des touches se  suivent
   toujours, on  peut  dire  que  le  lien  logique entre les lettres
   affich�es est un peu l�ger...

   Prenez   le  listing num�ro 3,  et commen�ons � l'�tudier. Tout le
   d�but, jusqu'au   commentaire   'la   touche   est   valable', est
   strictement identique au listing pr�c�dent. Ensuite nous attaquons
   la  partie utilisant le tableau.  L'adresse de celui-ci est pass�e
   en  A0 (Load Effective Adress),  ensuite  on retire  $3B � D0 afin
   que  celui-ci  ait  une  valeur  de  0 �  9.  Le tableau  que nous
   utilisons  est  compos� de  Words.  Or, un  word c'est  2  bytes, 
   et  la m�moire est compos�  de  bytes.  Pour  se d�placer  dans un
   tableau en word alors que notre unit� c'est  le byte, il faut donc
   se d�placer de 2 en 2. Il ne faut donc pas que notre  'compteur', 
   qui   est  ici D0,  prenne une valeur  du  type 0,1,2,3,4  etc... 
   mais plut�t une valeur telle que  0,2,4,6,8... 


   Puisqu'�  la suite de nos op�rations nous avons D0 avec une valeur
   du  type 0,1,2,3,4... il faut maintenant le multiplier par 2. Cela
   se   fait par l'op�ration MULU qui se lit  Multiply  Unsigned.  En
   effet  c'est une multiplication non-sign�e,  c'est-�-dire  qu'elle
   ne   prend  pas  en  compte le signe  de  ce  qui  est  multipli�,
   contrairement � l'op�ration MULS (Multiply signed).

   Maintenant, observons bien cette instruction:
   MOVE.W    0(A0,D0.W),D0
   Il  s'agit d'un MOVE donc d'un d�placement. Il se fait sur un word
   puisque   nous  avons .W Ce MOVE va prendre le D0 i�me word de  A0
   pour   le mettre dans D1.  Ainsi,  si nous appuyons sur  F3,  nous
   obtenons   $3D.  Nous  retirons  $3B  et  nous  obtenons  2,  nous
   multiplions  par 2, et donc D0 vaut maintenant 4. Nous allons donc
   pointer   sur le 4�me byte de A0 et pr�lever un word �  partir  de
   cet  endroit.  Le d�placement est en effet toujours compt� avec un
   nombre  de bytes, que le tableau soit en byte, en word ou en long.
   C'est   un  peu comme si vous vous d�placiez dans une rue avec des
   petites  maisons, des  moyennes ou des grandes, le d�placement  se
   comptera toujours en m�tres.

   Mais   que signifie le 0 devant la parenth�se ?  Et bien c'est  la
   valeur  d'un d�placement fixe � ajouter.  Prenons un exemple: Nous
   avons   un  tableau dans lequel on 'tape' suivant un  chiffre  qui
   nous   est fourni par un appui sur une touche.  Seulement on  doit
   pr�lever   des choses diff�rentes si la touche est  appuy�e  alors
   que   SHIFT est enfonc�e.  Il est alors possible de  se  dire:  si
   shift   n'est pas enfonc� alors se sont les premiers  �l�ments  du
   tableau  qui seront pris en compte,  mais avec shift ce seront les
   �l�ments de la fin. On pourra alors faire:

   MOVE.W    0(A0,D0.W),D1  ou bien si shift est appuy�, 
   MOVE.W    18(A0,D0.W),D1.  Ceci revient � prendre le D0 i�me word 
   de A0, en commen�ant � compter � 18 bytes du d�but de A0.

   Il   faut cependant se m�fier de plusieurs choses  concernant  les
   tableaux. Tout  d'abord bien faire attention au type de donn�es du
   tableau   afin  de  bien modifier le  'compteur'  en  cons�quence.
   Ensuite  bien faire attention au fait que le premier �l�ment c'est
   l'�l�ment 0 et  non  pas le 1.   Nous avions d�j� vu dans les tous
   premiers   cours  de  la s�rie 1 les  probl�mes  pouvant  survenir
   lorsque  l'on compte,  en oubliant parfois le 0.  Ce probl�me  est
   d'autant plus g�nant avec les tableaux que, si au lieu de  retirer
   $3B  dans mon exemple pour avoir un chiffre de 0 � 9,  je  n'avais
   retir�   que  $3A et ainsi obtenu 1 �  10,  mon  programme  aurait
   parfaitement  fonctionn�.  Il aurait simplement affich�  n'importe
   quoi  � la suite d'un appui sur F10. Or si vous avez un tableau de
   200  �l�ments   que vous appelez avec les  touches,  les  touches+
   shifts,  +control  etc...  la v�rification touche par touche  sera
   peut  �tre  laiss�e  de  cot�... Dans  notre  exemple, nous  avons
   utilis�  des words dans notre tableau.  Il aurait tout � fait  �t�
   possible d'utiliser des bytes.

   Modifiez  un peu le programme:  supprimer la ligne avec  MULU,  et
   modifiez  les datas.  Au lieu de mettre DC.W � l'adresse  TABLEAU,
   mettez  DC.B.  Pour terminer, puisque notre tableau est maintenant
   en  bytes  et  non  plus  en  words,il  faut  modifier l'adressage
   permettant  de  piocher dedans. Au lieu de MOVE.W 0(A0,D0.W),D1 il
   faut mettre maintenant MOVE.B 0(A0,D0.W),D1

   Attention cependant car nous avions parl� de l'impossibilit� de se
   servir  des  adresses impaires.  Pourtant, dans  ce  dernier  cas,
   comme  notre tableau est en bytes, si D0 vaut 3, nous nous retrou-
   vons  avec  une adresse impaire, et pourtant �a  marche! En effet 
   cela  marche  parce  que nous pr�levons un byte. En fait, le 68000
   peut  tr�s  bien  pr�lever  un  byte  �  une  adresse  impaire, en
   revanche,  ce   qu'il ne peut pas faire c'est pr�lever une  donn�e
   plus grande (word ou long) qui commence sur une adresse impaire et
   qui  donc  chevauche  les emplacements 'normaux'. Modifions encore
   une  fois  le programme.  Remettez le tableau en word, et remettez
   l'adressage  en  word  (MOVE.W  0(A0,D0.W),D1).  L'erreur  va donc
   venir  du  fait  que  nous avons oubli� le MULU, et donc que notre
   compteur  va �tre parfois impaire alors que notre tableau et notre
   mode d'adressage demande un compteur paire.

   Assemblez  et lancez.  Appuyez sur F1: tout ce passe bien! Normal,
   D0 apr�s  retrait  de $3B,  vaut 0 qui est donc pair.  Appuyez sur
   F3: m�me chose car D0 vaut 2. Par contre, un appui sur F2 se solde
   par  3 bombes et le retour � DEVPACK.  D�buggons  donc  notre pro-
   gramme:  alternate+D, et descendons jusqu'� la ligne:
   MOVE.W 0(A0,D0.W),D1

   Pla�ons   cette  ligne en haut de la fen�tre 1 et tapons control+B
   Un  breakpoint  s'y  met. Lan�ons avec control+R, et tapons sur la
   touche  F2.  Breakpoint,  nous revoici sous MONST. En regardant la
   valeur  de A0 nous connaissons l'adresse de notre tableau, adresse
   paire  en l'occurrence.  Par contre,  si vous avez appuyez sur F2,
   vous  devez  avoir  1 comme valeur de D0, donc une valeur impaire.
   Avancez  d'un  pas  sur  MOVE.W  0(A0,D0.W),D1 � l'aide Control+Z.
   Erreur  d'adresse!  Il  ne  vous  reste  plus  qu'�  quitter  par 
   Control+C.

   Bon,  nous   avons vu comment pr�lever un word ou un byte dans  un
   tableau.  Avec  un tout petit peu d'intelligence vous  devez  �tre
   capable   de pr�lever un long mot (au lieu de faire un MULU par  2
   on  en fait un par 4).  Prenons un peu de recul et rappelons  nous
   des   cours  pr�c�dents:  nous y avons �tudi� le  principe  de  ce
   'tube',  de   cette   m�moire   que  nous  commen�ons  �  utiliser
   abondamment.  Si vous avez un peu de m�moire justement, vous devez
   vous  rappeler  d'une  remarque  faite au tout d�but, disant qu'il
   fallait  bien se m�fier de confondre contenu du tube et adresse de
   ce contenu. Il est en effet tout � fait possible d'avoir

   IMAGE         incbin         A:\MAISON.PI1"
   PTN_IMAGE     DC.L           IMAGE

   A  l'adresse  IMAGE, nous trouvons dans le tube l'image elle-m�me,
   mais  �  l'adresse  PTN_IMAGE, nous  trouvons  un long mot, qui se
   trouve  �tre l'adresse de l'image. Avec un peu d'imagination, nous
   pouvons  donc  imaginer  un tableau compos� de long mot, ces longs
   mots  �tant des adresses d'images, de textes, mais aussi (pourquoi
   pas!) de routines!!!!!!

   Voici  le  squelette  d'un programme r�alisant une telle chose: Au
   d�part, m�me  chose  que  pr�c�demment, attente d'un appui touche,
   v�rification  de  la validit� de la touche, on trafique pour avoir
   un code du type 0,1,2,3,4... puis on le mulu par 4 puisque notre 
   tableau va �tre compos� de long mot.

            LEA       TABLEAU,A0
            MOVE.L    0(A0,D0.W),A0 
            JSR       (A0)
            BRA       DEBUT                et on recommence

   Nous  faisons un JSR (jump subroutine) au lieu d'un BSR. Pourquoi?
   essayez, et  regardez  l'annexe sur les instructions pour voir les
   diff�rences entre les 2 instructions!!!

   Mais de quoi est compos� notre tableau? eh bien, par exemple

   TABLEAU DC.L TOUT_VERT
    DC.L    TOUT_BLEU
    DC.L    QUITTER
    DC.L    DRING
    DC.L    COUCOU

   etc....

   Toutes ces entr�es �tant les adresses des routines. Par exemple

   COUCOU move.l #message,-(sp)
    move.w #9,-(sp)
    trap #1
    addq.l #6,sp
    rts

   La routine TOUT_VERT met toute la palette en vert etc....

   Il  est  de  m�me  possible  de  mettre en tableau des adresses de
   phrases et de passer l'adresse "pioch�e" � une routine qui affiche
   avec gemdos(9) par exemple.

   Une derni�re chose, qui est plus proche du syst�me de liste que de
   celui de tableau, mais qui est aussi bien utile. Nous avons �tudi�
   ici   des  possibilit�s  �manant  toujours  d'une  m�me  �vidence:
   les  donn�es  qui  nous  servent  �  pointer  dans  le tableau, se
   suivent ! Malheureusement  dans  de  nombreux cas, celles-ci ne se
   suivent pas...

   Voici  donc  une  autre  m�thode: Imaginons le cas d'un �diteur de
   texte, avec  plusieurs actions possibles (effacer le texte, sauver
   le  texte, l'imprimer, charger, �craser, scroller etc...) appel�es
   par  des  combinaisons  de touches. Pour �tre � la norme Wordstart
   (c'est  la  norme  clavier utilis�e par Devack: ALT+W=imprimer par
   exemple), j'ai  d'abord  relev�  avec un tout petit programme, les
   codes  renvoy�s  par  les  combinaisons  de  touches  Ensuite j'ai
   r�alis�  une liste de ces codes, liste en word car les codes ASCII
   ne  suffisent  plus dans le cas de combinaisons de touches (il est
   possible  bien  s�r de construire la combinaison touche enfonc�e/-
   touche de control).

   TAB_CODE dc.w $1519,$1615,$1312,$2e03,$FFFF

   Ensuite  j'ai r�alis� une liste avec les adresses de mes routines.
   Comme au d�part je n'en avais aucune de faite, j'en ai r�alis� une
   'bidon', nomm�e JRTS et qui ne fait.... qu'RTS!

   TAB_ROUTINE dc.l JRTS,JRTS,JRTS,JRTS

   Ensuite  j'ai  fait une boucle pour lire TAB_CODE, en comparant, �
   chaque  fois, la  valeur  trouv�e dans le tableau avec celle de la
   touche. En m�me temps je parcours TAB_ROUTINE afin qu'au moment o�
   je  lis le 3�me �l�ment de TAB_CODE, je sois en face du 3 �me �l�-
   ment de TAB_ROUTINE.

   Voici  le module. D7 contient le word correspondant � la touche ou
   � la combinaison de touche.

    LEA TAB_CODE,A0
    LEA TAB_ROUTINE,A1
   .ICI MOVE.W (A0)+,D0
    CMP.W #$FFFF,D0
    BEQ DEBUT
    MOVE.L (A1)+,A2
    CMP.W D0,D7
    BNE .ICI
    JSR (A2)
    BRA DEBUT

   L'adresse  de  la  liste  des  codes  est  mise en A0 et celle des
   adresses   de  routines  en  A1.  On  pr�l�ve  un  word  de  code.
   C'est $FFFF? si c'est le cas, c'est donc que nous sommes en fin de
   liste  donc  on  se  sauve  puisque  la  touche  choisit n'est pas
   valable. Sinon  on  pr�l�ve l'adresse dans le tableau des adresses
   de  routines. Le  code  du  tableau est-il le m�me que celui de la
   touche  ? Non, on boucle (notez ici le point devant le label. Cela
   indique  que  le  label  est  local. L'assembleur le rapportera au
   label le plus proche portant ce nom. Il est ainsi possible d'avoir
   plusieurs  label  .ICI  dans  un  programme,  ou  tout  autre  nom
   pourvu  qu'il  soit  pr�c�d�  d'un  point. Dans  le cas de petites
   boucles  par  exemple, cela  �vite  de chercher des noms de labels
   tordus!!!).

   Puisque  le code est identique � celui de la touche, on saute vers
   la routine, et au retour, on recommence.

   Les  avantages  de  cette  m�thode sont multiples. Tout d'abord la
   petite taille de la routine de test: s'il avait fallu r�aliser des
   tests du genre:

    cmp.w #$1519,d7
    bne.s .ici1
    bsr truc
    bra d�but
   .ici1 cmp.w #$1615,d7
    bne.s .ici2
    bsr truc2
    bra d�but
   .ici2
   etc.... la  taille aurait �t� sup�rieure, surtout que dans l'exem-
   ple il n'y a que 4 codes... Imaginez avec une trentaine!!! L'autre
   avantage  concerne  la  mise  au point du programme. En effet rien
   n'emp�che  de  pr�voir plein de routines mais de simplement mettre
   l'adresse d'un RTS, et progressivement de construire ces routines.
   Rien  n'emp�chera pour autant le programme de marcher. De m�me, le
   syst�me  du flag de fin ($FFFF) permet de rajouter tr�s facilement
   des codes et donc des routines.

   Voila  pour  les listes et tableaux!! les applications sont innom-
   brables  et  permettent  souvent  en  peu de lignes des tests, des
   recherches, des  calculs,  des  conversions  ou  des  branchements
   r�alisables autrement mais au prix de difficult�s immenses!

   Voici des id�es d'applications:

   codage  de  texte  (utilisation du code ASCII pour pointer dans un
   tableau donnant la valeur � substituer)

   animation  (tableau parcouru s�quentiellement donnant les adresses
   des images � afficher)

   gestion de touches

   gestion de souris (tableau avec les coordonn�es des zones �cran)
   menu d�roulant

   etc...
   

Back to ASM_Tutorial