Author: ros-arm-bringup Date: Fri Jan 1 00:51:26 2010 New Revision: 44841
URL: http://svn.reactos.org/svn/reactos?rev=44841&view=rev Log: NMI Support Patch 1: [HAL]: The I/O Permissions Map on a typical Privileged Mode x86 OS is all 0xFF's, so it's quite wasteful to copy-in/out the entire map each single BIOS Call. As an optimization, only save and restore non-0xFF entries. [NTOS]: Define and use constants for different IOPM values, instead of using hardcoded values.
Modified: trunk/reactos/hal/halx86/generic/bios.c trunk/reactos/include/ndk/i386/ketypes.h trunk/reactos/ntoskrnl/ke/i386/cpu.c
Modified: trunk/reactos/hal/halx86/generic/bios.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/hal/halx86/generic/bios.c?r... ============================================================================== --- trunk/reactos/hal/halx86/generic/bios.c [iso-8859-1] (original) +++ trunk/reactos/hal/halx86/generic/bios.c [iso-8859-1] Fri Jan 1 00:51:26 2010 @@ -1,9 +1,9 @@ /* - * PROJECT: ReactOS HAL - * LICENSE: GPL - See COPYING in the top level directory - * FILE: hal/halx86/generic/bios.c + * PROJECT: ReactOS Hardware Abstraction Layer (HAL) + * LICENSE: BSD - See COPYING.ARM in the top level directory + * FILE: halx86/generic/bios.c * PURPOSE: BIOS Access Routines - * PROGRAMMERS: Alex Ionescu (alex.ionescu@reactos.org) + * PROGRAMMERS: ReactOS Portable Systems Group */
/* INCLUDES *******************************************************************/ @@ -14,14 +14,15 @@
/* GLOBALS ********************************************************************/
-UCHAR HalpIopmSaveBuffer[0x2000]; ULONG HalpSavedPfn; HARDWARE_PTE HalpSavedPte; ULONG HalpGpfHandler; ULONG HalpBopHandler; +ULONG HalpSavedEsp0; USHORT HalpSavedIopmBase; -PUCHAR HalpSavedIoMap; -ULONG HalpSavedEsp0; +PUSHORT HalpSavedIoMap; +USHORT HalpSavedIoMapData[32][2]; +ULONG HalpSavedIoMapEntries;
#define GetPdeAddress(x) (PHARDWARE_PTE)(((((ULONG_PTR)(x)) >> 22) << 2) + 0xC0300000) #define GetPteAddress(x) (PHARDWARE_PTE)(((((ULONG_PTR)(x)) >> 12) << 2) + 0xC0000000) @@ -30,27 +31,61 @@
VOID NTAPI -HalpStoreAndClearIopm(IN PUCHAR IoMap) -{ - ULONG i; - - /* Backup the old I/O Map */ - RtlCopyMemory(HalpIopmSaveBuffer, IoMap, 0x2000); - - /* Erase the current one */ - for (i = 0; i < 0x2000; i++) IoMap[i] = 0; - for (i = 0x2000; i < 0x2004; i++) IoMap[i] = 0xFF; -} - -VOID -NTAPI -HalpRestoreIopm(IN PUCHAR IoMap) -{ - ULONG i; - - /* Restore the backed up copy, and initialize it */ - RtlCopyMemory(IoMap, HalpIopmSaveBuffer, 0x2000); - for (i = 0x2000; i < 0x2004; i++) IoMap[i] = 0xFF; +HalpStoreAndClearIopm(VOID) +{ + ULONG i, j; + PUSHORT Entry = HalpSavedIoMap; + + // + // Loop the I/O Map + // + for (i = j = 0; i < (IOPM_SIZE) / 2; i++) + { + // + // Check for non-FFFF entry + // + if (*Entry != 0xFFFF) + { + // + // Save it + // + ASSERT(j < 32); + HalpSavedIoMapData[j][0] = i; + HalpSavedIoMapData[j][1] = *Entry; + } + + // + // Clear it + // + *Entry++ = 0; + } + + // + // Terminate it + // + while (i++ < (IOPM_FULL_SIZE / 2)) *Entry++ = 0xFFFF; + + // + // Return the entries we saved + // + HalpSavedIoMapEntries = j; +} + +VOID +NTAPI +HalpRestoreIopm(VOID) +{ + ULONG i = HalpSavedIoMapEntries; + + // + // Set default state + // + RtlFillMemory(HalpSavedIoMap, 0xFF, IOPM_FULL_SIZE); + + // + // Restore the backed up copy, and initialize it + // + while (i--) HalpSavedIoMap[HalpSavedIoMapData[i][0]] = HalpSavedIoMapData[i][1]; }
VOID @@ -134,8 +169,8 @@ HalpSetupRealModeIoPermissionsAndTask(VOID) { /* Save a copy of the I/O Map and delete it */ - HalpSavedIoMap = (PUCHAR)&(KeGetPcr()->TSS->IoMaps[0]); - HalpStoreAndClearIopm(HalpSavedIoMap); + HalpSavedIoMap = (PUSHORT)&(KeGetPcr()->TSS->IoMaps[0]); + HalpStoreAndClearIopm();
/* Save the IOPM and switch to the real-mode one */ HalpSavedIopmBase = KeGetPcr()->TSS->IoMapBase; @@ -166,7 +201,7 @@ KeGetPcr()->TSS->Esp0 = HalpSavedEsp0;
/* Restore the I/O Map */ - HalpRestoreIopm(HalpSavedIoMap); + HalpRestoreIopm();
/* Restore the IOPM */ KeGetPcr()->TSS->IoMapBase = HalpSavedIopmBase;
Modified: trunk/reactos/include/ndk/i386/ketypes.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/include/ndk/i386/ketypes.h?... ============================================================================== --- trunk/reactos/include/ndk/i386/ketypes.h [iso-8859-1] (original) +++ trunk/reactos/include/ndk/i386/ketypes.h [iso-8859-1] Fri Jan 1 00:51:26 2010 @@ -129,7 +129,11 @@ // // IOPM Definitions // +#define IOPM_COUNT 1 +#define IOPM_SIZE 8192 +#define IOPM_FULL_SIZE 8196 #define IO_ACCESS_MAP_NONE 0 +#define IOPM_DIRECTION_MAP_SIZE 32 #define IOPM_OFFSET FIELD_OFFSET(KTSS, IoMaps[0].IoMap) #define KiComputeIopmOffset(MapNumber) \ (MapNumber == IO_ACCESS_MAP_NONE) ? \ @@ -708,8 +712,8 @@ // typedef struct _KiIoAccessMap { - UCHAR DirectionMap[32]; - UCHAR IoMap[8196]; + UCHAR DirectionMap[IOPM_DIRECTION_MAP_SIZE]; + UCHAR IoMap[IOPM_FULL_SIZE]; } KIIO_ACCESS_MAP;
typedef struct _KTSS @@ -747,8 +751,8 @@ USHORT Reserved8; USHORT Flags; USHORT IoMapBase; - KIIO_ACCESS_MAP IoMaps[1]; - UCHAR IntDirectionMap[32]; + KIIO_ACCESS_MAP IoMaps[IOPM_COUNT]; + UCHAR IntDirectionMap[IOPM_DIRECTION_MAP_SIZE]; } KTSS, *PKTSS;
//
Modified: trunk/reactos/ntoskrnl/ke/i386/cpu.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ke/i386/cpu.c?rev=... ============================================================================== --- trunk/reactos/ntoskrnl/ke/i386/cpu.c [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/ke/i386/cpu.c [iso-8859-1] Fri Jan 1 00:51:26 2010 @@ -582,11 +582,12 @@ }
/* Now clear the I/O Map */ - RtlFillMemory(Tss->IoMaps[0].IoMap, 8096, -1); + ASSERT(IOPM_COUNT == 1); + RtlFillMemory(Tss->IoMaps[0].IoMap, IOPM_FULL_SIZE, 0xFF);
/* Initialize Interrupt Direction Maps */ p = (PUCHAR)(Tss->IoMaps[0].DirectionMap); - RtlZeroMemory(p, 32); + RtlZeroMemory(p, IOPM_DIRECTION_MAP_SIZE);
/* Add DPMI support for interrupts */ p[0] = 4; @@ -595,7 +596,7 @@
/* Initialize the default Interrupt Direction Map */ p = Tss->IntDirectionMap; - RtlZeroMemory(Tss->IntDirectionMap, 32); + RtlZeroMemory(Tss->IntDirectionMap, IOPM_DIRECTION_MAP_SIZE);
/* Add DPMI support */ p[0] = 4;