• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Windows/MemoryLock.cpp
2 
3 #include "StdAfx.h"
4 
5 #include "../../C/CpuArch.h"
6 
7 #include "MemoryLock.h"
8 
9 namespace NWindows {
10 namespace NSecurity {
11 
12 #ifndef UNDER_CE
13 
14 #ifdef _UNICODE
15 #define MY_FUNC_SELECT(f) :: f
16 #else
17 #define MY_FUNC_SELECT(f) my_ ## f
18 extern "C" {
19 typedef BOOL (WINAPI * Func_OpenProcessToken)(HANDLE ProcessHandle, DWORD DesiredAccess, PHANDLE TokenHandle);
20 typedef BOOL (WINAPI * Func_LookupPrivilegeValue)(LPCTSTR lpSystemName, LPCTSTR lpName, PLUID lpLuid);
21 typedef BOOL (WINAPI * Func_AdjustTokenPrivileges)(HANDLE TokenHandle, BOOL DisableAllPrivileges,
22     PTOKEN_PRIVILEGES NewState, DWORD BufferLength, PTOKEN_PRIVILEGES PreviousState, PDWORD ReturnLength);
23 }
24 #define GET_PROC_ADDR(fff, name) Func_ ## fff  my_ ## fff  = (Func_ ## fff)GetProcAddress(hModule, name)
25 #endif
26 
EnablePrivilege(LPCTSTR privilegeName,bool enable)27 bool EnablePrivilege(LPCTSTR privilegeName, bool enable)
28 {
29   bool res = false;
30 
31   #ifndef _UNICODE
32 
33   HMODULE hModule = ::LoadLibrary(TEXT("Advapi32.dll"));
34   if (hModule == NULL)
35     return false;
36 
37   GET_PROC_ADDR(OpenProcessToken, "OpenProcessToken");
38   GET_PROC_ADDR(LookupPrivilegeValue, "LookupPrivilegeValueA");
39   GET_PROC_ADDR(AdjustTokenPrivileges, "AdjustTokenPrivileges");
40 
41   if (my_OpenProcessToken &&
42       my_AdjustTokenPrivileges &&
43       my_LookupPrivilegeValue)
44 
45   #endif
46 
47   {
48     HANDLE token;
49     if (MY_FUNC_SELECT(OpenProcessToken)(::GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &token))
50     {
51       TOKEN_PRIVILEGES tp;
52       if (MY_FUNC_SELECT(LookupPrivilegeValue)(NULL, privilegeName, &(tp.Privileges[0].Luid)))
53       {
54         tp.PrivilegeCount = 1;
55         tp.Privileges[0].Attributes = (enable ? SE_PRIVILEGE_ENABLED : 0);
56         if (MY_FUNC_SELECT(AdjustTokenPrivileges)(token, FALSE, &tp, 0, NULL, NULL))
57           res = (GetLastError() == ERROR_SUCCESS);
58       }
59       ::CloseHandle(token);
60     }
61   }
62 
63   #ifndef _UNICODE
64 
65   ::FreeLibrary(hModule);
66 
67   #endif
68 
69   return res;
70 }
71 
72 
73 
74 typedef void (WINAPI * Func_RtlGetVersion) (OSVERSIONINFOEXW *);
75 
76 /*
77   We suppose that Window 10 works incorrectly with "Large Pages" at:
78     - Windows 10 1703 (15063)
79     - Windows 10 1709 (16299)
80 
81     - Windows 10 1809 (17763) on some CPUs that have no 1 GB page support.
82          We need more information about that new BUG in Windows.
83 */
84 
Get_LargePages_RiskLevel()85 unsigned Get_LargePages_RiskLevel()
86 {
87   OSVERSIONINFOEXW vi;
88   HMODULE ntdll = ::GetModuleHandleW(L"ntdll.dll");
89   if (!ntdll)
90     return 0;
91   Func_RtlGetVersion func = (Func_RtlGetVersion)GetProcAddress(ntdll, "RtlGetVersion");
92   if (!func)
93     return 0;
94   func(&vi);
95   if (vi.dwPlatformId != VER_PLATFORM_WIN32_NT)
96     return 0;
97   if (vi.dwMajorVersion + vi.dwMinorVersion != 10)
98     return 0;
99   if (vi.dwBuildNumber <= 16299)
100     return 1;
101 
102   #ifdef MY_CPU_X86_OR_AMD64
103   if (!CPU_IsSupported_PageGB())
104     return 1;
105   #endif
106 
107   return 0;
108 }
109 
110 #endif
111 
112 }}
113