Implementation of PE->NE resource conversion routines (KERNEL.615-618).
This commit is contained in:
parent
f1779ed51d
commit
5443a7e658
@ -480,12 +480,12 @@ file krnl386.exe
|
|||||||
610 pascal FindSLThunkletCallback(long long) FindSLThunkletCallback
|
610 pascal FindSLThunkletCallback(long long) FindSLThunkletCallback
|
||||||
611 return FreeThunklet 8 0
|
611 return FreeThunklet 8 0
|
||||||
612 pascal16 IsSLThunklet(ptr) IsSLThunklet
|
612 pascal16 IsSLThunklet(ptr) IsSLThunklet
|
||||||
613 stub KERNEL_613 # (cbclient)
|
613 stub KERNEL_613
|
||||||
614 stub KERNEL_614 # (cbclient)
|
614 stub KERNEL_614
|
||||||
615 stub KERNEL_615 # (cbclient)
|
615 pascal16 ConvertDialog32To16(long long long) ConvertDialog32To16
|
||||||
616 stub KERNEL_616 # (cbclient)
|
616 pascal16 ConvertMenu32To16(long long long) ConvertMenu32To16
|
||||||
617 stub KERNEL_617 # (cbclient)
|
617 pascal16 GetMenu32Size(ptr) GetMenu32Size
|
||||||
618 stub KERNEL_618 # (cbclient)
|
618 pascal16 GetDialog32Size(ptr) GetDialog32Size
|
||||||
619 pascal16 RegisterCBClient(word ptr long) RegisterCBClient
|
619 pascal16 RegisterCBClient(word ptr long) RegisterCBClient
|
||||||
620 register CBClientThunkSL() CBClientThunkSL
|
620 register CBClientThunkSL() CBClientThunkSL
|
||||||
621 stub KERNEL_621 # (cbclient)
|
621 stub KERNEL_621 # (cbclient)
|
||||||
|
@ -6,6 +6,7 @@ VPATH = @srcdir@
|
|||||||
MODULE = ne
|
MODULE = ne
|
||||||
|
|
||||||
C_SRCS = \
|
C_SRCS = \
|
||||||
|
convert.c \
|
||||||
module.c \
|
module.c \
|
||||||
resource.c \
|
resource.c \
|
||||||
segment.c
|
segment.c
|
||||||
|
420
loader/ne/convert.c
Normal file
420
loader/ne/convert.c
Normal file
@ -0,0 +1,420 @@
|
|||||||
|
/*
|
||||||
|
* PE->NE resource conversion functions
|
||||||
|
*
|
||||||
|
* Copyright 1998 Ulrich Weigand
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "module.h"
|
||||||
|
#include "debug.h"
|
||||||
|
#include "debugtools.h"
|
||||||
|
#include "windows.h"
|
||||||
|
|
||||||
|
/**********************************************************************
|
||||||
|
* ConvertDialog32To16 (KERNEL.615)
|
||||||
|
*/
|
||||||
|
VOID WINAPI ConvertDialog32To16( LPVOID dialog32, DWORD size, LPVOID dialog16 )
|
||||||
|
{
|
||||||
|
LPVOID p = dialog32;
|
||||||
|
WORD nbItems, data, dialogEx;
|
||||||
|
DWORD style;
|
||||||
|
|
||||||
|
style = *((DWORD *)dialog16)++ = *((DWORD *)p)++;
|
||||||
|
dialogEx = (style == 0xffff0001); /* DIALOGEX resource */
|
||||||
|
if (dialogEx)
|
||||||
|
{
|
||||||
|
*((DWORD *)dialog16)++ = *((DWORD *)p)++; /* helpID */
|
||||||
|
*((DWORD *)dialog16)++ = *((DWORD *)p)++; /* exStyle */
|
||||||
|
style = *((DWORD *)dialog16)++ = *((DWORD *)p)++; /* style */
|
||||||
|
}
|
||||||
|
else
|
||||||
|
((DWORD *)p)++; /* exStyle ignored in 16-bit standard dialog */
|
||||||
|
|
||||||
|
nbItems = *((BYTE *)dialog16)++ = (BYTE)*((WORD *)p)++;
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* x */
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* y */
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* cx */
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* cy */
|
||||||
|
|
||||||
|
/* Transfer menu name */
|
||||||
|
switch (*((WORD *)p))
|
||||||
|
{
|
||||||
|
case 0x0000: ((WORD *)p)++; *((BYTE *)dialog16)++ = 0; break;
|
||||||
|
case 0xffff: ((WORD *)p)++; *((BYTE *)dialog16)++ = 0xff;
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; break;
|
||||||
|
default: lstrcpyWtoA( (LPSTR)dialog16, (LPWSTR)p );
|
||||||
|
((LPSTR)dialog16) += lstrlen32A( (LPSTR)dialog16 ) + 1;
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Transfer class name */
|
||||||
|
switch (*((WORD *)p))
|
||||||
|
{
|
||||||
|
case 0x0000: ((WORD *)p)++; *((BYTE *)dialog16)++ = 0; break;
|
||||||
|
case 0xffff: ((WORD *)p)++; *((BYTE *)dialog16)++ = 0xff;
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; break;
|
||||||
|
default: lstrcpyWtoA( (LPSTR)dialog16, (LPWSTR)p );
|
||||||
|
((LPSTR)dialog16) += lstrlen32A( (LPSTR)dialog16 ) + 1;
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Transfer window caption */
|
||||||
|
lstrcpyWtoA( (LPSTR)dialog16, (LPWSTR)p );
|
||||||
|
((LPSTR)dialog16) += lstrlen32A( (LPSTR)dialog16 ) + 1;
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
|
||||||
|
/* Transfer font info */
|
||||||
|
if (style & DS_SETFONT)
|
||||||
|
{
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* pointSize */
|
||||||
|
if (dialogEx)
|
||||||
|
{
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* weight */
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* italic */
|
||||||
|
}
|
||||||
|
lstrcpyWtoA( (LPSTR)dialog16, (LPWSTR)p ); /* faceName */
|
||||||
|
((LPSTR)dialog16) += lstrlen32A( (LPSTR)dialog16 ) + 1;
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Transfer dialog items */
|
||||||
|
while (nbItems)
|
||||||
|
{
|
||||||
|
/* align on DWORD boundary (32-bit only) */
|
||||||
|
p = (LPVOID)((((int)p) + 3) & ~3);
|
||||||
|
|
||||||
|
if (dialogEx)
|
||||||
|
{
|
||||||
|
*((DWORD *)dialog16)++ = *((DWORD *)p)++; /* helpID */
|
||||||
|
*((DWORD *)dialog16)++ = *((DWORD *)p)++; /* exStyle */
|
||||||
|
*((DWORD *)dialog16)++ = *((DWORD *)p)++; /* style */
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
style = *((DWORD *)p)++; /* save style */
|
||||||
|
((DWORD *)p)++; /* ignore exStyle */
|
||||||
|
}
|
||||||
|
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* x */
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* y */
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* cx */
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* cy */
|
||||||
|
|
||||||
|
if (dialogEx)
|
||||||
|
*((DWORD *)dialog16)++ = *((DWORD *)p)++; /* ID */
|
||||||
|
else
|
||||||
|
{
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; /* ID */
|
||||||
|
*((DWORD *)dialog16)++ = style; /* style from above */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Transfer class name */
|
||||||
|
switch (*((WORD *)p))
|
||||||
|
{
|
||||||
|
case 0x0000: ((WORD *)p)++; *((BYTE *)dialog16)++ = 0; break;
|
||||||
|
case 0xffff: ((WORD *)p)++;
|
||||||
|
*((BYTE *)dialog16)++ = (BYTE)*((WORD *)p)++; break;
|
||||||
|
default: lstrcpyWtoA( (LPSTR)dialog16, (LPWSTR)p );
|
||||||
|
((LPSTR)dialog16) += lstrlen32A( (LPSTR)dialog16 ) + 1;
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Transfer window name */
|
||||||
|
switch (*((WORD *)p))
|
||||||
|
{
|
||||||
|
case 0x0000: ((WORD *)p)++; *((BYTE *)dialog16)++ = 0; break;
|
||||||
|
case 0xffff: ((WORD *)p)++; *((BYTE *)dialog16)++ = 0xff;
|
||||||
|
*((WORD *)dialog16)++ = *((WORD *)p)++; break;
|
||||||
|
default: lstrcpyWtoA( (LPSTR)dialog16, (LPWSTR)p );
|
||||||
|
((LPSTR)dialog16) += lstrlen32A( (LPSTR)dialog16 ) + 1;
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Transfer data */
|
||||||
|
data = *((WORD *)p)++;
|
||||||
|
if (dialogEx)
|
||||||
|
*((WORD *)dialog16)++ = data;
|
||||||
|
else
|
||||||
|
*((BYTE *)dialog16)++ = (BYTE)data;
|
||||||
|
|
||||||
|
if (data)
|
||||||
|
{
|
||||||
|
memcpy( dialog16, p, data );
|
||||||
|
(LPSTR)dialog16 += data;
|
||||||
|
(LPSTR)p += data;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Next item */
|
||||||
|
nbItems--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**********************************************************************
|
||||||
|
* GetDialog32Size (KERNEL.618)
|
||||||
|
*/
|
||||||
|
WORD WINAPI GetDialog32Size( LPVOID dialog32 )
|
||||||
|
{
|
||||||
|
LPVOID p = dialog32;
|
||||||
|
WORD nbItems, data, dialogEx;
|
||||||
|
DWORD style;
|
||||||
|
|
||||||
|
style = *((DWORD *)p)++;
|
||||||
|
dialogEx = (style == 0xffff0001); /* DIALOGEX resource */
|
||||||
|
if (dialogEx)
|
||||||
|
{
|
||||||
|
((DWORD *)p)++; /* helpID */
|
||||||
|
((DWORD *)p)++; /* exStyle */
|
||||||
|
style = *((DWORD *)p)++; /* style */
|
||||||
|
}
|
||||||
|
else
|
||||||
|
((DWORD *)p)++; /* exStyle */
|
||||||
|
|
||||||
|
nbItems = *((WORD *)p)++;
|
||||||
|
((WORD *)p)++; /* x */
|
||||||
|
((WORD *)p)++; /* y */
|
||||||
|
((WORD *)p)++; /* cx */
|
||||||
|
((WORD *)p)++; /* cy */
|
||||||
|
|
||||||
|
/* Skip menu name */
|
||||||
|
switch (*((WORD *)p))
|
||||||
|
{
|
||||||
|
case 0x0000: ((WORD *)p)++; break;
|
||||||
|
case 0xffff: ((WORD *)p) += 2; break;
|
||||||
|
default: ((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1; break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Skip class name */
|
||||||
|
switch (*((WORD *)p))
|
||||||
|
{
|
||||||
|
case 0x0000: ((WORD *)p)++; break;
|
||||||
|
case 0xffff: ((WORD *)p) += 2; break;
|
||||||
|
default: ((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1; break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Skip window caption */
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
|
||||||
|
/* Skip font info */
|
||||||
|
if (style & DS_SETFONT)
|
||||||
|
{
|
||||||
|
((WORD *)p)++; /* pointSize */
|
||||||
|
if (dialogEx)
|
||||||
|
{
|
||||||
|
((WORD *)p)++; /* weight */
|
||||||
|
((WORD *)p)++; /* italic */
|
||||||
|
}
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1; /* faceName */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Skip dialog items */
|
||||||
|
while (nbItems)
|
||||||
|
{
|
||||||
|
/* align on DWORD boundary */
|
||||||
|
p = (LPVOID)((((int)p) + 3) & ~3);
|
||||||
|
|
||||||
|
if (dialogEx)
|
||||||
|
{
|
||||||
|
((DWORD *)p)++; /* helpID */
|
||||||
|
((DWORD *)p)++; /* exStyle */
|
||||||
|
((DWORD *)p)++; /* style */
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
((DWORD *)p)++; /* style */
|
||||||
|
((DWORD *)p)++; /* exStyle */
|
||||||
|
}
|
||||||
|
|
||||||
|
((WORD *)p)++; /* x */
|
||||||
|
((WORD *)p)++; /* y */
|
||||||
|
((WORD *)p)++; /* cx */
|
||||||
|
((WORD *)p)++; /* cy */
|
||||||
|
|
||||||
|
if (dialogEx)
|
||||||
|
((DWORD *)p)++; /* ID */
|
||||||
|
else
|
||||||
|
((WORD *)p)++; /* ID */
|
||||||
|
|
||||||
|
/* Skip class name */
|
||||||
|
switch (*((WORD *)p))
|
||||||
|
{
|
||||||
|
case 0x0000: ((WORD *)p)++; break;
|
||||||
|
case 0xffff: ((WORD *)p) += 2; break;
|
||||||
|
default: ((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1; break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Skip window name */
|
||||||
|
switch (*((WORD *)p))
|
||||||
|
{
|
||||||
|
case 0x0000: ((WORD *)p)++; break;
|
||||||
|
case 0xffff: ((WORD *)p) += 2; break;
|
||||||
|
default: ((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1; break;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Skip data */
|
||||||
|
data = *((WORD *)p)++;
|
||||||
|
(LPSTR)p += data;
|
||||||
|
|
||||||
|
/* Next item */
|
||||||
|
nbItems--;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (WORD)((LPSTR)p - (LPSTR)dialog32);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**********************************************************************
|
||||||
|
* ConvertMenu32To16 (KERNEL.616)
|
||||||
|
*/
|
||||||
|
VOID WINAPI ConvertMenu32To16( LPVOID menu32, DWORD size, LPVOID menu16 )
|
||||||
|
{
|
||||||
|
LPVOID p = menu32;
|
||||||
|
WORD version, headersize, flags, level = 1;
|
||||||
|
|
||||||
|
version = *((WORD *)menu16)++ = *((WORD *)p)++;
|
||||||
|
headersize = *((WORD *)menu16)++ = *((WORD *)p)++;
|
||||||
|
if ( headersize )
|
||||||
|
{
|
||||||
|
memcpy( menu16, p, headersize );
|
||||||
|
((LPSTR)menu16) += headersize;
|
||||||
|
((LPSTR)p) += headersize;
|
||||||
|
}
|
||||||
|
|
||||||
|
while ( level )
|
||||||
|
if ( version == 0 ) /* standard */
|
||||||
|
{
|
||||||
|
flags = *((WORD *)menu16)++ = *((WORD *)p)++;
|
||||||
|
if ( !(flags & MF_POPUP) )
|
||||||
|
*((WORD *)menu16)++ = *((WORD *)p)++; /* ID */
|
||||||
|
else
|
||||||
|
level++;
|
||||||
|
|
||||||
|
lstrcpyWtoA( (LPSTR)menu16, (LPWSTR)p );
|
||||||
|
((LPSTR)menu16) += lstrlen32A( (LPSTR)menu16 ) + 1;
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
|
||||||
|
if ( flags & MF_END )
|
||||||
|
level--;
|
||||||
|
}
|
||||||
|
else /* extended */
|
||||||
|
{
|
||||||
|
*((DWORD *)menu16)++ = *((DWORD *)p)++; /* fType */
|
||||||
|
*((DWORD *)menu16)++ = *((DWORD *)p)++; /* fState */
|
||||||
|
*((WORD *)menu16)++ = (WORD)*((DWORD *)p)++; /* ID */
|
||||||
|
flags = *((BYTE *)menu16)++ = (BYTE)*((WORD *)p)++;
|
||||||
|
|
||||||
|
lstrcpyWtoA( (LPSTR)menu16, (LPWSTR)p );
|
||||||
|
((LPSTR)menu16) += lstrlen32A( (LPSTR)menu16 ) + 1;
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
|
||||||
|
/* align on DWORD boundary (32-bit only) */
|
||||||
|
p = (LPVOID)((((int)p) + 3) & ~3);
|
||||||
|
|
||||||
|
/* If popup, transfer helpid */
|
||||||
|
if ( flags & 1)
|
||||||
|
{
|
||||||
|
*((DWORD *)menu16)++ = *((DWORD *)p)++;
|
||||||
|
level++;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( flags & MF_END )
|
||||||
|
level--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**********************************************************************
|
||||||
|
* GetMenu32Size (KERNEL.617)
|
||||||
|
*/
|
||||||
|
WORD WINAPI GetMenu32Size( LPVOID menu32 )
|
||||||
|
{
|
||||||
|
LPVOID p = menu32;
|
||||||
|
WORD version, headersize, flags, level = 1;
|
||||||
|
|
||||||
|
version = *((WORD *)p)++;
|
||||||
|
headersize = *((WORD *)p)++;
|
||||||
|
((LPSTR)p) += headersize;
|
||||||
|
|
||||||
|
while ( level )
|
||||||
|
if ( version == 0 ) /* standard */
|
||||||
|
{
|
||||||
|
flags = *((WORD *)p)++;
|
||||||
|
if ( !(flags & MF_POPUP) )
|
||||||
|
((WORD *)p)++; /* ID */
|
||||||
|
else
|
||||||
|
level++;
|
||||||
|
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
|
||||||
|
if ( flags & MF_END )
|
||||||
|
level--;
|
||||||
|
}
|
||||||
|
else /* extended */
|
||||||
|
{
|
||||||
|
((DWORD *)p)++; /* fType */
|
||||||
|
((DWORD *)p)++; /* fState */
|
||||||
|
((DWORD *)p)++; /* ID */
|
||||||
|
flags = *((WORD *)p)++;
|
||||||
|
|
||||||
|
((LPWSTR)p) += lstrlen32W( (LPWSTR)p ) + 1;
|
||||||
|
|
||||||
|
/* align on DWORD boundary (32-bit only) */
|
||||||
|
p = (LPVOID)((((int)p) + 3) & ~3);
|
||||||
|
|
||||||
|
/* If popup, skip helpid */
|
||||||
|
if ( flags & 1)
|
||||||
|
{
|
||||||
|
((DWORD *)p)++;
|
||||||
|
level++;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( flags & MF_END )
|
||||||
|
level--;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (WORD)((LPSTR)p - (LPSTR)menu32);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**********************************************************************
|
||||||
|
* NE_LoadPEResource
|
||||||
|
*/
|
||||||
|
HGLOBAL16 NE_LoadPEResource( NE_MODULE *pModule, WORD type, LPVOID bits, DWORD size )
|
||||||
|
{
|
||||||
|
HGLOBAL16 handle;
|
||||||
|
|
||||||
|
TRACE( resource, "module=%04x type=%04x\n", pModule->self, type );
|
||||||
|
if (!pModule || !bits || !size) return 0;
|
||||||
|
|
||||||
|
handle = GlobalAlloc16( 0, size );
|
||||||
|
|
||||||
|
switch (type)
|
||||||
|
{
|
||||||
|
case RT_MENU16:
|
||||||
|
ConvertMenu32To16( bits, size, GlobalLock16( handle ) );
|
||||||
|
break;
|
||||||
|
|
||||||
|
case RT_DIALOG16:
|
||||||
|
ConvertDialog32To16( bits, size, GlobalLock16( handle ) );
|
||||||
|
break;
|
||||||
|
|
||||||
|
case RT_STRING16:
|
||||||
|
FIXME( resource, "not yet implemented!\n" );
|
||||||
|
/* fall through */
|
||||||
|
|
||||||
|
default:
|
||||||
|
memcpy( GlobalLock16( handle ), bits, size );
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return handle;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**********************************************************************
|
||||||
|
* NE_FreePEResource
|
||||||
|
*/
|
||||||
|
BOOL16 NE_FreePEResource( NE_MODULE *pModule, HGLOBAL16 handle )
|
||||||
|
{
|
||||||
|
GlobalFree16( handle );
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
Loading…
x
Reference in New Issue
Block a user