2012-10-27 11 views
6

Sto guardando un Javascript emulator di un NES per cercare di capire come funziona.Perché l'indirizzo operativo è incrementato di due?

In this line:

addr = this.load(opaddr+2); 

Il codice operativo è incrementato di due. Tuttavia, il documentation (vedi Appendice E) Sto leggendo dice:

Zero pagina riguardante gli usi un singolo operando che funge da puntatore a un indirizzo a pagina zero ($ 0000- $ 00FF) in cui i dati essere gestito su può essere trovato. Usando l'indirizzamento della pagina zero, solo un byte è necessario per l'operando, quindi l'istruzione è più breve e, pertanto, più veloce da eseguire rispetto alle modalità di indirizzamento che accettano due operandi. Un esempio di istruzione a pagina zero è AND $ 12.

Quindi se l'argomento dell'operando è solo un byte, non dovrebbe apparire immediatamente dopo di esso ed essere + 1 invece di + 2? Perché +2?

Questo è come penso che funzioni, il che potrebbe essere errato. Supponiamo che la nostra memoria si presenta come:

------------------------- 
| 0 | 1 | 2 | 3 | 4 | 5 | <- index 
------------------------- 
| a | b | c | d | e | f | <- memory 
------------------------- 
^ 
    \ 
    PC 

e il nostro PC è 0, indicando a. Per questo ciclo, diciamo che il codice operativo:

var pc= 0; //for example's sake 
var opcode= memory[pc]; //a 

Quindi non dovrebbe essere il primo operando slot successivo, vale a dire b?

var first_operand = memory[pc + 1]; //b 
+1

Quanto è ampio l'opcode? –

+0

@PlatinumAzure il PC è a 16 bit, penso che l'opcode sia 8 bit –

+0

Penso che @PlatinumAzure sia sulla strada giusta. L'aggiunta è saltare l'opcode per ottenere l'operando a byte singolo. –

risposta

2

La tua analisi appare corretta a prima vista, ma dal momento che l'emulatore funziona ci deve essere qualcos'altro.

Il codice in questione è il seguente:

var opinf = this.opdata[this.nes.mmap.load(this.REG_PC+1)]; 
    var cycleCount = (opinf>>24); 
    var cycleAdd = 0; 

    // Find address mode: 
    var addrMode = (opinf >> 8) & 0xFF; 

    // Increment PC by number of op bytes: 
    var opaddr = this.REG_PC; 
    this.REG_PC += ((opinf >> 16) & 0xFF); 

    var addr = 0; 
    switch(addrMode){ 
     case 0:{ 
      // Zero Page mode. Use the address given after the opcode, 
      // but without high byte. 
      addr = this.load(opaddr+2); 
      break; 

noti come sulla prima riga mostrata, l'accesso alla memoria per ottenere le informazioni istruzione è all'indirizzo REG_PC+1. Quindi il PC punta effettivamente al byte precedente l'opcode in esecuzione e quindi gli operandi iniziano da quell'indirizzo + 2. L'opcode stesso è codificato come gli 8 byte inferiori di opinf e utilizzato nell'esecuzione passa una pagina o giù di segmento di codice mostrato.

+0

Grazie per la convalida, anche se questa era l'unica risposta ;-) Solo per informazioni la situazione che hai evidenziato è insolita. Il PC di solito punta all'istruzione corrente o all'istruzione successiva. Questa è la prima volta che ho visto un punto dietro l'istruzione corrente. – HBP

+0

Se non ti dispiace, ho una domanda di follow-up. Non dovresti leggere l'opcode direttamente su 'this.REG_PC', non su +1? Grazie –

+0

Non ho tracciato tutta la logica ma è essenzialmente solo una questione di coerenza. Avere un valore di PC inferiore a quello attuale è inusuale e abbastanza confuso, ma se il valore del PC è ** sempre ** uno in meno rispetto all'istruzione in esecuzione e si conta per questo in ** tutti ** i casi in cui il PC è riferito a tutti dovrebbe essere bene. – HBP

Problemi correlati