[APPHELP_APITEST] Remove some code duplication.
[reactos.git] / rostests / apitests / apphelp / layerapi.c
1 /*
2 * Copyright 2015,2016 Mark Jansen
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
17 */
18
19 #include <ntstatus.h>
20 #define WIN32_NO_STATUS
21 #include <windows.h>
22 #include <shlwapi.h>
23 #include <winnt.h>
24 #ifdef __REACTOS__
25 #include <ntndk.h>
26 #else
27 #include <winternl.h>
28 #endif
29 #include <winerror.h>
30 #include <stdio.h>
31
32 #include "wine/test.h"
33
34 /* data.c */
35 DWORD get_host_winver();
36
37 #define GPLK_USER 1
38 #define GPLK_MACHINE 2
39 #define MAX_LAYER_LENGTH 256
40 #define LAYER_APPLY_TO_SYSTEM_EXES 1
41
42
43 static HMODULE hdll;
44 static BOOL(WINAPI *pAllowPermLayer)(PCWSTR path);
45 static BOOL(WINAPI *pSdbSetPermLayerKeys)(PCWSTR wszPath, PCWSTR wszLayers, BOOL bMachine);
46 static BOOL(WINAPI *pSdbGetPermLayerKeys)(PCWSTR wszPath, PWSTR pwszLayers, PDWORD pdwBytes, DWORD dwFlags);
47 static BOOL(WINAPI *pSetPermLayerState)(PCWSTR wszPath, PCWSTR wszLayer, DWORD dwFlags, BOOL bMachine, BOOL bEnable);
48
49
50 static DWORD g_WinVersion;
51 #define WINVER_VISTA 0x0600
52 #define WINVER_WIN8 0x0602
53 #define WINVER_WIN10 0x1000
54
55
56 /* Helper function to disable Wow64 redirection on an os that reports it being enabled. */
57 static DWORD g_QueryFlag = 0xffffffff;
58 static DWORD QueryFlag(void)
59 {
60 if (g_QueryFlag == 0xffffffff)
61 {
62 ULONG_PTR wow64_ptr = 0;
63 NTSTATUS status = NtQueryInformationProcess(NtCurrentProcess(), ProcessWow64Information, &wow64_ptr, sizeof(wow64_ptr), NULL);
64 g_QueryFlag = (NT_SUCCESS(status) && wow64_ptr != 0) ? KEY_WOW64_64KEY : 0;
65 }
66 return g_QueryFlag;
67 }
68
69 /* Helper function to prepare the registry key with a value. */
70 static BOOL setLayerValue(BOOL bMachine, const char* valueName, const char* value)
71 {
72 HKEY key = NULL;
73 LSTATUS lstatus = RegCreateKeyExA(bMachine ? HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER,
74 "Software\\Microsoft\\Windows NT\\CurrentVersion\\AppCompatFlags\\Layers", 0, NULL, 0, QueryFlag() | KEY_SET_VALUE, NULL, &key, NULL);
75 if (lstatus == ERROR_SUCCESS)
76 {
77 if (value)
78 lstatus = RegSetValueExA(key, valueName, 0, REG_SZ, (const BYTE*)value, strlen(value)+1);
79 else
80 {
81 lstatus = RegDeleteValueA(key, valueName);
82 lstatus = (lstatus == ERROR_FILE_NOT_FOUND ? ERROR_SUCCESS : lstatus);
83 }
84 RegCloseKey(key);
85 }
86 return lstatus == ERROR_SUCCESS;
87 }
88
89
90 static void expect_LayerValue_imp(BOOL bMachine, const char* valueName, const char* value)
91 {
92 HKEY key = NULL;
93 LSTATUS lstatus = RegCreateKeyExA(bMachine ? HKEY_LOCAL_MACHINE : HKEY_CURRENT_USER,
94 "Software\\Microsoft\\Windows NT\\CurrentVersion\\AppCompatFlags\\Layers", 0, NULL, 0, QueryFlag() | KEY_QUERY_VALUE, NULL, &key, NULL);
95 winetest_ok(lstatus == ERROR_SUCCESS, "Expected to be able to open a registry key\n");
96 if (lstatus == ERROR_SUCCESS)
97 {
98 char data[512] = { 0 };
99 DWORD dwType = 0;
100 DWORD dwDataLen = sizeof(data);
101 lstatus = RegQueryValueExA(key, valueName, NULL, &dwType, (LPBYTE)data, &dwDataLen);
102 if (value)
103 {
104 winetest_ok(lstatus == ERROR_SUCCESS, "Expected to get a valid value, err: %u\n", lstatus);
105 if (lstatus == ERROR_SUCCESS)
106 {
107 winetest_ok(dwType == REG_SZ, "Expected the type to be REG_SZ, was: %u\n", dwType);
108 winetest_ok(!strcmp(data, value), "Expected the data to be: '%s', was: '%s'\n", value, data);
109 }
110 }
111 else
112 {
113 winetest_ok(lstatus == ERROR_FILE_NOT_FOUND, "Expected not to find the value %s\n", valueName);
114 }
115 RegCloseKey(key);
116 }
117 }
118
119 static void expect_LayerValue_imp2(BOOL bMachine, const char* valueName, const char* value, int use_alt, const char* alt_value)
120 {
121 expect_LayerValue_imp(bMachine, valueName, use_alt ? alt_value : value);
122 }
123
124
125 void expect_Sdb_imp(PCSTR path, DWORD type, BOOL result, DWORD lenResult, PCSTR stringResult)
126 {
127 WCHAR pathW[MAX_PATH], buffer[MAX_LAYER_LENGTH] = { 0 };
128 char resultBuffer[MAX_LAYER_LENGTH] = { 0 };
129 DWORD dwBufSize = sizeof(buffer);
130
131 /* In case of a failure, the buffer size is sometimes set to 0, and sometimes not touched,
132 depending on the version. Either case is fine, since the function returns FALSE anyway. */
133
134 MultiByteToWideChar(CP_ACP, 0, path, -1, pathW, MAX_PATH);
135
136 winetest_ok(pSdbGetPermLayerKeys(pathW, buffer, &dwBufSize, type) == result, "Expected pSdbGetPermLayerKeys to %s\n", (result ? "succeed" : "fail"));
137 if (!result && lenResult == 0xffffffff)
138 winetest_ok(dwBufSize == 0 || dwBufSize == sizeof(buffer), "Expected dwBufSize to be 0 or %u, was %u\n", sizeof(buffer), dwBufSize);
139 else
140 winetest_ok(dwBufSize == lenResult ||
141 /* W2k3 is off by 2 when concatenating user / machine */
142 broken(g_WinVersion < WINVER_VISTA && type == (GPLK_MACHINE|GPLK_USER) && (lenResult + 2) == dwBufSize),
143 "Expected dwBufSize to be %u, was %u\n", lenResult, dwBufSize);
144 if (result)
145 {
146 winetest_ok(lstrlenW(buffer) * sizeof(WCHAR) + sizeof(WCHAR) == lenResult, "Expected lstrlenW(buffer)*2+2 to be %u, was %u\n",
147 lenResult, lstrlenW(buffer) * sizeof(WCHAR) + sizeof(WCHAR));
148 }
149 WideCharToMultiByte(CP_ACP, 0, buffer, -1, resultBuffer, sizeof(resultBuffer), NULL, NULL);
150 winetest_ok(!strcmp(stringResult, resultBuffer), "Expected the result to be '%s', was '%s'\n", stringResult, resultBuffer);
151 }
152
153
154 /* In case of a failure, let the location be from where the function was invoked, not inside the function itself. */
155 #define expect_Sdb (winetest_set_location(__FILE__, __LINE__), 0) ? (void)0 : expect_Sdb_imp
156 #define expect_LayerValue (winetest_set_location(__FILE__, __LINE__), 0) ? (void)0 : expect_LayerValue_imp
157 #define expect_LayerValue2 (winetest_set_location(__FILE__, __LINE__), 0) ? (void)0 : expect_LayerValue_imp2
158
159
160 BOOL wrapAllowPermLayer(const char* str)
161 {
162 WCHAR buf[100];
163 MultiByteToWideChar(CP_ACP, 0, str, -1, buf, 100);
164 return pAllowPermLayer(buf);
165 }
166
167 /* Brute forcing all ascii chars in the first 2 places seems to indicate that all it cares for is:
168 - Second char has to be a ':'
169 if it's not a ':', display a diagnostic message (and a different one for '\\').
170 - First char does not really matter, as long as it's not on a DRIVE_REMOTE (but, according to the logging this is meant to check for a CDROM drive...)
171 */
172 static void test_AllowPermLayer(void)
173 {
174 char buf[20];
175 char drive_letter;
176 UINT drivetype = 0;
177 ok(pAllowPermLayer(NULL) == FALSE, "Expected AllowPermLayer to fail for NULL\n");
178 if (g_WinVersion < WINVER_WIN8)
179 {
180 ok(wrapAllowPermLayer("-:"), "Expected AllowPermLayer to succeed\n");
181 ok(wrapAllowPermLayer("@:"), "Expected AllowPermLayer to succeed\n");
182 ok(wrapAllowPermLayer("4:"), "Expected AllowPermLayer to succeed\n");
183 ok(wrapAllowPermLayer("*:"), "Expected AllowPermLayer to succeed\n");
184 }
185 ok(wrapAllowPermLayer("*a") == FALSE, "Expected AllowPermLayer to fail\n");
186 ok(wrapAllowPermLayer("*\\") == FALSE, "Expected AllowPermLayer to fail\n");
187 for (drive_letter = 'a'; drive_letter <= 'z'; ++drive_letter)
188 {
189 sprintf(buf, "%c:\\", drive_letter);
190 drivetype = GetDriveTypeA(buf);
191 ok(wrapAllowPermLayer(buf) == (drivetype != DRIVE_REMOTE), "Expected AllowPermLayer to be %d for %c:\\\n", (drivetype != DRIVE_REMOTE), drive_letter);
192 }
193 }
194
195 static BOOL wrapSdbSetPermLayerKeys(PCWSTR wszPath, PCSTR szLayers, BOOL bMachine)
196 {
197 WCHAR wszLayers[MAX_LAYER_LENGTH];
198 MultiByteToWideChar(CP_ACP, 0, szLayers, -1, wszLayers, MAX_LAYER_LENGTH);
199 return pSdbSetPermLayerKeys(wszPath, wszLayers, bMachine);
200 }
201
202 static void test_SdbSetPermLayerKeysLevel(BOOL bMachine, const char* file)
203 {
204 WCHAR fileW[MAX_PATH+20];
205 WCHAR emptyString[1] = { 0 };
206
207 MultiByteToWideChar(CP_ACP, 0, file, -1, fileW, MAX_PATH+20);
208
209 /* Test some parameter validation. */
210 ok(pSdbSetPermLayerKeys(NULL, NULL, bMachine) == FALSE, "Expected SdbSetPermLayerKeys to fail\n");
211 ok(pSdbSetPermLayerKeys(NULL, emptyString, bMachine) == FALSE, "Expected SdbSetPermLayerKeys to fail\n");
212 ok(pSdbSetPermLayerKeys(emptyString, emptyString, bMachine) == FALSE, "Expected SdbSetPermLayerKeys to fail\n");
213 ok(pSdbSetPermLayerKeys(fileW, NULL, bMachine) == TRUE, "Expected SdbSetPermLayerKeys to succeed\n");
214 ok(pSdbSetPermLayerKeys(fileW, emptyString, bMachine) == TRUE, "Expected SdbSetPermLayerKeys to fail\n");
215
216 /* Basic tests */
217 ok(wrapSdbSetPermLayerKeys(fileW, "TEST1", bMachine), "Expected SdbSetPermLayerKeys to succeed\n");
218 expect_LayerValue(bMachine, file, "TEST1");
219
220 ok(wrapSdbSetPermLayerKeys(fileW, "TEST1 TEST2", bMachine), "Expected SdbSetPermLayerKeys to succeed\n");
221 expect_LayerValue(bMachine, file, "TEST1 TEST2");
222
223 /* SdbSetPermLayerKeys does not do any validation of the value passed in. */
224 ok(wrapSdbSetPermLayerKeys(fileW, "!#$% TEST1 TEST2", bMachine), "Expected SdbSetPermLayerKeys to succeed\n");
225 expect_LayerValue(bMachine, file, "!#$% TEST1 TEST2");
226
227 ok(wrapSdbSetPermLayerKeys(fileW, "!#$% TEST1 TEST2", bMachine), "Expected SdbSetPermLayerKeys to succeed\n");
228 expect_LayerValue(bMachine, file, "!#$% TEST1 TEST2");
229
230 ok(pSdbSetPermLayerKeys(fileW, NULL, bMachine) == TRUE, "Expected SdbSetPermLayerKeys to succeed\n");
231 expect_LayerValue(bMachine, file, NULL);
232
233 ok(wrapSdbSetPermLayerKeys(fileW, " ", bMachine), "Expected SdbSetPermLayerKeys to succeed\n");
234 expect_LayerValue(bMachine, file, " ");
235
236 ok(pSdbSetPermLayerKeys(fileW, NULL, bMachine) == TRUE, "Expected SdbSetPermLayerKeys to fail\n");
237 expect_LayerValue(bMachine, file, NULL);
238 }
239
240 static void test_SdbGetPermLayerKeys(void)
241 {
242 WCHAR pathW[MAX_PATH], buffer[MAX_LAYER_LENGTH] = { 0 };
243 char file[MAX_PATH + 20], tmp[MAX_PATH + 20];
244 BOOL bUser, bMachine;
245 HANDLE hfile;
246 DWORD dwBufSize = sizeof(buffer);
247
248 GetTempPathA(MAX_PATH, tmp);
249 GetLongPathNameA(tmp, file, sizeof(file));
250 PathCombineA(tmp, file, "notexist.exe");
251 PathAppendA(file, "test_file.exe");
252
253 /* Check that we can access the keys */
254 bUser = setLayerValue(FALSE, file, "RUNASADMIN WINXPSP3");
255 expect_LayerValue(FALSE, file, "RUNASADMIN WINXPSP3");
256 ok(bUser, "Expected to be able to set atleast the flags for the user\n");
257 if (!bUser)
258 {
259 skip("Cannot do any tests if I cannot set some values\n");
260 return;
261 }
262 bMachine = setLayerValue(TRUE, file, "WINXPSP3 WINXPSP2");
263 if (bMachine)
264 {
265 expect_LayerValue(TRUE, file, "WINXPSP3 WINXPSP2");
266 }
267
268
269 hfile = CreateFileA(file, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
270 ok(hfile != INVALID_HANDLE_VALUE, "CreateFile failed on '%s'..\n", file);
271 if (hfile == INVALID_HANDLE_VALUE)
272 {
273 skip("Running these tests is useless without a file present\n");
274 return;
275 }
276 CloseHandle(hfile);
277
278 MultiByteToWideChar(CP_ACP, 0, file, -1, pathW, MAX_PATH);
279
280 /* Parameter validation */
281 ok(pSdbGetPermLayerKeys(NULL, NULL, NULL, 0) == FALSE, "Expected pSdbGetPermLayerKeys to fail\n");
282 ok(pSdbGetPermLayerKeys(pathW, NULL, NULL, 0) == FALSE, "Expected pSdbGetPermLayerKeys to fail\n");
283 ok(pSdbGetPermLayerKeys(pathW, buffer, NULL, 0) == FALSE, "Expected pSdbGetPermLayerKeys to fail\n");
284 ok(pSdbGetPermLayerKeys(pathW, buffer, &dwBufSize, 0) == FALSE, "Expected pSdbGetPermLayerKeys to fail\n");
285 ok(dwBufSize == 0, "Expected dwBufSize to be %u, was %u\n", 0, dwBufSize);
286
287 /* It fails on a nonexisting file */
288 expect_Sdb(tmp, GPLK_USER | GPLK_MACHINE, FALSE, 0xffffffff, "");
289 expect_Sdb(file, GPLK_USER, TRUE, 40, "RUNASADMIN WINXPSP3");
290 GetShortPathNameA(file, tmp, sizeof(tmp));
291 expect_Sdb(tmp, GPLK_USER, TRUE, 40, "RUNASADMIN WINXPSP3");
292
293 if (bMachine)
294 {
295 /* Query from HKLM */
296 expect_Sdb(file, GPLK_MACHINE, TRUE, 36, "WINXPSP3 WINXPSP2");
297 /* Query from both, showing that duplicates are not removed */
298 expect_Sdb(file, GPLK_USER | GPLK_MACHINE, TRUE, 76, "WINXPSP3 WINXPSP2 RUNASADMIN WINXPSP3");
299
300 /* Showing that no validation is done on the value read. */
301 ok(setLayerValue(TRUE, file, "!#!# WINXPSP3 WINXPSP3 !# WINXPSP2 "), "Expected setLayerValue not to fail\n");
302 expect_Sdb(file, GPLK_MACHINE, TRUE, 82, "!#!# WINXPSP3 WINXPSP3 !# WINXPSP2 ");
303 /* Showing that a space is inserted, even if the last char was already a space. */
304 expect_Sdb(file, GPLK_USER | GPLK_MACHINE, TRUE, 122, "!#!# WINXPSP3 WINXPSP3 !# WINXPSP2 RUNASADMIN WINXPSP3");
305 /* Now clear the user key */
306 setLayerValue(FALSE, file, NULL);
307 /* Request both, to show that the last space (from the key) is not cut off. */
308 expect_Sdb(file, GPLK_USER | GPLK_MACHINE, TRUE, 82, "!#!# WINXPSP3 WINXPSP3 !# WINXPSP2 ");
309 setLayerValue(FALSE, file, "RUNASADMIN WINXPSP3");
310 }
311 else
312 {
313 skip("Skipping tests for HKLM, cannot alter the registry\n");
314 }
315 /* Fail from these paths */
316 sprintf(tmp, "\\?\\%s", file);
317 expect_Sdb(tmp, GPLK_USER, FALSE, 0xffffffff, "");
318 sprintf(tmp, "\\??\\%s", file);
319 expect_Sdb(tmp, GPLK_USER, FALSE, 0xffffffff, "");
320
321 ok(setLayerValue(FALSE, file, "!#!# RUNASADMIN RUNASADMIN !# WINXPSP3 "), "Expected setLayerValue not to fail\n");
322 /* There is no validation on information read back. */
323 expect_Sdb(file, GPLK_USER, TRUE, 90, "!#!# RUNASADMIN RUNASADMIN !# WINXPSP3 ");
324
325
326 /* Cleanup */
327 ok(DeleteFileA(file), "DeleteFile failed....\n");
328 setLayerValue(FALSE, file, NULL);
329 setLayerValue(TRUE, file, NULL);
330 }
331
332
333 static BOOL wrapSetPermLayerState(PCWSTR wszPath, PCSTR szLayer, DWORD dwFlags, BOOL bMachine, BOOL bEnable)
334 {
335 WCHAR wszLayer[MAX_LAYER_LENGTH];
336 MultiByteToWideChar(CP_ACP, 0, szLayer, -1, wszLayer, MAX_LAYER_LENGTH);
337 return pSetPermLayerState(wszPath, wszLayer, dwFlags, bMachine, bEnable);
338 }
339
340 static void test_SetPermLayerStateLevel(BOOL bMachine, const char* file)
341 {
342 WCHAR fileW[MAX_PATH+20];
343 WCHAR emptyString[1] = { 0 };
344 DWORD dwFlag;
345
346 MultiByteToWideChar(CP_ACP, 0, file, -1, fileW, MAX_PATH+20);
347
348 /* Test some parameter validation. */
349 ok(pSetPermLayerState(fileW, NULL, 0, bMachine, 0) == FALSE, "Expected SetPermLayerState to fail\n");
350 expect_LayerValue(bMachine, file, NULL);
351
352 ok(pSetPermLayerState(fileW, NULL, 0, bMachine, 1) == FALSE, "Expected SetPermLayerState to fail\n");
353 expect_LayerValue(bMachine, file, NULL);
354
355 ok(wrapSetPermLayerState(fileW, "", 0, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
356 expect_LayerValue(bMachine, file, NULL);
357
358 ok(wrapSetPermLayerState(fileW, "", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
359 expect_LayerValue(bMachine, file, NULL);
360
361 ok(wrapSetPermLayerState(NULL, NULL, 0, bMachine, 0) == FALSE, "Expected SetPermLayerState to fail\n");
362 expect_LayerValue(bMachine, NULL, NULL);
363
364 ok(wrapSetPermLayerState(NULL, NULL, 0, bMachine, 1) == FALSE, "Expected SetPermLayerState to fail\n");
365 expect_LayerValue(bMachine, NULL, NULL);
366
367 ok(wrapSetPermLayerState(emptyString, "", 0, bMachine, 0) == FALSE, "Expected SetPermLayerState to fail\n");
368 expect_LayerValue(bMachine, NULL, NULL);
369
370 ok(wrapSetPermLayerState(emptyString, "", 0, bMachine, 1) == FALSE, "Expected SetPermLayerState to fail\n");
371 expect_LayerValue(bMachine, NULL, NULL);
372
373 ok(wrapSetPermLayerState(emptyString, "TEST", 0, bMachine, 0) == FALSE, "Expected SetPermLayerState to fail\n");
374 expect_LayerValue(bMachine, NULL, NULL);
375
376 if (g_WinVersion <= WINVER_WIN8)
377 {
378 ok(wrapSetPermLayerState(emptyString, "TEST", 0, bMachine, 1) == FALSE, "Expected SetPermLayerState to fail\n");
379 expect_LayerValue(bMachine, NULL, NULL);
380 }
381
382
383 /* Now, on to the actual tests. */
384 expect_LayerValue(bMachine, file, NULL);
385 ok(wrapSetPermLayerState(fileW, "TEST", 0, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
386 expect_LayerValue(bMachine, file, NULL);
387
388 ok(wrapSetPermLayerState(fileW, "TEST", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
389 expect_LayerValue(bMachine, file, "TEST");
390
391 ok(wrapSetPermLayerState(fileW, "", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
392 expect_LayerValue(bMachine, file, "TEST");
393
394 ok(wrapSetPermLayerState(fileW, "test", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
395 expect_LayerValue(bMachine, file, "test");
396
397 ok(wrapSetPermLayerState(fileW, "TEST", 0, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
398 expect_LayerValue(bMachine, file, NULL);
399
400 ok(wrapSetPermLayerState(fileW, "TEST", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
401 expect_LayerValue(bMachine, file, "TEST");
402
403 ok(wrapSetPermLayerState(fileW, "TEST1", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
404 expect_LayerValue2(bMachine, file, "TEST TEST1", g_WinVersion >= WINVER_WIN8, "TEST1 TEST");
405
406 ok(wrapSetPermLayerState(fileW, "TEST2", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
407 expect_LayerValue2(bMachine, file, "TEST TEST1 TEST2", g_WinVersion >= WINVER_WIN8, "TEST2 TEST1 TEST");
408
409 ok(wrapSetPermLayerState(fileW, "TEST1", 0, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
410 expect_LayerValue2(bMachine, file, "TEST TEST2", g_WinVersion >= WINVER_WIN8, "TEST2 TEST");
411
412 ok(wrapSetPermLayerState(fileW, "TEST", 0, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
413 expect_LayerValue(bMachine, file, "TEST2");
414
415 ok(wrapSetPermLayerState(fileW, "TEST2", 0, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
416 expect_LayerValue(bMachine, file, NULL);
417
418 /* Valid flags until win8: !# */
419 /* Key is empty, now play around with the flags. */
420 for (dwFlag = ((g_WinVersion >= WINVER_WIN8) ? 6 : 2); dwFlag < 32; ++dwFlag)
421 {
422 ok(wrapSetPermLayerState(fileW, "TEST", (1<<dwFlag), bMachine, 1) == FALSE, "Expected SetPermLayerState to fail on 0x%x\n", (1<<dwFlag));
423 }
424 expect_LayerValue(bMachine, file, NULL);
425
426 /* Add layer flags */
427 ok(wrapSetPermLayerState(fileW, "TEST", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
428 expect_LayerValue(bMachine, file, "# TEST");
429
430 ok(wrapSetPermLayerState(fileW, "TEST2", 2, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
431 expect_LayerValue2(bMachine, file, "!# TEST TEST2", g_WinVersion >= WINVER_WIN8, "!# TEST2 TEST");
432
433 ok(wrapSetPermLayerState(fileW, "TEST", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
434 expect_LayerValue2(bMachine, file, "!# TEST2 TEST", g_WinVersion >= WINVER_WIN8, "!# TEST TEST2");
435
436 ok(wrapSetPermLayerState(fileW, "TEST3", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
437 expect_LayerValue2(bMachine, file, "!# TEST2 TEST TEST3", g_WinVersion >= WINVER_WIN8, "!# TEST3 TEST TEST2");
438
439 /* Remove on a flag removes that flag from the start. */
440 ok(wrapSetPermLayerState(fileW, "TEST2", 2, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
441 expect_LayerValue2(bMachine, file, "# TEST TEST3", g_WinVersion >= WINVER_WIN8, "# TEST3 TEST");
442
443 ok(wrapSetPermLayerState(fileW, "", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
444 expect_LayerValue2(bMachine, file, "TEST TEST3", g_WinVersion >= WINVER_WIN8, "TEST3 TEST");
445
446 ok(wrapSetPermLayerState(fileW, "", LAYER_APPLY_TO_SYSTEM_EXES | 2, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
447 expect_LayerValue2(bMachine, file, "!# TEST TEST3", g_WinVersion >= WINVER_WIN8, "!# TEST3 TEST");
448
449 ok(wrapSetPermLayerState(fileW, "TEST3", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
450 expect_LayerValue(bMachine, file, "! TEST");
451
452 ok(wrapSetPermLayerState(fileW, "TEST", 2, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
453 expect_LayerValue(bMachine, file, NULL);
454
455 /* Try adding multiple layers: */
456 ok(wrapSetPermLayerState(fileW, "TEST TEST2", LAYER_APPLY_TO_SYSTEM_EXES | 2, bMachine, 1) == FALSE, "Expected SetPermLayerState to fail\n");
457 expect_LayerValue(bMachine, file, NULL);
458
459 ok(wrapSetPermLayerState(fileW, "TEST2", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
460 expect_LayerValue(bMachine, file, "TEST2");
461
462 /* Try adding flags in via layer string */
463 ok(wrapSetPermLayerState(fileW, "#", 0, bMachine, 1) == FALSE, "Expected SetPermLayerState to fail\n");
464 expect_LayerValue(bMachine, file, "TEST2");
465
466 ok(wrapSetPermLayerState(fileW, "!", 0, bMachine, 1) == FALSE, "Expected SetPermLayerState to fail\n");
467 expect_LayerValue(bMachine, file, "TEST2");
468
469 /* Now we prepare the registry with some crap to see how data is validated. */
470 setLayerValue(bMachine, file, "!#!# TEST2 TEST2 !# TEST ");
471
472 ok(wrapSetPermLayerState(fileW, "TEST1", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
473 expect_LayerValue2(bMachine, file, "!# TEST2 TEST2 !# TEST TEST1", g_WinVersion >= WINVER_WIN8, "!# TEST1 TEST2 TEST2 !# TEST");
474
475 /* Removing a duplicate entry will remove all instances of it */
476 ok(wrapSetPermLayerState(fileW, "TEST2", 0, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
477 expect_LayerValue2(bMachine, file, "!# !# TEST TEST1", g_WinVersion >= WINVER_WIN8, "!# TEST1 !# TEST");
478
479 /* Adding a flag cleans other flags (from the start) */
480 ok(wrapSetPermLayerState(fileW, "", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
481 expect_LayerValue2(bMachine, file, "!# TEST TEST1", g_WinVersion >= WINVER_WIN8, "!# TEST1 !# TEST");
482
483 if(g_WinVersion < WINVER_WIN8)
484 {
485 ok(wrapSetPermLayerState(fileW, "$%$%^^", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
486 expect_LayerValue(bMachine, file, "!# TEST TEST1 $%$%^^");
487 }
488
489 setLayerValue(bMachine, file, "!#!# TEST2 !# TEST ");
490 ok(wrapSetPermLayerState(fileW, "", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
491 expect_LayerValue(bMachine, file, "! TEST2 !# TEST");
492
493 /* Tabs are treated as spaces */
494 setLayerValue(bMachine, file, "!#!# TEST2 \t TEST2 !# \t TEST ");
495 ok(wrapSetPermLayerState(fileW, "TEST2", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
496 expect_LayerValue2(bMachine, file, "!# !# TEST TEST2", g_WinVersion >= WINVER_WIN8, "!# TEST2 !# TEST");
497
498 /* Newlines are left as-is */
499 setLayerValue(bMachine, file, "!#!# TEST2 \n TEST2 !# \r\n TEST ");
500 ok(wrapSetPermLayerState(fileW, "TEST2", 0, bMachine, 1) == TRUE, "Expected SetPermLayerState to succeed\n");
501 expect_LayerValue2(bMachine, file, "!# \n !# \r\n TEST TEST2", g_WinVersion >= WINVER_WIN8, "!# TEST2 \n !# \r\n TEST");
502
503 /* Whitespace and duplicate flags are eaten from the start */
504 setLayerValue(bMachine, file, " !#!# TEST2 \t TEST2 !# \t TEST ");
505 ok(wrapSetPermLayerState(fileW, "", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
506 expect_LayerValue(bMachine, file, "! TEST2 TEST2 !# TEST");
507
508 setLayerValue(bMachine, file, "!# !# TEST2 !# TEST ");
509 ok(wrapSetPermLayerState(fileW, "", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
510 expect_LayerValue(bMachine, file, "! TEST2 !# TEST");
511
512 ok(wrapSetPermLayerState(fileW, "", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
513 expect_LayerValue(bMachine, file, "! TEST2 !# TEST");
514
515 ok(wrapSetPermLayerState(fileW, "", 2, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
516 expect_LayerValue(bMachine, file, "TEST2 !# TEST");
517
518 /* First flags are cleaned, then a layer is removed. */
519 ok(wrapSetPermLayerState(fileW, "TEST2", 2, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
520 expect_LayerValue(bMachine, file, "!# TEST");
521
522 /* Nothing is changed, still it succeeds. */
523 ok(wrapSetPermLayerState(fileW, "TEST2", 2, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
524 expect_LayerValue(bMachine, file, "# TEST");
525
526 /* And remove the last bits. */
527 ok(wrapSetPermLayerState(fileW, "TEST", LAYER_APPLY_TO_SYSTEM_EXES, bMachine, 0) == TRUE, "Expected SetPermLayerState to succeed\n");
528 expect_LayerValue(bMachine, file, NULL);
529 }
530
531 static void test_SetPermLayer(void)
532 {
533 char file[MAX_PATH + 20], tmp[MAX_PATH + 20];
534 HANDLE hfile;
535
536 GetTempPathA(MAX_PATH, tmp);
537 GetLongPathNameA(tmp, file, sizeof(file));
538 PathAppendA(file, "test_file.exe");
539
540 hfile = CreateFileA(file, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
541 ok(hfile != INVALID_HANDLE_VALUE, "CreateFile failed for '%s'\n", file);
542 if (hfile == INVALID_HANDLE_VALUE)
543 {
544 skip("Running these tests is useless without a file present\n");
545 return;
546 }
547 CloseHandle(hfile);
548
549 if (setLayerValue(FALSE, file, NULL))
550 {
551 test_SdbSetPermLayerKeysLevel(FALSE, file);
552 test_SetPermLayerStateLevel(FALSE, file);
553 }
554 else
555 {
556 skip("Skipping SetPermLayerStateLevel tests for User, because I cannot prepare the environment\n");
557 }
558 if (setLayerValue(TRUE, file, NULL))
559 {
560 test_SdbSetPermLayerKeysLevel(TRUE, file);
561 test_SetPermLayerStateLevel(TRUE, file);
562 }
563 else
564 {
565 skip("Skipping SetPermLayerStateLevel tests for Machine (HKLM), because I cannot prepare the environment\n");
566 }
567 ok(DeleteFileA(file), "DeleteFile failed....\n");
568 }
569
570 static BOOL create_file(LPCSTR dir, LPCSTR name, int filler, size_t size)
571 {
572 char target[MAX_PATH], *tmp;
573 HANDLE file;
574 PathCombineA(target, dir, name);
575
576 tmp = malloc(size);
577 memset(tmp, filler, size);
578
579 file = CreateFileA(target, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
580 if(file == INVALID_HANDLE_VALUE)
581 return FALSE;
582
583 WriteFile(file, tmp, size, &size, NULL);
584 CloseHandle(file);
585 free(tmp);
586 return TRUE;
587 }
588
589 static BOOL delete_file(LPCSTR dir, LPCSTR name)
590 {
591 char target[MAX_PATH];
592 PathCombineA(target, dir, name);
593 return DeleteFileA(target);
594 }
595
596 static char g_FakeDrive = 0;
597
598 UINT (WINAPI *pGetDriveTypeW)(LPCWSTR target) = NULL;
599 UINT WINAPI mGetDriveTypeW(LPCWSTR target)
600 {
601 UINT uRet = pGetDriveTypeW(target);
602 if(g_FakeDrive && target && (char)*target == g_FakeDrive)
603 return DRIVE_CDROM;
604 return uRet;
605 }
606
607
608 static PIMAGE_IMPORT_DESCRIPTOR FindImportDescriptor(PBYTE DllBase, PCSTR DllName)
609 {
610 ULONG Size;
611 PIMAGE_IMPORT_DESCRIPTOR ImportDescriptor = RtlImageDirectoryEntryToData((HMODULE)DllBase, TRUE, IMAGE_DIRECTORY_ENTRY_IMPORT, &Size);
612 while (ImportDescriptor->Name && ImportDescriptor->OriginalFirstThunk)
613 {
614 PCHAR Name = (PCHAR)(DllBase + ImportDescriptor->Name);
615 if (!lstrcmpiA(Name, DllName))
616 {
617 return ImportDescriptor;
618 }
619 ImportDescriptor++;
620 }
621 return NULL;
622 }
623
624 static BOOL RedirectIat(PCSTR TargetDllName, PCSTR DllName, PCSTR FunctionName, ULONG_PTR NewFunction, ULONG_PTR* OriginalFunction)
625 {
626 PBYTE DllBase = (PBYTE)GetModuleHandleA(TargetDllName);
627 if (DllBase)
628 {
629 PIMAGE_IMPORT_DESCRIPTOR ImportDescriptor = FindImportDescriptor(DllBase, DllName);
630 if (ImportDescriptor)
631 {
632 // On loaded images, OriginalFirstThunk points to the name / ordinal of the function
633 PIMAGE_THUNK_DATA OriginalThunk = (PIMAGE_THUNK_DATA)(DllBase + ImportDescriptor->OriginalFirstThunk);
634 // FirstThunk points to the resolved address.
635 PIMAGE_THUNK_DATA FirstThunk = (PIMAGE_THUNK_DATA)(DllBase + ImportDescriptor->FirstThunk);
636 while (OriginalThunk->u1.AddressOfData && FirstThunk->u1.Function)
637 {
638 if (!IMAGE_SNAP_BY_ORDINAL32(OriginalThunk->u1.AddressOfData))
639 {
640 PIMAGE_IMPORT_BY_NAME ImportName = (PIMAGE_IMPORT_BY_NAME)(DllBase + OriginalThunk->u1.AddressOfData);
641 if (!lstrcmpiA((PCSTR)ImportName->Name, FunctionName))
642 {
643 DWORD dwOld;
644 VirtualProtect(&FirstThunk->u1.Function, sizeof(ULONG_PTR), PAGE_EXECUTE_READWRITE, &dwOld);
645 *OriginalFunction = FirstThunk->u1.Function;
646 FirstThunk->u1.Function = NewFunction;
647 VirtualProtect(&FirstThunk->u1.Function, sizeof(ULONG_PTR), dwOld, &dwOld);
648 return TRUE;
649 }
650 }
651 OriginalThunk++;
652 FirstThunk++;
653 }
654 skip("Unable to find the Import '%s' from '%s' in %s'\n", FunctionName, DllName, TargetDllName);
655 }
656 else
657 {
658 skip("Unable to find the ImportDescriptor for '%s' in '%s'\n", DllName, TargetDllName);
659 }
660 }
661 else
662 {
663 skip("Unable to find the loaded module '%s'\n", TargetDllName);
664 }
665 return FALSE;
666 }
667
668 static BOOL RestoreIat(PCSTR target, PCSTR DllName, PCSTR FunctionName, ULONG_PTR OriginalFunction)
669 {
670 ULONG_PTR old = 0;
671 return RedirectIat(target, DllName, FunctionName, OriginalFunction, &old);
672 }
673
674 static BOOL wrapSdbSetPermLayerKeys2(LPCSTR dir, LPCSTR name, PCSTR szLayers, BOOL bMachine)
675 {
676 char szPath[MAX_PATH];
677 WCHAR wszPath[MAX_PATH], wszLayers[MAX_LAYER_LENGTH];
678 PathCombineA(szPath, dir, name);
679 MultiByteToWideChar(CP_ACP, 0, szLayers, -1, wszLayers, MAX_LAYER_LENGTH);
680 MultiByteToWideChar(CP_ACP, 0, szPath, -1, wszPath, MAX_PATH);
681 return pSdbSetPermLayerKeys(wszPath, wszLayers, bMachine);
682 }
683
684
685 BOOL expect_files(const char* dir, int num, ...)
686 {
687 char finddir[MAX_PATH + 20];
688 va_list args;
689 WIN32_FIND_DATAA find = { 0 };
690 HANDLE hFind;
691 int cmp = 0;
692
693 va_start(args, num);
694
695 PathCombineA(finddir, dir, "*");
696 hFind = FindFirstFileA(finddir, &find);
697 if (hFind != INVALID_HANDLE_VALUE)
698 {
699 const char* file;
700 do
701 {
702 if (!(find.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
703 {
704 if (--num < 0)
705 break;
706 file = va_arg(args, const char*);
707 cmp = strcmp(file, find.cFileName);
708 }
709 } while (cmp == 0 && FindNextFileA(hFind, &find));
710 FindClose(hFind);
711 }
712 va_end(args);
713 return cmp == 0 && num == 0;
714 }
715
716
717 static void test_Sign_Media(void)
718 {
719 char workdir[MAX_PATH], subdir[MAX_PATH], drive[5] = "Z:";
720 BOOL ret;
721
722 DWORD logical_drives = GetLogicalDrives();
723 g_FakeDrive = 0;
724 for (drive[0] = 'D'; drive[0] <= 'Z'; drive[0]++)
725 {
726 DWORD idx = 1 << (drive[0] - 'D' + 3);
727 if (!(logical_drives & idx))
728 {
729 g_FakeDrive = drive[0];
730 break;
731 }
732 }
733 if (!g_FakeDrive)
734 {
735 skip("Unable to find a free drive\n");
736 return;
737 }
738
739 ret = GetTempPathA(MAX_PATH, workdir);
740 ok(ret, "GetTempPathA error: %d\n", GetLastError());
741 PathAppendA(workdir, "apphelp_test");
742
743 ret = CreateDirectoryA(workdir, NULL);
744 ok(ret, "CreateDirectoryA error: %d\n", GetLastError());
745
746 PathCombineA(subdir, workdir, "sub");
747 ret = CreateDirectoryA(subdir, NULL);
748 ok(ret, "CreateDirectoryA error: %d\n", GetLastError());
749
750 ret = DefineDosDeviceA(DDD_NO_BROADCAST_SYSTEM, drive, workdir);
751 ok(ret, "DefineDosDeviceA error: %d\n", GetLastError());
752 if(ret)
753 {
754 ret = RedirectIat("apphelp.dll", "kernel32.dll", "GetDriveTypeW", (ULONG_PTR)mGetDriveTypeW, (ULONG_PTR*)&pGetDriveTypeW);
755 if (g_WinVersion < WINVER_WIN8)
756 ok(ret, "Expected redirect_iat to succeed\n");
757 if(ret)
758 {
759 ok(create_file(workdir, "test.exe", 'a', 4), "create_file error: %d\n", GetLastError());
760
761 ok(wrapSdbSetPermLayerKeys2(drive, "test.exe", "TEST", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
762 /* 4 */
763 /* test.exe */
764 expect_LayerValue(0, "SIGN.MEDIA=4 test.exe", "TEST");
765 ok(wrapSdbSetPermLayerKeys2(drive, "test.exe", "", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
766
767 ok(create_file(workdir, "test.txt", 'a', 1), "create_file error: %d\n", GetLastError());
768
769 if (!expect_files(workdir, 2, "test.exe", "test.txt"))
770 {
771 skip("Skipping test, files are not returned in the expected order by the FS\n");
772 }
773 else
774 {
775 ok(wrapSdbSetPermLayerKeys2(drive, "test.exe", "TEST", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
776 /* (4 << 1) ^ 1 */
777 /* test.exe test.txt */
778 expect_LayerValue(0, "SIGN.MEDIA=9 test.exe", "TEST");
779 ok(wrapSdbSetPermLayerKeys2(drive, "test.exe", "", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
780 }
781
782 ok(create_file(workdir, "test.zz", 'a', 0x1000), "create_file error: %d\n", GetLastError());
783
784 if (!expect_files(workdir, 3, "test.exe", "test.txt", "test.zz"))
785 {
786 skip("Skipping test, files are not returned in the expected order by the FS\n");
787 }
788 else
789 {
790 ok(wrapSdbSetPermLayerKeys2(drive, "test.exe", "TEST", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
791 /* (((4 << 1) ^ 1) << 1) ^ 0x1000 */
792 /* test.exe test.txt test.zz */
793 expect_LayerValue(0, "SIGN.MEDIA=1012 test.exe", "TEST");
794 ok(wrapSdbSetPermLayerKeys2(drive, "test.exe", "", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
795 }
796
797 ok(create_file(subdir, "test.exe", 'a', 0x10203), "create_file error: %d\n", GetLastError());
798
799 if (!expect_files(subdir, 1, "test.exe"))
800 {
801 skip("Skipping test, files are not returned in the expected order by the FS\n");
802 }
803 else
804 {
805 ok(wrapSdbSetPermLayerKeys2(drive, "sub\\test.exe", "TEST", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
806 /* 0x10203 */
807 /* test.exe */
808 expect_LayerValue(0, "SIGN.MEDIA=10203 sub\\test.exe", "TEST");
809 ok(wrapSdbSetPermLayerKeys2(drive, "sub\\test.exe", "", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
810 }
811
812 ok(create_file(subdir, "test.bbb", 'a', 0), "create_file error: %d\n", GetLastError());
813
814 if (!expect_files(subdir, 2, "test.bbb", "test.exe"))
815 {
816 skip("Skipping test, files are not returned in the expected order by the FS\n");
817 }
818 else
819 {
820 ok(wrapSdbSetPermLayerKeys2(drive, "sub\\test.exe", "TEST", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
821 /* 0x10203 */
822 /* test.exe */
823 expect_LayerValue(0, "SIGN.MEDIA=10203 sub\\test.exe", "TEST");
824 ok(wrapSdbSetPermLayerKeys2(drive, "sub\\test.exe", "", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
825 }
826
827 ok(create_file(subdir, "TEST.txt", 'a', 0x30201), "create_file error: %d\n", GetLastError());
828
829 if (!expect_files(subdir, 3, "test.bbb", "test.exe", "TEST.txt"))
830 {
831 skip("Skipping test, files are not returned in the expected order by the FS\n");
832 }
833 else
834 {
835 ok(wrapSdbSetPermLayerKeys2(drive, "sub\\test.exe", "TEST", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
836 /* (0x10203 << 1) ^ 0x30201 */
837 /* test.exe TEST.txt */
838 expect_LayerValue(0, "SIGN.MEDIA=10607 sub\\test.exe", "TEST");
839 ok(wrapSdbSetPermLayerKeys2(drive, "sub\\test.exe", "", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
840 }
841
842 ok(create_file(subdir, "TEST.aaa", 'a', 0x3a2a1), "create_file error: %d\n", GetLastError());
843
844 if (!expect_files(subdir, 4, "TEST.aaa", "test.bbb", "test.exe", "TEST.txt"))
845 {
846 skip("Skipping test, files are not returned in the expected order by the FS\n");
847 }
848 else
849 {
850 ok(wrapSdbSetPermLayerKeys2(drive, "sub\\test.exe", "TEST", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
851 /* (((0x3a2a1 << 1) ^ 0x10203) << 1) ^ 0x30201 */
852 /* TEST.aaa test.exe TEST.txt */
853 expect_LayerValue(0, "SIGN.MEDIA=F8C83 sub\\test.exe", "TEST");
854 ok(wrapSdbSetPermLayerKeys2(drive, "sub\\test.exe", "", 0), "Expected wrapSdbSetPermLayerKeys2 to succeed\n");
855 }
856
857 ret = RestoreIat("apphelp.dll", "kernel32.dll", "GetDriveTypeW", (ULONG_PTR)pGetDriveTypeW);
858 ok(ret, "Expected restore_iat to succeed\n");
859
860 ok(delete_file(subdir, "test.bbb"), "delete_file error: %d\n", GetLastError());
861 ok(delete_file(subdir, "TEST.aaa"), "delete_file error: %d\n", GetLastError());
862 ok(delete_file(subdir, "TEST.txt"), "delete_file error: %d\n", GetLastError());
863 ok(delete_file(subdir, "test.exe"), "delete_file error: %d\n", GetLastError());
864 ok(delete_file(workdir, "test.zz"), "delete_file error: %d\n", GetLastError());
865 ok(delete_file(workdir, "test.txt"), "delete_file error: %d\n", GetLastError());
866 ok(delete_file(workdir, "test.exe"), "delete_file error: %d\n", GetLastError());
867 }
868 ret = DefineDosDeviceA(DDD_REMOVE_DEFINITION | DDD_NO_BROADCAST_SYSTEM, drive, NULL);
869 ok(ret, "DefineDosDeviceA error: %d\n", GetLastError());
870 }
871 ret = RemoveDirectoryA(subdir);
872 ok(ret, "RemoveDirectoryA error: %d\n", GetLastError());
873 ret = RemoveDirectoryA(workdir);
874 ok(ret, "RemoveDirectoryA error: %d\n", GetLastError());
875 }
876
877
878 START_TEST(layerapi)
879 {
880 /*SetEnvironmentVariable("SHIM_DEBUG_LEVEL", "4");*/
881 hdll = LoadLibraryA("apphelp.dll");
882 pAllowPermLayer = (void *)GetProcAddress(hdll, "AllowPermLayer");
883 pSdbSetPermLayerKeys = (void *)GetProcAddress(hdll, "SdbSetPermLayerKeys");
884 pSdbGetPermLayerKeys = (void *)GetProcAddress(hdll, "SdbGetPermLayerKeys");
885 pSetPermLayerState = (void *)GetProcAddress(hdll, "SetPermLayerState");
886 g_WinVersion = get_host_winver();
887
888 if (!pAllowPermLayer)
889 {
890 skip("Skipping tests with AllowPermLayer, function not found\n");
891 }
892 else
893 {
894 test_AllowPermLayer();
895 }
896
897 if (!pSdbSetPermLayerKeys)
898 {
899 skip("Skipping tests with SdbSetPermLayerKeys, function not found\n");
900 }
901 else
902 {
903 if (!pSdbGetPermLayerKeys)
904 {
905 skip("Skipping tests with SdbGetPermLayerKeys, function not found\n");
906 }
907 else
908 {
909 test_SdbGetPermLayerKeys();
910 }
911
912 if (!pSetPermLayerState)
913 {
914 skip("Skipping tests with SetPermLayerState, function not found\n");
915 }
916 else
917 {
918 test_SetPermLayer();
919 test_Sign_Media();
920 }
921 }
922 }