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 NtQueryOpenSubKeys API 5 * COPYRIGHT: Copyright 2023 George Bișoc <george.bisoc@reactos.org> 6 */ 7 8 #include "precomp.h" 9 10 START_TEST(NtQueryOpenSubKeys) 11 { 12 NTSTATUS Status; 13 OBJECT_ATTRIBUTES ObjectAttributes; 14 ULONG Subkeys; 15 UNICODE_STRING RegistryKey = RTL_CONSTANT_STRING(L"\\Registry"); 16 UNICODE_STRING SystemKey = RTL_CONSTANT_STRING(L"\\Registry\\Machine\\SYSTEM"); 17 UNICODE_STRING SoftwareKey = RTL_CONSTANT_STRING(L"\\Registry\\Machine\\SOFTWARE"); 18 UNICODE_STRING DefaultUserKey = RTL_CONSTANT_STRING(L"\\Registry\\User\\.DEFAULT"); 19 20 /* We give no object attributes and no return variable */ 21 Status = NtQueryOpenSubKeys(NULL, NULL); 22 ok_ntstatus(Status, STATUS_ACCESS_VIOLATION); 23 24 /* Build a key path to the main registry tree */ 25 InitializeObjectAttributes(&ObjectAttributes, 26 &RegistryKey, 27 OBJ_CASE_INSENSITIVE, 28 NULL, 29 NULL); 30 31 /* We give object attributes but no return variable */ 32 Status = NtQueryOpenSubKeys(&ObjectAttributes, NULL); 33 ok_ntstatus(Status, STATUS_ACCESS_VIOLATION); 34 35 /* 36 * We give no object attributes but return variable. 37 * 38 * NOTE: Windows 10 and Server 2003 return different kinds of status 39 * codes. In Server 2003 it returns STATUS_ACCESS_VIOLATION because 40 * this function implements more probe checks against the object 41 * attributes parameter (namely the path name of the object) so it 42 * fails earlier. In Windows 10 instead the function only probes the 43 * memory address of the object attributes so that it resides in the boundary 44 * of the UM memory range so the function lets this NULL parameter 45 * slide through until ObOpenObjectByName hits this parameter as being 46 * NULL and returns STATUS_INVALID_PARAMETER. Currently ReactOS follows 47 * the behavior of Windows 10. 48 */ 49 Status = NtQueryOpenSubKeys(NULL, &Subkeys); 50 ok(Status == STATUS_ACCESS_VIOLATION || Status == STATUS_INVALID_PARAMETER, 51 "STATUS_ACCESS_VIOLATION or STATUS_INVALID_PARAMETER expected, got 0x%lx\n", Status); 52 53 /* Garbage return variable, this function doesn't check for alignment */ 54 Status = NtQueryOpenSubKeys(&ObjectAttributes, (PVOID)1); 55 ok_ntstatus(Status, STATUS_ACCESS_VIOLATION); 56 57 /* Return the open subkeys of this key now */ 58 Status = NtQueryOpenSubKeys(&ObjectAttributes, &Subkeys); 59 ok_ntstatus(Status, STATUS_SUCCESS); 60 61 trace("\\Registry has %lu opened subkeys\n", Subkeys); 62 63 /* Build a key path to the SYSTEM key */ 64 InitializeObjectAttributes(&ObjectAttributes, 65 &SystemKey, 66 OBJ_CASE_INSENSITIVE, 67 NULL, 68 NULL); 69 70 /* Return the open subkeys of this key now */ 71 Status = NtQueryOpenSubKeys(&ObjectAttributes, &Subkeys); 72 ok_ntstatus(Status, STATUS_SUCCESS); 73 74 trace("\\Registry\\Machine\\SYSTEM has %lu opened subkeys\n", Subkeys); 75 76 /* Build a key path to the SYSTEM key */ 77 InitializeObjectAttributes(&ObjectAttributes, 78 &SoftwareKey, 79 OBJ_CASE_INSENSITIVE, 80 NULL, 81 NULL); 82 83 /* Return the open subkeys of this key now */ 84 Status = NtQueryOpenSubKeys(&ObjectAttributes, &Subkeys); 85 ok_ntstatus(Status, STATUS_SUCCESS); 86 87 trace("\\Registry\\Machine\\SOFTWARE has %lu opened subkeys\n", Subkeys); 88 89 /* Build a key path to the default user key */ 90 InitializeObjectAttributes(&ObjectAttributes, 91 &DefaultUserKey, 92 OBJ_CASE_INSENSITIVE, 93 NULL, 94 NULL); 95 96 /* Return the open subkeys of this key now */ 97 Status = NtQueryOpenSubKeys(&ObjectAttributes, &Subkeys); 98 ok_ntstatus(Status, STATUS_SUCCESS); 99 100 trace("\\Registry\\User\\.DEFAULT has %lu opened subkeys\n", Subkeys); 101 } 102