|
|
/*++
Copyright (c) 2000 Microsoft Corporation
Module Name:
NFLFever2000.cpp
Abstract: The app reads past the end of files that it's copied into memory. The shim allocates additional memory for it
Note we included an in-memory patch for Win2k. On Whistler it's not required, the rest of the shim does the work. Notes:
This is an app specific shim.
History: 01/11/2000 linstev Created 10/03/2000 maonis Modified (the acm stuff is now in a general purpose shim) --*/
#include "precomp.h"
IMPLEMENT_SHIM_BEGIN(NFLFever2000) #include "ShimHookMacro.h"
APIHOOK_ENUM_BEGIN APIHOOK_ENUM_ENTRY(GetFileSize) APIHOOK_ENUM_ENTRY(RtlAllocateHeap) APIHOOK_ENUM_ENTRY(mmioSetInfo) APIHOOK_ENUM_END
DWORD g_dwFileSize = -1; BOOL g_bPatched = FALSE;
/*++
Hook GetFileSize to make sure we get the correct heap allocations.
--*/
DWORD APIHOOK(GetFileSize)( HANDLE hFile, LPDWORD lpFileSizeHigh ) { DWORD dwRet = ORIGINAL_API(GetFileSize)(hFile, lpFileSizeHigh);
g_dwFileSize = dwRet;
PBYTE p; ULONG oldProtect;
if (!g_bPatched) { p = (PBYTE)0x10995d0; if (!IsBadReadPtr(p, 1) && (*p == 0x8b)) { VirtualProtect(p, 3, PAGE_READWRITE, &oldProtect); *p = 0xc2; *(p + 1) = 0x8; *(p + 2) = 0x0; VirtualProtect(p, 3, oldProtect, &oldProtect); g_bPatched = TRUE; } }
return dwRet; }
/*++
Increase the heap allocation size.
--*/
PVOID APIHOOK(RtlAllocateHeap) ( PVOID HeapHandle, ULONG Flags, SIZE_T Size ) { if (Size == g_dwFileSize) { DPFN( eDbgLevelError, "Adjusted heap allocation from %d to %d\n", Size, Size+0x1000); Size += 0x1000; }
return ORIGINAL_API(RtlAllocateHeap)(HeapHandle, Flags, Size); }
/*++
Make the buffer read/write.
--*/
MMRESULT APIHOOK(mmioSetInfo)( HMMIO hmmio, LPMMIOINFO lpmmioinfo, UINT wFlags ) { //
// BUGBUG: Not needed on XP, but still required on Win2k
// This fix causes sound to skip, see #304678.
//
// Win2k used to check if the buffer could be written to, instead of just
// read. We fixed this on XP. However, it's not enough to just copy the
// buffer, because it's used later.
// Not clear what the actual fix is though.
//
/*
HPSTR p = NULL;
if (lpmmioinfo && lpmmioinfo->pchBuffer && (IsBadWritePtr(lpmmioinfo->pchBuffer, lpmmioinfo->cchBuffer) && !IsBadReadPtr(lpmmioinfo->pchBuffer, lpmmioinfo->cchBuffer))) { p = (HPSTR) malloc(lpmmioinfo->cchBuffer); if (p) { DPFN( eDbgLevelError, "Fixing mmioSetInfo buffer"); MoveMemory(p, lpmmioinfo->pchBuffer, lpmmioinfo->cchBuffer); lpmmioinfo->pchBuffer = p; } }
MMRESULT mRet = ORIGINAL_API(mmioSetInfo)(hmmio, lpmmioinfo, wFlags);
if (p) { free(p); }
return mRet; */
return ORIGINAL_API(mmioSetInfo)(hmmio, lpmmioinfo, wFlags); } /*++
Register hooked functions
--*/
HOOK_BEGIN
APIHOOK_ENTRY(KERNEL32.DLL, GetFileSize) APIHOOK_ENTRY(NTDLL.DLL, RtlAllocateHeap) APIHOOK_ENTRY(WINMM.DLL, mmioSetInfo)
HOOK_END
IMPLEMENT_SHIM_END
|