[successivo] [precedente] [inizio] [fine] [indice generale] [indice ridotto] [indice analitico] [home] [volume] [parte]


Capitolo 561.   Rappresentazione dei dati in memoria attraverso un esempio

Viene proposto un esempio in cui si utilizzano i tipi principali di variabili inizializzate in memoria, con due listati equivalenti, il primo adatto a GNU AS mentre il secondo è per NASM. In particolare, nel secondo listato, non potendo dichiarare variabili da 64 bit, sono state usate coppie di variabili a 32 bit, inizializzate tenendo conto dell'inversione little endian.

#
.section .data
numero8:    .byte   0b00010010                         # 0x12       # 18
numero16:   .short  0b0001001000110100                 # 0x1234     # 4660
numero32:   .int    0b00010010001101000101011001111000 # 0x12345678 # 305419896
numero64:   .quad   0x123456789ABCDEF0
carattere:  .byte   'A'
stringa:    .ascii  "testo"
caratteri:  .byte   'T', 'E', 'S', 'T', 'O'
            .skip 3, 0xFF
            .rept 4
            .byte   'Z'
            .endr
numeri8:    .byte   0x12, 0x34, 0x56, 0x78, 0x9A
numeri16:   .short  0xBCDE, 0xF012, 0x3456, 0x789A
numeri32:   .int    0xBCDEF012, 0x3456789A, 0xBCDEF012
numeri64:   .quad   0x3456789ABCDEF012, 0x3456789ABCDEF012
fine:       .byte   'F', 'I', 'N', 'E'
#
.section .text
.globl _start
#
_start:
    mov   $0, %ebx
    mov   $1, %eax
    int   $0x80
;
section .data
numero8:    db   00010010b                         ; 0x12        = 18
numero16:   dw   0001001000110100b                 ; 0x1234      = 4660
numero32:   dd   00010010001101000101011001111000b ; 0x12345678  = 305419896
numero64:   dd   0x9ABCDEF0, 0x12345678            ; 0x123456789ABCDEF0
carattere:  db   'A'
stringa:    db   "testo"
caratteri:  db   'T', 'E', 'S', 'T', 'O'
times 3     db   0xFF
times 4     db   'Z'
;
;
numeri8:    db   0x12, 0x34, 0x56, 0x78, 0x9A
numeri16:   dw   0xBCDE, 0xF012, 0x3456, 0x789A
numeri32:   dd   0xBCDEF012, 0x3456789A, 0xBCDEF012
numeri64:   dd   0xBCDEF012, 0x3456789A, 0xBCDEF012, 0x3456789A
fine:       db   'F', 'I', 'N', 'E'
;
section .text
global _start
;
_start:
    mov   ebx, 0
    mov   eax, 1
    int   0x80

Il programma in questione non fa alcunché e serve solo per verificare con GDB come sono rappresentati i dati in memoria e come questi si possono leggere. Complessivamente, le variabili occupano 78 byte, secondo lo schema che si vede nella figura successiva, dove vengono riprodotte anche le inversioni dovute alla rappresentazione little endian:

memoria

Per leggere la memoria già inizializzata con GDB non è necessario avviare il programma, in quanto, appena aperto, questa è subito accessibile:

gdb nome_programma[Invio]

(gdb) print /x (char[78])numero8[Invio]

$1 = {0x12, 0x34, 0x12, 0x78, 0x56, 0x34, 0x12, 0xf0, 0xde, 0xbc, 0x9a, 0x78,
  0x56, 0x34, 0x12, 0x41, 0x74, 0x65, 0x73, 0x74, 0x6f, 0x54, 0x45, 0x53,
  0x54, 0x4f, 0xff, 0xff, 0xff, 0x5a, 0x5a, 0x5a, 0x5a, 0x12, 0x34, 0x56,
  0x78, 0x9a, 0xde, 0xbc, 0x12, 0xf0, 0x56, 0x34, 0x9a, 0x78, 0x12, 0xf0,
  0xde, 0xbc, 0x9a, 0x78, 0x56, 0x34, 0x12, 0xf0, 0xde, 0xbc, 0x12, 0xf0,
  0xde, 0xbc, 0x9a, 0x78, 0x56, 0x34, 0x12, 0xf0, 0xde, 0xbc, 0x9a, 0x78,
  0x56, 0x34, 0x46, 0x49, 0x4e, 0x45}

