GNU/Linux xterm bash 132 views

📌 Demostración: Imprimir un registro en hexadecimal en ARM64 Assembly

💻 Lenguajes de Interfaz en TECNM Campus ITT
👨‍💻 Autor: Alejandro Suarez Sandoval
📅 Fecha: 2025/04/02

🎯 Descripción

Este programa imprime un registro en hexadecimal y lo muestra en la terminal.
La implementación se realiza en:

Assembly ARM64 para RaspbianOS en Raspberry Pi

🔧 Compilación en Raspberry Pi (ARM64)

as registro_hexadecimal.s -o registro_hexadecimal.o  
ld registro_hexadecimal.o -o registro_hexadecimal

▶️ Ejecución

./registro_hexadecimal

👀 Código fuente

🔗 Código fuente en Gist: Programa 4 Imprimir registro en hexadecimal Código Assembly ARM64 para RaspbianOS

/*
 ______  ____               ____  __ __      
/\  _  \/\  _`\   /'\_/`\  /'___\/\ \\ \     
\ \ \L\ \ \ \L\ \/\      \/\ \__/\ \ \\ \    
 \ \  __ \ \ ,  /\ \ \__\ \ \  _``\ \ \\ \_  
  \ \ \/\ \ \ \\ \\ \ \_/\ \ \ \L\ \ \__ ,__\
   \ \_\ \_\ \_\ \_\ \_\\ \_\ \____/\/_/\_\_/
    \/_/\/_/\/_/\/ /\/_/ \/_/\/___/    \/_/  
                                             
♡ ∩_∩ 
(„• ֊ •„)♡
| ̄U U ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄| 
| • Lenguajes de Interfaz en TECNM Campus ITT                      |   
| • Autor: Alejandro Suarez Sandoval                               | 
| • Fecha: 2025/04/02                                              | 
| • Descripción: Programa para imprimir un registro                |
|   en hexadecimal en C y Assembly ARM64 para RaspbianOS.          | 
| • Demostración:                                                  |
|   https://asciinema.org/a/711587                                 |
| • Compilación (Raspberry Pi ARM64):                              |  
|     as registro_hexadecimal.s -o registro_hexadecimal.o          |  
|     ld registro_hexadecimal.o -o registro_hexadecimal            |  
| • Ejecución: ./registro_hexadecimal                              |  
 ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄                                        

⠂⠄⠄⠂⠁⠁⠂⠄⠄⠂⠁⠁⠂⠄⠄⠂ ⠂⠄⠄⠂☆
═════════•°• Demostración Código en lenguaje C •°•═════════

#include <stdio.h>

int main() {
    // Definir el valor del registro en 4 partes
    unsigned short part1 = 0x1234; // Los primeros 16 bits
    unsigned short part2 = 0xFEDC; // Los siguientes 16 bits
    unsigned short part3 = 0x4F5D; // Los siguientes 16 bits
    unsigned short part4 = 0x6E3A; // Los últimos 16 bits

    // Combinamos las partes en un valor de 64 bits
    unsigned long long reg_value = ((unsigned long long)part1 << 48) |
                                   ((unsigned long long)part2 << 32) |
                                   ((unsigned long long)part3 << 16) |
    printf("0x%llX\n", reg_value);
    // Imprimimos el valor combinado en formato hexadecimal
}
    return 0;
}

════════════════════•°• ☆ •°•══════════════════════════════
/*

/* ⠂⠄⠄⠂⠁⠁⠂⠄⠄⠂⠁⠁⠂⠄⠄⠂ ⠂⠄⠄⠂☆
═════════════•°• Código en ARM64 Assembly •°•═════════════ */

// X0-X2 - parámetros para los servicios de funciones de Linux
// X1 - también es la dirección del byte que estamos escribiendo
// X4 - registro que queremos imprimir
// W5 - índice del bucle
// W6 - carácter actual
// X8 - número de la función de Linux

.global _start  // Dirección de inicio del programa

_start:
    // Inicialización del valor en el registro X4, que contiene el número que se imprimirá
    MOV    X4, #0x1234
    MOVK   X4, #0xABCD, LSL #16
    MOVK   X4, #0x5678, LSL #32
    MOVK   X4, #0x9DEF, LSL #48
    // Cargar la dirección de la cadena de caracteres donde se almacenará el número hexadecimal
    LDR    X1, =hexstr // inicio de la cadena
    ADD    X1, X1, #17  // comenzar desde el dígito menos significativo

    // El bucle es FOR W5 = 16 A 1 PASO -1
    MOV    W5, #16  // 16 dígitos a imprimir
loop:
    AND    W6, W4, #0xf   // enmascarar el dígito menos significativo
    CMP    W6, #10        // verificar si es 0-9 o A-F
    B.GE   letter          // saltar si el dígito es mayor o igual que 10

    // Si es un número, convertirlo a un dígito ASCII
    ADD    W6, W6, #'0'
    B      cont            // saltar al final

letter:  // manejar los dígitos A a F
    ADD    W6, W6, #('A' - 10)

cont:    // fin de la condición
    STRB   W6, [X1]       // almacenar el dígito ASCII
    SUB    X1, X1, #1     // decrementar la dirección para el siguiente dígito
    LSR    X4, X4, #4     // desplazar a la derecha el número para procesar el siguiente dígito

    // siguiente iteración del bucle W5
    SUBS   W5, W5, #1     // restar 1 de W5
    B.NE   loop           // si no hemos terminado, continuar con el bucle

    // Configuración de los parámetros para imprimir el número hexadecimal
    MOV    X0, #1         // 1 = StdOut (salida estándar)
    LDR    X1, =hexstr    // dirección de la cadena a imprimir
    MOV    X2, #19        // longitud de la cadena
    MOV    X8, #64        // código de la llamada al sistema 'write' de Linux
    SVC    0              // llamada al sistema para imprimir la cadena

    // Configuración de los parámetros para salir del programa
    MOV    X0, #0         // código de retorno 0
    MOV    X8, #93        // código de servicio 93 para terminar el programa
    SVC    0              // llamada al sistema para terminar el programa

.data
hexstr:      .ascii "0x123456789ABCDEFG\n" // cadena para imprimir