1 /* 2 * PROJECT: ReactOS API tests 3 * LICENSE: GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later) 4 * PURPOSE: Tests for the NtSetInformationProcess API 5 * COPYRIGHT: Copyright 2020 George Bișoc <george.bisoc@reactos.org> 6 */ 7 8 #include "precomp.h" 9 #include <internal/ps_i.h> 10 11 static 12 void 13 Test_ProcBasePriorityClass(void) 14 { 15 NTSTATUS Status; 16 17 /* 18 * Assign a priority of HIGH_PRIORITY (see pstypes.h). 19 * The function will fail with a status of STATUS_PRIVILEGE_NOT_HELD 20 * as the process who executed the caller doesn't have the requested 21 * privileges to perform the operation. 22 */ 23 KPRIORITY BasePriority = HIGH_PRIORITY; 24 25 /* Everything is NULL */ 26 Status = NtSetInformationProcess(NULL, 27 ProcessBasePriority, 28 NULL, 29 0); 30 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 31 32 /* Set the base priority to an invalid process handle */ 33 Status = NtSetInformationProcess(NULL, 34 ProcessBasePriority, 35 &BasePriority, 36 sizeof(KPRIORITY)); 37 ok_hex(Status, STATUS_INVALID_HANDLE); 38 39 /* Don't input anything to the caller but the length information is valid */ 40 Status = NtSetInformationProcess(NtCurrentProcess(), 41 ProcessBasePriority, 42 NULL, 43 sizeof(KPRIORITY)); 44 ok_hex(Status, STATUS_ACCESS_VIOLATION); 45 46 /* Give the base priority input to the caller but length is invalid */ 47 Status = NtSetInformationProcess(NtCurrentProcess(), 48 ProcessBasePriority, 49 &BasePriority, 50 0); 51 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 52 53 /* The input buffer is misaligned and length information invalid */ 54 Status = NtSetInformationProcess(NtCurrentProcess(), 55 ProcessBasePriority, 56 (PVOID)1, 57 0); 58 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 59 60 /* The input buffer is misaligned */ 61 Status = NtSetInformationProcess(NtCurrentProcess(), 62 ProcessBasePriority, 63 (PVOID)1, 64 sizeof(KPRIORITY)); 65 ok_hex(Status, STATUS_DATATYPE_MISALIGNMENT); 66 67 /* The input buffer is misaligned (try with an alignment of 2) */ 68 Status = NtSetInformationProcess(NtCurrentProcess(), 69 ProcessBasePriority, 70 (PVOID)2, 71 sizeof(KPRIORITY)); 72 ok_hex(Status, STATUS_DATATYPE_MISALIGNMENT); 73 74 /* Set the base priority but we have lack privileges to do so */ 75 Status = NtSetInformationProcess(NtCurrentProcess(), 76 ProcessBasePriority, 77 &BasePriority, 78 sizeof(KPRIORITY)); 79 ok_hex(Status, STATUS_PRIVILEGE_NOT_HELD); 80 81 /* 82 * Assign a random priority value this time and 83 * set the base priority to the current process. 84 */ 85 BasePriority = 8; 86 Status = NtSetInformationProcess(NtCurrentProcess(), 87 ProcessBasePriority, 88 &BasePriority, 89 sizeof(KPRIORITY)); 90 ok_hex(Status, STATUS_SUCCESS); 91 } 92 93 static 94 void 95 Test_ProcRaisePriorityClass(void) 96 { 97 NTSTATUS Status; 98 99 /* Raise the priority as much as possible */ 100 ULONG RaisePriority = MAXIMUM_PRIORITY; 101 102 /* Everything is NULL */ 103 Status = NtSetInformationProcess(NULL, 104 ProcessRaisePriority, 105 NULL, 106 0); 107 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 108 109 /* A invalid handle to process is given */ 110 Status = NtSetInformationProcess(NULL, 111 ProcessRaisePriority, 112 &RaisePriority, 113 sizeof(ULONG)); 114 ok_hex(Status, STATUS_INVALID_HANDLE); 115 116 /* The input buffer is misaligned and length information invalid */ 117 Status = NtSetInformationProcess(NtCurrentProcess(), 118 ProcessRaisePriority, 119 (PVOID)1, 120 0); 121 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 122 123 /* A NULL buffer has been accessed */ 124 Status = NtSetInformationProcess(NtCurrentProcess(), 125 ProcessRaisePriority, 126 NULL, 127 sizeof(ULONG)); 128 ok_hex(Status, STATUS_ACCESS_VIOLATION); 129 130 /* The input buffer is misaligned */ 131 Status = NtSetInformationProcess(NtCurrentProcess(), 132 ProcessRaisePriority, 133 (PVOID)1, 134 sizeof(ULONG)); 135 ok_hex(Status, STATUS_DATATYPE_MISALIGNMENT); 136 137 /* The input buffer is misaligned -- try with an alignment size of 2 */ 138 Status = NtSetInformationProcess(NtCurrentProcess(), 139 ProcessRaisePriority, 140 (PVOID)2, 141 sizeof(ULONG)); 142 ok_hex(Status, STATUS_DATATYPE_MISALIGNMENT); 143 144 /* Raise the priority of the given current process */ 145 Status = NtSetInformationProcess(NtCurrentProcess(), 146 ProcessRaisePriority, 147 &RaisePriority, 148 sizeof(ULONG)); 149 ok_hex(Status, STATUS_SUCCESS); 150 } 151 152 static 153 void 154 Test_ProcForegroundBackgroundClass(void) 155 { 156 NTSTATUS Status; 157 PPROCESS_FOREGROUND_BACKGROUND ProcForeground; 158 159 ProcForeground = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(PROCESS_FOREGROUND_BACKGROUND)); 160 if (ProcForeground == NULL) 161 { 162 skip("Failed to allocate memory block from heap for PROCESS_FOREGROUND_BACKGROUND!\n"); 163 return; 164 } 165 166 /* As a test, set the foreground of the retrieved current process to FALSE */ 167 ProcForeground->Foreground = FALSE; 168 169 /* Set everything NULL for the caller */ 170 Status = NtSetInformationProcess(NULL, 171 ProcessForegroundInformation, 172 NULL, 173 0); 174 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 175 176 /* Give an invalid process handle (but the input buffer and length are correct) */ 177 Status = NtSetInformationProcess(NULL, 178 ProcessForegroundInformation, 179 ProcForeground, 180 sizeof(PROCESS_FOREGROUND_BACKGROUND)); 181 ok_hex(Status, STATUS_INVALID_HANDLE); 182 183 /* Give a buffer data to the argument input as NULL */ 184 Status = NtSetInformationProcess(NtCurrentProcess(), 185 ProcessForegroundInformation, 186 NULL, 187 sizeof(PROCESS_FOREGROUND_BACKGROUND)); 188 ok_hex(Status, STATUS_ACCESS_VIOLATION); 189 190 /* Set the information process foreground with an incorrect buffer alignment and zero buffer length */ 191 Status = NtSetInformationProcess(NtCurrentProcess(), 192 ProcessForegroundInformation, 193 (PVOID)1, 194 0); 195 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 196 197 /* 198 * Set the information process foreground with an incorrect buffer alignment but correct size length. 199 * The function will return STATUS_ACCESS_VIOLATION as the alignment probe requirement is not performed 200 * in this class. 201 */ 202 Status = NtSetInformationProcess(NtCurrentProcess(), 203 ProcessForegroundInformation, 204 (PVOID)1, 205 sizeof(PROCESS_FOREGROUND_BACKGROUND)); 206 ok_hex(Status, STATUS_ACCESS_VIOLATION); 207 208 /* Set the foreground information to the current given process, we must expect the function should succeed */ 209 Status = NtSetInformationProcess(NtCurrentProcess(), 210 ProcessForegroundInformation, 211 ProcForeground, 212 sizeof(PROCESS_FOREGROUND_BACKGROUND)); 213 ok_hex(Status, STATUS_SUCCESS); 214 215 /* Clear all the stuff */ 216 HeapFree(GetProcessHeap(), 0, ProcForeground); 217 } 218 219 static 220 void 221 Test_ProcessWx86InformationClass(void) 222 { 223 NTSTATUS Status; 224 ULONG VdmPower = 1; 225 226 /* Everything is NULL */ 227 Status = NtSetInformationProcess(NULL, 228 ProcessWx86Information, 229 NULL, 230 0); 231 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 232 233 /* Don't set anything to the process */ 234 Status = NtSetInformationProcess(NtCurrentProcess(), 235 ProcessWx86Information, 236 NULL, 237 sizeof(VdmPower)); 238 ok_hex(Status, STATUS_ACCESS_VIOLATION); 239 240 /* The buffer is misaligned and information length is wrong */ 241 Status = NtSetInformationProcess(NtCurrentProcess(), 242 ProcessWx86Information, 243 (PVOID)1, 244 0); 245 ok_hex(Status, STATUS_INFO_LENGTH_MISMATCH); 246 247 /* The buffer is misaligned */ 248 Status = NtSetInformationProcess(NtCurrentProcess(), 249 ProcessWx86Information, 250 (PVOID)1, 251 sizeof(VdmPower)); 252 ok_hex(Status, STATUS_DATATYPE_MISALIGNMENT); 253 254 /* The buffer is misaligned -- try with an alignment size of 2 */ 255 Status = NtSetInformationProcess(NtCurrentProcess(), 256 ProcessWx86Information, 257 (PVOID)2, 258 sizeof(VdmPower)); 259 ok_hex(Status, STATUS_DATATYPE_MISALIGNMENT); 260 261 /* We do not have privileges to set the VDM power */ 262 Status = NtSetInformationProcess(NtCurrentProcess(), 263 ProcessWx86Information, 264 &VdmPower, 265 sizeof(VdmPower)); 266 ok_hex(Status, STATUS_PRIVILEGE_NOT_HELD); 267 } 268 269 static 270 void 271 Test_ProcSetAlignmentProbe(void) 272 { 273 ULONG InfoClass; 274 275 /* Iterate over the process info classes and begin the tests */ 276 for (InfoClass = 0; InfoClass < _countof(PsProcessInfoClass); InfoClass++) 277 { 278 /* The buffer is misaligned */ 279 QuerySetProcessValidator(SET, 280 InfoClass, 281 (PVOID)(ULONG_PTR)1, 282 PsProcessInfoClass[InfoClass].RequiredSizeSET, 283 STATUS_DATATYPE_MISALIGNMENT); 284 285 /* We set an invalid buffer address */ 286 QuerySetProcessValidator(SET, 287 InfoClass, 288 (PVOID)(ULONG_PTR)PsProcessInfoClass[InfoClass].AlignmentSET, 289 PsProcessInfoClass[InfoClass].RequiredSizeSET, 290 STATUS_ACCESS_VIOLATION); 291 292 /* The information length is wrong */ 293 QuerySetProcessValidator(SET, 294 InfoClass, 295 (PVOID)(ULONG_PTR)PsProcessInfoClass[InfoClass].AlignmentSET, 296 PsProcessInfoClass[InfoClass].RequiredSizeSET - 1, 297 STATUS_INFO_LENGTH_MISMATCH); 298 } 299 } 300 301 START_TEST(NtSetInformationProcess) 302 { 303 Test_ProcForegroundBackgroundClass(); 304 Test_ProcBasePriorityClass(); 305 Test_ProcRaisePriorityClass(); 306 Test_ProcessWx86InformationClass(); 307 Test_ProcSetAlignmentProbe(); 308 } 309