Site hosted by Angelfire.com: Build your free website today!

Tutorial 1: Lo básico

En este tutorial asumo que el lector sabe como usar MASM. Si no estás familiarizado con MASM, descarga win32asm.exe y estudia el texto dentro del paquete antes de seguir con este tutorial. Bueno. Ahora estás listo. Ok vamos !

Teoría:

Los programas de Win32 corren en modo protegido, disponible desde el 80286. Pero ahora el 80286 es historia. Asi que ahora debemos interesarnos en el 80386 y sus descendientes. Windows corre cada programa de 32 bits en espacios virtuales de memoria separados. Eso significa que cada programa de Win32 tiene sus propios 4 GB de memoria en el espacio de direcciones. Como sea, esto no significa que cada programa de Win32 tenga 4GB de memora física, sino que el programa puede direccionar cualquier dirección en ese rango.

Windows hará cualquier cosa que sea necesaria para hacer que la memoria y las referencias del programas sean válidas. Por supuesto, el programa debe adherirse a las reglas impuestas por Windows, si no, causará un error de protección general. Cada programa está solo en su espacio de direcciones. Esto contrasta con la situación en Win16. Todos los programas de Win16 podían *verse* unos a otros. No es lo mismo en Win32. Esto reduce la posibilidad de que un programa escriba sobre el código/datos de otros programas.

El modelo de la memoria es también drásticamente diferente al de los antiguos días del mundo de 16-bits. Bajo Win32, ya no necesitamos meternos nunca más con el modelo o los segmentos de memoria! Hay un solo tipo de modelo de memoria: El modelo plano (flat).

Ahora, no hay solamente segmentos de 64k. La memoria es un largo y continuo espacio de 4GB. Eso también significa que no tendrás que jugar mas con los registros de los segmentos. Ahora puedes usar cualquier registro de segmento para direccionar a cualquier punto en el espacio de la memoría. Eso es una GENIAL ayuda para los programadores. Esto hace la programación de ensamblador para Win32 tan fácil como C.

Cuando programas bajo Win32, debes tener en cuenta unas cuantas reglas importantes. Una es que Windows usa esi ,edi ebp y ebx internamente y no espera que los valores en esos registros cambien. Asi que recuerda esta regla primero: si usas cualquiera de estos cuatro registros en tu función callback, nunca olvides restaurarlos antes de regresar el control a Windows. Una función callback es una función escrita por tí que Windows llama cuando algún evento específico se produce. El ejemplo mas obvio es el procedimiento de ventana. Esto no significa que no puedas usar estos cuatro registros; sí puedes. Solo asegúrate de restaurarlos antes de pasarle el control a Windows.

Contenido:

Aquí hay un esqueleto de un programa. Si no entiendes algo de los códigos, que no cunda el pánico. Los explicaré cada uno de ellos mas abajo.

.386
.MODEL Flat, STDCALL
.DATA
    <Tu data (información) inicializada>
    ......
.DATA?
   <Tu data NO inicializada>
   ......
.CONST
   <Tus constantes>
   ......
.CODE
   <Etiqueta>
    <Tu código>
   .....
    end <Etiqueta>


Sip, eso es todo, vamos a analizar el programa esqueleto.

.386
Esto es una directiva para el ensamblador, que le dice que vamos a usar el conjunto de instrucciones del 80386. También puedes usar .486,.586 pero es mas seguro ponerle .386. Hay actualmente dos formas casi idénticas para cada modelo de CPU. .386/.386p, .486/.486p. Esas versiones de "p"  son necesarias cuando tu programa usa instrucciones privilegiadas. Las instrucciones privilegiadas son las instrucciones reservadas por la CPU/sistema operativo cuando están en modo protegido. Solamente pueden ser usadas por un código privilegiado, asi como los virtual device drivers (controladores de dispositivos virtuales = VXD).

.MODEL FLAT, STDCALL
.MODEL es una directiva para el ensamblador que especifíca el modelo de memoria de tu programa. Bajo Win32, hay un solo tipo de memoria, la PLANA(
FLAT).
STDCALL Indica al ensamblador la convención de paso de los parámetros. La convención de paso de parámetros especifica el orden que debe seguirse para pasar parámetros, izquierda-a-derecha o derecha-a-izquierda, y también equilibrará la pila después de una llamada (call)

Bajo Win16, hay dos tipos de convenciones para las llamadas a funciones: C y PASCAL
La convención para pasar parámetros de derecha a izquierda en cada llamada (call), es decir, el parámetro de más a la derecha es empujado primero a la pila. La rutina que hace la llamada es la responsable de equilibrar el marco de la pila después de la llamada (call). Por ejemplo, si vamos a llamar a una función con nombre foo(int primera_parte, int segunda_parte, int tercera_parte) en lenguaje C la convención sería así en asm:
push  [tercera_parte]              ; Empuja el tercer parámetro
push  [segunda_parte]            ; Seguido por el segundo
push  [
primera_parte]             ; Y aqui se pone de primero
call    foo
add    sp, 12                                ; La llamada equilibra el marco de la pila
La convención de llamadas en PASCAL es totalmente al revés de la convención de C. Pasa los parámetros de izquierda a derecha y la rutina que llama es responsable de equilibrarse después de la llamada.

El sistema Win16 adopta la convención de PASCAL porque produce códigos más pequeños. La convención de C es eficiente cuando no sabes cuántos parámetros serán pasados a la función como es el caso de wsprintf(). En el caso de wsprintf(), no hay manera de determinar cuántos parámetros serán empujados por esta función a la pila, así que no se puede hacer el balanceo de la pila.

STDCALL es la convención híbrida entre C y PASCAL. Pasa parámetros de derecha a izquierda, pero la llamada es la responsable por el balance de la pila después de la llamada. La plataforma de Win32 usa el modelo STDCALL exclusivamente. Excepto en un caso: wsprintf(). Debes usar la convención de llamada C con la función wsprintf().

.DATA
.DATA?
.CONST
.CODE

Estas 4 directivas son las llamadas 'secciones'. No tienes segmentos en Win32, ¿recuerdas?, pero puedes dividir todo el espacio de direcciones en secciones lógicas. El comienzo de una sección demuestra el fin de la otra sección previa. Hay dos grupos de secciones: data y code. Las secciones Data están divididas en tres categorías:

No tienes que usar las tres secciones en tu programa. Declara solo la(s) sección(es) que quieres usar.

Existe solo una sección para el código (code):.CODE. Aquí es donde tu código reside.

<etiqueta>
end <etiqueta>
Donde está la <etiqueta> se puede usar cualquier nombre como etiqueta para especificar la extensión de tu código.. Ambas etiquetas deben ser idénticas. Todos tus códigos deben residir entre <etiqueta> y end <etiqueta>


[Iczelion's Win32 Assembly HomePage]

[Traducido por Henry para la escuela de win32asm]

Índice

Siguiente

n u M I T_o r's   Programming Page

Este tutorial, original de Iczelion, ha sido revisado por:   n u M I T_o r   [ kUT ]