msi: Fix the INSTALLPROPERTY_LASTUSEDTYPE case.
[wine.git] / dlls / msi / tests / source.c
blob7c8b4d70e1b8860b024b3837a71bce6b2508f086
1 /*
2 * Tests for MSI Source functions
4 * Copyright (C) 2006 James Hawkins
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21 #define _WIN32_MSI 300
23 #include <stdio.h>
25 #include <windows.h>
26 #include <msiquery.h>
27 #include <msidefs.h>
28 #include <msi.h>
29 #include <sddl.h>
31 #include "wine/test.h"
33 static BOOL (WINAPI *pConvertSidToStringSidA)(PSID, LPSTR*);
34 static UINT (WINAPI *pMsiSourceListGetInfoA)
35 (LPCSTR, LPCSTR, MSIINSTALLCONTEXT, DWORD, LPCSTR, LPSTR, LPDWORD);
36 static UINT (WINAPI *pMsiSourceListAddSourceExA)
37 (LPCSTR, LPCSTR, MSIINSTALLCONTEXT, DWORD, LPCSTR, DWORD);
39 static void init_functionpointers(void)
41 HMODULE hmsi = GetModuleHandleA("msi.dll");
42 HMODULE hadvapi32 = GetModuleHandleA("advapi32.dll");
44 #define GET_PROC(dll, func) \
45 p ## func = (void *)GetProcAddress(dll, #func); \
46 if(!p ## func) \
47 trace("GetProcAddress(%s) failed\n", #func);
49 GET_PROC(hmsi, MsiSourceListAddSourceExA)
50 GET_PROC(hmsi, MsiSourceListGetInfoA)
52 GET_PROC(hadvapi32, ConvertSidToStringSidA)
54 #undef GET_PROC
57 /* copied from dlls/msi/registry.c */
58 static BOOL squash_guid(LPCWSTR in, LPWSTR out)
60 DWORD i,n=1;
61 GUID guid;
63 if (FAILED(CLSIDFromString((LPOLESTR)in, &guid)))
64 return FALSE;
66 for(i=0; i<8; i++)
67 out[7-i] = in[n++];
68 n++;
69 for(i=0; i<4; i++)
70 out[11-i] = in[n++];
71 n++;
72 for(i=0; i<4; i++)
73 out[15-i] = in[n++];
74 n++;
75 for(i=0; i<2; i++)
77 out[17+i*2] = in[n++];
78 out[16+i*2] = in[n++];
80 n++;
81 for( ; i<8; i++)
83 out[17+i*2] = in[n++];
84 out[16+i*2] = in[n++];
86 out[32]=0;
87 return TRUE;
90 static void create_test_guid(LPSTR prodcode, LPSTR squashed)
92 WCHAR guidW[MAX_PATH];
93 WCHAR squashedW[MAX_PATH];
94 GUID guid;
95 HRESULT hr;
96 int size;
98 hr = CoCreateGuid(&guid);
99 ok(hr == S_OK, "Expected S_OK, got %d\n", hr);
101 size = StringFromGUID2(&guid, (LPOLESTR)guidW, MAX_PATH);
102 ok(size == 39, "Expected 39, got %d\n", hr);
104 WideCharToMultiByte(CP_ACP, 0, guidW, size, prodcode, MAX_PATH, NULL, NULL);
105 squash_guid(guidW, squashedW);
106 WideCharToMultiByte(CP_ACP, 0, squashedW, -1, squashed, MAX_PATH, NULL, NULL);
109 static void get_user_sid(LPSTR *usersid)
111 HANDLE token;
112 BYTE buf[1024];
113 DWORD size;
114 PTOKEN_USER user;
116 OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &token);
117 size = sizeof(buf);
118 GetTokenInformation(token, TokenUser, (void *)buf, size, &size);
119 user = (PTOKEN_USER)buf;
120 pConvertSidToStringSidA(user->User.Sid, usersid);
123 static void check_reg_str(HKEY prodkey, LPCSTR name, LPCSTR expected, BOOL bcase, DWORD line)
125 char val[MAX_PATH];
126 DWORD size, type;
127 LONG res;
129 size = MAX_PATH;
130 val[0] = '\0';
131 res = RegQueryValueExA(prodkey, name, NULL, &type, (LPBYTE)val, &size);
133 if (res != ERROR_SUCCESS || (type != REG_SZ && type != REG_EXPAND_SZ))
135 ok_(__FILE__, line)(FALSE, "Key doesn't exist or wrong type\n");
136 return;
139 if (!expected)
140 ok_(__FILE__, line)(lstrlenA(val) == 0, "Expected empty string, got %s\n", val);
141 else
143 if (bcase)
144 ok_(__FILE__, line)(!lstrcmpA(val, expected), "Expected %s, got %s\n", expected, val);
145 else
146 ok_(__FILE__, line)(!lstrcmpiA(val, expected), "Expected %s, got %s\n", expected, val);
150 #define CHECK_REG_STR(prodkey, name, expected) \
151 check_reg_str(prodkey, name, expected, TRUE, __LINE__);
153 static void test_MsiSourceListGetInfo(void)
155 CHAR prodcode[MAX_PATH];
156 CHAR prod_squashed[MAX_PATH];
157 CHAR keypath[MAX_PATH*2];
158 CHAR value[MAX_PATH];
159 LPSTR usersid;
160 LPCSTR data;
161 LONG res;
162 UINT r;
163 HKEY userkey, hkey, media;
164 DWORD size;
166 if (!pMsiSourceListGetInfoA)
168 skip("Skipping MsiSourceListGetInfoA tests\n");
169 return;
172 create_test_guid(prodcode, prod_squashed);
173 get_user_sid(&usersid);
175 /* NULL szProductCodeOrPatchCode */
176 r = pMsiSourceListGetInfoA(NULL, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
177 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
178 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
180 /* empty szProductCodeOrPatchCode */
181 r = pMsiSourceListGetInfoA("", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
182 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
183 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
185 /* garbage szProductCodeOrPatchCode */
186 r = pMsiSourceListGetInfoA("garbage", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
187 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
188 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
190 /* szProductCodeOrPatchCode */
191 r = pMsiSourceListGetInfoA("garbage", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
192 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
193 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
195 /* guid without brackets */
196 r = pMsiSourceListGetInfoA("51CD2AD5-0482-4C46-8DDD-0ED1022AA1AA", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
197 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
198 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
200 /* guid with brackets */
201 r = pMsiSourceListGetInfoA("{51CD2AD5-0482-4C46-8DDD-0ED1022AA1AA}", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
202 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
203 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
205 /* same length as guid, but random */
206 r = pMsiSourceListGetInfoA("ADKD-2KSDFF2-DKK1KNFJASD9GLKWME-1I3KAD", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
207 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
208 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
210 /* invalid context */
211 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_NONE,
212 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
213 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
215 /* another invalid context */
216 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_ALLUSERMANAGED,
217 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
218 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
220 /* yet another invalid context */
221 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_ALL,
222 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
223 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
225 /* mix two valid contexts */
226 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERMANAGED | MSIINSTALLCONTEXT_USERUNMANAGED,
227 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
228 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
230 /* invalid option */
231 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
232 4, INSTALLPROPERTY_PACKAGENAME, NULL, NULL);
233 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
235 /* NULL property */
236 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
237 MSICODE_PRODUCT, NULL, NULL, NULL);
238 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
240 /* empty property */
241 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
242 MSICODE_PRODUCT, "", NULL, NULL);
243 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
245 /* value is non-NULL while size is NULL */
246 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
247 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, value, NULL);
248 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
250 /* size is non-NULL while value is NULL */
251 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
252 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, &size);
253 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
255 lstrcpyA(keypath, "Software\\Microsoft\\Installer\\Products\\");
256 lstrcatA(keypath, prod_squashed);
258 res = RegCreateKeyA(HKEY_CURRENT_USER, keypath, &userkey);
259 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
261 /* user product key exists */
262 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
263 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, &size);
264 ok(r == ERROR_BAD_CONFIGURATION, "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
266 res = RegCreateKeyA(userkey, "SourceList", &hkey);
267 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
269 /* SourceList key exists */
270 size = 0xdeadbeef;
271 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
272 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, &size);
273 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
274 ok(size == 0, "Expected 0, got %d\n", size);
276 data = "msitest.msi";
277 res = RegSetValueExA(hkey, "PackageName", 0, REG_SZ, (const BYTE *)data, lstrlenA(data) + 1);
278 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
280 /* PackageName value exists */
281 size = 0xdeadbeef;
282 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
283 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, NULL, &size);
284 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
285 ok(size == 11, "Expected 11, got %d\n", size);
287 /* read the value, don't change size */
288 lstrcpyA(value, "aaa");
289 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
290 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, value, &size);
291 ok(r == ERROR_MORE_DATA, "Expected ERROR_MORE_DATA, got %d\n", r);
292 ok(!lstrcmpA(value, "aaa"), "Expected 'aaa', got %s\n", value);
293 ok(size == 11, "Expected 11, got %d\n", size);
295 /* read the value, fix size */
296 size++;
297 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
298 MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, value, &size);
299 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
300 ok(!lstrcmpA(value, "msitest.msi"), "Expected 'msitest.msi', got %s\n", value);
301 ok(size == 11, "Expected 11, got %d\n", size);
303 /* empty property now that product key exists */
304 size = 0xdeadbeef;
305 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
306 MSICODE_PRODUCT, "", NULL, &size);
307 ok(r == ERROR_UNKNOWN_PROPERTY, "Expected ERROR_UNKNOWN_PROPERTY, got %d\n", r);
308 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
310 /* nonexistent property now that product key exists */
311 size = 0xdeadbeef;
312 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
313 MSICODE_PRODUCT, "nonexistent", NULL, &size);
314 ok(r == ERROR_UNKNOWN_PROPERTY, "Expected ERROR_UNKNOWN_PROPERTY, got %d\n", r);
315 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
317 data = "tester";
318 res = RegSetValueExA(hkey, "nonexistent", 0, REG_SZ, (const BYTE *)data, lstrlenA(data) + 1);
319 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
321 /* nonexistent property now that nonexistent value exists */
322 size = 0xdeadbeef;
323 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
324 MSICODE_PRODUCT, "nonexistent", NULL, &size);
325 ok(r == ERROR_UNKNOWN_PROPERTY, "Expected ERROR_UNKNOWN_PROPERTY, got %d\n", r);
326 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
328 /* invalid option now that product key exists */
329 size = 0xdeadbeef;
330 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
331 4, INSTALLPROPERTY_PACKAGENAME, NULL, &size);
332 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
333 ok(size == 11, "Expected 11, got %d\n", size);
335 /* INSTALLPROPERTY_MEDIAPACKAGEPATH, media key does not exist */
336 size = MAX_PATH;
337 lstrcpyA(value, "aaa");
338 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
339 MSICODE_PRODUCT, INSTALLPROPERTY_MEDIAPACKAGEPATH,
340 value, &size);
341 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
342 ok(!lstrcmpA(value, ""), "Expected \"\", got \"%s\"\n", value);
343 ok(size == 0, "Expected 0, got %d\n", size);
345 res = RegCreateKeyA(hkey, "Media", &media);
346 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
348 data = "path";
349 res = RegSetValueExA(media, "MediaPackage", 0, REG_SZ,
350 (const BYTE *)data, lstrlenA(data) + 1);
351 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
353 /* INSTALLPROPERTY_MEDIAPACKAGEPATH */
354 size = MAX_PATH;
355 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
356 MSICODE_PRODUCT, INSTALLPROPERTY_MEDIAPACKAGEPATH,
357 value, &size);
358 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
359 ok(!lstrcmpA(value, "path"), "Expected \"path\", got \"%s\"\n", value);
360 ok(size == 4, "Expected 4, got %d\n", size);
362 /* INSTALLPROPERTY_DISKPROMPT */
363 data = "prompt";
364 res = RegSetValueExA(media, "DiskPrompt", 0, REG_SZ,
365 (const BYTE *)data, lstrlenA(data) + 1);
366 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
368 size = MAX_PATH;
369 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
370 MSICODE_PRODUCT, INSTALLPROPERTY_DISKPROMPT,
371 value, &size);
372 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
373 ok(!lstrcmpA(value, "prompt"), "Expected \"prompt\", got \"%s\"\n", value);
374 ok(size == 6, "Expected 6, got %d\n", size);
376 data = "";
377 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
378 (const BYTE *)data, lstrlenA(data) + 1);
379 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
381 /* INSTALLPROPERTY_LASTUSEDSOURCE, source is empty */
382 size = MAX_PATH;
383 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
384 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE,
385 value, &size);
386 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
387 ok(!lstrcmpA(value, ""), "Expected \"\", got \"%s\"\n", value);
388 ok(size == 0, "Expected 0, got %d\n", size);
390 data = "source";
391 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
392 (const BYTE *)data, lstrlenA(data) + 1);
393 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
395 /* INSTALLPROPERTY_LASTUSEDSOURCE */
396 size = MAX_PATH;
397 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
398 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE,
399 value, &size);
400 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
401 ok(!lstrcmpA(value, "source"), "Expected \"source\", got \"%s\"\n", value);
402 ok(size == 6, "Expected 6, got %d\n", size);
404 /* INSTALLPROPERTY_LASTUSEDSOURCE, size is too short */
405 size = 4;
406 lstrcpyA(value, "aaa");
407 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
408 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE,
409 value, &size);
410 ok(r == ERROR_MORE_DATA, "Expected ERROR_MORE_DATA, got %d\n", r);
411 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got \"%s\"\n", value);
412 ok(size == 6, "Expected 6, got %d\n", size);
414 /* INSTALLPROPERTY_LASTUSEDSOURCE, size is exactly 6 */
415 size = 6;
416 lstrcpyA(value, "aaa");
417 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
418 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE,
419 value, &size);
420 ok(r == ERROR_MORE_DATA, "Expected ERROR_MORE_DATA, got %d\n", r);
421 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got \"%s\"\n", value);
422 ok(size == 6, "Expected 6, got %d\n", size);
424 data = "a;source";
425 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
426 (const BYTE *)data, lstrlenA(data) + 1);
427 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
429 /* INSTALLPROPERTY_LASTUSEDSOURCE, one semi-colon */
430 size = MAX_PATH;
431 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
432 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE,
433 value, &size);
434 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
435 ok(!lstrcmpA(value, "source"), "Expected \"source\", got \"%s\"\n", value);
436 ok(size == 6, "Expected 6, got %d\n", size);
438 data = "a:source";
439 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
440 (const BYTE *)data, lstrlenA(data) + 1);
441 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
443 /* INSTALLPROPERTY_LASTUSEDSOURCE, one colon */
444 size = MAX_PATH;
445 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
446 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE,
447 value, &size);
448 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
449 ok(!lstrcmpA(value, "a:source"), "Expected \"a:source\", got \"%s\"\n", value);
450 ok(size == 8, "Expected 8, got %d\n", size);
452 /* INSTALLPROPERTY_LASTUSEDTYPE, invalid source format */
453 size = MAX_PATH;
454 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
455 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDTYPE,
456 value, &size);
457 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
458 ok(!lstrcmpA(value, ""), "Expected \"\", got \"%s\"\n", value);
459 ok(size == 0, "Expected 0, got %d\n", size);
461 data = "x;y;z";
462 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
463 (const BYTE *)data, lstrlenA(data) + 1);
464 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
466 /* INSTALLPROPERTY_LASTUSEDTYPE, invalid source format */
467 size = MAX_PATH;
468 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
469 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDTYPE,
470 value, &size);
471 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
472 ok(!lstrcmpA(value, ""), "Expected \"\", got \"%s\"\n", value);
473 ok(size == 0, "Expected 0, got %d\n", size);
475 data = "n;y;z";
476 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
477 (const BYTE *)data, lstrlenA(data) + 1);
478 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
480 /* INSTALLPROPERTY_LASTUSEDTYPE */
481 size = MAX_PATH;
482 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
483 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDTYPE,
484 value, &size);
485 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
486 ok(!lstrcmpA(value, "n"), "Expected \"n\", got \"%s\"\n", value);
487 ok(size == 1, "Expected 1, got %d\n", size);
489 data = "negatory";
490 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
491 (const BYTE *)data, lstrlenA(data) + 1);
492 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
494 /* INSTALLPROPERTY_LASTUSEDTYPE */
495 size = MAX_PATH;
496 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
497 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDTYPE,
498 value, &size);
499 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
500 ok(!lstrcmpA(value, "n"), "Expected \"n\", got \"%s\"\n", value);
501 ok(size == 1, "Expected 1, got %d\n", size);
503 data = "megatron";
504 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
505 (const BYTE *)data, lstrlenA(data) + 1);
506 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
508 /* INSTALLPROPERTY_LASTUSEDTYPE */
509 size = MAX_PATH;
510 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
511 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDTYPE,
512 value, &size);
513 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
514 ok(!lstrcmpA(value, "m"), "Expected \"m\", got \"%s\"\n", value);
515 ok(size == 1, "Expected 1, got %d\n", size);
517 data = "useless";
518 res = RegSetValueExA(hkey, "LastUsedSource", 0, REG_SZ,
519 (const BYTE *)data, lstrlenA(data) + 1);
520 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
522 /* INSTALLPROPERTY_LASTUSEDTYPE */
523 size = MAX_PATH;
524 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
525 MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDTYPE,
526 value, &size);
527 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
528 ok(!lstrcmpA(value, "u"), "Expected \"u\", got \"%s\"\n", value);
529 ok(size == 1, "Expected 1, got %d\n", size);
531 RegDeleteValueA(media, "MediaPackage");
532 RegDeleteValueA(media, "DiskPrompt");
533 RegDeleteKeyA(media, "");
534 RegDeleteValueA(hkey, "LastUsedSource");
535 RegDeleteValueA(hkey, "nonexistent");
536 RegDeleteValueA(hkey, "PackageName");
537 RegDeleteKeyA(hkey, "");
538 RegDeleteKeyA(userkey, "");
539 RegCloseKey(hkey);
540 RegCloseKey(userkey);
542 /* try a patch */
543 size = 0xdeadbeef;
544 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
545 MSICODE_PATCH, INSTALLPROPERTY_PACKAGENAME, NULL, &size);
546 ok(r == ERROR_UNKNOWN_PATCH, "Expected ERROR_UNKNOWN_PATCH, got %d\n", r);
547 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
549 lstrcpyA(keypath, "Software\\Microsoft\\Installer\\Patches\\");
550 lstrcatA(keypath, prod_squashed);
552 res = RegCreateKeyA(HKEY_CURRENT_USER, keypath, &userkey);
553 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
555 /* patch key exists
556 * NOTE: using prodcode guid, but it really doesn't matter
558 size = 0xdeadbeef;
559 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
560 MSICODE_PATCH, INSTALLPROPERTY_PACKAGENAME, NULL, &size);
561 ok(r == ERROR_BAD_CONFIGURATION, "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
562 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
564 res = RegCreateKeyA(userkey, "SourceList", &hkey);
565 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
567 /* SourceList key exists */
568 size = 0xdeadbeef;
569 r = pMsiSourceListGetInfoA(prodcode, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
570 MSICODE_PATCH, INSTALLPROPERTY_PACKAGENAME, NULL, &size);
571 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
572 ok(size == 0, "Expected 0, got %d\n", size);
574 RegDeleteKeyA(hkey, "");
575 RegDeleteKeyA(userkey, "");
576 RegCloseKey(hkey);
577 RegCloseKey(userkey);
580 static void test_MsiSourceListAddSourceEx(void)
582 CHAR prodcode[MAX_PATH];
583 CHAR prod_squashed[MAX_PATH];
584 CHAR keypath[MAX_PATH*2];
585 CHAR value[MAX_PATH];
586 LPSTR usersid;
587 LONG res;
588 UINT r;
589 HKEY prodkey, userkey, hkey;
590 HKEY url, net;
591 DWORD size;
593 if (!pMsiSourceListAddSourceExA)
595 skip("Skipping MsiSourceListAddSourceExA tests\n");
596 return;
599 create_test_guid(prodcode, prod_squashed);
600 get_user_sid(&usersid);
602 /* GetLastError is not set by the function */
604 /* NULL szProductCodeOrPatchCode */
605 r = pMsiSourceListAddSourceExA(NULL, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
606 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
607 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
609 /* empty szProductCodeOrPatchCode */
610 r = pMsiSourceListAddSourceExA("", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
611 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
612 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
614 /* garbage szProductCodeOrPatchCode */
615 r = pMsiSourceListAddSourceExA("garbage", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
616 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
617 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
619 /* guid without brackets */
620 r = pMsiSourceListAddSourceExA("51CD2AD5-0482-4C46-8DDD-0ED1022AA1AA", usersid,
621 MSIINSTALLCONTEXT_USERUNMANAGED,
622 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
623 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
625 /* guid with brackets */
626 r = pMsiSourceListAddSourceExA("{51CD2AD5-0482-4C46-8DDD-0ED1022AA1AA}", usersid,
627 MSIINSTALLCONTEXT_USERUNMANAGED,
628 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
629 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
631 /* MSIINSTALLCONTEXT_USERUNMANAGED */
633 r = pMsiSourceListAddSourceExA(prodcode, usersid,
634 MSIINSTALLCONTEXT_USERUNMANAGED,
635 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
636 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
638 lstrcpyA(keypath, "Software\\Microsoft\\Installer\\Products\\");
639 lstrcatA(keypath, prod_squashed);
641 res = RegCreateKeyA(HKEY_CURRENT_USER, keypath, &userkey);
642 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
644 /* user product key exists */
645 r = pMsiSourceListAddSourceExA(prodcode, usersid,
646 MSIINSTALLCONTEXT_USERUNMANAGED,
647 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
648 ok(r == ERROR_BAD_CONFIGURATION, "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
650 res = RegCreateKeyA(userkey, "SourceList", &url);
651 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
652 RegCloseKey(url);
654 /* SourceList key exists */
655 r = pMsiSourceListAddSourceExA(prodcode, usersid,
656 MSIINSTALLCONTEXT_USERUNMANAGED,
657 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
658 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
660 res = RegOpenKeyA(userkey, "SourceList\\URL", &url);
661 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
663 size = MAX_PATH;
664 res = RegQueryValueExA(url, "1", NULL, NULL, (LPBYTE)value, &size);
665 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
666 ok(!lstrcmpA(value, "C:\\source/"), "Expected 'C:\\source/', got %s\n", value);
667 ok(size == 11, "Expected 11, got %d\n", size);
669 /* add another source, index 0 */
670 r = pMsiSourceListAddSourceExA(prodcode, usersid,
671 MSIINSTALLCONTEXT_USERUNMANAGED,
672 MSICODE_PRODUCT | MSISOURCETYPE_URL, "another", 0);
673 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
675 size = MAX_PATH;
676 res = RegQueryValueExA(url, "1", NULL, NULL, (LPBYTE)value, &size);
677 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
678 ok(!lstrcmpA(value, "C:\\source/"), "Expected 'C:\\source/', got %s\n", value);
679 ok(size == 11, "Expected 11, got %d\n", size);
681 size = MAX_PATH;
682 res = RegQueryValueExA(url, "2", NULL, NULL, (LPBYTE)value, &size);
683 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
684 ok(!lstrcmpA(value, "another/"), "Expected 'another/', got %s\n", value);
685 ok(size == 9, "Expected 9, got %d\n", size);
687 /* add another source, index 1 */
688 r = pMsiSourceListAddSourceExA(prodcode, usersid,
689 MSIINSTALLCONTEXT_USERUNMANAGED,
690 MSICODE_PRODUCT | MSISOURCETYPE_URL, "third/", 1);
691 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
693 size = MAX_PATH;
694 res = RegQueryValueExA(url, "1", NULL, NULL, (LPBYTE)value, &size);
695 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
696 ok(!lstrcmpA(value, "third/"), "Expected 'third/', got %s\n", value);
697 ok(size == 7, "Expected 7, got %d\n", size);
699 size = MAX_PATH;
700 res = RegQueryValueExA(url, "2", NULL, NULL, (LPBYTE)value, &size);
701 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
702 ok(!lstrcmpA(value, "C:\\source/"), "Expected 'C:\\source/', got %s\n", value);
703 ok(size == 11, "Expected 11, got %d\n", size);
705 size = MAX_PATH;
706 res = RegQueryValueExA(url, "3", NULL, NULL, (LPBYTE)value, &size);
707 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
708 ok(!lstrcmpA(value, "another/"), "Expected 'another/', got %s\n", value);
709 ok(size == 9, "Expected 9, got %d\n", size);
711 /* add another source, index > N */
712 r = pMsiSourceListAddSourceExA(prodcode, usersid,
713 MSIINSTALLCONTEXT_USERUNMANAGED,
714 MSICODE_PRODUCT | MSISOURCETYPE_URL, "last/", 5);
715 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
717 size = MAX_PATH;
718 res = RegQueryValueExA(url, "1", NULL, NULL, (LPBYTE)value, &size);
719 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
720 ok(!lstrcmpA(value, "third/"), "Expected 'third/', got %s\n", value);
721 ok(size == 7, "Expected 7, got %d\n", size);
723 size = MAX_PATH;
724 res = RegQueryValueExA(url, "2", NULL, NULL, (LPBYTE)value, &size);
725 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
726 ok(!lstrcmpA(value, "C:\\source/"), "Expected 'C:\\source/', got %s\n", value);
727 ok(size == 11, "Expected 11, got %d\n", size);
729 size = MAX_PATH;
730 res = RegQueryValueExA(url, "3", NULL, NULL, (LPBYTE)value, &size);
731 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
732 ok(!lstrcmpA(value, "another/"), "Expected 'another/', got %s\n", value);
733 ok(size == 9, "Expected 9, got %d\n", size);
735 size = MAX_PATH;
736 res = RegQueryValueExA(url, "4", NULL, NULL, (LPBYTE)value, &size);
737 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
738 ok(!lstrcmpA(value, "last/"), "Expected 'last/', got %s\n", value);
739 ok(size == 6, "Expected 6, got %d\n", size);
741 /* just MSISOURCETYPE_NETWORK */
742 r = pMsiSourceListAddSourceExA(prodcode, usersid,
743 MSIINSTALLCONTEXT_USERUNMANAGED,
744 MSISOURCETYPE_NETWORK, "source", 0);
745 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
747 res = RegOpenKeyA(userkey, "SourceList\\Net", &net);
748 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
750 size = MAX_PATH;
751 res = RegQueryValueExA(net, "1", NULL, NULL, (LPBYTE)value, &size);
752 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
753 ok(!lstrcmpA(value, "source\\"), "Expected 'source\\', got %s\n", value);
754 ok(size == 8, "Expected 8, got %d\n", size);
756 /* just MSISOURCETYPE_URL */
757 r = pMsiSourceListAddSourceExA(prodcode, usersid,
758 MSIINSTALLCONTEXT_USERUNMANAGED,
759 MSISOURCETYPE_URL, "source", 0);
760 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
762 size = MAX_PATH;
763 res = RegQueryValueExA(url, "1", NULL, NULL, (LPBYTE)value, &size);
764 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
765 ok(!lstrcmpA(value, "third/"), "Expected 'third/', got %s\n", value);
766 ok(size == 7, "Expected 7, got %d\n", size);
768 size = MAX_PATH;
769 res = RegQueryValueExA(url, "2", NULL, NULL, (LPBYTE)value, &size);
770 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
771 ok(!lstrcmpA(value, "C:\\source/"), "Expected 'C:\\source/', got %s\n", value);
772 ok(size == 11, "Expected 11, got %d\n", size);
774 size = MAX_PATH;
775 res = RegQueryValueExA(url, "3", NULL, NULL, (LPBYTE)value, &size);
776 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
777 ok(!lstrcmpA(value, "another/"), "Expected 'another/', got %s\n", value);
778 ok(size == 9, "Expected 9, got %d\n", size);
780 size = MAX_PATH;
781 res = RegQueryValueExA(url, "4", NULL, NULL, (LPBYTE)value, &size);
782 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
783 ok(!lstrcmpA(value, "last/"), "Expected 'last/', got %s\n", value);
784 ok(size == 6, "Expected 6, got %d\n", size);
786 size = MAX_PATH;
787 res = RegQueryValueExA(url, "5", NULL, NULL, (LPBYTE)value, &size);
788 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
789 ok(!lstrcmpA(value, "source/"), "Expected 'source/', got %s\n", value);
790 ok(size == 8, "Expected 8, got %d\n", size);
792 /* NULL szUserSid */
793 r = pMsiSourceListAddSourceExA(prodcode, NULL,
794 MSIINSTALLCONTEXT_USERUNMANAGED,
795 MSISOURCETYPE_NETWORK, "nousersid", 0);
796 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
798 size = MAX_PATH;
799 res = RegQueryValueExA(net, "1", NULL, NULL, (LPBYTE)value, &size);
800 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
801 ok(!lstrcmpA(value, "source\\"), "Expected 'source\\', got %s\n", value);
802 ok(size == 8, "Expected 8, got %d\n", size);
804 size = MAX_PATH;
805 res = RegQueryValueExA(net, "2", NULL, NULL, (LPBYTE)value, &size);
806 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
807 ok(!lstrcmpA(value, "nousersid\\"), "Expected 'nousersid\\', got %s\n", value);
808 ok(size == 11, "Expected 11, got %d\n", size);
810 /* invalid options, must have source type */
811 r = pMsiSourceListAddSourceExA(prodcode, usersid,
812 MSIINSTALLCONTEXT_USERUNMANAGED,
813 MSICODE_PRODUCT, "source", 0);
814 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
816 r = pMsiSourceListAddSourceExA(prodcode, usersid,
817 MSIINSTALLCONTEXT_USERUNMANAGED,
818 MSICODE_PATCH, "source", 0);
819 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
821 /* NULL szSource */
822 r = pMsiSourceListAddSourceExA(prodcode, usersid,
823 MSIINSTALLCONTEXT_USERUNMANAGED,
824 MSISOURCETYPE_URL, NULL, 1);
825 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
827 /* empty szSource */
828 r = pMsiSourceListAddSourceExA(prodcode, usersid,
829 MSIINSTALLCONTEXT_USERUNMANAGED,
830 MSISOURCETYPE_URL, "", 1);
831 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
833 /* MSIINSTALLCONTEXT_USERMANAGED, non-NULL szUserSid */
835 r = pMsiSourceListAddSourceExA(prodcode, usersid,
836 MSIINSTALLCONTEXT_USERMANAGED,
837 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
838 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
840 lstrcpyA(keypath, "Software\\Microsoft\\Windows\\CurrentVersion\\Installer\\Managed\\");
841 lstrcatA(keypath, usersid);
842 lstrcatA(keypath, "\\Installer\\Products\\");
843 lstrcatA(keypath, prod_squashed);
845 res = RegCreateKeyA(HKEY_LOCAL_MACHINE, keypath, &prodkey);
846 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
848 /* product key exists */
849 r = pMsiSourceListAddSourceExA(prodcode, usersid,
850 MSIINSTALLCONTEXT_USERMANAGED,
851 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
852 ok(r == ERROR_BAD_CONFIGURATION, "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
854 res = RegCreateKeyA(prodkey, "SourceList", &hkey);
855 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
856 RegCloseKey(hkey);
858 /* SourceList exists */
859 r = pMsiSourceListAddSourceExA(prodcode, usersid,
860 MSIINSTALLCONTEXT_USERMANAGED,
861 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
862 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
864 res = RegOpenKeyA(prodkey, "SourceList\\URL", &url);
865 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
867 size = MAX_PATH;
868 res = RegQueryValueExA(url, "1", NULL, NULL, (LPBYTE)value, &size);
869 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
870 ok(!lstrcmpA(value, "C:\\source/"), "Expected 'C:\\source/', got %s\n", value);
871 ok(size == 11, "Expected 11, got %d\n", size);
873 RegCloseKey(url);
875 /* MSIINSTALLCONTEXT_USERMANAGED, NULL szUserSid */
877 r = pMsiSourceListAddSourceExA(prodcode, NULL,
878 MSIINSTALLCONTEXT_USERMANAGED,
879 MSICODE_PRODUCT | MSISOURCETYPE_URL, "another", 0);
880 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
882 res = RegOpenKeyA(prodkey, "SourceList\\URL", &url);
883 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
885 size = MAX_PATH;
886 res = RegQueryValueExA(url, "1", NULL, NULL, (LPBYTE)value, &size);
887 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
888 ok(!lstrcmpA(value, "C:\\source/"), "Expected 'C:\\source/', got %s\n", value);
889 ok(size == 11, "Expected 11, got %d\n", size);
891 size = MAX_PATH;
892 res = RegQueryValueExA(url, "2", NULL, NULL, (LPBYTE)value, &size);
893 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
894 ok(!lstrcmpA(value, "another/"), "Expected 'another/', got %s\n", value);
895 ok(size == 9, "Expected 9, got %d\n", size);
897 RegCloseKey(url);
898 RegCloseKey(prodkey);
900 /* MSIINSTALLCONTEXT_MACHINE */
902 /* szUserSid must be NULL for MSIINSTALLCONTEXT_MACHINE */
903 r = pMsiSourceListAddSourceExA(prodcode, usersid,
904 MSIINSTALLCONTEXT_MACHINE,
905 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
906 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
908 r = pMsiSourceListAddSourceExA(prodcode, NULL,
909 MSIINSTALLCONTEXT_MACHINE,
910 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
911 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
913 lstrcpyA(keypath, "Software\\Classes\\Installer\\Products\\");
914 lstrcatA(keypath, prod_squashed);
916 res = RegCreateKeyA(HKEY_LOCAL_MACHINE, keypath, &prodkey);
917 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
919 /* product key exists */
920 r = pMsiSourceListAddSourceExA(prodcode, NULL,
921 MSIINSTALLCONTEXT_MACHINE,
922 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
923 ok(r == ERROR_BAD_CONFIGURATION, "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
925 res = RegCreateKeyA(prodkey, "SourceList", &hkey);
926 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
927 RegCloseKey(hkey);
929 /* SourceList exists */
930 r = pMsiSourceListAddSourceExA(prodcode, NULL,
931 MSIINSTALLCONTEXT_MACHINE,
932 MSICODE_PRODUCT | MSISOURCETYPE_URL, "C:\\source", 0);
933 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
935 res = RegOpenKeyA(prodkey, "SourceList\\URL", &url);
936 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
938 size = MAX_PATH;
939 res = RegQueryValueExA(url, "1", NULL, NULL, (LPBYTE)value, &size);
940 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
941 ok(!lstrcmpA(value, "C:\\source/"), "Expected 'C:\\source/', got %s\n", value);
942 ok(size == 11, "Expected 11, got %d\n", size);
944 RegCloseKey(url);
945 RegCloseKey(prodkey);
946 HeapFree(GetProcessHeap(), 0, usersid);
949 static void test_MsiSourceListEnumSources(void)
951 CHAR prodcode[MAX_PATH];
952 CHAR prod_squashed[MAX_PATH];
953 CHAR keypath[MAX_PATH*2];
954 CHAR value[MAX_PATH];
955 LPSTR usersid;
956 LONG res;
957 UINT r;
958 HKEY prodkey, userkey;
959 HKEY url, net, source;
960 DWORD size;
962 create_test_guid(prodcode, prod_squashed);
963 get_user_sid(&usersid);
965 /* GetLastError is not set by the function */
967 /* NULL szProductCodeOrPatchCode */
968 size = 0xdeadbeef;
969 r = MsiSourceListEnumSourcesA(NULL, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
970 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
971 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
972 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
974 /* empty szProductCodeOrPatchCode */
975 size = 0xdeadbeef;
976 r = MsiSourceListEnumSourcesA("", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
977 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
978 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
979 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
981 /* garbage szProductCodeOrPatchCode */
982 size = 0xdeadbeef;
983 r = MsiSourceListEnumSourcesA("garbage", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
984 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
985 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
986 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
988 /* guid without brackets */
989 size = 0xdeadbeef;
990 r = MsiSourceListEnumSourcesA("51CD2AD5-0482-4C46-8DDD-0ED1022AA1AA",
991 usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
992 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
993 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
994 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
996 /* guid with brackets */
997 size = 0xdeadbeef;
998 r = MsiSourceListEnumSourcesA("{51CD2AD5-0482-4C46-8DDD-0ED1022AA1AA}",
999 usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
1000 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1001 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1002 ok(size == 0xdeadbeef, "Expected 0xdeadbeef, got %d\n", size);
1004 /* MSIINSTALLCONTEXT_USERUNMANAGED */
1006 size = MAX_PATH;
1007 lstrcpyA(value, "aaa");
1008 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1009 MSIINSTALLCONTEXT_USERUNMANAGED,
1010 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1011 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1012 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1013 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1015 lstrcpyA(keypath, "Software\\Microsoft\\Installer\\Products\\");
1016 lstrcatA(keypath, prod_squashed);
1018 res = RegCreateKeyA(HKEY_CURRENT_USER, keypath, &userkey);
1019 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1021 /* user product key exists */
1022 size = MAX_PATH;
1023 lstrcpyA(value, "aaa");
1024 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1025 MSIINSTALLCONTEXT_USERUNMANAGED,
1026 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1027 ok(r == ERROR_BAD_CONFIGURATION, "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
1028 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1029 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1031 res = RegCreateKeyA(userkey, "SourceList", &source);
1032 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1034 /* SourceList key exists */
1035 size = MAX_PATH;
1036 lstrcpyA(value, "aaa");
1037 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1038 MSIINSTALLCONTEXT_USERUNMANAGED,
1039 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1040 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1041 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1042 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1044 res = RegCreateKeyA(source, "URL", &url);
1045 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1047 /* URL key exists */
1048 size = MAX_PATH;
1049 lstrcpyA(value, "aaa");
1050 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1051 MSIINSTALLCONTEXT_USERUNMANAGED,
1052 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1053 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1054 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1055 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1057 res = RegSetValueExA(url, "1", 0, REG_SZ, (LPBYTE)"first", 6);
1058 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1060 res = RegSetValueExA(url, "2", 0, REG_SZ, (LPBYTE)"second", 7);
1061 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1063 res = RegSetValueExA(url, "4", 0, REG_SZ, (LPBYTE)"fourth", 7);
1064 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1066 /* sources exist */
1067 size = MAX_PATH;
1068 lstrcpyA(value, "aaa");
1069 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1070 MSIINSTALLCONTEXT_USERUNMANAGED,
1071 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1072 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1073 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1074 ok(size == 5, "Expected 5, got %d\n", size);
1076 /* try index 0 again */
1077 size = MAX_PATH;
1078 lstrcpyA(value, "aaa");
1079 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1080 MSIINSTALLCONTEXT_USERUNMANAGED,
1081 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1082 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1083 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1084 ok(size == 5, "Expected 5, got %d\n", size);
1086 /* both szSource and pcchSource are NULL, index 0 */
1087 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1088 MSIINSTALLCONTEXT_USERUNMANAGED,
1089 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, NULL, NULL);
1090 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1092 /* both szSource and pcchSource are NULL, index 1 */
1093 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1094 MSIINSTALLCONTEXT_USERUNMANAGED,
1095 MSICODE_PRODUCT | MSISOURCETYPE_URL, 1, NULL, NULL);
1096 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1098 /* size is exactly 5 */
1099 size = 5;
1100 lstrcpyA(value, "aaa");
1101 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1102 MSIINSTALLCONTEXT_USERUNMANAGED,
1103 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1104 ok(r == ERROR_MORE_DATA, "Expected ERROR_MORE_DATA, got %d\n", r);
1105 ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got %s\n", value);
1106 ok(size == 5, "Expected 5, got %d\n", size);
1108 /* szSource is non-NULL while pcchSource is NULL */
1109 lstrcpyA(value, "aaa");
1110 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1111 MSIINSTALLCONTEXT_USERUNMANAGED,
1112 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, NULL);
1113 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1114 ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got %s\n", value);
1116 /* try index 1 after failure */
1117 size = MAX_PATH;
1118 lstrcpyA(value, "aaa");
1119 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1120 MSIINSTALLCONTEXT_USERUNMANAGED,
1121 MSICODE_PRODUCT | MSISOURCETYPE_URL, 1, value, &size);
1122 ok(r == ERROR_INVALID_PARAMETER,
1123 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1124 ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got %s\n", value);
1125 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1127 /* reset the enumeration */
1128 size = MAX_PATH;
1129 lstrcpyA(value, "aaa");
1130 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1131 MSIINSTALLCONTEXT_USERUNMANAGED,
1132 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1133 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1134 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1135 ok(size == 5, "Expected 5, got %d\n", size);
1137 /* try index 1 */
1138 size = MAX_PATH;
1139 lstrcpyA(value, "aaa");
1140 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1141 MSIINSTALLCONTEXT_USERUNMANAGED,
1142 MSICODE_PRODUCT | MSISOURCETYPE_URL, 1, value, &size);
1143 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1144 ok(!lstrcmpA(value, "second"), "Expected \"second\", got %s\n", value);
1145 ok(size == 6, "Expected 6, got %d\n", size);
1147 /* try index 1 again */
1148 size = MAX_PATH;
1149 lstrcpyA(value, "aaa");
1150 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1151 MSIINSTALLCONTEXT_USERUNMANAGED,
1152 MSICODE_PRODUCT | MSISOURCETYPE_URL, 1, value, &size);
1153 ok(r == ERROR_INVALID_PARAMETER,
1154 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1155 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1156 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1158 /* try index 2 */
1159 size = MAX_PATH;
1160 lstrcpyA(value, "aaa");
1161 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1162 MSIINSTALLCONTEXT_USERUNMANAGED,
1163 MSICODE_PRODUCT | MSISOURCETYPE_URL, 2, value, &size);
1164 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1165 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1166 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1168 /* try index < 0 */
1169 size = MAX_PATH;
1170 lstrcpyA(value, "aaa");
1171 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1172 MSIINSTALLCONTEXT_USERUNMANAGED,
1173 MSICODE_PRODUCT | MSISOURCETYPE_URL, -1, value, &size);
1174 ok(r == ERROR_INVALID_PARAMETER,
1175 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1176 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1177 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1179 /* NULL szUserSid */
1180 size = MAX_PATH;
1181 lstrcpyA(value, "aaa");
1182 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1183 MSIINSTALLCONTEXT_USERUNMANAGED,
1184 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1185 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1186 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1187 ok(size == 5, "Expected 5, got %d\n", size);
1189 /* invalid dwOptions, must be one of MSICODE_ and MSISOURCETYPE_ */
1190 size = MAX_PATH;
1191 lstrcpyA(value, "aaa");
1192 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1193 MSIINSTALLCONTEXT_USERUNMANAGED,
1194 MSICODE_PRODUCT, 0, value, &size);
1195 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1196 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1197 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1199 /* invalid dwOptions, must be one of MSICODE_ and MSISOURCETYPE_ */
1200 size = MAX_PATH;
1201 lstrcpyA(value, "aaa");
1202 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1203 MSIINSTALLCONTEXT_USERUNMANAGED,
1204 MSICODE_PATCH, 0, value, &size);
1205 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1206 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1207 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1209 /* invalid dwOptions, must be one of MSICODE_ and MSISOURCETYPE_ */
1210 size = MAX_PATH;
1211 lstrcpyA(value, "aaa");
1212 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1213 MSIINSTALLCONTEXT_USERUNMANAGED,
1214 MSICODE_PRODUCT | MSICODE_PATCH | MSISOURCETYPE_URL,
1215 0, value, &size);
1216 ok(r == ERROR_UNKNOWN_PATCH, "Expected ERROR_SUCCESS, got %d\n", r);
1217 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1218 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1220 /* invalid dwOptions, must be one of MSICODE_ and MSISOURCETYPE_ */
1221 size = MAX_PATH;
1222 lstrcpyA(value, "aaa");
1223 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1224 MSIINSTALLCONTEXT_USERUNMANAGED,
1225 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK | MSISOURCETYPE_URL,
1226 0, value, &size);
1227 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1228 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1229 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1231 RegDeleteValueA(url, "1");
1232 RegDeleteValueA(url, "2");
1233 RegDeleteValueA(url, "4");
1234 RegDeleteKeyA(url, "");
1235 RegCloseKey(url);
1237 /* SourceList key exists */
1238 size = MAX_PATH;
1239 lstrcpyA(value, "aaa");
1240 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1241 MSIINSTALLCONTEXT_USERUNMANAGED,
1242 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1243 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1244 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1245 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1247 res = RegCreateKeyA(source, "Net", &net);
1248 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1250 /* Net key exists */
1251 size = MAX_PATH;
1252 lstrcpyA(value, "aaa");
1253 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1254 MSIINSTALLCONTEXT_USERUNMANAGED,
1255 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1256 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1257 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1258 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1260 res = RegSetValueExA(net, "1", 0, REG_SZ, (LPBYTE)"first", 6);
1261 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1263 /* sources exist */
1264 size = MAX_PATH;
1265 lstrcpyA(value, "aaa");
1266 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1267 MSIINSTALLCONTEXT_USERUNMANAGED,
1268 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1269 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1270 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1271 ok(size == 5, "Expected 5, got %d\n", size);
1273 RegDeleteValueA(net, "1");
1274 RegDeleteKeyA(net, "");
1275 RegCloseKey(net);
1276 RegDeleteKeyA(source, "");
1277 RegCloseKey(source);
1278 RegDeleteKeyA(userkey, "");
1279 RegCloseKey(userkey);
1281 /* MSIINSTALLCONTEXT_USERMANAGED */
1283 size = MAX_PATH;
1284 lstrcpyA(value, "aaa");
1285 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1286 MSIINSTALLCONTEXT_USERMANAGED,
1287 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1288 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1289 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1290 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1292 lstrcpyA(keypath, "Software\\Microsoft\\Windows\\CurrentVersion\\Installer\\Managed\\");
1293 lstrcatA(keypath, usersid);
1294 lstrcatA(keypath, "\\Installer\\Products\\");
1295 lstrcatA(keypath, prod_squashed);
1297 res = RegCreateKeyA(HKEY_LOCAL_MACHINE, keypath, &userkey);
1298 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1300 /* user product key exists */
1301 size = MAX_PATH;
1302 lstrcpyA(value, "aaa");
1303 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1304 MSIINSTALLCONTEXT_USERMANAGED,
1305 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1306 ok(r == ERROR_BAD_CONFIGURATION, "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
1307 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1308 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1310 res = RegCreateKeyA(userkey, "SourceList", &source);
1311 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1313 /* SourceList key exists */
1314 size = MAX_PATH;
1315 lstrcpyA(value, "aaa");
1316 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1317 MSIINSTALLCONTEXT_USERMANAGED,
1318 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1319 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1320 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1321 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1323 res = RegCreateKeyA(source, "URL", &url);
1324 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1326 /* URL key exists */
1327 size = MAX_PATH;
1328 lstrcpyA(value, "aaa");
1329 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1330 MSIINSTALLCONTEXT_USERMANAGED,
1331 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1332 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1333 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1334 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1336 res = RegSetValueExA(url, "1", 0, REG_SZ, (LPBYTE)"first", 6);
1337 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1339 /* sources exist */
1340 size = MAX_PATH;
1341 lstrcpyA(value, "aaa");
1342 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1343 MSIINSTALLCONTEXT_USERMANAGED,
1344 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1345 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1346 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1347 ok(size == 5, "Expected 5, got %d\n", size);
1349 /* NULL szUserSid */
1350 size = MAX_PATH;
1351 lstrcpyA(value, "aaa");
1352 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1353 MSIINSTALLCONTEXT_USERMANAGED,
1354 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1355 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1356 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1357 ok(size == 5, "Expected 5, got %d\n", size);
1359 RegDeleteValueA(url, "1");
1360 RegDeleteKeyA(url, "");
1361 RegCloseKey(url);
1363 /* SourceList key exists */
1364 size = MAX_PATH;
1365 lstrcpyA(value, "aaa");
1366 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1367 MSIINSTALLCONTEXT_USERMANAGED,
1368 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1369 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1370 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1371 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1373 res = RegCreateKeyA(source, "Net", &net);
1374 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1376 /* Net key exists */
1377 size = MAX_PATH;
1378 lstrcpyA(value, "aaa");
1379 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1380 MSIINSTALLCONTEXT_USERMANAGED,
1381 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1382 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1383 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1384 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1386 res = RegSetValueExA(net, "1", 0, REG_SZ, (LPBYTE)"first", 6);
1387 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1389 /* sources exist */
1390 size = MAX_PATH;
1391 lstrcpyA(value, "aaa");
1392 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1393 MSIINSTALLCONTEXT_USERMANAGED,
1394 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1395 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1396 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1397 ok(size == 5, "Expected 5, got %d\n", size);
1399 RegDeleteValueA(net, "1");
1400 RegDeleteKeyA(net, "");
1401 RegCloseKey(net);
1402 RegDeleteKeyA(source, "");
1403 RegCloseKey(source);
1404 RegDeleteKeyA(userkey, "");
1405 RegCloseKey(userkey);
1407 /* MSIINSTALLCONTEXT_MACHINE */
1409 /* szUserSid is non-NULL */
1410 size = MAX_PATH;
1411 lstrcpyA(value, "aaa");
1412 r = MsiSourceListEnumSourcesA(prodcode, usersid,
1413 MSIINSTALLCONTEXT_MACHINE,
1414 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1415 ok(r == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1416 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1417 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1419 /* szUserSid is non-NULL */
1420 size = MAX_PATH;
1421 lstrcpyA(value, "aaa");
1422 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1423 MSIINSTALLCONTEXT_MACHINE,
1424 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1425 ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1426 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1427 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1429 lstrcpyA(keypath, "Software\\Classes\\Installer\\Products\\");
1430 lstrcatA(keypath, prod_squashed);
1432 res = RegCreateKeyA(HKEY_LOCAL_MACHINE, keypath, &prodkey);
1433 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1435 /* user product key exists */
1436 size = MAX_PATH;
1437 lstrcpyA(value, "aaa");
1438 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1439 MSIINSTALLCONTEXT_MACHINE,
1440 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1441 ok(r == ERROR_BAD_CONFIGURATION, "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
1442 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1443 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1445 res = RegCreateKeyA(prodkey, "SourceList", &source);
1446 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1448 /* SourceList key exists */
1449 size = MAX_PATH;
1450 lstrcpyA(value, "aaa");
1451 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1452 MSIINSTALLCONTEXT_MACHINE,
1453 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1454 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1455 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1456 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1458 res = RegCreateKeyA(source, "URL", &url);
1459 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1461 /* URL key exists */
1462 size = MAX_PATH;
1463 lstrcpyA(value, "aaa");
1464 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1465 MSIINSTALLCONTEXT_MACHINE,
1466 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1467 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1468 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1469 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1471 res = RegSetValueExA(url, "1", 0, REG_SZ, (LPBYTE)"first", 6);
1472 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1474 /* sources exist */
1475 size = MAX_PATH;
1476 lstrcpyA(value, "aaa");
1477 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1478 MSIINSTALLCONTEXT_MACHINE,
1479 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1480 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1481 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1482 ok(size == 5, "Expected 5, got %d\n", size);
1484 /* NULL szUserSid */
1485 size = MAX_PATH;
1486 lstrcpyA(value, "aaa");
1487 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1488 MSIINSTALLCONTEXT_MACHINE,
1489 MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
1490 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1491 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1492 ok(size == 5, "Expected 5, got %d\n", size);
1494 RegDeleteValueA(url, "1");
1495 RegDeleteKeyA(url, "");
1496 RegCloseKey(url);
1498 /* SourceList key exists */
1499 size = MAX_PATH;
1500 lstrcpyA(value, "aaa");
1501 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1502 MSIINSTALLCONTEXT_MACHINE,
1503 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1504 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1505 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1506 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1508 res = RegCreateKeyA(source, "Net", &net);
1509 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1511 /* Net key exists */
1512 size = MAX_PATH;
1513 lstrcpyA(value, "aaa");
1514 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1515 MSIINSTALLCONTEXT_MACHINE,
1516 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1517 ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
1518 ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
1519 ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
1521 res = RegSetValueExA(net, "1", 0, REG_SZ, (LPBYTE)"first", 6);
1522 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1524 /* sources exist */
1525 size = MAX_PATH;
1526 lstrcpyA(value, "aaa");
1527 r = MsiSourceListEnumSourcesA(prodcode, NULL,
1528 MSIINSTALLCONTEXT_MACHINE,
1529 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
1530 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1531 ok(!lstrcmpA(value, "first"), "Expected \"first\", got %s\n", value);
1532 ok(size == 5, "Expected 5, got %d\n", size);
1534 RegDeleteValueA(net, "1");
1535 RegDeleteKeyA(net, "");
1536 RegCloseKey(net);
1537 RegDeleteKeyA(source, "");
1538 RegCloseKey(source);
1539 RegDeleteKeyA(prodkey, "");
1540 RegCloseKey(prodkey);
1543 static void test_MsiSourceListSetInfo(void)
1545 CHAR prodcode[MAX_PATH];
1546 CHAR prod_squashed[MAX_PATH];
1547 CHAR keypath[MAX_PATH*2];
1548 HKEY prodkey, userkey;
1549 HKEY net, url, media, source;
1550 LPSTR usersid;
1551 LONG res;
1552 UINT r;
1554 create_test_guid(prodcode, prod_squashed);
1555 get_user_sid(&usersid);
1557 /* GetLastError is not set by the function */
1559 /* NULL szProductCodeOrPatchCode */
1560 r = MsiSourceListSetInfoA(NULL, usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
1561 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1562 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1563 ok(r == ERROR_INVALID_PARAMETER,
1564 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1566 /* empty szProductCodeOrPatchCode */
1567 r = MsiSourceListSetInfoA("", usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
1568 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1569 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1570 ok(r == ERROR_INVALID_PARAMETER,
1571 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1573 /* garbage szProductCodeOrPatchCode */
1574 r = MsiSourceListSetInfoA("garbage", usersid,
1575 MSIINSTALLCONTEXT_USERUNMANAGED,
1576 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1577 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1578 ok(r == ERROR_INVALID_PARAMETER,
1579 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1581 /* guid without brackets */
1582 r = MsiSourceListSetInfoA("51CD2AD5-0482-4C46-8DDD-0ED1022AA1AA",
1583 usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
1584 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1585 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1586 ok(r == ERROR_INVALID_PARAMETER,
1587 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1589 /* guid with brackets */
1590 r = MsiSourceListSetInfoA("{51CD2AD5-0482-4C46-8DDD-0ED1022AA1AA}",
1591 usersid, MSIINSTALLCONTEXT_USERUNMANAGED,
1592 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1593 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1594 ok(r == ERROR_UNKNOWN_PRODUCT,
1595 "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1597 /* dwOptions is MSICODE_PRODUCT */
1598 r = MsiSourceListSetInfoA(prodcode, usersid,
1599 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1600 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1601 ok(r == ERROR_UNKNOWN_PRODUCT,
1602 "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1604 /* dwOptions is MSICODE_PATCH */
1605 r = MsiSourceListSetInfoA(prodcode, usersid,
1606 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PATCH,
1607 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1608 ok(r == ERROR_UNKNOWN_PATCH, "Expected ERROR_UNKNOWN_PATCH, got %d\n", r);
1610 /* dwOptions is both MSICODE_PRODUCT and MSICODE_PATCH */
1611 r = MsiSourceListSetInfoA(prodcode, usersid,
1612 MSIINSTALLCONTEXT_USERUNMANAGED,
1613 MSICODE_PRODUCT | MSICODE_PATCH | MSISOURCETYPE_URL,
1614 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1615 ok(r == ERROR_UNKNOWN_PATCH, "Expected ERROR_UNKNOWN_PATCH, got %d\n", r);
1617 /* dwOptions has both MSISOURCETYPE_NETWORK and MSISOURCETYPE_URL */
1618 r = MsiSourceListSetInfoA(prodcode, NULL,
1619 MSIINSTALLCONTEXT_USERUNMANAGED,
1620 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK | MSISOURCETYPE_URL,
1621 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1622 ok(r == ERROR_UNKNOWN_PRODUCT,
1623 "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1625 /* LastUsedSource and dwOptions has both
1626 * MSISOURCETYPE_NETWORK and MSISOURCETYPE_URL
1628 r = MsiSourceListSetInfoA(prodcode, NULL,
1629 MSIINSTALLCONTEXT_USERUNMANAGED,
1630 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK | MSISOURCETYPE_URL,
1631 INSTALLPROPERTY_LASTUSEDSOURCE, "path");
1632 ok(r == ERROR_UNKNOWN_PRODUCT,
1633 "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1635 /* LastUsedSource and dwOptions has no source type */
1636 r = MsiSourceListSetInfoA(prodcode, NULL,
1637 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1638 INSTALLPROPERTY_LASTUSEDSOURCE, "path");
1639 ok(r == ERROR_UNKNOWN_PRODUCT,
1640 "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
1642 /* MSIINSTALLCONTEXT_USERUNMANAGED */
1644 lstrcpyA(keypath, "Software\\Microsoft\\Installer\\Products\\");
1645 lstrcatA(keypath, prod_squashed);
1647 res = RegCreateKeyA(HKEY_CURRENT_USER, keypath, &userkey);
1648 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1650 /* user product key exists */
1651 r = MsiSourceListSetInfoA(prodcode, NULL,
1652 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1653 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1654 ok(r == ERROR_BAD_CONFIGURATION,
1655 "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
1657 res = RegCreateKeyA(userkey, "SourceList", &source);
1658 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1660 /* SourceList key exists, no source type */
1661 r = MsiSourceListSetInfoA(prodcode, NULL,
1662 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1663 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1664 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1666 /* Media key is created by MsiSourceListSetInfo */
1667 res = RegOpenKeyA(source, "Media", &media);
1668 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1669 CHECK_REG_STR(media, "MediaPackage", "path");
1671 /* set the info again */
1672 r = MsiSourceListSetInfoA(prodcode, NULL,
1673 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1674 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path2");
1675 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1676 CHECK_REG_STR(media, "MediaPackage", "path2");
1678 /* NULL szProperty */
1679 r = MsiSourceListSetInfoA(prodcode, NULL,
1680 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1681 NULL, "path");
1682 ok(r == ERROR_INVALID_PARAMETER,
1683 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1685 /* empty szProperty */
1686 r = MsiSourceListSetInfoA(prodcode, NULL,
1687 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1688 "", "path");
1689 ok(r == ERROR_UNKNOWN_PROPERTY,
1690 "Expected ERROR_UNKNOWN_PROPERTY, got %d\n", r);
1692 /* NULL szValue */
1693 r = MsiSourceListSetInfoA(prodcode, NULL,
1694 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1695 INSTALLPROPERTY_MEDIAPACKAGEPATH, NULL);
1696 ok(r == ERROR_UNKNOWN_PROPERTY,
1697 "Expected ERROR_UNKNOWN_PROPERTY, got %d\n", r);
1699 /* empty szValue */
1700 r = MsiSourceListSetInfoA(prodcode, NULL,
1701 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1702 INSTALLPROPERTY_MEDIAPACKAGEPATH, "");
1703 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1704 CHECK_REG_STR(media, "MediaPackage", "");
1706 /* INSTALLPROPERTY_MEDIAPACKAGEPATH, MSISOURCETYPE_NETWORK */
1707 r = MsiSourceListSetInfoA(prodcode, NULL,
1708 MSIINSTALLCONTEXT_USERUNMANAGED,
1709 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1710 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1711 ok(r == ERROR_INVALID_PARAMETER,
1712 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1714 /* INSTALLPROPERTY_MEDIAPACKAGEPATH, MSISOURCETYPE_URL */
1715 r = MsiSourceListSetInfoA(prodcode, NULL,
1716 MSIINSTALLCONTEXT_USERUNMANAGED,
1717 MSICODE_PRODUCT | MSISOURCETYPE_URL,
1718 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1719 ok(r == ERROR_INVALID_PARAMETER,
1720 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1722 /* INSTALLPROPERTY_DISKPROMPT */
1723 r = MsiSourceListSetInfoA(prodcode, NULL,
1724 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1725 INSTALLPROPERTY_DISKPROMPT, "prompt");
1726 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1727 CHECK_REG_STR(media, "DiskPrompt", "prompt");
1729 /* INSTALLPROPERTY_DISKPROMPT, MSISOURCETYPE_NETWORK */
1730 r = MsiSourceListSetInfoA(prodcode, NULL,
1731 MSIINSTALLCONTEXT_USERUNMANAGED,
1732 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1733 INSTALLPROPERTY_DISKPROMPT, "prompt");
1734 ok(r == ERROR_INVALID_PARAMETER,
1735 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1737 /* INSTALLPROPERTY_DISKPROMPT, MSISOURCETYPE_URL */
1738 r = MsiSourceListSetInfoA(prodcode, NULL,
1739 MSIINSTALLCONTEXT_USERUNMANAGED,
1740 MSICODE_PRODUCT | MSISOURCETYPE_URL,
1741 INSTALLPROPERTY_DISKPROMPT, "prompt");
1742 ok(r == ERROR_INVALID_PARAMETER,
1743 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1745 /* INSTALLPROPERTY_LASTUSEDSOURCE */
1746 r = MsiSourceListSetInfoA(prodcode, NULL,
1747 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1748 INSTALLPROPERTY_LASTUSEDSOURCE, "source");
1749 ok(r == ERROR_INVALID_PARAMETER,
1750 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1752 /* INSTALLPROPERTY_LASTUSEDSOURCE, MSISOURCETYPE_NETWORK */
1753 r = MsiSourceListSetInfoA(prodcode, NULL,
1754 MSIINSTALLCONTEXT_USERUNMANAGED,
1755 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1756 INSTALLPROPERTY_LASTUSEDSOURCE, "source");
1757 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1759 /* Net key is created by MsiSourceListSetInfo */
1760 res = RegOpenKeyA(source, "Net", &net);
1761 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1762 CHECK_REG_STR(net, "1", "source\\")
1763 CHECK_REG_STR(source, "LastUsedSource", "n;1;source");
1765 /* source has forward slash */
1766 r = MsiSourceListSetInfoA(prodcode, NULL,
1767 MSIINSTALLCONTEXT_USERUNMANAGED,
1768 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1769 INSTALLPROPERTY_LASTUSEDSOURCE, "source/");
1770 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1771 CHECK_REG_STR(net, "1", "source\\");
1772 CHECK_REG_STR(net, "2", "source/\\");
1773 CHECK_REG_STR(source, "LastUsedSource", "n;2;source/");
1775 /* INSTALLPROPERTY_LASTUSEDSOURCE, MSISOURCETYPE_URL */
1776 r = MsiSourceListSetInfoA(prodcode, NULL,
1777 MSIINSTALLCONTEXT_USERUNMANAGED,
1778 MSICODE_PRODUCT | MSISOURCETYPE_URL,
1779 INSTALLPROPERTY_LASTUSEDSOURCE, "source");
1780 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1782 /* URL key is created by MsiSourceListSetInfo */
1783 res = RegOpenKeyA(source, "URL", &url);
1784 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1785 CHECK_REG_STR(url, "1", "source/");
1786 CHECK_REG_STR(source, "LastUsedSource", "u;1;source");
1788 /* source has backslash */
1789 r = MsiSourceListSetInfoA(prodcode, NULL,
1790 MSIINSTALLCONTEXT_USERUNMANAGED,
1791 MSICODE_PRODUCT | MSISOURCETYPE_URL,
1792 INSTALLPROPERTY_LASTUSEDSOURCE, "source\\");
1793 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1794 CHECK_REG_STR(url, "1", "source/");
1795 CHECK_REG_STR(url, "2", "source\\/");
1796 CHECK_REG_STR(source, "LastUsedSource", "u;2;source\\");
1798 /* INSTALLPROPERTY_LASTUSEDSOURCE, MSISOURCETYPE_MEDIA */
1799 r = MsiSourceListSetInfoA(prodcode, NULL,
1800 MSIINSTALLCONTEXT_USERUNMANAGED,
1801 MSICODE_PRODUCT | MSISOURCETYPE_MEDIA,
1802 INSTALLPROPERTY_LASTUSEDSOURCE, "source");
1803 ok(r == ERROR_INVALID_PARAMETER,
1804 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1806 /* INSTALLPROPERTY_PACKAGENAME */
1807 r = MsiSourceListSetInfoA(prodcode, NULL,
1808 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1809 INSTALLPROPERTY_PACKAGENAME, "name");
1810 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1811 CHECK_REG_STR(source, "PackageName", "name");
1813 /* INSTALLPROPERTY_PACKAGENAME, MSISOURCETYPE_NETWORK */
1814 r = MsiSourceListSetInfoA(prodcode, NULL,
1815 MSIINSTALLCONTEXT_USERUNMANAGED,
1816 MSICODE_PRODUCT | MSISOURCETYPE_NETWORK,
1817 INSTALLPROPERTY_PACKAGENAME, "name");
1818 ok(r == ERROR_INVALID_PARAMETER,
1819 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1821 /* INSTALLPROPERTY_PACKAGENAME, MSISOURCETYPE_URL */
1822 r = MsiSourceListSetInfoA(prodcode, NULL,
1823 MSIINSTALLCONTEXT_USERUNMANAGED,
1824 MSICODE_PRODUCT | MSISOURCETYPE_URL,
1825 INSTALLPROPERTY_PACKAGENAME, "name");
1826 ok(r == ERROR_INVALID_PARAMETER,
1827 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1829 /* INSTALLPROPERTY_LASTUSEDTYPE */
1830 r = MsiSourceListSetInfoA(prodcode, NULL,
1831 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1832 INSTALLPROPERTY_LASTUSEDTYPE, "type");
1833 ok(r == ERROR_UNKNOWN_PROPERTY,
1834 "Expected ERROR_UNKNOWN_PROPERTY, got %d\n", r);
1836 /* definitely unknown property */
1837 r = MsiSourceListSetInfoA(prodcode, NULL,
1838 MSIINSTALLCONTEXT_USERUNMANAGED, MSICODE_PRODUCT,
1839 "unknown", "val");
1840 ok(r == ERROR_UNKNOWN_PROPERTY,
1841 "Expected ERROR_UNKNOWN_PROPERTY, got %d\n", r);
1843 RegDeleteValueA(net, "1");
1844 RegDeleteKeyA(net, "");
1845 RegCloseKey(net);
1846 RegDeleteValueA(url, "1");
1847 RegDeleteKeyA(url, "");
1848 RegCloseKey(url);
1849 RegDeleteValueA(media, "MediaPackage");
1850 RegDeleteValueA(media, "DiskPrompt");
1851 RegDeleteKeyA(media, "");
1852 RegCloseKey(media);
1853 RegDeleteValueA(source, "PackageName");
1854 RegDeleteKeyA(source, "");
1855 RegCloseKey(source);
1856 RegDeleteKeyA(userkey, "");
1857 RegCloseKey(userkey);
1859 /* MSIINSTALLCONTEXT_USERMANAGED */
1861 lstrcpyA(keypath, "Software\\Microsoft\\Windows\\CurrentVersion\\Installer\\Managed\\");
1862 lstrcatA(keypath, usersid);
1863 lstrcatA(keypath, "\\Installer\\Products\\");
1864 lstrcatA(keypath, prod_squashed);
1866 res = RegCreateKeyA(HKEY_LOCAL_MACHINE, keypath, &userkey);
1867 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1869 /* user product key exists */
1870 r = MsiSourceListSetInfoA(prodcode, NULL,
1871 MSIINSTALLCONTEXT_USERMANAGED, MSICODE_PRODUCT,
1872 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1873 ok(r == ERROR_BAD_CONFIGURATION,
1874 "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
1876 res = RegCreateKeyA(userkey, "SourceList", &source);
1877 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1879 /* SourceList key exists, no source type */
1880 r = MsiSourceListSetInfoA(prodcode, NULL,
1881 MSIINSTALLCONTEXT_USERMANAGED, MSICODE_PRODUCT,
1882 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1883 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1885 /* Media key is created by MsiSourceListSetInfo */
1886 res = RegOpenKeyA(source, "Media", &media);
1887 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1888 CHECK_REG_STR(media, "MediaPackage", "path");
1890 RegDeleteValueA(media, "MediaPackage");
1891 RegDeleteKeyA(media, "");
1892 RegCloseKey(media);
1893 RegDeleteKeyA(source, "");
1894 RegCloseKey(source);
1895 RegDeleteKeyA(userkey, "");
1896 RegCloseKey(userkey);
1898 /* MSIINSTALLCONTEXT_MACHINE */
1900 lstrcpyA(keypath, "Software\\Classes\\Installer\\Products\\");
1901 lstrcatA(keypath, prod_squashed);
1903 res = RegCreateKeyA(HKEY_LOCAL_MACHINE, keypath, &prodkey);
1904 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1906 /* user product key exists */
1907 r = MsiSourceListSetInfoA(prodcode, NULL,
1908 MSIINSTALLCONTEXT_MACHINE, MSICODE_PRODUCT,
1909 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1910 ok(r == ERROR_BAD_CONFIGURATION,
1911 "Expected ERROR_BAD_CONFIGURATION, got %d\n", r);
1913 res = RegCreateKeyA(prodkey, "SourceList", &source);
1914 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1916 /* SourceList key exists, no source type */
1917 r = MsiSourceListSetInfoA(prodcode, NULL,
1918 MSIINSTALLCONTEXT_MACHINE, MSICODE_PRODUCT,
1919 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1920 ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
1922 /* Media key is created by MsiSourceListSetInfo */
1923 res = RegOpenKeyA(source, "Media", &media);
1924 ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
1925 CHECK_REG_STR(media, "MediaPackage", "path");
1927 /* szUserSid is non-NULL */
1928 r = MsiSourceListSetInfoA(prodcode, usersid,
1929 MSIINSTALLCONTEXT_MACHINE, MSICODE_PRODUCT,
1930 INSTALLPROPERTY_MEDIAPACKAGEPATH, "path");
1931 ok(r == ERROR_INVALID_PARAMETER,
1932 "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
1934 RegDeleteValueA(media, "MediaPackage");
1935 RegDeleteKeyA(media, "");
1936 RegCloseKey(media);
1937 RegDeleteKeyA(source, "");
1938 RegCloseKey(source);
1939 RegDeleteKeyA(prodkey, "");
1940 RegCloseKey(prodkey);
1943 START_TEST(source)
1945 init_functionpointers();
1947 test_MsiSourceListGetInfo();
1948 test_MsiSourceListAddSourceEx();
1949 test_MsiSourceListEnumSources();
1950 test_MsiSourceListSetInfo();