Quello che viene richiesto con il comando appena mostrato è di mostrare la memoria a partire dall'indirizzo corrispondente all'etichetta numero8 (pertanto dall'inizio), in forma di array di byte, composto da 78 elementi. Si può verificare la corrispondenza tra quanto ottenuto e la figura mostrata in precedenza.

Con i comandi successivi si ispezionano le variabili, singolarmente. È sempre necessario dichiarare la dimensione a cui si è interessati, quando questa è diversa da quella predefinita (32 bit). Non è possibile ispezionare le variabili da 64 bit in modo complessivo, pertanto occorre arrangiarsi, come se fossero array di due numeri a 32 bit. Nei comandi mostrati appare spesso l'opzione /f, con la quale si dichiara il tipo di rappresentazione che si vuole ottenere.

(gdb) print /x (char)numero8[Invio]

$2 = 0x12

(gdb) print (char)numero8[Invio]

$3 = 18 '\022'

(gdb) print /x (short)numero16[Invio]

$4 = 0x1234

(gdb) print (short)numero16[Invio]

$5 = 4660

(gdb) print /x (int)numero32[Invio]

$6 = 0x12345678

(gdb) print (int)numero32[Invio]

$7 = 305419896

(gdb) print /x (int[2])numero64[Invio]

$8 = {0x9abcdef0, 0x12345678}

(gdb) print (char)carattere[Invio]

$9 = 65 'A'

(gdb) print (char[11])carattere[Invio]

$10 = "AtestoTESTO"

(gdb) print (char[5])stringa[Invio]

$11 = "testo"

(gdb) print (char[5])caratteri[Invio]

$12 = "TESTO"

(gdb) print /x (char[12])caratteri[Invio]

$13 = {0x54, 0x45, 0x53, 0x54, 0x4f, 0xff, 0xff, 0xff, 0x5a, 0x5a, 0x5a, 0x5a}

(gdb) print /x (char[5])numeri8[Invio]

$14 = {0x12, 0x34, 0x56, 0x78, 0x9a}

(gdb) print /d (char[5])numeri8[Invio]

$15 = {18, 52, 86, 120, -102}

(gdb) print /x (short[4])numeri16[Invio]

$16 = {0xbcde, 0xf012, 0x3456, 0x789a}

(gdb) print /d (short[4])numeri16[Invio]

$17 = {-17186, -4078, 13398, 30874}

(gdb) print /d (unsigned short[4])numeri16[Invio]

$18 = {48350, 61458, 13398, 30874}

(gdb) print /x (int[3])numeri32[Invio]

$19 = {0xbcdef012, 0x3456789a, 0xbcdef012}

(gdb) print /d (int[3])numeri32[Invio]

$20 = {-1126240238, 878082202, -1126240238}

(gdb) print /d (unsigned int[3])numeri32[Invio]

$21 = {3168727058, 878082202, 3168727058}

(gdb) print /x (int[4])numeri64[Invio]

$22 = {0xbcdef012, 0x3456789a, 0xbcdef012, 0x3456789a}

(gdb) print (char[4])fine[Invio]

$23 = "FINE"

Appunti di informatica libera 2008 --- Copyright © 2000-2008 Daniele Giacomini -- <appunti2 (ad) gmail·com>


Dovrebbe essere possibile fare riferimento a questa pagina anche con il nome rappresentazione_dei_dati_in_memoria_attraverso_un_esempio.htm

[successivo] [precedente] [inizio] [fine] [indice generale] [indice ridotto] [indice analitico] [home]

Valid ISO-HTML!

CSS validator!

Gjlg Metamotore e Web Directory