Make the total amount of EMS pages configurable.
Allocate memory for EMS instead of sharing a part of the guest memory.


svn path=/trunk/; revision=67325
This commit is contained in:
Aleksandar Andrejevic 2015-04-20 14:02:18 +00:00
parent bbb62e8795
commit cc252d78bd
4 changed files with 72 additions and 20 deletions

View file

@ -666,7 +666,11 @@ Bios32Post(VOID)
SearchAndInitRoms(&BiosContext); SearchAndInitRoms(&BiosContext);
/* Initialize EMS */ /* Initialize EMS */
EmsInitialize(); if (!EmsInitialize(EMS_TOTAL_PAGES))
{
DPRINT1("Could not initialize EMS. EMS will not be available.\n"
"Try reducing the number of EMS pages.\n");
}
/* /*
* End of the 32-bit POST portion. We then fall back into 16-bit where * End of the 32-bit POST portion. We then fall back into 16-bit where

View file

@ -21,6 +21,9 @@
// #define BIOS_TIME_INTERRUPT 0x1A // #define BIOS_TIME_INTERRUPT 0x1A
// #define BIOS_SYS_TIMER_INTERRUPT 0x1C // #define BIOS_SYS_TIMER_INTERRUPT 0x1C
/* 16 MB of EMS memory */
#define EMS_TOTAL_PAGES 1024
/* FUNCTIONS ******************************************************************/ /* FUNCTIONS ******************************************************************/
BOOLEAN Bios32Initialize(VOID); BOOLEAN Bios32Initialize(VOID);

View file

