¿Por qué es necesario Thunking?
Los controladores en modo kernel deben validar el tamaño de cualquier búfer de E/S pasado desde una aplicación en modo de usuario. Si una aplicación de 32 bits pasa un búfer que contiene tipos de datos de precisión de puntero a un controlador de 64 bits y no tiene lugar ningún matones, el controlador esperará que el búfer sea mayor que realmente. Esto se debe a que la precisión del puntero es de 32 bits en Microsoft Windows de 32 bits y 64 bits en Windows de 64 bits. Por ejemplo, considere la siguiente definición de estructura:
typedef struct _DRIVER_DATA
{
HANDLE Event;
UNICODE_STRING ObjectName;
} DRIVER_DATA;
En Windows de 32 bits, el tamaño de la estructura de DRIVER_DATA es de 12 bytes. En esta tabla se muestran los tamaños del miembro Event y los miembros ObjectName de la estructura DRIVER_DATA:
Evento | ObjectName (longitud de USHORT) | ObjectName (longitud máxima de USHORT) | ObjectName (Búfer PWSTR) |
---|---|---|---|
32 bits | 16 bits | 16 bits | 32 bits |
(4 bytes) | (2 bytes) | (2 bytes) | (4 bytes) |
En Windows de 64 bits, el tamaño de la estructura de DRIVER_DATA es de 24 bytes. (Se requieren 4 bytes de relleno de estructura para que el miembro buffer se pueda alinear en un límite de 8 bytes).
Evento | ObjectName (longitud de USHORT) | ObjectName (longitud máxima de USHORT) | Vacío (relleno de estructura) | ObjectName (Búfer PWSTR) |
---|---|---|---|---|
64 bits | 16 bits | 16 bits | 32 bits | 64 bits |
(8 bytes) | (2 bytes) | (2 bytes) | (4 bytes) | (8 bytes) |
Si un controlador de 64 bits recibe 12 bytes de DRIVER_DATA cuando esperaba 24 bytes, se producirá un error en la validación del tamaño. Para evitar esto, el controlador debe detectar si una aplicación de 32 bits envió una estructura de DRIVER_DATA y, si es así, thunkla correctamente antes de realizar la validación.
Por ejemplo, una versión thunked de la estructura de DRIVER_DATA anterior podría definirse de la siguiente manera:
typedef struct _DRIVER_DATA32
{
VOID *POINTER_32 Event;
UNICODE_STRING32 ObjectName;
} DRIVER_DATA32;
Dado que solo contiene tipos de datos de precisión fija, esta nueva estructura tiene el mismo tamaño en Windows de 32 bits y Windows de 64 bits.
Evento | ObjectName (longitud de USHORT) | ObjectName (longitud máxima de USHORT) | Búfer de ULONG |
---|---|---|---|
32 bits | 16 bits | 16 bits | 32 bits |
(4 bytes) | (2 bytes) | (2 bytes) | (4 bytes) |