Programación General > ASM (Ensamblador)

 Problemas Con El Salto A Modo Protegido

(1/2) > >>

germancho7186:
Yo tengo el mismo problema.

Este el código de mi kernel:


--- Código: Text --- [BITS 16]    jmp Start GDT:GDT_NULL:    dq 0GDT_CODE:    dw 0FFFFh    dw 0    db 0    db 10011010b    db 11001111b    db 0GDT_DATA:    dw 0FFFFh    dw 0    db 0    db 10010010b    db 11001111b    db 0GDT_END:GDT_DESC:    db GDT_END - GDT    dw GDT    Start:    cli    mov ax, ax    mov ds, ax        lgdt [GDT_DESC]        mov eax, cr0    or eax, 1    mov cr0, eax        jmp 08h:ProtectedMode    [BITS 32]ProtectedMode:     jmp $      
Cuando lo ejecuto en VirtualPC, me aparece un mensaje que dice: "Error irrecuperable del procesador". Alguien me podría explicar porque no funciona.

posman:

--- Cita de: "germancho7186" ---Yo tengo el mismo problema.

Este el código de mi kernel:


--- Código: Text --- ...GDT_DESC:    db GDT_END - GDT    dw GDT    Start:    cli    mov ax, ax    mov ds, ax...  
Cuando lo ejecuto en VirtualPC, me aparece un mensaje que dice: "Error irrecuperable del procesador". Alguien me podría explicar porque no funciona.
--- Fin de la cita ---

Veo 2 errores en las declaraciones en GDT_DESC

1. En el registro de la GDT (GDTR) se guardan 48 bits: 16 bits para el limite y 32 bits para la direccion base. Tu estas declarando unicamente 24 bits (8 bits para el limite y 16 bits para la direccion base)
2. En el limite, a la resta tambien debes agregar "- 1"

--- Código: Text ---GDT_DESC:    dw GDT_END - GDT - 1    dd GDT  
No entiendo para que utilizas la instruccion mov ax, ax que esta despues de CLI. Tal vez lo que querias utilizar era xor ax, ax para hacer AX = 0. Pero aun asi estaria incorrecto si quisieras asignar ese valor a DS. El segmento de datos, segun tu GDT, deberia tener el valor 0x10 (tercer descriptor, el primer descriptor es el nulo)

El primer descriptor es el nulo, nunca se utiliza.
El segundo descriptor es para el segmento de codigo y el valor que se utiliza para hacer referencia a el es 0x08
El tercer descriptor es el segmento de datos y el valor para utilizar este segmento es 0x10

germancho7186:
Aun no logro hacerlo funcionar, ¿que es lo que estoy haciendo mal?


--- Código: Text ---[BITS 16]    jmp StartGDT:GDT_NULL:    dq 0GDT_CODE:    dw 0FFFFh    dw 0    db 0    db 10011010b    db 11001111b    db 0GDT_DATA:    dw 0FFFFh    dw 0    db 0    db 10010010b    db 11001111b    db 0GDT_END:GDT_DESC:    dw GDT_END - GDT - 1    dd GDT    dw 0Start:    cli    xor ax, ax    mov ds, ax        lgdt [GDT_DESC]        mov eax, cr0    or eax, 1    mov cr0, eax        ;jmp dword 08h:10000h                   ; ???    ;jmp dword 08h:ProtectedMode            ; ???    jmp dword GDT_CODE:ProtectedMode     [BITS 32]ProtectedMode:     jmp $     
Estoy usando el NASM.
nasm -f bin kernel.asm -o kernel.bin

Eternal Idol:
Esto no es un Kernel para empezar, es apenas un loader primigenio.

GDT_END - GDT era correcto (da el tamaño justo que tiene que ser numero de descriptores * 8 - tamaño de cada descriptor -) con palabra (dw) como bien dijo posman que debe ser.

El problema que tenes ahora es con el salto y es muy simple de solucionar, el ensamblador asume que el origen de tu programa va a ser 0000:0000h cuando en realidad sera 0000:7C00h, poniendo esta linea al principio hace lo esperado (un bucle infinito):


--- Código: Text ---org 07C00h 
El salto correcto es:

--- Código: Text ---jmp 08h:ProtectedMode 
PD. Supongo que ya entendiste parte de lo que te dije en el otro foro.

germancho7186:
No, el bootloader ya lo tengo, y este debería ser el kernel.

Si escribo el código en 16 bits todo funciona bien, el problema es cuando intento pasar a modo protegido.

Navegación

[0] Índice de Mensajes

[#] Página Siguiente

Ir a la versión completa