@ -19,10 +19,12 @@
/* PRIVATE VARIABLES **********************************************************/ /* PRIVATE VARIABLES **********************************************************/
static RTL_BITMAP AllocBitmap; static RTL_BITMAP AllocBitmap;
static ULONG BitmapBuffer[(EMS_TOTAL_PAGES + sizeof(ULONG) - 1) / sizeof(ULONG)]; static PULONG BitmapBuffer = NULL;
static EMS_PAGE PageTable[EMS_TOTAL_PAGES]; static PEMS_PAGE PageTable = NULL;
static EMS_HANDLE HandleTable[EMS_MAX_HANDLES]; static EMS_HANDLE HandleTable[EMS_MAX_HANDLES];
static PVOID Mapping[EMS_PHYSICAL_PAGES] = { NULL }; static PVOID Mapping[EMS_PHYSICAL_PAGES] = { NULL };
static ULONG EmsTotalPages = 0;
static PVOID EmsMemory = NULL;
/* PRIVATE FUNCTIONS **********************************************************/ /* PRIVATE FUNCTIONS **********************************************************/
@ -137,7 +139,8 @@ static USHORT EmsMap(USHORT Handle, UCHAR PhysicalPage, USHORT LogicalPage)
PageEntry = GetLogicalPage(HandleEntry, LogicalPage); PageEntry = GetLogicalPage(HandleEntry, LogicalPage);
if (!PageEntry) return EMS_STATUS_INV_LOGICAL_PAGE; if (!PageEntry) return EMS_STATUS_INV_LOGICAL_PAGE;
Mapping[PhysicalPage] = (PVOID)(EMS_ADDRESS + ARRAY_INDEX(PageEntry, PageTable) * EMS_PAGE_SIZE); Mapping[PhysicalPage] = (PVOID)((ULONG_PTR)EmsMemory
+ ARRAY_INDEX(PageEntry, PageTable) * EMS_PAGE_SIZE);
return EMS_STATUS_OK; return EMS_STATUS_OK;
} }
@ -165,7 +168,7 @@ static VOID WINAPI EmsIntHandler(LPWORD Stack)
{ {
setAH(EMS_STATUS_OK); setAH(EMS_STATUS_OK);
setBX(RtlNumberOfClearBits(&AllocBitmap)); setBX(RtlNumberOfClearBits(&AllocBitmap));
setDX(EMS_TOTAL_PAGES); setDX(EmsTotalPages);
break; break;
} }
@ -230,10 +233,9 @@ static VOID WINAPI EmsIntHandler(LPWORD Stack)
break; break;
} }
SourcePtr = (PUCHAR)REAL_TO_PHYS(EMS_ADDRESS SourcePtr = (PUCHAR)((ULONG_PTR)EmsMemory
+ ARRAY_INDEX(PageEntry, PageTable) + ARRAY_INDEX(PageEntry, PageTable) * EMS_PAGE_SIZE
* EMS_PAGE_SIZE + Data->SourceOffset);
+ Data->SourceOffset);
} }
else else
{ {
@ -260,10 +262,9 @@ static VOID WINAPI EmsIntHandler(LPWORD Stack)
break; break;
} }
DestPtr = (PUCHAR)REAL_TO_PHYS(EMS_ADDRESS DestPtr = (PUCHAR)((ULONG_PTR)EmsMemory
+ ARRAY_INDEX(PageEntry, PageTable) + ARRAY_INDEX(PageEntry, PageTable) * EMS_PAGE_SIZE
* EMS_PAGE_SIZE + Data->DestOffset);
+ Data->DestOffset);
} }
else else
{ {
@ -346,13 +347,10 @@ static BOOLEAN NTAPI EmsWriteMemory(ULONG Address, PVOID Buffer, ULONG Size)
/* PUBLIC FUNCTIONS ***********************************************************/ /* PUBLIC FUNCTIONS ***********************************************************/
VOID EmsInitialize(VOID) BOOLEAN EmsInitialize(ULONG TotalPages)
{ {
ULONG i; ULONG i;
RtlZeroMemory(BitmapBuffer, sizeof(BitmapBuffer));
RtlInitializeBitMap(&AllocBitmap, BitmapBuffer, EMS_TOTAL_PAGES);
for (i = 0; i < EMS_MAX_HANDLES; i++) for (i = 0; i < EMS_MAX_HANDLES; i++)
{ {
HandleTable[i].Allocated = FALSE; HandleTable[i].Allocated = FALSE;
@ -360,16 +358,65 @@ VOID EmsInitialize(VOID)
InitializeListHead(&HandleTable[i].PageList); InitializeListHead(&HandleTable[i].PageList);
} }
EmsTotalPages = TotalPages;
BitmapBuffer = RtlAllocateHeap(RtlGetProcessHeap(),
HEAP_ZERO_MEMORY,
((TotalPages + 31) / 32) * sizeof(ULONG));
if (BitmapBuffer == NULL) return FALSE;
RtlInitializeBitMap(&AllocBitmap, BitmapBuffer, TotalPages);
PageTable = (PEMS_PAGE)RtlAllocateHeap(RtlGetProcessHeap(),
HEAP_ZERO_MEMORY,
TotalPages * sizeof(EMS_PAGE));
if (PageTable == NULL)
{
RtlFreeHeap(RtlGetProcessHeap(), 0, BitmapBuffer);
BitmapBuffer = NULL;
return FALSE;
}
EmsMemory = (PVOID)RtlAllocateHeap(RtlGetProcessHeap(), 0, TotalPages * EMS_PAGE_SIZE);
if (EmsMemory == NULL)
{
RtlFreeHeap(RtlGetProcessHeap(), 0, PageTable);
PageTable = NULL;
RtlFreeHeap(RtlGetProcessHeap(), 0, BitmapBuffer);
BitmapBuffer = NULL;
return FALSE;
}
MemInstallFastMemoryHook((PVOID)TO_LINEAR(EMS_SEGMENT, 0), MemInstallFastMemoryHook((PVOID)TO_LINEAR(EMS_SEGMENT, 0),
EMS_PHYSICAL_PAGES * EMS_PAGE_SIZE, EMS_PHYSICAL_PAGES * EMS_PAGE_SIZE,
EmsReadMemory, EmsReadMemory,
EmsWriteMemory); EmsWriteMemory);
RegisterBiosInt32(EMS_INTERRUPT_NUM, EmsIntHandler); RegisterBiosInt32(EMS_INTERRUPT_NUM, EmsIntHandler);
return TRUE;
} }
VOID EmsCleanup(VOID) VOID EmsCleanup(VOID)
{ {
MemRemoveFastMemoryHook((PVOID)TO_LINEAR(EMS_SEGMENT, 0), MemRemoveFastMemoryHook((PVOID)TO_LINEAR(EMS_SEGMENT, 0),
EMS_PHYSICAL_PAGES * EMS_PAGE_SIZE); EMS_PHYSICAL_PAGES * EMS_PAGE_SIZE);
if (EmsMemory)
{
RtlFreeHeap(RtlGetProcessHeap(), 0, EmsMemory);
EmsMemory = NULL;
}
if (PageTable)
{
RtlFreeHeap(RtlGetProcessHeap(), 0, PageTable);
PageTable = NULL;
}
if (BitmapBuffer)
{
RtlFreeHeap(RtlGetProcessHeap(), 0, BitmapBuffer);
BitmapBuffer = NULL;
}
} }

View file

@ -15,10 +15,8 @@
#define EMS_INTERRUPT_NUM 0x67 #define EMS_INTERRUPT_NUM 0x67
#define EMS_SEGMENT 0xD000 #define EMS_SEGMENT 0xD000
#define EMS_MAX_HANDLES 16 #define EMS_MAX_HANDLES 16
#define EMS_TOTAL_PAGES 256
#define EMS_PAGE_BITS 14 #define EMS_PAGE_BITS 14
#define EMS_PAGE_SIZE (1 << EMS_PAGE_BITS) #define EMS_PAGE_SIZE (1 << EMS_PAGE_BITS)
#define EMS_ADDRESS 0xA00000
#define EMS_PHYSICAL_PAGES 4 #define EMS_PHYSICAL_PAGES 4
#define EMS_STATUS_OK 0x00 #define EMS_STATUS_OK 0x00
@ -63,7 +61,7 @@ typedef struct _EMS_COPY_DATA
/* FUNCTIONS ******************************************************************/ /* FUNCTIONS ******************************************************************/
VOID EmsInitialize(VOID); BOOLEAN EmsInitialize(ULONG TotalPages);
VOID EmsCleanup(VOID); VOID EmsCleanup(VOID);
#endif // _EMS_H_ #endif // _EMS_H_