misc/libphysfs/lzma/CPP/Windows/MemoryLock.cpp
author nemo
Mon, 10 Apr 2017 12:06:43 -0400
changeset 12213 bb5522e88ab2
permissions -rw-r--r--
bulk copy of latest physfs to our misc/libphysfs since this seems to fix an off-by-1 error reliably hit in readln read of 1 byte probably introduced in the addition of the buffered read. Whether this is excessive or whether libphysfs should even be maintained by us is another matter. But at least we shouldn't crash

// Common/MemoryLock.cpp

#include "StdAfx.h"

namespace NWindows {
namespace NSecurity {

#ifndef _UNICODE
typedef BOOL (WINAPI * OpenProcessTokenP)(HANDLE ProcessHandle, DWORD DesiredAccess, PHANDLE TokenHandle);
typedef BOOL (WINAPI * LookupPrivilegeValueP)(LPCTSTR lpSystemName, LPCTSTR lpName, PLUID  lpLuid);
typedef BOOL (WINAPI * AdjustTokenPrivilegesP)(HANDLE TokenHandle, BOOL DisableAllPrivileges,
    PTOKEN_PRIVILEGES NewState, DWORD BufferLength, PTOKEN_PRIVILEGES PreviousState,PDWORD ReturnLength);
#endif

#ifdef _UNICODE
bool EnableLockMemoryPrivilege(
#else
static bool EnableLockMemoryPrivilege2(HMODULE hModule,
#endif
bool enable)
{
  #ifndef _UNICODE
  if (hModule == NULL)
    return false;
  OpenProcessTokenP openProcessToken = (OpenProcessTokenP)GetProcAddress(hModule, "OpenProcessToken");
  LookupPrivilegeValueP lookupPrivilegeValue = (LookupPrivilegeValueP)GetProcAddress(hModule, "LookupPrivilegeValueA" );
  AdjustTokenPrivilegesP adjustTokenPrivileges = (AdjustTokenPrivilegesP)GetProcAddress(hModule, "AdjustTokenPrivileges");
  if (openProcessToken == NULL || adjustTokenPrivileges == NULL || lookupPrivilegeValue == NULL)
    return false;
  #endif

  HANDLE token;
  if (!
    #ifdef _UNICODE
    ::OpenProcessToken
    #else
    openProcessToken
    #endif
    (::GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &token))
    return false;
  TOKEN_PRIVILEGES tp;
  bool res = false;
  if (
    #ifdef _UNICODE
    ::LookupPrivilegeValue
    #else
    lookupPrivilegeValue
    #endif
    (NULL, SE_LOCK_MEMORY_NAME, &(tp.Privileges[0].Luid)))
  {
    tp.PrivilegeCount = 1;
    tp.Privileges[0].Attributes = enable ? SE_PRIVILEGE_ENABLED: 0;
    if (
      #ifdef _UNICODE
      ::AdjustTokenPrivileges
      #else
      adjustTokenPrivileges
      #endif
      (token, FALSE, &tp, 0, NULL, NULL))
      res = (GetLastError() == ERROR_SUCCESS);
  }
  ::CloseHandle(token);
  return res;
}

#ifndef _UNICODE
bool EnableLockMemoryPrivilege(bool enable)
{
  HMODULE hModule = LoadLibrary(TEXT("Advapi32.dll"));
  if(hModule == NULL)
    return false;
  bool res = EnableLockMemoryPrivilege2(hModule, enable);
  ::FreeLibrary(hModule);
  return res;
}
#endif

}}