Pages: 1 2 [3] 4 5 ... 16   Bas de page
Imprimer
Auteur Fil de discussion: Infos hardware Nes  (Lu 34675 fois)
0 Membres et 1 Invité sur ce fil de discussion.
zeblackos Hors ligne
VIP
****
Messages: 1212


Voir le profil
Apple][ fan - Disciple Molluskien depuis 1907

« Réponse #30 : 21 Janvier 2008, 20:08:43 »

 Azn
oups ...j'avais loupé le post supplémentaire juste avant ma première réponse.
Sur un 6502, les instructions complètes peuvent avoir plusieurs tailles différentes (en fonction des modes d'adressage par exemple).
Quand on stocke le contenu d'un octet en page zéro par exemple, l'instruction est plus courte que lorsque l'on stoche un octet en RAM 'normale'...
Donc, il faut augmenter le compteur ordinal en fonction de la taille de l'instruction complète (ce qui complique un peu la vie)...
 Wink
Journalisée
Risike Hors ligne
Mega Member
***
Messages: 1387


Voir le profil
Disciple Alekmaulo-Copperien !

« Réponse #31 : 21 Janvier 2008, 20:26:17 »

2 choses alors....
1 - l'histoire de ADC....
en 6502, c'est la seule instruction qui permette de faire une addition... mais elle tient toujours compte du flag 'CARRY'.
Donc, si tu veux faire une addition sans compter la retenue, il faut 'nettoyer' préalablement la retenue.

De plus, pour les calculs, on passe TOUJOURS par le registre "accumulateur" (d'où son nom peut-être ?):

exemple :
SEC          // met la 'carry' à 1
LDA #$28  // charge A avec  40
ADC #$34  // ajoute 52
STA $0800 // stocke le résultat (0x5D) dans l'adresse $0800
Pourquoi 0x5D ?
parce que c'est 0x28 + 0x34 + 1.

autre exemple :
CLC          // met la 'carry' à 0 (donc, de belles dents blanches)
LDA #$28  // charge A avec  40
ADC #$34  // ajoute 52
STA $0800 // stocke le résultat (0x5C) dans l'adresse $0800
Pourquoi 0x5C ?
parce que c'est 0x28 + 0x34 + 0.

vala...

Sinon, il me paraît logique d'augmenter le compteur ordinal du nombre de bytes correspondants à l'instruction complète (1,2 ou plus...) sinon tu vas te retrouver à vouloir interpréter un opérande et pas une instruction.
Smiley


Citation
ADC               Add memory to accumulator with carry                ADC

  Operation:  A + M + C -> A, C                         N Z C I D V
                                                        / / / _ _ /
                                (Ref: 2.2.1)
  +----------------+-----------------------+---------+---------+----------+
  | Addressing Mode| Assembly Language Form| OP CODE |No. Bytes|No. Cycles|
  +----------------+-----------------------+---------+---------+----------+
  |  Immediate     |   ADC #Oper           |    69   |    2    |    2     |
  |  Zero Page     |   ADC Oper            |    65   |    2    |    3     |
  |  Zero Page,X   |   ADC Oper,X          |    75   |    2    |    4     |
  |  Absolute      |   ADC Oper            |    60   |    3    |    4     |
  |  Absolute,X    |   ADC Oper,X          |    70   |    3    |    4*    |
  |  Absolute,Y    |   ADC Oper,Y          |    79   |    3    |    4*    |
  |  (Indirect,X)  |   ADC (Oper,X)        |    61   |    2    |    6     |
  |  (Indirect),Y  |   ADC (Oper),Y        |    71   |    2    |    5*    |
  +----------------+-----------------------+---------+---------+----------+
  * Add 1 if page boundary is crossed.

Je suppose qu'on met z=1 si le résultat de l'opération est égal à 0 et N=1 si le résultat est négatif ? Mais dans V on met quoi ?

Et une dernière question : pour les registres, est-ce que ça change quelques chose d'utliser des signed ou des unsigned types en C ?
Journalisée

Le travail y'en a pas beaucoup, faut le laisser à ceux qu'aiment ça !

(Coluche)
zeblackos Hors ligne
VIP
****
Messages: 1212


Voir le profil
Apple][ fan - Disciple Molluskien depuis 1907

« Réponse #32 : 21 Janvier 2008, 21:30:14 »

 Azn
Là tu parles de la manière dont le résultat de l'opération affecte le registre d'état.
Alors, yes, ADC affecte
n
v
z
c

C'est une histoire de représentation des nombres. Avec un 6502, les bytes servent le plus souvent à coder 256 valeurs non signées - de 0 à 255. On peut considérer aussi que les nombres sont signés. C'est à ce moment que V intervient. Pour signaler un débordement.
Le détail est un peu chaud à poster directos, mais ce lien devrait te plaire :
http://www.6502.org/tutorials/vflag.html

Smiley
« Dernière édition: 21 Janvier 2008, 21:37:29 par zeblackos » Journalisée
Risike Hors ligne
Mega Member
***
Messages: 1387


Voir le profil
Disciple Alekmaulo-Copperien !

« Réponse #33 : 21 Janvier 2008, 21:39:23 »

admettons que l'on fasse 0xFF + 0x02. On a donc le résultat qui fait 0x101 (soit 257 en décimal). On a donc le fameux V qui sera = 1 on est d'accord. Mais le résultat de l'opération sera quoi ? On fait ça cycliquement à savoir 0x101 - 0xFF = 0x2 ? ou 0x101 - 0xFF - 1 = 0x1 ? Ou autre ?

Ensuite j'ai remarqué des trucs qui allaient pas dans les docs : regarde.
Citation
BMI                    BMI Branch on result minus 
Citation
BMI - Branch if Minus

If the negative flag is set then add the relative displacement to the program counter to cause a branch to a new location.

Dans 2 docs, deux instructions sont présentés différements. D'un coté on met le PC a une certaine valeur et de l'autre on lui ajoute une certaine valeur ! ça pue !
Journalisée

Le travail y'en a pas beaucoup, faut le laisser à ceux qu'aiment ça !

(Coluche)
zeblackos Hors ligne
VIP
****
Messages: 1212


Voir le profil
Apple][ fan - Disciple Molluskien depuis 1907

« Réponse #34 : 22 Janvier 2008, 09:15:42 »

 Azn
"Comment qu'c'est grôs ?"
 Grin
Pour la première partie de ta question, je te laisse mater le lien que je t'ai filé... c'est plutôt complet comme explication...

Pour le coup du BMI.... beh ouaip, c'est juste ce qui est dit.
BMI est un branchement conditionnel. La condition, c'est l'état du bit "n" (si n= 1 on saute).
Pas compliqué... sauf que c'est une instruction sur 2 octets... et le branchement est RELATIF !...
On n'indique pas l'adresse ABSOLUE, mais un déplacement par rapport à la prochaine instruction...
C'est rare en 6502, mais dans le cas d'instructions de branchement conditionnel, on a ce cas de figure : l'adresse de destination n'est pas représentée 'en dur' (sur 2 octets (comme $0805 par exemple)), mais sur UN octet.
On ne peut donc pas sauter très loin... car cet octet est codé en représentation appelée 'complément à 2' (je crois... pfffui...c'est loin mes 14 ans !...). C'est un octet signé.
-128 à -1 = les valeurs de $80 de $FF
0 à 127 = les valeurs de $00 à $7F.
On a une amplitude de saut "relatif" de + ou moins 127 ou 128 octets... c'est peu.

Il faut bien additionner (comme le dit ta doc) ces valeurs au compteur ordinal pour trouver l'adresse de branchement.
ex :

0300 - A2 FF     : LDX $FF
0302 - A9 A0     : LDA $A0
0304 - 9D 00 06 : STA $0600,x
0307 - CA         : DEX
0308 - E0 50     : CPX #$50
030A - 30 F8     : BMI $0304      ; BMI à (ICI+2) + valeur donnée = (0x30a+2) + (- 8 (F8 signé = -8))
030C - 60         : RTS

As-tu compris le truc ?
:
BMI à (ICI+2) + valeur donnée = (0x30a+2) + (1 (01 signé = 1))
30A - 30 01   : BMI $030D

Pourquoi le (+2) ? beh parce que normalement, le compteur ordinal pointe déjà l'instruction suivante quand il exécute celle-là.

Si des experts passent dans le coin, vous pouvez corriger, mais je crois que je ne délire pas trop sur ce coup là...
:/
++
blk.
Journalisée
Risike Hors ligne
Mega Member
***
Messages: 1387


Voir le profil
Disciple Alekmaulo-Copperien !

« Réponse #35 : 22 Janvier 2008, 10:26:33 »

ça guets ma couille !

Oua je suis plus rien !
Quand dans le tableau d'instructions on a bytes = 1 comme pour CLC par exemple, on doit incrémenter le PC de combien après avoir traité l'instruction ? de 1 ou de 1+1 ?
Journalisée

Le travail y'en a pas beaucoup, faut le laisser à ceux qu'aiment ça !

(Coluche)
zeblackos Hors ligne
VIP
****
Messages: 1212


Voir le profil
Apple][ fan - Disciple Molluskien depuis 1907

« Réponse #36 : 22 Janvier 2008, 10:37:39 »

lol
 Azn
Beh +1... il faut que ton compteur ordinal pointe en permanence vers l'instruction qui devra être exécutée ensuite.
Après, tu gères ça comme tu veux... pour le BMI, je t'ai juste dit ce que fait le processeur, et j'ai souligné le fait que c'était un adressage relatif.... contrairement aux sauts inconditionnels (JPM - JSR..) l'adresse de saut est codée sur 1 octet signé (au lieu de 2 octets non signés indiquant l'adresse absolue à atteindre).
Avec un BMI, tu peux donc sauter en avant ou EN ARRIERE à une distance maxi de + ou - 127 octets...
 Smiley
Journalisée
Risike Hors ligne
Mega Member
***
Messages: 1387


Voir le profil
Disciple Alekmaulo-Copperien !

« Réponse #37 : 22 Janvier 2008, 10:40:48 »

mais tu écris BMI $030D...
030D c'est pas un octet...
« Dernière édition: 22 Janvier 2008, 12:14:12 par Risike » Journalisée

Le travail y'en a pas beaucoup, faut le laisser à ceux qu'aiment ça !

(Coluche)
Risike Hors ligne
Mega Member
***
Messages: 1387


Voir le profil
Disciple Alekmaulo-Copperien !

« Réponse #38 : 22 Janvier 2008, 10:42:48 »

Ma fonction BMi :

Code
(c):
void op_30_BMI(){ //TOCORRECT
    printf("BMI %x", opCode2);
    if(get_sign()){
           cpu.reg_PC += opCode2;
           bytes = 0;
   }else bytes = 2;
}

où bytes est le nombre de bytes à ajouter au PC et opCode2 est en fait le byte après l'opcode.

A mon avis je dois caster mon opcode2 en signed char et ajouter encore 2 a mon PC dans le cas ou la condistion est vraie. QUelqu'un peut confirmer ou pas ?

ce qui donnerait :

Code
(c):
void op_30_BMI(){ //TOCORRECT
    printf("BMI %x", opCode2);
    if(get_sign())
           cpu.reg_PC += (signed char)opCode2;
    bytes = 2;
}

Code
(c):
#define get_sign()           (cpu.reg_P & 0x80)

ça m'a l'air bon ça non ?
« Dernière édition: 22 Janvier 2008, 11:09:32 par Risike » Journalisée

Le travail y'en a pas beaucoup, faut le laisser à ceux qu'aiment ça !

(Coluche)
zeblackos Hors ligne
VIP
****
Messages: 1212


Voir le profil
Apple][ fan - Disciple Molluskien depuis 1907

« Réponse #39 : 22 Janvier 2008, 12:21:19 »

mais tu écris BMI $030D...
030D c'est pas un octet...
Argh ... ouaip, sorry, j'imaginais que le programme bidon donné pour l'exemple continuait en séquence
030D : 4C 00 C6 JMP $C600 (par exemple, ou n'importe quoi d'autre...)

Maintenant, ta fonction BMI... comme je suis nul en C, et que je ne sais pas grand chose sur les "cast"... eh beh ... ça me parle moyen...
Mais dans tous les cas, si tu commences par ajouter 2 au PC, c'est good... ensuite, soit tu remodifies le PC, soit tu ne fais rien (il pointe déjà vers l'instruction suivante...)

------------------
PC<--PC+2 // comme ça c'est déjà fait...
si(get_sign) PC<-- PC + valeur signée de l'opcode 2  // si on saute, ok, on modifie le PC
sinon........... rien de plus...

ps : ton opCode2, je crois bien que c'est en fait un opérande...

 Azn
voilà... je ne peux pas grand chose de plus... et j'espère n'avoir pas dit trop de trucs idiots... pour une fois.
« Dernière édition: 22 Janvier 2008, 12:24:19 par zeblackos » Journalisée
Alekmaul Hors ligne
Papi codeur et
Administrateur
*****
Messages: 1403


Voir le profil WWW
Out of memory error ...

« Réponse #40 : 22 Janvier 2008, 13:07:20 »

A mon avis, BMI devrait être codé comme cela :

Code
(c):
void op_30_BMI(){ //TOCORRECT    
printf("BMI %x", opCode2);    
           if ( opCode2> 0x7f ) {
             cpu.reg_PC  = (cpu.reg_PC - 255 + opCode2) & 0xffff;
           }
           else {
             cpu.reg_PC = (cpu.reg_PC + 1 + opCode2) & 0xffff;
           }
}
 

sans oublier de tester le flag negate avant de le faire et 'ajouter le bon nombre de cycles d'horloge ensuite (3 cycles)
Journalisée

Mon site PortableDev : l'émulation sur GBA et sur DS
Risike Hors ligne
Mega Member
***
Messages: 1387


Voir le profil
Disciple Alekmaulo-Copperien !

« Réponse #41 : 22 Janvier 2008, 13:27:49 »

Alekmaul je suis d'accord mais je ne pige pas pourquoi tu fais un & 0xffff...
Sinon le coup des cycles d'horloge j'ai pas trop compris. ça sert à quoi ? De toute façon on rafraichi notre écran toutes les x opérations traitées.
Ton tuto Chip8 ne parle pas de cette notion je crois.

EDIT : non en fait je vois pas pourquoi  cpu.reg_PC = (cpu.reg_PC + 1 + opCode2) & 0xffff;

Ti oubli aussi la condition "si le signe est à 1" et tu oublies mon byte=2. Qui me sert a incrémenter le PC en plus du saut.
« Dernière édition: 22 Janvier 2008, 13:34:18 par Risike » Journalisée

Le travail y'en a pas beaucoup, faut le laisser à ceux qu'aiment ça !

(Coluche)
Alekmaul Hors ligne
Papi codeur et
Administrateur
*****
Messages: 1403


Voir le profil WWW
Out of memory error ...

« Réponse #42 : 22 Janvier 2008, 13:34:10 »

je fais & 0xffff car certains programmes prennent le malin plaisir à faire des bmi +0x7e en étant proche de 0xffff, ce qui fait que tu dépasserais la limite possible pour du 8 bits ...
Journalisée

Mon site PortableDev : l'émulation sur GBA et sur DS
Risike Hors ligne
Mega Member
***
Messages: 1387


Voir le profil
Disciple Alekmaulo-Copperien !

« Réponse #43 : 22 Janvier 2008, 13:38:57 »

Bon si tu le dis !
Et pour le reste ? Tu as du répondre avant que j'édite mon post.
Journalisée

Le travail y'en a pas beaucoup, faut le laisser à ceux qu'aiment ça !

(Coluche)
Alekmaul Hors ligne
Papi codeur et
Administrateur
*****
Messages: 1403


Voir le profil WWW
Out of memory error ...

« Réponse #44 : 22 Janvier 2008, 14:20:07 »

Oui, pardon +1 et 255 car je n'ai pas incrémenté, dans mon émulateur, après la récupération del'opcode, je le fais directement là.
Si le signe est à un, je l'avais dis dans mon message "sans oublier de tester le flag negate avant de le faire " car j'avais repris la même présentation que toi.
Si tu veux "ma vrai version", la voici :
Code
(c):
       case 0x30 :                             /* BMI */
         if ( nflag != 0 ) {
           bytebuffer= oric_mem[pc];
           if ( bytebuffer > 0x7f ) {
             pc        = (pc - 255 + bytebuffer) & 0xffff;
           }
           else {
             pc        = (pc + 1 + bytebuffer) & 0xffff;
           }
           cycle       = cycle + 3;
         }
         else {
           pc          = (pc + 1) & 0xffff;
           cycle       = cycle + 2;
         }
 
Journalisée

Mon site PortableDev : l'émulation sur GBA et sur DS
Pages: 1 2 [3] 4 5 ... 16   Haut de page
Imprimer

Aller à: