2013-10-26 10 views
5

Sto seguendo questo corso e sto davvero cercando di capire il concetto della direttiva .align.Informazioni sull'assemblaggio MIPS .ALIGN e indirizzamento di memoria

Ecco un esempio, che non riuscivo a capire:

enter image description here

So che all'interno del segmento di dati, ci sono gli indirizzi, a partire da 0x10010000,0x10010020, ecc.

E so che all'interno di ciascun indirizzo ci sono 8 campi di memoria, ognuno con 32 bit.

Ora, ciò che non capisco è, come e perché var2 all'interno dell'indirizzo 0x10010010? str1 si trova nell'indirizzo 0x10010003 perché abbiamo riservato 3 bit per lo var1.

L'ultima cosa è, che cosa esattamente la direttiva .align' doing? when I tested it in Mars4, it only shifted the data into the next memory field when I used align 3` e fino, ma io in realtà non capisco.

Mi dispiace se questo è molto confuso ragazzi, sono un po 'disperato qui.

risposta

9

L'allineamento è importante per un processore MIPS, a lui piace solo leggere i valori multi-byte dalla memoria in un indirizzo che è un multiplo della dimensione dei dati.

Il campo .ASCIIZ può essere posizionato ovunque poiché una stringa viene letta un byte alla volta. Quindi metterlo a 0x10010003 va bene.

Il campo .WORD deve essere allineato a un multiplo di 4. Quindi non può essere inserito in 0x1001000E, la successiva posizione disponibile dopo la stringa. L'assemblatore sposta intenzionalmente il valore e lascia due byte non utilizzati. Al prossimo indirizzo che è un multiplo di 4, 0x10010010.

La direttiva .ALIGN è un modo per ignorare le regole di allineamento predefinite. Il prossimo campo dopo la direttiva sarà allineato a un multiplo di 2 alla potenza di n dove n è il valore .ALIGN. Nel tuo caso è pow (2, 3) = 8 byte.

Quale è ciò che viene visualizzato, senza la direttiva .ALIGN il campo .HALF viene memorizzato in 0x10010014. Non un multiplo di 8 quindi viene spostato su 0x10010018.

L'esempio è altrimenti artificiale, alcuna ragione evidente per usare la direttiva .align qui dal .HALF richiede solo di allineamento ad un multiplo di 2, quindi riporlo in 0x10010014 sarebbe stato soddisfacente.

+1

Stavo scrivendo la mia risposta al telefono mentre non c'era nessuno ... il tuo avrebbe ovviato alla necessità di un altro. – gnometorule

+0

Grazie a tutti per le vostre risposte! Domanda: in che modo 0x10010010 è un multiplo di 4? – Sobiaholic

+0

0x10010010 = 2^28 + 2^16 + 2^4, che è una moltiplicazione di 4. Se il calcolo non ha senso per te, ti preghiamo di leggere di nuovo sui numeri esadecimali. – gnometorule

3

Determinate direttive di assemblaggio implicano che i dati siano memorizzati allineati, il che significa che inizia da un indirizzo che è una potenza di due. Ricordiamo prima di un paio di convenzioni in MIPS:

(1) una "parola" è di 4 byte (a volte si vede definito come 2 byte),

(2) un halfword (.half) sono 2 byte e

(3). null null termina la stringa (come in C).

Utilizzando questo, è già stato spiegato come vengono memorizzati var1 e str1. Perché il buffer di 2 byte vuoti prima di var2? Perché è dichiarato un .word, e (per (1) sopra) verrà memorizzato a partire da una posizione di memoria che è un multiplo di 4. Se lo avessi dichiarato a .half, non avresti avuto 2 byte vuoti tra str1 e var2.

var2 è dichiarato un .half - è un indirizzo a 16 bit (2 byte) che si adatta a uno. Tuttavia, prima di dichiararlo, l'allineamento è cambiato in 3. Ora, controlla la prima frase: questa è la potenza si alza 2 a; quindi allineamo effettivamente a 8. Ciò significa che fino a quando non verranno sostituite, le variabili verranno posizionate come dichiarate, ma in aggiunta la loro posizione di memoria iniziale deve essere un multiplo di 8. Quindi, l'assemblatore inserisce 4 byte vuoti per memorizzare var3 in un multiplo di 8.