include/msvcrt: Define more CPU control word flags.
[wine] / dlls / msi / tests / install.c
1 /*
2  * Copyright (C) 2006 James Hawkins
3  *
4  * A test program for installing MSI products.
5  *
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.
10  *
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.
15  *
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
19  */
20
21 #define _WIN32_MSI 300
22 #define COBJMACROS
23
24 #include <stdio.h>
25
26 #include <windows.h>
27 #include <msiquery.h>
28 #include <msidefs.h>
29 #include <msi.h>
30 #include <fci.h>
31 #include <objidl.h>
32 #include <srrestoreptapi.h>
33 #include <shlobj.h>
34
35 #include "wine/test.h"
36
37 static UINT (WINAPI *pMsiQueryComponentStateA)
38     (LPCSTR, LPCSTR, MSIINSTALLCONTEXT, LPCSTR, INSTALLSTATE*);
39 static UINT (WINAPI *pMsiSetExternalUIRecord)
40     (INSTALLUI_HANDLER_RECORD, DWORD, LPVOID, PINSTALLUI_HANDLER_RECORD);
41 static UINT (WINAPI *pMsiSourceListEnumSourcesA)
42     (LPCSTR, LPCSTR, MSIINSTALLCONTEXT, DWORD, DWORD, LPSTR, LPDWORD);
43 static UINT (WINAPI *pMsiSourceListGetInfoA)
44     (LPCSTR, LPCSTR, MSIINSTALLCONTEXT, DWORD, LPCSTR, LPSTR, LPDWORD);
45 static INSTALLSTATE (WINAPI *pMsiGetComponentPathExA)
46     (LPCSTR, LPCSTR, LPCSTR, MSIINSTALLCONTEXT, LPSTR, LPDWORD);
47
48 static BOOL (WINAPI *pConvertSidToStringSidA)(PSID, LPSTR*);
49 static BOOL (WINAPI *pGetTokenInformation)( HANDLE, TOKEN_INFORMATION_CLASS, LPVOID, DWORD, PDWORD );
50 static BOOL (WINAPI *pOpenProcessToken)( HANDLE, DWORD, PHANDLE );
51 static LONG (WINAPI *pRegDeleteKeyExA)(HKEY, LPCSTR, REGSAM, DWORD);
52 static BOOL (WINAPI *pIsWow64Process)(HANDLE, PBOOL);
53
54 static HMODULE hsrclient = 0;
55 static BOOL (WINAPI *pSRRemoveRestorePoint)(DWORD);
56 static BOOL (WINAPI *pSRSetRestorePointA)(RESTOREPOINTINFOA*, STATEMGRSTATUS*);
57
58 static BOOL on_win9x = FALSE;
59 static BOOL is_wow64;
60 static const BOOL is_64bit = sizeof(void *) > sizeof(int);
61
62 static const char *msifile = "msitest.msi";
63 static const char *msifile2 = "winetest2.msi";
64 static const char *mstfile = "winetest.mst";
65 static CHAR CURR_DIR[MAX_PATH];
66 static CHAR PROG_FILES_DIR[MAX_PATH];
67 static CHAR PROG_FILES_DIR_NATIVE[MAX_PATH];
68 static CHAR COMMON_FILES_DIR[MAX_PATH];
69 static CHAR APP_DATA_DIR[MAX_PATH];
70 static CHAR WINDOWS_DIR[MAX_PATH];
71
72 /* msi database data */
73
74 static const CHAR component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
75                                     "s72\tS38\ts72\ti2\tS255\tS72\n"
76                                     "Component\tComponent\n"
77                                     "Five\t{8CC92E9D-14B2-4CA4-B2AA-B11D02078087}\tNEWDIR\t2\t\tfive.txt\n"
78                                     "Four\t{FD37B4EA-7209-45C0-8917-535F35A2F080}\tCABOUTDIR\t2\t\tfour.txt\n"
79                                     "One\t{783B242E-E185-4A56-AF86-C09815EC053C}\tMSITESTDIR\t2\tNOT REINSTALL\tone.txt\n"
80                                     "Three\t{010B6ADD-B27D-4EDD-9B3D-34C4F7D61684}\tCHANGEDDIR\t2\t\tthree.txt\n"
81                                     "Two\t{BF03D1A6-20DA-4A65-82F3-6CAC995915CE}\tFIRSTDIR\t2\t\ttwo.txt\n"
82                                     "dangler\t{6091DF25-EF96-45F1-B8E9-A9B1420C7A3C}\tTARGETDIR\t4\t\tregdata\n"
83                                     "component\t\tMSITESTDIR\t0\t1\tfile\n"
84                                     "service_comp\t\tMSITESTDIR\t0\t1\tservice_file";
85
86 static const CHAR directory_dat[] = "Directory\tDirectory_Parent\tDefaultDir\n"
87                                     "s72\tS72\tl255\n"
88                                     "Directory\tDirectory\n"
89                                     "CABOUTDIR\tMSITESTDIR\tcabout\n"
90                                     "CHANGEDDIR\tMSITESTDIR\tchanged:second\n"
91                                     "FIRSTDIR\tMSITESTDIR\tfirst\n"
92                                     "MSITESTDIR\tProgramFilesFolder\tmsitest\n"
93                                     "NEWDIR\tCABOUTDIR\tnew\n"
94                                     "ProgramFilesFolder\tTARGETDIR\t.\n"
95                                     "TARGETDIR\t\tSourceDir";
96
97 static const CHAR feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
98                                   "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
99                                   "Feature\tFeature\n"
100                                   "Five\t\tFive\tThe Five Feature\t5\t3\tNEWDIR\t0\n"
101                                   "Four\t\tFour\tThe Four Feature\t4\t3\tCABOUTDIR\t0\n"
102                                   "One\t\tOne\tThe One Feature\t1\t3\tMSITESTDIR\t0\n"
103                                   "Three\t\tThree\tThe Three Feature\t3\t3\tCHANGEDDIR\t0\n"
104                                   "Two\t\tTwo\tThe Two Feature\t2\t3\tFIRSTDIR\t0\n"
105                                   "feature\t\t\t\t2\t1\tTARGETDIR\t0\n"
106                                   "service_feature\t\t\t\t2\t1\tTARGETDIR\t0";
107
108 static const CHAR feature_comp_dat[] = "Feature_\tComponent_\n"
109                                        "s38\ts72\n"
110                                        "FeatureComponents\tFeature_\tComponent_\n"
111                                        "Five\tFive\n"
112                                        "Four\tFour\n"
113                                        "One\tOne\n"
114                                        "Three\tThree\n"
115                                        "Two\tTwo\n"
116                                        "feature\tcomponent\n"
117                                        "service_feature\tservice_comp\n";
118
119 static const CHAR file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
120                                "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
121                                "File\tFile\n"
122                                "five.txt\tFive\tfive.txt\t1000\t\t\t16384\t5\n"
123                                "four.txt\tFour\tfour.txt\t1000\t\t\t16384\t4\n"
124                                "one.txt\tOne\tone.txt\t1000\t\t\t0\t1\n"
125                                "three.txt\tThree\tthree.txt\t1000\t\t\t0\t3\n"
126                                "two.txt\tTwo\ttwo.txt\t1000\t\t\t0\t2\n"
127                                "file\tcomponent\tfilename\t100\t\t\t8192\t1\n"
128                                "service_file\tservice_comp\tservice.exe\t100\t\t\t8192\t1";
129
130 static const CHAR install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
131                                            "s72\tS255\tI2\n"
132                                            "InstallExecuteSequence\tAction\n"
133                                            "AllocateRegistrySpace\tNOT Installed\t1550\n"
134                                            "CostFinalize\t\t1000\n"
135                                            "CostInitialize\t\t800\n"
136                                            "FileCost\t\t900\n"
137                                            "ResolveSource\t\t950\n"
138                                            "MoveFiles\t\t1700\n"
139                                            "InstallFiles\t\t4000\n"
140                                            "DuplicateFiles\t\t4500\n"
141                                            "WriteEnvironmentStrings\t\t4550\n"
142                                            "CreateShortcuts\t\t4600\n"
143                                            "InstallServices\t\t5000\n"
144                                            "InstallFinalize\t\t6600\n"
145                                            "InstallInitialize\t\t1500\n"
146                                            "InstallValidate\t\t1400\n"
147                                            "LaunchConditions\t\t100\n"
148                                            "WriteRegistryValues\tSourceDir And SOURCEDIR\t5000";
149
150 static const CHAR media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
151                                 "i2\ti4\tL64\tS255\tS32\tS72\n"
152                                 "Media\tDiskId\n"
153                                 "1\t3\t\t\tDISK1\t\n"
154                                 "2\t5\t\tmsitest.cab\tDISK2\t\n";
155
156 static const CHAR property_dat[] = "Property\tValue\n"
157                                    "s72\tl0\n"
158                                    "Property\tProperty\n"
159                                    "DefaultUIFont\tDlgFont8\n"
160                                    "HASUIRUN\t0\n"
161                                    "INSTALLLEVEL\t3\n"
162                                    "InstallMode\tTypical\n"
163                                    "Manufacturer\tWine\n"
164                                    "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
165                                    "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
166                                    "ProductID\tnone\n"
167                                    "ProductLanguage\t1033\n"
168                                    "ProductName\tMSITEST\n"
169                                    "ProductVersion\t1.1.1\n"
170                                    "PROMPTROLLBACKCOST\tP\n"
171                                    "Setup\tSetup\n"
172                                    "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
173                                    "AdminProperties\tPOSTADMIN\n"
174                                    "ROOTDRIVE\tC:\\\n"
175                                    "SERVNAME\tTestService\n"
176                                    "SERVDISP\tTestServiceDisp\n"
177                                    "MSIFASTINSTALL\t1\n";
178
179 static const CHAR aup_property_dat[] = "Property\tValue\n"
180                                        "s72\tl0\n"
181                                        "Property\tProperty\n"
182                                        "DefaultUIFont\tDlgFont8\n"
183                                        "HASUIRUN\t0\n"
184                                        "ALLUSERS\t1\n"
185                                        "INSTALLLEVEL\t3\n"
186                                        "InstallMode\tTypical\n"
187                                        "Manufacturer\tWine\n"
188                                        "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
189                                        "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
190                                        "ProductID\tnone\n"
191                                        "ProductLanguage\t1033\n"
192                                        "ProductName\tMSITEST\n"
193                                        "ProductVersion\t1.1.1\n"
194                                        "PROMPTROLLBACKCOST\tP\n"
195                                        "Setup\tSetup\n"
196                                        "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
197                                        "AdminProperties\tPOSTADMIN\n"
198                                        "ROOTDRIVE\tC:\\\n"
199                                        "SERVNAME\tTestService\n"
200                                        "SERVDISP\tTestServiceDisp\n"
201                                        "MSIFASTINSTALL\t1\n";
202
203 static const CHAR aup2_property_dat[] = "Property\tValue\n"
204                                         "s72\tl0\n"
205                                         "Property\tProperty\n"
206                                         "DefaultUIFont\tDlgFont8\n"
207                                         "HASUIRUN\t0\n"
208                                         "ALLUSERS\t2\n"
209                                         "INSTALLLEVEL\t3\n"
210                                         "InstallMode\tTypical\n"
211                                         "Manufacturer\tWine\n"
212                                         "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
213                                         "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
214                                         "ProductID\tnone\n"
215                                         "ProductLanguage\t1033\n"
216                                         "ProductName\tMSITEST\n"
217                                         "ProductVersion\t1.1.1\n"
218                                         "PROMPTROLLBACKCOST\tP\n"
219                                         "Setup\tSetup\n"
220                                         "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
221                                         "AdminProperties\tPOSTADMIN\n"
222                                         "ROOTDRIVE\tC:\\\n"
223                                         "SERVNAME\tTestService\n"
224                                         "SERVDISP\tTestServiceDisp\n"
225                                         "MSIFASTINSTALL\t1\n";
226
227 static const CHAR icon_property_dat[] = "Property\tValue\n"
228                                         "s72\tl0\n"
229                                         "Property\tProperty\n"
230                                         "DefaultUIFont\tDlgFont8\n"
231                                         "HASUIRUN\t0\n"
232                                         "INSTALLLEVEL\t3\n"
233                                         "InstallMode\tTypical\n"
234                                         "Manufacturer\tWine\n"
235                                         "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
236                                         "ProductCode\t{7DF88A49-996F-4EC8-A022-BF956F9B2CBB}\n"
237                                         "ProductID\tnone\n"
238                                         "ProductLanguage\t1033\n"
239                                         "ProductName\tMSITEST\n"
240                                         "ProductVersion\t1.1.1\n"
241                                         "PROMPTROLLBACKCOST\tP\n"
242                                         "Setup\tSetup\n"
243                                         "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
244                                         "AdminProperties\tPOSTADMIN\n"
245                                         "ROOTDRIVE\tC:\\\n"
246                                         "SERVNAME\tTestService\n"
247                                         "SERVDISP\tTestServiceDisp\n"
248                                         "MSIFASTINSTALL\t1\n";
249
250 static const CHAR shortcut_dat[] = "Shortcut\tDirectory_\tName\tComponent_\tTarget\tArguments\tDescription\tHotkey\tIcon_\tIconIndex\tShowCmd\tWkDir\n"
251                                    "s72\ts72\tl128\ts72\ts72\tS255\tL255\tI2\tS72\tI2\tI2\tS72\n"
252                                    "Shortcut\tShortcut\n"
253                                    "Shortcut\tMSITESTDIR\tShortcut\tcomponent\tShortcut\t\tShortcut\t\t\t\t\t\n";
254
255 static const CHAR condition_dat[] = "Feature_\tLevel\tCondition\n"
256                                     "s38\ti2\tS255\n"
257                                     "Condition\tFeature_\tLevel\n"
258                                     "One\t4\t1\n";
259
260 static const CHAR up_property_dat[] = "Property\tValue\n"
261                                       "s72\tl0\n"
262                                       "Property\tProperty\n"
263                                       "DefaultUIFont\tDlgFont8\n"
264                                       "HASUIRUN\t0\n"
265                                       "INSTALLLEVEL\t3\n"
266                                       "InstallMode\tTypical\n"
267                                       "Manufacturer\tWine\n"
268                                       "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
269                                       "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
270                                       "ProductID\tnone\n"
271                                       "ProductLanguage\t1033\n"
272                                       "ProductName\tMSITEST\n"
273                                       "ProductVersion\t1.1.1\n"
274                                       "PROMPTROLLBACKCOST\tP\n"
275                                       "Setup\tSetup\n"
276                                       "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
277                                       "AdminProperties\tPOSTADMIN\n"
278                                       "ROOTDRIVE\tC:\\\n"
279                                       "SERVNAME\tTestService\n"
280                                       "SERVDISP\tTestServiceDisp\n"
281                                       "RemovePreviousVersions\t1\n"
282                                       "MSIFASTINSTALL\t1\n";
283
284 static const CHAR up2_property_dat[] = "Property\tValue\n"
285                                        "s72\tl0\n"
286                                        "Property\tProperty\n"
287                                        "DefaultUIFont\tDlgFont8\n"
288                                        "HASUIRUN\t0\n"
289                                        "INSTALLLEVEL\t3\n"
290                                        "InstallMode\tTypical\n"
291                                        "Manufacturer\tWine\n"
292                                        "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
293                                        "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
294                                        "ProductID\tnone\n"
295                                        "ProductLanguage\t1033\n"
296                                        "ProductName\tMSITEST\n"
297                                        "ProductVersion\t1.1.2\n"
298                                        "PROMPTROLLBACKCOST\tP\n"
299                                        "Setup\tSetup\n"
300                                        "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
301                                        "AdminProperties\tPOSTADMIN\n"
302                                        "ROOTDRIVE\tC:\\\n"
303                                        "SERVNAME\tTestService\n"
304                                        "SERVDISP\tTestServiceDisp\n"
305                                        "MSIFASTINSTALL\t1\n";
306
307 static const CHAR up3_property_dat[] = "Property\tValue\n"
308                                        "s72\tl0\n"
309                                        "Property\tProperty\n"
310                                        "DefaultUIFont\tDlgFont8\n"
311                                        "HASUIRUN\t0\n"
312                                        "INSTALLLEVEL\t3\n"
313                                        "InstallMode\tTypical\n"
314                                        "Manufacturer\tWine\n"
315                                        "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
316                                        "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
317                                        "ProductID\tnone\n"
318                                        "ProductLanguage\t1033\n"
319                                        "ProductName\tMSITEST\n"
320                                        "ProductVersion\t1.1.2\n"
321                                        "PROMPTROLLBACKCOST\tP\n"
322                                        "Setup\tSetup\n"
323                                        "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
324                                        "AdminProperties\tPOSTADMIN\n"
325                                        "ROOTDRIVE\tC:\\\n"
326                                        "SERVNAME\tTestService\n"
327                                        "SERVDISP\tTestServiceDisp\n"
328                                        "RemovePreviousVersions\t1\n"
329                                        "MSIFASTINSTALL\t1\n";
330
331 static const CHAR registry_dat[] = "Registry\tRoot\tKey\tName\tValue\tComponent_\n"
332                                    "s72\ti2\tl255\tL255\tL0\ts72\n"
333                                    "Registry\tRegistry\n"
334                                    "Apples\t1\tSOFTWARE\\Wine\\msitest\tName\timaname\tOne\n"
335                                    "Oranges\t1\tSOFTWARE\\Wine\\msitest\tnumber\t#314\tTwo\n"
336                                    "regdata\t1\tSOFTWARE\\Wine\\msitest\tblah\tbad\tdangler\n"
337                                    "OrderTest\t1\tSOFTWARE\\Wine\\msitest\tOrderTestName\tOrderTestValue\tcomponent";
338
339 static const CHAR service_install_dat[] = "ServiceInstall\tName\tDisplayName\tServiceType\tStartType\tErrorControl\t"
340                                           "LoadOrderGroup\tDependencies\tStartName\tPassword\tArguments\tComponent_\tDescription\n"
341                                           "s72\ts255\tL255\ti4\ti4\ti4\tS255\tS255\tS255\tS255\tS255\ts72\tL255\n"
342                                           "ServiceInstall\tServiceInstall\n"
343                                           "TestService\t[SERVNAME]\t[SERVDISP]\t2\t3\t0\t\t\tTestService\t\t\tservice_comp\t\t";
344
345 static const CHAR service_control_dat[] = "ServiceControl\tName\tEvent\tArguments\tWait\tComponent_\n"
346                                           "s72\tl255\ti2\tL255\tI2\ts72\n"
347                                           "ServiceControl\tServiceControl\n"
348                                           "ServiceControl\tTestService\t8\t\t0\tservice_comp";
349
350 /* tables for test_continuouscabs */
351 static const CHAR cc_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
352                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
353                                        "Component\tComponent\n"
354                                        "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n"
355                                        "augustus\t\tMSITESTDIR\t0\t1\taugustus\n"
356                                        "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n";
357
358 static const CHAR cc2_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
359                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
360                                         "Component\tComponent\n"
361                                         "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n"
362                                         "augustus\t\tMSITESTDIR\t0\t0\taugustus\n"
363                                         "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n";
364
365 static const CHAR cc_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
366                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
367                                      "Feature\tFeature\n"
368                                      "feature\t\t\t\t2\t1\tTARGETDIR\t0";
369
370 static const CHAR cc_feature_comp_dat[] = "Feature_\tComponent_\n"
371                                           "s38\ts72\n"
372                                           "FeatureComponents\tFeature_\tComponent_\n"
373                                           "feature\tmaximus\n"
374                                           "feature\taugustus\n"
375                                           "feature\tcaesar";
376
377 static const CHAR cc_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
378                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
379                                   "File\tFile\n"
380                                   "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
381                                   "augustus\taugustus\taugustus\t50000\t\t\t16384\t2\n"
382                                   "caesar\tcaesar\tcaesar\t500\t\t\t16384\t12";
383
384 static const CHAR cc2_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
385                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
386                                    "File\tFile\n"
387                                    "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
388                                    "augustus\taugustus\taugustus\t50000\t\t\t16384\t2\n"
389                                    "tiberius\tmaximus\ttiberius\t500\t\t\t16384\t3\n"
390                                    "caesar\tcaesar\tcaesar\t500\t\t\t16384\t12";
391
392 static const CHAR cc_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
393                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
394                                    "Media\tDiskId\n"
395                                    "1\t10\t\ttest1.cab\tDISK1\t\n"
396                                    "2\t2\t\ttest2.cab\tDISK2\t\n"
397                                    "3\t12\t\ttest3.cab\tDISK3\t\n";
398
399 static const CHAR co_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
400                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
401                                   "File\tFile\n"
402                                   "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
403                                   "augustus\taugustus\taugustus\t50000\t\t\t16384\t2\n"
404                                   "caesar\tcaesar\tcaesar\t500\t\t\t16384\t3";
405
406 static const CHAR co_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
407                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
408                                    "Media\tDiskId\n"
409                                    "1\t10\t\ttest1.cab\tDISK1\t\n"
410                                    "2\t2\t\ttest2.cab\tDISK2\t\n"
411                                    "3\t3\t\ttest3.cab\tDISK3\t\n";
412
413 static const CHAR co2_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
414                                     "i2\ti4\tL64\tS255\tS32\tS72\n"
415                                     "Media\tDiskId\n"
416                                     "1\t10\t\ttest1.cab\tDISK1\t\n"
417                                     "2\t12\t\ttest3.cab\tDISK3\t\n"
418                                     "3\t2\t\ttest2.cab\tDISK2\t\n";
419
420 static const CHAR mm_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
421                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
422                                   "File\tFile\n"
423                                   "maximus\tmaximus\tmaximus\t500\t\t\t512\t1\n"
424                                   "augustus\taugustus\taugustus\t500\t\t\t512\t2\n"
425                                   "caesar\tcaesar\tcaesar\t500\t\t\t16384\t3";
426
427 static const CHAR mm_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
428                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
429                                    "Media\tDiskId\n"
430                                    "1\t3\t\ttest1.cab\tDISK1\t\n";
431
432 static const CHAR ss_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
433                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
434                                    "Media\tDiskId\n"
435                                    "1\t2\t\ttest1.cab\tDISK1\t\n"
436                                    "2\t2\t\ttest2.cab\tDISK2\t\n"
437                                    "3\t12\t\ttest3.cab\tDISK3\t\n";
438
439 /* tables for test_uiLevelFlags */
440 static const CHAR ui_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
441                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
442                                        "Component\tComponent\n"
443                                        "maximus\t\tMSITESTDIR\t0\tHASUIRUN=1\tmaximus\n"
444                                        "augustus\t\tMSITESTDIR\t0\t1\taugustus\n"
445                                        "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n";
446
447 static const CHAR ui_install_ui_seq_dat[] = "Action\tCondition\tSequence\n"
448                                            "s72\tS255\tI2\n"
449                                            "InstallUISequence\tAction\n"
450                                            "SetUIProperty\t\t5\n"
451                                            "ExecuteAction\t\t1100\n";
452
453 static const CHAR ui_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
454                                            "s72\ti2\tS64\tS0\tS255\n"
455                                            "CustomAction\tAction\n"
456                                            "SetUIProperty\t51\tHASUIRUN\t1\t\n";
457
458 static const CHAR rof_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
459                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
460                                         "Component\tComponent\n"
461                                         "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n";
462
463 static const CHAR rof_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
464                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
465                                       "Feature\tFeature\n"
466                                       "feature\t\tFeature\tFeature\t2\t1\tTARGETDIR\t0\n"
467                                       "montecristo\t\tFeature\tFeature\t2\t1\tTARGETDIR\t0";
468
469 static const CHAR rof_feature_comp_dat[] = "Feature_\tComponent_\n"
470                                            "s38\ts72\n"
471                                            "FeatureComponents\tFeature_\tComponent_\n"
472                                            "feature\tmaximus\n"
473                                            "montecristo\tmaximus";
474
475 static const CHAR rof_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
476                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
477                                    "File\tFile\n"
478                                    "maximus\tmaximus\tmaximus\t500\t\t\t8192\t1";
479
480 static const CHAR rof_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
481                                     "i2\ti4\tL64\tS255\tS32\tS72\n"
482                                     "Media\tDiskId\n"
483                                     "1\t1\t\t\tDISK1\t\n";
484
485 static const CHAR rofc_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
486                                     "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
487                                     "File\tFile\n"
488                                     "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1";
489
490 static const CHAR rofc_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
491                                      "i2\ti4\tL64\tS255\tS32\tS72\n"
492                                      "Media\tDiskId\n"
493                                      "1\t1\t\ttest1.cab\tDISK1\t\n";
494
495 static const CHAR lus2_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
496                                      "i2\ti4\tL64\tS255\tS32\tS72\n"
497                                      "Media\tDiskId\n"
498                                      "1\t1\t\t#test1.cab\tDISK1\t\n";
499
500 static const CHAR sdp_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
501                                                "s72\tS255\tI2\n"
502                                                "InstallExecuteSequence\tAction\n"
503                                                "AllocateRegistrySpace\tNOT Installed\t1550\n"
504                                                "CostFinalize\t\t1000\n"
505                                                "CostInitialize\t\t800\n"
506                                                "FileCost\t\t900\n"
507                                                "InstallFiles\t\t4000\n"
508                                                "InstallFinalize\t\t6600\n"
509                                                "InstallInitialize\t\t1500\n"
510                                                "InstallValidate\t\t1400\n"
511                                                "LaunchConditions\t\t100\n"
512                                                "SetDirProperty\t\t950";
513
514 static const CHAR sdp_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
515                                             "s72\ti2\tS64\tS0\tS255\n"
516                                             "CustomAction\tAction\n"
517                                             "SetDirProperty\t51\tMSITESTDIR\t[CommonFilesFolder]msitest\\\t\n";
518
519 static const CHAR pv_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
520                                               "s72\tS255\tI2\n"
521                                               "InstallExecuteSequence\tAction\n"
522                                               "LaunchConditions\t\t100\n"
523                                               "CostInitialize\t\t800\n"
524                                               "FileCost\t\t900\n"
525                                               "CostFinalize\t\t1000\n"
526                                               "InstallValidate\t\t1400\n"
527                                               "InstallInitialize\t\t1500\n"
528                                               "InstallFiles\t\t4000\n"
529                                               "InstallFinalize\t\t6600\n";
530
531 static const CHAR cie_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
532                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
533                                         "Component\tComponent\n"
534                                         "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n"
535                                         "augustus\t\tMSITESTDIR\t0\t1\taugustus\n"
536                                         "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n"
537                                         "gaius\t\tMSITESTDIR\t0\t1\tgaius\n";
538
539 static const CHAR cie_feature_comp_dat[] = "Feature_\tComponent_\n"
540                                            "s38\ts72\n"
541                                            "FeatureComponents\tFeature_\tComponent_\n"
542                                            "feature\tmaximus\n"
543                                            "feature\taugustus\n"
544                                            "feature\tcaesar\n"
545                                            "feature\tgaius";
546
547 static const CHAR cie_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
548                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
549                                    "File\tFile\n"
550                                    "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
551                                    "augustus\taugustus\taugustus\t50000\t\t\t16384\t2\n"
552                                    "caesar\tcaesar\tcaesar\t500\t\t\t16384\t12\n"
553                                    "gaius\tgaius\tgaius\t500\t\t\t8192\t11";
554
555 static const CHAR cie_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
556                                     "i2\ti4\tL64\tS255\tS32\tS72\n"
557                                     "Media\tDiskId\n"
558                                     "1\t1\t\ttest1.cab\tDISK1\t\n"
559                                     "2\t2\t\ttest2.cab\tDISK2\t\n"
560                                     "3\t12\t\ttest3.cab\tDISK3\t\n";
561
562 static const CHAR ci_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
563                                               "s72\tS255\tI2\n"
564                                               "InstallExecuteSequence\tAction\n"
565                                               "CostFinalize\t\t1000\n"
566                                               "CostInitialize\t\t800\n"
567                                               "FileCost\t\t900\n"
568                                               "InstallFiles\t\t4000\n"
569                                               "InstallServices\t\t5000\n"
570                                               "InstallFinalize\t\t6600\n"
571                                               "InstallInitialize\t\t1500\n"
572                                               "RunInstall\t\t1600\n"
573                                               "InstallValidate\t\t1400\n"
574                                               "LaunchConditions\t\t100";
575
576 static const CHAR ci_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
577                                             "s72\ti2\tS64\tS0\tS255\n"
578                                             "CustomAction\tAction\n"
579                                             "RunInstall\t87\tmsitest\\concurrent.msi\tMYPROP=[UILevel]\t\n";
580
581 static const CHAR ci_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
582                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
583                                        "Component\tComponent\n"
584                                        "maximus\t{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}\tMSITESTDIR\t0\tUILevel=5\tmaximus\n";
585
586 static const CHAR ci2_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
587                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
588                                         "Component\tComponent\n"
589                                         "augustus\t\tMSITESTDIR\t0\tUILevel=3 AND MYPROP=5\taugustus\n";
590
591 static const CHAR ci2_feature_comp_dat[] = "Feature_\tComponent_\n"
592                                            "s38\ts72\n"
593                                            "FeatureComponents\tFeature_\tComponent_\n"
594                                            "feature\taugustus";
595
596 static const CHAR ci2_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
597                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
598                                    "File\tFile\n"
599                                    "augustus\taugustus\taugustus\t500\t\t\t8192\t1";
600
601 static const CHAR spf_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
602                                             "s72\ti2\tS64\tS0\tS255\n"
603                                             "CustomAction\tAction\n"
604                                             "SetFolderProp\t51\tMSITESTDIR\t[ProgramFilesFolder]\\msitest\\added\t\n";
605
606 static const CHAR spf_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
607                                                "s72\tS255\tI2\n"
608                                                "InstallExecuteSequence\tAction\n"
609                                                "CostFinalize\t\t1000\n"
610                                                "CostInitialize\t\t800\n"
611                                                "FileCost\t\t900\n"
612                                                "SetFolderProp\t\t950\n"
613                                                "InstallFiles\t\t4000\n"
614                                                "InstallServices\t\t5000\n"
615                                                "InstallFinalize\t\t6600\n"
616                                                "InstallInitialize\t\t1500\n"
617                                                "InstallValidate\t\t1400\n"
618                                                "LaunchConditions\t\t100";
619
620 static const CHAR spf_install_ui_seq_dat[] = "Action\tCondition\tSequence\n"
621                                              "s72\tS255\tI2\n"
622                                              "InstallUISequence\tAction\n"
623                                              "CostInitialize\t\t800\n"
624                                              "FileCost\t\t900\n"
625                                              "CostFinalize\t\t1000\n"
626                                              "ExecuteAction\t\t1100\n";
627
628 static const CHAR pp_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
629                                               "s72\tS255\tI2\n"
630                                               "InstallExecuteSequence\tAction\n"
631                                               "ValidateProductID\t\t700\n"
632                                               "CostInitialize\t\t800\n"
633                                               "FileCost\t\t900\n"
634                                               "CostFinalize\t\t1000\n"
635                                               "InstallValidate\t\t1400\n"
636                                               "InstallInitialize\t\t1500\n"
637                                               "ProcessComponents\tPROCESS_COMPONENTS=1 Or FULL=1\t1600\n"
638                                               "UnpublishFeatures\tUNPUBLISH_FEATURES=1 Or FULL=1\t1800\n"
639                                               "RemoveFiles\t\t3500\n"
640                                               "InstallFiles\t\t4000\n"
641                                               "RegisterUser\tREGISTER_USER=1 Or FULL=1\t6000\n"
642                                               "RegisterProduct\tREGISTER_PRODUCT=1 Or FULL=1\t6100\n"
643                                               "PublishFeatures\tPUBLISH_FEATURES=1 Or FULL=1\t6300\n"
644                                               "PublishProduct\tPUBLISH_PRODUCT=1 Or FULL=1\t6400\n"
645                                               "InstallFinalize\t\t6600";
646
647 static const CHAR tp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
648                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
649                                        "Component\tComponent\n"
650                                        "augustus\t\tMSITESTDIR\t0\tprop=\"val\"\taugustus\n";
651
652 static const CHAR cwd_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
653                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
654                                         "Component\tComponent\n"
655                                         "augustus\t\tMSITESTDIR\t0\t\taugustus\n";
656
657 static const CHAR adm_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
658                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
659                                         "Component\tComponent\n"
660                                         "augustus\t\tMSITESTDIR\t0\tPOSTADMIN=1\taugustus";
661
662 static const CHAR adm_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
663                                             "s72\ti2\tS64\tS0\tS255\n"
664                                             "CustomAction\tAction\n"
665                                             "SetPOSTADMIN\t51\tPOSTADMIN\t1\t\n";
666
667 static const CHAR adm_admin_exec_seq_dat[] = "Action\tCondition\tSequence\n"
668                                              "s72\tS255\tI2\n"
669                                              "AdminExecuteSequence\tAction\n"
670                                              "CostFinalize\t\t1000\n"
671                                              "CostInitialize\t\t800\n"
672                                              "FileCost\t\t900\n"
673                                              "SetPOSTADMIN\t\t950\n"
674                                              "InstallFiles\t\t4000\n"
675                                              "InstallFinalize\t\t6600\n"
676                                              "InstallInitialize\t\t1500\n"
677                                              "InstallValidate\t\t1400\n"
678                                              "LaunchConditions\t\t100";
679
680 static const CHAR amp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
681                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
682                                         "Component\tComponent\n"
683                                         "augustus\t\tMSITESTDIR\t0\tMYPROP=2718 and MyProp=42\taugustus\n";
684
685 static const CHAR rem_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
686                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
687                                    "File\tFile\n"
688                                    "hydrogen\thydrogen\thydrogen\t0\t\t\t8192\t1\n"
689                                    "helium\thelium\thelium\t0\t\t\t8192\t1\n"
690                                    "lithium\tlithium\tlithium\t0\t\t\t8192\t1";
691
692 static const CHAR rem_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
693                                                "s72\tS255\tI2\n"
694                                                "InstallExecuteSequence\tAction\n"
695                                                "ValidateProductID\t\t700\n"
696                                                "CostInitialize\t\t800\n"
697                                                "FileCost\t\t900\n"
698                                                "CostFinalize\t\t1000\n"
699                                                "InstallValidate\t\t1400\n"
700                                                "InstallInitialize\t\t1500\n"
701                                                "ProcessComponents\t\t1600\n"
702                                                "UnpublishFeatures\t\t1800\n"
703                                                "RemoveFiles\t\t3500\n"
704                                                "InstallFiles\t\t4000\n"
705                                                "RegisterProduct\t\t6100\n"
706                                                "PublishFeatures\t\t6300\n"
707                                                "PublishProduct\t\t6400\n"
708                                                "InstallFinalize\t\t6600";
709
710 static const CHAR mc_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
711                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
712                                         "Component\tComponent\n"
713                                         "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n"
714                                         "augustus\t\tMSITESTDIR\t0\t1\taugustus\n"
715                                         "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n"
716                                         "gaius\t\tMSITESTDIR\t0\tGAIUS=1\tgaius\n";
717
718 static const CHAR mc_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
719                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
720                                   "File\tFile\n"
721                                   "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
722                                   "augustus\taugustus\taugustus\t500\t\t\t0\t2\n"
723                                   "caesar\tcaesar\tcaesar\t500\t\t\t16384\t3\n"
724                                   "gaius\tgaius\tgaius\t500\t\t\t16384\t4";
725
726 static const CHAR mc_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
727                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
728                                    "Media\tDiskId\n"
729                                    "1\t1\t\ttest1.cab\tDISK1\t\n"
730                                    "2\t2\t\ttest2.cab\tDISK2\t\n"
731                                    "3\t3\t\ttest3.cab\tDISK3\t\n"
732                                    "4\t4\t\ttest3.cab\tDISK3\t\n";
733
734 static const CHAR mc_file_hash_dat[] = "File_\tOptions\tHashPart1\tHashPart2\tHashPart3\tHashPart4\n"
735                                        "s72\ti2\ti4\ti4\ti4\ti4\n"
736                                        "MsiFileHash\tFile_\n"
737                                        "caesar\t0\t850433704\t-241429251\t675791761\t-1221108824";
738
739 static const CHAR wrv_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
740                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
741                                         "Component\tComponent\n"
742                                         "augustus\t\tMSITESTDIR\t0\t\taugustus\n";
743
744 static const CHAR ca51_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
745                                          "s72\tS38\ts72\ti2\tS255\tS72\n"
746                                          "Component\tComponent\n"
747                                          "augustus\t\tMSITESTDIR\t0\tMYPROP=42\taugustus\n";
748
749 static const CHAR ca51_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
750                                                 "s72\tS255\tI2\n"
751                                                 "InstallExecuteSequence\tAction\n"
752                                                 "ValidateProductID\t\t700\n"
753                                                 "GoodSetProperty\t\t725\n"
754                                                 "BadSetProperty\t\t750\n"
755                                                 "CostInitialize\t\t800\n"
756                                                 "ResolveSource\t\t810\n"
757                                                 "FileCost\t\t900\n"
758                                                 "SetSourceDir\tSRCDIR\t910\n"
759                                                 "CostFinalize\t\t1000\n"
760                                                 "InstallValidate\t\t1400\n"
761                                                 "InstallInitialize\t\t1500\n"
762                                                 "InstallFiles\t\t4000\n"
763                                                 "InstallFinalize\t\t6600";
764
765 static const CHAR ca51_custom_action_dat[] = "Action\tType\tSource\tTarget\n"
766                                              "s72\ti2\tS64\tS0\n"
767                                              "CustomAction\tAction\n"
768                                              "GoodSetProperty\t51\tMYPROP\t42\n"
769                                              "BadSetProperty\t51\t\tMYPROP\n"
770                                              "SetSourceDir\t51\tSourceDir\t[SRCDIR]\n";
771
772 static const CHAR is_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
773                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
774                                      "Feature\tFeature\n"
775                                      "one\t\t\t\t2\t1\t\t0\n" /* favorLocal */
776                                      "two\t\t\t\t2\t1\t\t1\n" /* favorSource */
777                                      "three\t\t\t\t2\t1\t\t4\n" /* favorAdvertise */
778                                      "four\t\t\t\t2\t0\t\t0"; /* disabled */
779
780 static const CHAR is_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
781                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
782                                        "Component\tComponent\n"
783                                        "alpha\t\tMSITESTDIR\t0\t\talpha_file\n" /* favorLocal:Local */
784                                        "beta\t\tMSITESTDIR\t1\t\tbeta_file\n" /* favorLocal:Source */
785                                        "gamma\t\tMSITESTDIR\t2\t\tgamma_file\n" /* favorLocal:Optional */
786                                        "theta\t\tMSITESTDIR\t0\t\ttheta_file\n" /* favorSource:Local */
787                                        "delta\t\tMSITESTDIR\t1\t\tdelta_file\n" /* favorSource:Source */
788                                        "epsilon\t\tMSITESTDIR\t2\t\tepsilon_file\n" /* favorSource:Optional */
789                                        "zeta\t\tMSITESTDIR\t0\t\tzeta_file\n" /* favorAdvertise:Local */
790                                        "iota\t\tMSITESTDIR\t1\t\tiota_file\n" /* favorAdvertise:Source */
791                                        "eta\t\tMSITESTDIR\t2\t\teta_file\n" /* favorAdvertise:Optional */
792                                        "kappa\t\tMSITESTDIR\t0\t\tkappa_file\n" /* disabled:Local */
793                                        "lambda\t\tMSITESTDIR\t1\t\tlambda_file\n" /* disabled:Source */
794                                        "mu\t\tMSITESTDIR\t2\t\tmu_file\n"; /* disabled:Optional */
795
796 static const CHAR is_feature_comp_dat[] = "Feature_\tComponent_\n"
797                                           "s38\ts72\n"
798                                           "FeatureComponents\tFeature_\tComponent_\n"
799                                           "one\talpha\n"
800                                           "one\tbeta\n"
801                                           "one\tgamma\n"
802                                           "two\ttheta\n"
803                                           "two\tdelta\n"
804                                           "two\tepsilon\n"
805                                           "three\tzeta\n"
806                                           "three\tiota\n"
807                                           "three\teta\n"
808                                           "four\tkappa\n"
809                                           "four\tlambda\n"
810                                           "four\tmu";
811
812 static const CHAR is_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
813                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
814                                   "File\tFile\n"
815                                   "alpha_file\talpha\talpha\t500\t\t\t8192\t1\n"
816                                   "beta_file\tbeta\tbeta\t500\t\t\t8291\t2\n"
817                                   "gamma_file\tgamma\tgamma\t500\t\t\t8192\t3\n"
818                                   "theta_file\ttheta\ttheta\t500\t\t\t8192\t4\n"
819                                   "delta_file\tdelta\tdelta\t500\t\t\t8192\t5\n"
820                                   "epsilon_file\tepsilon\tepsilon\t500\t\t\t8192\t6\n"
821                                   "zeta_file\tzeta\tzeta\t500\t\t\t8192\t7\n"
822                                   "iota_file\tiota\tiota\t500\t\t\t8192\t8\n"
823                                   "eta_file\teta\teta\t500\t\t\t8192\t9\n"
824                                   "kappa_file\tkappa\tkappa\t500\t\t\t8192\t10\n"
825                                   "lambda_file\tlambda\tlambda\t500\t\t\t8192\t11\n"
826                                   "mu_file\tmu\tmu\t500\t\t\t8192\t12";
827
828 static const CHAR is_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
829                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
830                                    "Media\tDiskId\n"
831                                    "1\t12\t\t\tDISK1\t\n";
832
833 static const CHAR sp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
834                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
835                                         "Component\tComponent\n"
836                                         "augustus\t\tTWODIR\t0\t\taugustus\n";
837
838 static const CHAR sp_directory_dat[] = "Directory\tDirectory_Parent\tDefaultDir\n"
839                                        "s72\tS72\tl255\n"
840                                        "Directory\tDirectory\n"
841                                        "TARGETDIR\t\tSourceDir\n"
842                                        "ProgramFilesFolder\tTARGETDIR\t.\n"
843                                        "MSITESTDIR\tProgramFilesFolder\tmsitest:.\n"
844                                        "ONEDIR\tMSITESTDIR\t.:shortone|longone\n"
845                                        "TWODIR\tONEDIR\t.:shorttwo|longtwo";
846
847 static const CHAR mcp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
848                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
849                                         "Component\tComponent\n"
850                                         "hydrogen\t{C844BD1E-1907-4C00-8BC9-150BD70DF0A1}\tMSITESTDIR\t2\t\thydrogen\n"
851                                         "helium\t{5AD3C142-CEF8-490D-B569-784D80670685}\tMSITESTDIR\t2\t\thelium\n"
852                                         "lithium\t{4AF28FFC-71C7-4307-BDE4-B77C5338F56F}\tMSITESTDIR\t2\tPROPVAR=42\tlithium\n";
853
854 static const CHAR mcp_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
855                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
856                                       "Feature\tFeature\n"
857                                       "hydroxyl\t\thydroxyl\thydroxyl\t2\t1\tTARGETDIR\t0\n"
858                                       "heliox\t\theliox\theliox\t2\t5\tTARGETDIR\t0\n"
859                                       "lithia\t\tlithia\tlithia\t2\t10\tTARGETDIR\t0";
860
861 static const CHAR mcp_feature_comp_dat[] = "Feature_\tComponent_\n"
862                                            "s38\ts72\n"
863                                            "FeatureComponents\tFeature_\tComponent_\n"
864                                            "hydroxyl\thydrogen\n"
865                                            "heliox\thelium\n"
866                                            "lithia\tlithium";
867
868 static const CHAR mcomp_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
869                                      "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
870                                      "File\tFile\n"
871                                      "hydrogen\thydrogen\thydrogen\t0\t\t\t8192\t1\n"
872                                      "helium\thelium\thelium\t0\t\t\t8192\t1\n"
873                                      "lithium\tlithium\tlithium\t0\t\t\t8192\t1\n"
874                                      "beryllium\tmissingcomp\tberyllium\t0\t\t\t8192\t1";
875
876 static const CHAR ai_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
877                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
878                                   "File\tFile\n"
879                                   "five.txt\tFive\tfive.txt\t1000\t\t\t16384\t5\n"
880                                   "four.txt\tFour\tfour.txt\t1000\t\t\t16384\t4\n"
881                                   "one.txt\tOne\tone.txt\t1000\t\t\t16384\t1\n"
882                                   "three.txt\tThree\tthree.txt\t1000\t\t\t16384\t3\n"
883                                   "two.txt\tTwo\ttwo.txt\t1000\t\t\t16384\t2\n"
884                                   "file\tcomponent\tfilename\t100\t\t\t8192\t1\n"
885                                   "service_file\tservice_comp\tservice.exe\t100\t\t\t8192\t1";
886
887 static const CHAR ip_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
888                                               "s72\tS255\tI2\n"
889                                               "InstallExecuteSequence\tAction\n"
890                                               "CostFinalize\t\t1000\n"
891                                               "ValidateProductID\t\t700\n"
892                                               "CostInitialize\t\t800\n"
893                                               "FileCost\t\t900\n"
894                                               "RemoveFiles\t\t3500\n"
895                                               "InstallFiles\t\t4000\n"
896                                               "RegisterUser\t\t6000\n"
897                                               "RegisterProduct\t\t6100\n"
898                                               "PublishFeatures\t\t6300\n"
899                                               "PublishProduct\t\t6400\n"
900                                               "InstallFinalize\t\t6600\n"
901                                               "InstallInitialize\t\t1500\n"
902                                               "ProcessComponents\t\t1600\n"
903                                               "UnpublishFeatures\t\t1800\n"
904                                               "InstallValidate\t\t1400\n"
905                                               "LaunchConditions\t\t100\n"
906                                               "TestInstalledProp\tInstalled AND NOT REMOVE\t950\n";
907
908 static const CHAR ip_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
909                                            "s72\ti2\tS64\tS0\tS255\n"
910                                            "CustomAction\tAction\n"
911                                            "TestInstalledProp\t19\t\tTest failed\t\n";
912
913 static const CHAR aup_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
914                                                "s72\tS255\tI2\n"
915                                                "InstallExecuteSequence\tAction\n"
916                                                "CostFinalize\t\t1000\n"
917                                                "ValidateProductID\t\t700\n"
918                                                "CostInitialize\t\t800\n"
919                                                "FileCost\t\t900\n"
920                                                "RemoveFiles\t\t3500\n"
921                                                "InstallFiles\t\t4000\n"
922                                                "RegisterUser\t\t6000\n"
923                                                "RegisterProduct\t\t6100\n"
924                                                "PublishFeatures\t\t6300\n"
925                                                "PublishProduct\t\t6400\n"
926                                                "InstallFinalize\t\t6600\n"
927                                                "InstallInitialize\t\t1500\n"
928                                                "ProcessComponents\t\t1600\n"
929                                                "UnpublishFeatures\t\t1800\n"
930                                                "InstallValidate\t\t1400\n"
931                                                "LaunchConditions\t\t100\n"
932                                                "TestAllUsersProp\tALLUSERS AND NOT REMOVE\t50\n";
933
934 static const CHAR aup2_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
935                                                 "s72\tS255\tI2\n"
936                                                 "InstallExecuteSequence\tAction\n"
937                                                 "CostFinalize\t\t1000\n"
938                                                 "ValidateProductID\t\t700\n"
939                                                 "CostInitialize\t\t800\n"
940                                                 "FileCost\t\t900\n"
941                                                 "RemoveFiles\t\t3500\n"
942                                                 "InstallFiles\t\t4000\n"
943                                                 "RegisterUser\t\t6000\n"
944                                                 "RegisterProduct\t\t6100\n"
945                                                 "PublishFeatures\t\t6300\n"
946                                                 "PublishProduct\t\t6400\n"
947                                                 "InstallFinalize\t\t6600\n"
948                                                 "InstallInitialize\t\t1500\n"
949                                                 "ProcessComponents\t\t1600\n"
950                                                 "UnpublishFeatures\t\t1800\n"
951                                                 "InstallValidate\t\t1400\n"
952                                                 "LaunchConditions\t\t100\n"
953                                                 "TestAllUsersProp\tALLUSERS=2 AND NOT REMOVE\t50\n";
954
955 static const CHAR aup3_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
956                                                 "s72\tS255\tI2\n"
957                                                 "InstallExecuteSequence\tAction\n"
958                                                 "CostFinalize\t\t1000\n"
959                                                 "ValidateProductID\t\t700\n"
960                                                 "CostInitialize\t\t800\n"
961                                                 "FileCost\t\t900\n"
962                                                 "RemoveFiles\t\t3500\n"
963                                                 "InstallFiles\t\t4000\n"
964                                                 "RegisterUser\t\t6000\n"
965                                                 "RegisterProduct\t\t6100\n"
966                                                 "PublishFeatures\t\t6300\n"
967                                                 "PublishProduct\t\t6400\n"
968                                                 "InstallFinalize\t\t6600\n"
969                                                 "InstallInitialize\t\t1500\n"
970                                                 "ProcessComponents\t\t1600\n"
971                                                 "UnpublishFeatures\t\t1800\n"
972                                                 "InstallValidate\t\t1400\n"
973                                                 "LaunchConditions\t\t100\n"
974                                                 "TestAllUsersProp\tALLUSERS=1 AND NOT REMOVE\t50\n";
975
976 static const CHAR aup_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
977                                             "s72\ti2\tS64\tS0\tS255\n"
978                                             "CustomAction\tAction\n"
979                                             "TestAllUsersProp\t19\t\tTest failed\t\n";
980
981 static const CHAR fo_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
982                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
983                                   "File\tFile\n"
984                                   "override.txt\toverride\toverride.txt\t1000\t\t\t8192\t1\n"
985                                   "preselected.txt\tpreselected\tpreselected.txt\t1000\t\t\t8192\t2\n"
986                                   "notpreselected.txt\tnotpreselected\tnotpreselected.txt\t1000\t\t\t8192\t3\n";
987
988 static const CHAR fo_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
989                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
990                                      "Feature\tFeature\n"
991                                      "override\t\t\toverride feature\t1\t1\tMSITESTDIR\t0\n"
992                                      "preselected\t\t\tpreselected feature\t1\t1\tMSITESTDIR\t0\n"
993                                      "notpreselected\t\t\tnotpreselected feature\t1\t1\tMSITESTDIR\t0\n";
994
995 static const CHAR fo_condition_dat[] = "Feature_\tLevel\tCondition\n"
996                                        "s38\ti2\tS255\n"
997                                        "Condition\tFeature_\tLevel\n"
998                                        "preselected\t0\tPreselected\n"
999                                        "notpreselected\t0\tNOT Preselected\n";
1000
1001 static const CHAR fo_feature_comp_dat[] = "Feature_\tComponent_\n"
1002                                           "s38\ts72\n"
1003                                           "FeatureComponents\tFeature_\tComponent_\n"
1004                                           "override\toverride\n"
1005                                           "preselected\tpreselected\n"
1006                                           "notpreselected\tnotpreselected\n";
1007
1008 static const CHAR fo_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1009                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
1010                                        "Component\tComponent\n"
1011                                        "override\t{0A00FB1D-97B0-4B42-ADF0-BB8913416623}\tMSITESTDIR\t0\t\toverride.txt\n"
1012                                        "preselected\t{44E1DB75-605A-43DD-8CF5-CAB17F1BBD60}\tMSITESTDIR\t0\t\tpreselected.txt\n"
1013                                        "notpreselected\t{E1647733-5E75-400A-A92E-5E60B4D4EF9F}\tMSITESTDIR\t0\t\tnotpreselected.txt\n";
1014
1015 static const CHAR fo_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
1016                                            "s72\ti2\tS64\tS0\tS255\n"
1017                                            "CustomAction\tAction\n"
1018                                            "SetPreselected\t51\tPreselected\t1\t\n";
1019
1020 static const CHAR fo_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1021                                               "s72\tS255\tI2\n"
1022                                               "InstallExecuteSequence\tAction\n"
1023                                               "LaunchConditions\t\t100\n"
1024                                               "SetPreselected\tpreselect=1\t200\n"
1025                                               "CostInitialize\t\t800\n"
1026                                               "FileCost\t\t900\n"
1027                                               "CostFinalize\t\t1000\n"
1028                                               "InstallValidate\t\t1400\n"
1029                                               "InstallInitialize\t\t1500\n"
1030                                               "ProcessComponents\t\t1600\n"
1031                                               "RemoveFiles\t\t1700\n"
1032                                               "InstallFiles\t\t2000\n"
1033                                               "RegisterProduct\t\t5000\n"
1034                                               "PublishFeatures\t\t5100\n"
1035                                               "PublishProduct\t\t5200\n"
1036                                               "InstallFinalize\t\t6000\n";
1037
1038 static const CHAR sd_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1039                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1040                                   "File\tFile\n"
1041                                   "sourcedir.txt\tsourcedir\tsourcedir.txt\t1000\t\t\t8192\t1\n";
1042
1043 static const CHAR sd_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1044                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1045                                      "Feature\tFeature\n"
1046                                      "sourcedir\t\t\tsourcedir feature\t1\t2\tMSITESTDIR\t0\n";
1047
1048 static const CHAR sd_feature_comp_dat[] = "Feature_\tComponent_\n"
1049                                           "s38\ts72\n"
1050                                           "FeatureComponents\tFeature_\tComponent_\n"
1051                                           "sourcedir\tsourcedir\n";
1052
1053 static const CHAR sd_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1054                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
1055                                        "Component\tComponent\n"
1056                                        "sourcedir\t{DD422F92-3ED8-49B5-A0B7-F266F98357DF}\tMSITESTDIR\t0\t\tsourcedir.txt\n";
1057
1058 static const CHAR sd_install_ui_seq_dat[] = "Action\tCondition\tSequence\n"
1059                                             "s72\tS255\tI2\n"
1060                                             "InstallUISequence\tAction\n"
1061                                             "TestSourceDirProp1\tnot SourceDir and not SOURCEDIR and not Installed\t99\n"
1062                                             "AppSearch\t\t100\n"
1063                                             "TestSourceDirProp2\tnot SourceDir and not SOURCEDIR and not Installed\t101\n"
1064                                             "LaunchConditions\tnot Installed \t110\n"
1065                                             "TestSourceDirProp3\tnot SourceDir and not SOURCEDIR and not Installed\t111\n"
1066                                             "FindRelatedProducts\t\t120\n"
1067                                             "TestSourceDirProp4\tnot SourceDir and not SOURCEDIR and not Installed\t121\n"
1068                                             "CCPSearch\t\t130\n"
1069                                             "TestSourceDirProp5\tnot SourceDir and not SOURCEDIR and not Installed\t131\n"
1070                                             "RMCCPSearch\t\t140\n"
1071                                             "TestSourceDirProp6\tnot SourceDir and not SOURCEDIR and not Installed\t141\n"
1072                                             "ValidateProductID\t\t150\n"
1073                                             "TestSourceDirProp7\tnot SourceDir and not SOURCEDIR and not Installed\t151\n"
1074                                             "CostInitialize\t\t800\n"
1075                                             "TestSourceDirProp8\tnot SourceDir and not SOURCEDIR and not Installed\t801\n"
1076                                             "FileCost\t\t900\n"
1077                                             "TestSourceDirProp9\tnot SourceDir and not SOURCEDIR and not Installed\t901\n"
1078                                             "IsolateComponents\t\t1000\n"
1079                                             "TestSourceDirProp10\tnot SourceDir and not SOURCEDIR and not Installed\t1001\n"
1080                                             "CostFinalize\t\t1100\n"
1081                                             "TestSourceDirProp11\tnot SourceDir and not SOURCEDIR and not Installed\t1101\n"
1082                                             "MigrateFeatureStates\t\t1200\n"
1083                                             "TestSourceDirProp12\tnot SourceDir and not SOURCEDIR and not Installed\t1201\n"
1084                                             "ExecuteAction\t\t1300\n"
1085                                             "TestSourceDirProp13\tnot SourceDir and not SOURCEDIR and not Installed\t1301\n";
1086
1087 static const CHAR sd_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1088                                               "s72\tS255\tI2\n"
1089                                               "InstallExecuteSequence\tAction\n"
1090                                               "TestSourceDirProp14\tSourceDir and SOURCEDIR and not Installed\t99\n"
1091                                               "LaunchConditions\t\t100\n"
1092                                               "TestSourceDirProp15\tSourceDir and SOURCEDIR and not Installed\t101\n"
1093                                               "ValidateProductID\t\t700\n"
1094                                               "TestSourceDirProp16\tSourceDir and SOURCEDIR and not Installed\t701\n"
1095                                               "CostInitialize\t\t800\n"
1096                                               "TestSourceDirProp17\tSourceDir and SOURCEDIR and not Installed\t801\n"
1097                                               "ResolveSource\tResolveSource and not Installed\t850\n"
1098                                               "TestSourceDirProp18\tResolveSource and not SourceDir and not SOURCEDIR and not Installed\t851\n"
1099                                               "TestSourceDirProp19\tnot ResolveSource and SourceDir and SOURCEDIR and not Installed\t852\n"
1100                                               "FileCost\t\t900\n"
1101                                               "TestSourceDirProp20\tSourceDir and SOURCEDIR and not Installed\t901\n"
1102                                               "IsolateComponents\t\t1000\n"
1103                                               "TestSourceDirProp21\tSourceDir and SOURCEDIR and not Installed\t1001\n"
1104                                               "CostFinalize\t\t1100\n"
1105                                               "TestSourceDirProp22\tSourceDir and SOURCEDIR and not Installed\t1101\n"
1106                                               "MigrateFeatureStates\t\t1200\n"
1107                                               "TestSourceDirProp23\tSourceDir and SOURCEDIR and not Installed\t1201\n"
1108                                               "InstallValidate\t\t1400\n"
1109                                               "TestSourceDirProp24\tSourceDir and SOURCEDIR and not Installed\t1401\n"
1110                                               "InstallInitialize\t\t1500\n"
1111                                               "TestSourceDirProp25\tSourceDir and SOURCEDIR and not Installed\t1501\n"
1112                                               "ProcessComponents\t\t1600\n"
1113                                               "TestSourceDirProp26\tnot SourceDir and not SOURCEDIR and not Installed\t1601\n"
1114                                               "UnpublishFeatures\t\t1800\n"
1115                                               "TestSourceDirProp27\tnot SourceDir and not SOURCEDIR and not Installed\t1801\n"
1116                                               "RemoveFiles\t\t3500\n"
1117                                               "TestSourceDirProp28\tnot SourceDir and not SOURCEDIR and not Installed\t3501\n"
1118                                               "InstallFiles\t\t4000\n"
1119                                               "TestSourceDirProp29\tnot SourceDir and not SOURCEDIR and not Installed\t4001\n"
1120                                               "RegisterUser\t\t6000\n"
1121                                               "TestSourceDirProp30\tnot SourceDir and not SOURCEDIR and not Installed\t6001\n"
1122                                               "RegisterProduct\t\t6100\n"
1123                                               "TestSourceDirProp31\tnot SourceDir and not SOURCEDIR and not Installed\t6101\n"
1124                                               "PublishFeatures\t\t6300\n"
1125                                               "TestSourceDirProp32\tnot SourceDir and not SOURCEDIR and not Installed\t6301\n"
1126                                               "PublishProduct\t\t6400\n"
1127                                               "TestSourceDirProp33\tnot SourceDir and not SOURCEDIR and not Installed\t6401\n"
1128                                               "InstallExecute\t\t6500\n"
1129                                               "TestSourceDirProp34\tnot SourceDir and not SOURCEDIR and not Installed\t6501\n"
1130                                               "InstallFinalize\t\t6600\n"
1131                                               "TestSourceDirProp35\tnot SourceDir and not SOURCEDIR and not Installed\t6601\n";
1132
1133 static const CHAR sd_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
1134                                            "s72\ti2\tS64\tS0\tS255\n"
1135                                            "CustomAction\tAction\n"
1136                                            "TestSourceDirProp1\t19\t\tTest 1 failed\t\n"
1137                                            "TestSourceDirProp2\t19\t\tTest 2 failed\t\n"
1138                                            "TestSourceDirProp3\t19\t\tTest 3 failed\t\n"
1139                                            "TestSourceDirProp4\t19\t\tTest 4 failed\t\n"
1140                                            "TestSourceDirProp5\t19\t\tTest 5 failed\t\n"
1141                                            "TestSourceDirProp6\t19\t\tTest 6 failed\t\n"
1142                                            "TestSourceDirProp7\t19\t\tTest 7 failed\t\n"
1143                                            "TestSourceDirProp8\t19\t\tTest 8 failed\t\n"
1144                                            "TestSourceDirProp9\t19\t\tTest 9 failed\t\n"
1145                                            "TestSourceDirProp10\t19\t\tTest 10 failed\t\n"
1146                                            "TestSourceDirProp11\t19\t\tTest 11 failed\t\n"
1147                                            "TestSourceDirProp12\t19\t\tTest 12 failed\t\n"
1148                                            "TestSourceDirProp13\t19\t\tTest 13 failed\t\n"
1149                                            "TestSourceDirProp14\t19\t\tTest 14 failed\t\n"
1150                                            "TestSourceDirProp15\t19\t\tTest 15 failed\t\n"
1151                                            "TestSourceDirProp16\t19\t\tTest 16 failed\t\n"
1152                                            "TestSourceDirProp17\t19\t\tTest 17 failed\t\n"
1153                                            "TestSourceDirProp18\t19\t\tTest 18 failed\t\n"
1154                                            "TestSourceDirProp19\t19\t\tTest 19 failed\t\n"
1155                                            "TestSourceDirProp20\t19\t\tTest 20 failed\t\n"
1156                                            "TestSourceDirProp21\t19\t\tTest 21 failed\t\n"
1157                                            "TestSourceDirProp22\t19\t\tTest 22 failed\t\n"
1158                                            "TestSourceDirProp23\t19\t\tTest 23 failed\t\n"
1159                                            "TestSourceDirProp24\t19\t\tTest 24 failed\t\n"
1160                                            "TestSourceDirProp25\t19\t\tTest 25 failed\t\n"
1161                                            "TestSourceDirProp26\t19\t\tTest 26 failed\t\n"
1162                                            "TestSourceDirProp27\t19\t\tTest 27 failed\t\n"
1163                                            "TestSourceDirProp28\t19\t\tTest 28 failed\t\n"
1164                                            "TestSourceDirProp29\t19\t\tTest 29 failed\t\n"
1165                                            "TestSourceDirProp30\t19\t\tTest 30 failed\t\n"
1166                                            "TestSourceDirProp31\t19\t\tTest 31 failed\t\n"
1167                                            "TestSourceDirProp32\t19\t\tTest 32 failed\t\n"
1168                                            "TestSourceDirProp33\t19\t\tTest 33 failed\t\n"
1169                                            "TestSourceDirProp34\t19\t\tTest 34 failed\t\n"
1170                                            "TestSourceDirProp35\t19\t\tTest 35 failed\t\n";
1171
1172 typedef struct _msi_table
1173 {
1174     const CHAR *filename;
1175     const CHAR *data;
1176     int size;
1177 } msi_table;
1178
1179 #define ADD_TABLE(x) {#x".idt", x##_dat, sizeof(x##_dat)}
1180
1181 static const msi_table tables[] =
1182 {
1183     ADD_TABLE(component),
1184     ADD_TABLE(directory),
1185     ADD_TABLE(feature),
1186     ADD_TABLE(feature_comp),
1187     ADD_TABLE(file),
1188     ADD_TABLE(install_exec_seq),
1189     ADD_TABLE(media),
1190     ADD_TABLE(property),
1191     ADD_TABLE(registry),
1192     ADD_TABLE(service_install),
1193     ADD_TABLE(service_control)
1194 };
1195
1196 static const msi_table sc_tables[] =
1197 {
1198     ADD_TABLE(component),
1199     ADD_TABLE(directory),
1200     ADD_TABLE(feature),
1201     ADD_TABLE(feature_comp),
1202     ADD_TABLE(file),
1203     ADD_TABLE(install_exec_seq),
1204     ADD_TABLE(media),
1205     ADD_TABLE(property),
1206     ADD_TABLE(shortcut)
1207 };
1208
1209 static const msi_table ps_tables[] =
1210 {
1211     ADD_TABLE(component),
1212     ADD_TABLE(directory),
1213     ADD_TABLE(feature),
1214     ADD_TABLE(feature_comp),
1215     ADD_TABLE(file),
1216     ADD_TABLE(install_exec_seq),
1217     ADD_TABLE(media),
1218     ADD_TABLE(property),
1219     ADD_TABLE(condition)
1220 };
1221
1222 static const msi_table up_tables[] =
1223 {
1224     ADD_TABLE(component),
1225     ADD_TABLE(directory),
1226     ADD_TABLE(feature),
1227     ADD_TABLE(feature_comp),
1228     ADD_TABLE(file),
1229     ADD_TABLE(install_exec_seq),
1230     ADD_TABLE(media),
1231     ADD_TABLE(up_property),
1232     ADD_TABLE(registry),
1233     ADD_TABLE(service_install),
1234     ADD_TABLE(service_control)
1235 };
1236
1237 static const msi_table up2_tables[] =
1238 {
1239     ADD_TABLE(component),
1240     ADD_TABLE(directory),
1241     ADD_TABLE(feature),
1242     ADD_TABLE(feature_comp),
1243     ADD_TABLE(file),
1244     ADD_TABLE(install_exec_seq),
1245     ADD_TABLE(media),
1246     ADD_TABLE(up2_property),
1247     ADD_TABLE(registry),
1248     ADD_TABLE(service_install),
1249     ADD_TABLE(service_control)
1250 };
1251
1252 static const msi_table up3_tables[] =
1253 {
1254     ADD_TABLE(component),
1255     ADD_TABLE(directory),
1256     ADD_TABLE(feature),
1257     ADD_TABLE(feature_comp),
1258     ADD_TABLE(file),
1259     ADD_TABLE(install_exec_seq),
1260     ADD_TABLE(media),
1261     ADD_TABLE(up3_property),
1262     ADD_TABLE(registry),
1263     ADD_TABLE(service_install),
1264     ADD_TABLE(service_control)
1265 };
1266
1267 static const msi_table up4_tables[] =
1268 {
1269     ADD_TABLE(component),
1270     ADD_TABLE(directory),
1271     ADD_TABLE(feature),
1272     ADD_TABLE(feature_comp),
1273     ADD_TABLE(file),
1274     ADD_TABLE(pp_install_exec_seq),
1275     ADD_TABLE(media),
1276     ADD_TABLE(property),
1277     ADD_TABLE(registry),
1278     ADD_TABLE(service_install),
1279     ADD_TABLE(service_control)
1280 };
1281
1282 static const msi_table up5_tables[] =
1283 {
1284     ADD_TABLE(component),
1285     ADD_TABLE(directory),
1286     ADD_TABLE(feature),
1287     ADD_TABLE(feature_comp),
1288     ADD_TABLE(file),
1289     ADD_TABLE(pp_install_exec_seq),
1290     ADD_TABLE(media),
1291     ADD_TABLE(up_property),
1292     ADD_TABLE(registry),
1293     ADD_TABLE(service_install),
1294     ADD_TABLE(service_control)
1295 };
1296
1297 static const msi_table up6_tables[] =
1298 {
1299     ADD_TABLE(component),
1300     ADD_TABLE(directory),
1301     ADD_TABLE(feature),
1302     ADD_TABLE(feature_comp),
1303     ADD_TABLE(file),
1304     ADD_TABLE(pp_install_exec_seq),
1305     ADD_TABLE(media),
1306     ADD_TABLE(up2_property),
1307     ADD_TABLE(registry),
1308     ADD_TABLE(service_install),
1309     ADD_TABLE(service_control)
1310 };
1311
1312 static const msi_table up7_tables[] =
1313 {
1314     ADD_TABLE(component),
1315     ADD_TABLE(directory),
1316     ADD_TABLE(feature),
1317     ADD_TABLE(feature_comp),
1318     ADD_TABLE(file),
1319     ADD_TABLE(pp_install_exec_seq),
1320     ADD_TABLE(media),
1321     ADD_TABLE(up3_property),
1322     ADD_TABLE(registry),
1323     ADD_TABLE(service_install),
1324     ADD_TABLE(service_control)
1325 };
1326
1327 static const msi_table cc_tables[] =
1328 {
1329     ADD_TABLE(cc_component),
1330     ADD_TABLE(directory),
1331     ADD_TABLE(cc_feature),
1332     ADD_TABLE(cc_feature_comp),
1333     ADD_TABLE(cc_file),
1334     ADD_TABLE(install_exec_seq),
1335     ADD_TABLE(cc_media),
1336     ADD_TABLE(property),
1337 };
1338
1339 static const msi_table cc2_tables[] =
1340 {
1341     ADD_TABLE(cc2_component),
1342     ADD_TABLE(directory),
1343     ADD_TABLE(cc_feature),
1344     ADD_TABLE(cc_feature_comp),
1345     ADD_TABLE(cc2_file),
1346     ADD_TABLE(install_exec_seq),
1347     ADD_TABLE(cc_media),
1348     ADD_TABLE(property),
1349 };
1350
1351 static const msi_table co_tables[] =
1352 {
1353     ADD_TABLE(cc_component),
1354     ADD_TABLE(directory),
1355     ADD_TABLE(cc_feature),
1356     ADD_TABLE(cc_feature_comp),
1357     ADD_TABLE(co_file),
1358     ADD_TABLE(install_exec_seq),
1359     ADD_TABLE(co_media),
1360     ADD_TABLE(property),
1361 };
1362
1363 static const msi_table co2_tables[] =
1364 {
1365     ADD_TABLE(cc_component),
1366     ADD_TABLE(directory),
1367     ADD_TABLE(cc_feature),
1368     ADD_TABLE(cc_feature_comp),
1369     ADD_TABLE(cc_file),
1370     ADD_TABLE(install_exec_seq),
1371     ADD_TABLE(co2_media),
1372     ADD_TABLE(property),
1373 };
1374
1375 static const msi_table mm_tables[] =
1376 {
1377     ADD_TABLE(cc_component),
1378     ADD_TABLE(directory),
1379     ADD_TABLE(cc_feature),
1380     ADD_TABLE(cc_feature_comp),
1381     ADD_TABLE(mm_file),
1382     ADD_TABLE(install_exec_seq),
1383     ADD_TABLE(mm_media),
1384     ADD_TABLE(property),
1385 };
1386
1387 static const msi_table ss_tables[] =
1388 {
1389     ADD_TABLE(cc_component),
1390     ADD_TABLE(directory),
1391     ADD_TABLE(cc_feature),
1392     ADD_TABLE(cc_feature_comp),
1393     ADD_TABLE(cc_file),
1394     ADD_TABLE(install_exec_seq),
1395     ADD_TABLE(ss_media),
1396     ADD_TABLE(property),
1397 };
1398
1399 static const msi_table ui_tables[] =
1400 {
1401     ADD_TABLE(ui_component),
1402     ADD_TABLE(directory),
1403     ADD_TABLE(cc_feature),
1404     ADD_TABLE(cc_feature_comp),
1405     ADD_TABLE(cc_file),
1406     ADD_TABLE(install_exec_seq),
1407     ADD_TABLE(ui_install_ui_seq),
1408     ADD_TABLE(ui_custom_action),
1409     ADD_TABLE(cc_media),
1410     ADD_TABLE(property),
1411 };
1412
1413 static const msi_table rof_tables[] =
1414 {
1415     ADD_TABLE(rof_component),
1416     ADD_TABLE(directory),
1417     ADD_TABLE(rof_feature),
1418     ADD_TABLE(rof_feature_comp),
1419     ADD_TABLE(rof_file),
1420     ADD_TABLE(install_exec_seq),
1421     ADD_TABLE(rof_media),
1422     ADD_TABLE(property),
1423 };
1424
1425 static const msi_table rofc_tables[] =
1426 {
1427     ADD_TABLE(rof_component),
1428     ADD_TABLE(directory),
1429     ADD_TABLE(rof_feature),
1430     ADD_TABLE(rof_feature_comp),
1431     ADD_TABLE(rofc_file),
1432     ADD_TABLE(install_exec_seq),
1433     ADD_TABLE(rofc_media),
1434     ADD_TABLE(property),
1435 };
1436
1437 static const msi_table sdp_tables[] =
1438 {
1439     ADD_TABLE(rof_component),
1440     ADD_TABLE(directory),
1441     ADD_TABLE(rof_feature),
1442     ADD_TABLE(rof_feature_comp),
1443     ADD_TABLE(rof_file),
1444     ADD_TABLE(sdp_install_exec_seq),
1445     ADD_TABLE(sdp_custom_action),
1446     ADD_TABLE(rof_media),
1447     ADD_TABLE(property),
1448 };
1449
1450 static const msi_table cie_tables[] =
1451 {
1452     ADD_TABLE(cie_component),
1453     ADD_TABLE(directory),
1454     ADD_TABLE(cc_feature),
1455     ADD_TABLE(cie_feature_comp),
1456     ADD_TABLE(cie_file),
1457     ADD_TABLE(install_exec_seq),
1458     ADD_TABLE(cie_media),
1459     ADD_TABLE(property),
1460 };
1461
1462 static const msi_table ci_tables[] =
1463 {
1464     ADD_TABLE(ci_component),
1465     ADD_TABLE(directory),
1466     ADD_TABLE(rof_feature),
1467     ADD_TABLE(rof_feature_comp),
1468     ADD_TABLE(rof_file),
1469     ADD_TABLE(ci_install_exec_seq),
1470     ADD_TABLE(rof_media),
1471     ADD_TABLE(property),
1472     ADD_TABLE(ci_custom_action),
1473 };
1474
1475 static const msi_table ci2_tables[] =
1476 {
1477     ADD_TABLE(ci2_component),
1478     ADD_TABLE(directory),
1479     ADD_TABLE(rof_feature),
1480     ADD_TABLE(ci2_feature_comp),
1481     ADD_TABLE(ci2_file),
1482     ADD_TABLE(install_exec_seq),
1483     ADD_TABLE(rof_media),
1484     ADD_TABLE(property),
1485 };
1486
1487 static const msi_table spf_tables[] =
1488 {
1489     ADD_TABLE(ci_component),
1490     ADD_TABLE(directory),
1491     ADD_TABLE(rof_feature),
1492     ADD_TABLE(rof_feature_comp),
1493     ADD_TABLE(rof_file),
1494     ADD_TABLE(spf_install_exec_seq),
1495     ADD_TABLE(rof_media),
1496     ADD_TABLE(property),
1497     ADD_TABLE(spf_custom_action),
1498     ADD_TABLE(spf_install_ui_seq),
1499 };
1500
1501 static const msi_table lus0_tables[] =
1502 {
1503     ADD_TABLE(ci_component),
1504     ADD_TABLE(directory),
1505     ADD_TABLE(rof_feature),
1506     ADD_TABLE(rof_feature_comp),
1507     ADD_TABLE(rof_file),
1508     ADD_TABLE(pp_install_exec_seq),
1509     ADD_TABLE(rof_media),
1510     ADD_TABLE(property),
1511 };
1512
1513 static const msi_table lus1_tables[] =
1514 {
1515     ADD_TABLE(ci_component),
1516     ADD_TABLE(directory),
1517     ADD_TABLE(rof_feature),
1518     ADD_TABLE(rof_feature_comp),
1519     ADD_TABLE(rof_file),
1520     ADD_TABLE(pp_install_exec_seq),
1521     ADD_TABLE(rofc_media),
1522     ADD_TABLE(property),
1523 };
1524
1525 static const msi_table lus2_tables[] =
1526 {
1527     ADD_TABLE(ci_component),
1528     ADD_TABLE(directory),
1529     ADD_TABLE(rof_feature),
1530     ADD_TABLE(rof_feature_comp),
1531     ADD_TABLE(rof_file),
1532     ADD_TABLE(pp_install_exec_seq),
1533     ADD_TABLE(lus2_media),
1534     ADD_TABLE(property),
1535 };
1536
1537 static const msi_table tp_tables[] =
1538 {
1539     ADD_TABLE(tp_component),
1540     ADD_TABLE(directory),
1541     ADD_TABLE(rof_feature),
1542     ADD_TABLE(ci2_feature_comp),
1543     ADD_TABLE(ci2_file),
1544     ADD_TABLE(install_exec_seq),
1545     ADD_TABLE(rof_media),
1546     ADD_TABLE(property),
1547 };
1548
1549 static const msi_table cwd_tables[] =
1550 {
1551     ADD_TABLE(cwd_component),
1552     ADD_TABLE(directory),
1553     ADD_TABLE(rof_feature),
1554     ADD_TABLE(ci2_feature_comp),
1555     ADD_TABLE(ci2_file),
1556     ADD_TABLE(install_exec_seq),
1557     ADD_TABLE(rof_media),
1558     ADD_TABLE(property),
1559 };
1560
1561 static const msi_table adm_tables[] =
1562 {
1563     ADD_TABLE(adm_component),
1564     ADD_TABLE(directory),
1565     ADD_TABLE(rof_feature),
1566     ADD_TABLE(ci2_feature_comp),
1567     ADD_TABLE(ci2_file),
1568     ADD_TABLE(install_exec_seq),
1569     ADD_TABLE(rof_media),
1570     ADD_TABLE(property),
1571     ADD_TABLE(adm_custom_action),
1572     ADD_TABLE(adm_admin_exec_seq),
1573 };
1574
1575 static const msi_table amp_tables[] =
1576 {
1577     ADD_TABLE(amp_component),
1578     ADD_TABLE(directory),
1579     ADD_TABLE(rof_feature),
1580     ADD_TABLE(ci2_feature_comp),
1581     ADD_TABLE(ci2_file),
1582     ADD_TABLE(install_exec_seq),
1583     ADD_TABLE(rof_media),
1584     ADD_TABLE(property),
1585 };
1586
1587 static const msi_table mc_tables[] =
1588 {
1589     ADD_TABLE(mc_component),
1590     ADD_TABLE(directory),
1591     ADD_TABLE(cc_feature),
1592     ADD_TABLE(cie_feature_comp),
1593     ADD_TABLE(mc_file),
1594     ADD_TABLE(install_exec_seq),
1595     ADD_TABLE(mc_media),
1596     ADD_TABLE(property),
1597     ADD_TABLE(mc_file_hash),
1598 };
1599
1600 static const msi_table sf_tables[] =
1601 {
1602     ADD_TABLE(wrv_component),
1603     ADD_TABLE(directory),
1604     ADD_TABLE(rof_feature),
1605     ADD_TABLE(ci2_feature_comp),
1606     ADD_TABLE(ci2_file),
1607     ADD_TABLE(install_exec_seq),
1608     ADD_TABLE(rof_media),
1609     ADD_TABLE(property),
1610 };
1611
1612 static const msi_table ca51_tables[] =
1613 {
1614     ADD_TABLE(ca51_component),
1615     ADD_TABLE(directory),
1616     ADD_TABLE(rof_feature),
1617     ADD_TABLE(ci2_feature_comp),
1618     ADD_TABLE(ci2_file),
1619     ADD_TABLE(ca51_install_exec_seq),
1620     ADD_TABLE(rof_media),
1621     ADD_TABLE(property),
1622     ADD_TABLE(ca51_custom_action),
1623 };
1624
1625 static const msi_table is_tables[] =
1626 {
1627     ADD_TABLE(is_component),
1628     ADD_TABLE(directory),
1629     ADD_TABLE(is_feature),
1630     ADD_TABLE(is_feature_comp),
1631     ADD_TABLE(is_file),
1632     ADD_TABLE(install_exec_seq),
1633     ADD_TABLE(is_media),
1634     ADD_TABLE(property),
1635 };
1636
1637 static const msi_table sp_tables[] =
1638 {
1639     ADD_TABLE(sp_component),
1640     ADD_TABLE(sp_directory),
1641     ADD_TABLE(rof_feature),
1642     ADD_TABLE(ci2_feature_comp),
1643     ADD_TABLE(ci2_file),
1644     ADD_TABLE(install_exec_seq),
1645     ADD_TABLE(rof_media),
1646     ADD_TABLE(property),
1647 };
1648
1649 static const msi_table mcp_tables[] =
1650 {
1651     ADD_TABLE(mcp_component),
1652     ADD_TABLE(directory),
1653     ADD_TABLE(mcp_feature),
1654     ADD_TABLE(mcp_feature_comp),
1655     ADD_TABLE(rem_file),
1656     ADD_TABLE(rem_install_exec_seq),
1657     ADD_TABLE(rof_media),
1658     ADD_TABLE(property),
1659 };
1660
1661 static const msi_table mcomp_tables[] =
1662 {
1663     ADD_TABLE(mcp_component),
1664     ADD_TABLE(directory),
1665     ADD_TABLE(mcp_feature),
1666     ADD_TABLE(mcp_feature_comp),
1667     ADD_TABLE(mcomp_file),
1668     ADD_TABLE(rem_install_exec_seq),
1669     ADD_TABLE(rof_media),
1670     ADD_TABLE(property),
1671 };
1672
1673 static const msi_table ai_tables[] =
1674 {
1675     ADD_TABLE(component),
1676     ADD_TABLE(directory),
1677     ADD_TABLE(feature),
1678     ADD_TABLE(feature_comp),
1679     ADD_TABLE(ai_file),
1680     ADD_TABLE(install_exec_seq),
1681     ADD_TABLE(media),
1682     ADD_TABLE(property)
1683 };
1684
1685 static const msi_table pc_tables[] =
1686 {
1687     ADD_TABLE(ca51_component),
1688     ADD_TABLE(directory),
1689     ADD_TABLE(rof_feature),
1690     ADD_TABLE(ci2_feature_comp),
1691     ADD_TABLE(ci2_file),
1692     ADD_TABLE(install_exec_seq),
1693     ADD_TABLE(rof_media),
1694     ADD_TABLE(property)
1695 };
1696
1697 static const msi_table ip_tables[] =
1698 {
1699     ADD_TABLE(component),
1700     ADD_TABLE(directory),
1701     ADD_TABLE(feature),
1702     ADD_TABLE(feature_comp),
1703     ADD_TABLE(file),
1704     ADD_TABLE(ip_install_exec_seq),
1705     ADD_TABLE(ip_custom_action),
1706     ADD_TABLE(media),
1707     ADD_TABLE(property)
1708 };
1709
1710 static const msi_table aup_tables[] =
1711 {
1712     ADD_TABLE(component),
1713     ADD_TABLE(directory),
1714     ADD_TABLE(feature),
1715     ADD_TABLE(feature_comp),
1716     ADD_TABLE(file),
1717     ADD_TABLE(aup_install_exec_seq),
1718     ADD_TABLE(aup_custom_action),
1719     ADD_TABLE(media),
1720     ADD_TABLE(property)
1721 };
1722
1723 static const msi_table aup2_tables[] =
1724 {
1725     ADD_TABLE(component),
1726     ADD_TABLE(directory),
1727     ADD_TABLE(feature),
1728     ADD_TABLE(feature_comp),
1729     ADD_TABLE(file),
1730     ADD_TABLE(aup2_install_exec_seq),
1731     ADD_TABLE(aup_custom_action),
1732     ADD_TABLE(media),
1733     ADD_TABLE(aup_property)
1734 };
1735
1736 static const msi_table aup3_tables[] =
1737 {
1738     ADD_TABLE(component),
1739     ADD_TABLE(directory),
1740     ADD_TABLE(feature),
1741     ADD_TABLE(feature_comp),
1742     ADD_TABLE(file),
1743     ADD_TABLE(aup2_install_exec_seq),
1744     ADD_TABLE(aup_custom_action),
1745     ADD_TABLE(media),
1746     ADD_TABLE(aup2_property)
1747 };
1748
1749 static const msi_table aup4_tables[] =
1750 {
1751     ADD_TABLE(component),
1752     ADD_TABLE(directory),
1753     ADD_TABLE(feature),
1754     ADD_TABLE(feature_comp),
1755     ADD_TABLE(file),
1756     ADD_TABLE(aup3_install_exec_seq),
1757     ADD_TABLE(aup_custom_action),
1758     ADD_TABLE(media),
1759     ADD_TABLE(aup2_property)
1760 };
1761
1762 static const msi_table fiu_tables[] =
1763 {
1764     ADD_TABLE(rof_component),
1765     ADD_TABLE(directory),
1766     ADD_TABLE(rof_feature),
1767     ADD_TABLE(rof_feature_comp),
1768     ADD_TABLE(rof_file),
1769     ADD_TABLE(pp_install_exec_seq),
1770     ADD_TABLE(rof_media),
1771     ADD_TABLE(property),
1772 };
1773
1774 static const msi_table fiuc_tables[] =
1775 {
1776     ADD_TABLE(rof_component),
1777     ADD_TABLE(directory),
1778     ADD_TABLE(rof_feature),
1779     ADD_TABLE(rof_feature_comp),
1780     ADD_TABLE(rofc_file),
1781     ADD_TABLE(pp_install_exec_seq),
1782     ADD_TABLE(rofc_media),
1783     ADD_TABLE(property),
1784 };
1785
1786 static const msi_table sd_tables[] =
1787 {
1788     ADD_TABLE(directory),
1789     ADD_TABLE(sd_component),
1790     ADD_TABLE(sd_feature),
1791     ADD_TABLE(sd_feature_comp),
1792     ADD_TABLE(sd_file),
1793     ADD_TABLE(sd_install_exec_seq),
1794     ADD_TABLE(sd_install_ui_seq),
1795     ADD_TABLE(sd_custom_action),
1796     ADD_TABLE(media),
1797     ADD_TABLE(property)
1798 };
1799
1800 static const msi_table fo_tables[] =
1801 {
1802     ADD_TABLE(directory),
1803     ADD_TABLE(fo_file),
1804     ADD_TABLE(fo_component),
1805     ADD_TABLE(fo_feature),
1806     ADD_TABLE(fo_condition),
1807     ADD_TABLE(fo_feature_comp),
1808     ADD_TABLE(fo_custom_action),
1809     ADD_TABLE(fo_install_exec_seq),
1810     ADD_TABLE(media),
1811     ADD_TABLE(property)
1812 };
1813
1814 static const msi_table icon_base_tables[] =
1815 {
1816     ADD_TABLE(ci_component),
1817     ADD_TABLE(directory),
1818     ADD_TABLE(rof_feature),
1819     ADD_TABLE(rof_feature_comp),
1820     ADD_TABLE(rof_file),
1821     ADD_TABLE(pp_install_exec_seq),
1822     ADD_TABLE(rof_media),
1823     ADD_TABLE(icon_property),
1824 };
1825
1826 static const msi_table pv_tables[] =
1827 {
1828     ADD_TABLE(rof_component),
1829     ADD_TABLE(directory),
1830     ADD_TABLE(rof_feature),
1831     ADD_TABLE(rof_feature_comp),
1832     ADD_TABLE(rof_file),
1833     ADD_TABLE(pv_install_exec_seq),
1834     ADD_TABLE(rof_media),
1835     ADD_TABLE(property)
1836 };
1837
1838 /* cabinet definitions */
1839
1840 /* make the max size large so there is only one cab file */
1841 #define MEDIA_SIZE          0x7FFFFFFF
1842 #define FOLDER_THRESHOLD    900000
1843
1844 /* the FCI callbacks */
1845
1846 static void * CDECL mem_alloc(ULONG cb)
1847 {
1848     return HeapAlloc(GetProcessHeap(), 0, cb);
1849 }
1850
1851 static void CDECL mem_free(void *memory)
1852 {
1853     HeapFree(GetProcessHeap(), 0, memory);
1854 }
1855
1856 static BOOL CDECL get_next_cabinet(PCCAB pccab, ULONG  cbPrevCab, void *pv)
1857 {
1858     sprintf(pccab->szCab, pv, pccab->iCab);
1859     return TRUE;
1860 }
1861
1862 static LONG CDECL progress(UINT typeStatus, ULONG cb1, ULONG cb2, void *pv)
1863 {
1864     return 0;
1865 }
1866
1867 static int CDECL file_placed(PCCAB pccab, char *pszFile, LONG cbFile,
1868                              BOOL fContinuation, void *pv)
1869 {
1870     return 0;
1871 }
1872
1873 static INT_PTR CDECL fci_open(char *pszFile, int oflag, int pmode, int *err, void *pv)
1874 {
1875     HANDLE handle;
1876     DWORD dwAccess = 0;
1877     DWORD dwShareMode = 0;
1878     DWORD dwCreateDisposition = OPEN_EXISTING;
1879     
1880     dwAccess = GENERIC_READ | GENERIC_WRITE;
1881     /* FILE_SHARE_DELETE is not supported by Windows Me/98/95 */
1882     dwShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE;
1883
1884     if (GetFileAttributesA(pszFile) != INVALID_FILE_ATTRIBUTES)
1885         dwCreateDisposition = OPEN_EXISTING;
1886     else
1887         dwCreateDisposition = CREATE_NEW;
1888
1889     handle = CreateFileA(pszFile, dwAccess, dwShareMode, NULL,
1890                          dwCreateDisposition, 0, NULL);
1891
1892     ok(handle != INVALID_HANDLE_VALUE, "Failed to CreateFile %s\n", pszFile);
1893
1894     return (INT_PTR)handle;
1895 }
1896
1897 static UINT CDECL fci_read(INT_PTR hf, void *memory, UINT cb, int *err, void *pv)
1898 {
1899     HANDLE handle = (HANDLE)hf;
1900     DWORD dwRead;
1901     BOOL res;
1902     
1903     res = ReadFile(handle, memory, cb, &dwRead, NULL);
1904     ok(res, "Failed to ReadFile\n");
1905
1906     return dwRead;
1907 }
1908
1909 static UINT CDECL fci_write(INT_PTR hf, void *memory, UINT cb, int *err, void *pv)
1910 {
1911     HANDLE handle = (HANDLE)hf;
1912     DWORD dwWritten;
1913     BOOL res;
1914
1915     res = WriteFile(handle, memory, cb, &dwWritten, NULL);
1916     ok(res, "Failed to WriteFile\n");
1917
1918     return dwWritten;
1919 }
1920
1921 static int CDECL fci_close(INT_PTR hf, int *err, void *pv)
1922 {
1923     HANDLE handle = (HANDLE)hf;
1924     ok(CloseHandle(handle), "Failed to CloseHandle\n");
1925
1926     return 0;
1927 }
1928
1929 static LONG CDECL fci_seek(INT_PTR hf, LONG dist, int seektype, int *err, void *pv)
1930 {
1931     HANDLE handle = (HANDLE)hf;
1932     DWORD ret;
1933     
1934     ret = SetFilePointer(handle, dist, NULL, seektype);
1935     ok(ret != INVALID_SET_FILE_POINTER, "Failed to SetFilePointer\n");
1936
1937     return ret;
1938 }
1939
1940 static int CDECL fci_delete(char *pszFile, int *err, void *pv)
1941 {
1942     BOOL ret = DeleteFileA(pszFile);
1943     ok(ret, "Failed to DeleteFile %s\n", pszFile);
1944
1945     return 0;
1946 }
1947
1948 static void init_functionpointers(void)
1949 {
1950     HMODULE hmsi = GetModuleHandleA("msi.dll");
1951     HMODULE hadvapi32 = GetModuleHandleA("advapi32.dll");
1952     HMODULE hkernel32 = GetModuleHandleA("kernel32.dll");
1953
1954 #define GET_PROC(mod, func) \
1955     p ## func = (void*)GetProcAddress(mod, #func); \
1956     if(!p ## func) \
1957       trace("GetProcAddress(%s) failed\n", #func);
1958
1959     GET_PROC(hmsi, MsiQueryComponentStateA);
1960     GET_PROC(hmsi, MsiSetExternalUIRecord);
1961     GET_PROC(hmsi, MsiSourceListEnumSourcesA);
1962     GET_PROC(hmsi, MsiSourceListGetInfoA);
1963     GET_PROC(hmsi, MsiGetComponentPathExA);
1964
1965     GET_PROC(hadvapi32, ConvertSidToStringSidA);
1966     GET_PROC(hadvapi32, GetTokenInformation);
1967     GET_PROC(hadvapi32, OpenProcessToken);
1968     GET_PROC(hadvapi32, RegDeleteKeyExA)
1969     GET_PROC(hkernel32, IsWow64Process)
1970
1971     hsrclient = LoadLibraryA("srclient.dll");
1972     GET_PROC(hsrclient, SRRemoveRestorePoint);
1973     GET_PROC(hsrclient, SRSetRestorePointA);
1974
1975 #undef GET_PROC
1976 }
1977
1978 static BOOL is_process_limited(void)
1979 {
1980     HANDLE token;
1981
1982     if (!pOpenProcessToken || !pGetTokenInformation) return FALSE;
1983
1984     if (pOpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &token))
1985     {
1986         BOOL ret;
1987         TOKEN_ELEVATION_TYPE type = TokenElevationTypeDefault;
1988         DWORD size;
1989
1990         ret = pGetTokenInformation(token, TokenElevationType, &type, sizeof(type), &size);
1991         CloseHandle(token);
1992         return (ret && type == TokenElevationTypeLimited);
1993     }
1994     return FALSE;
1995 }
1996
1997 static BOOL check_win9x(void)
1998 {
1999     SC_HANDLE scm;
2000
2001     scm = OpenSCManager(NULL, NULL, GENERIC_ALL);
2002     if (!scm && (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED))
2003         return TRUE;
2004
2005     CloseServiceHandle(scm);
2006
2007     return FALSE;
2008 }
2009
2010 static BOOL check_record(MSIHANDLE rec, UINT field, LPCSTR val)
2011 {
2012     CHAR buffer[0x20];
2013     UINT r;
2014     DWORD sz;
2015
2016     sz = sizeof buffer;
2017     r = MsiRecordGetString(rec, field, buffer, &sz);
2018     return (r == ERROR_SUCCESS ) && !strcmp(val, buffer);
2019 }
2020
2021 static BOOL CDECL get_temp_file(char *pszTempName, int cbTempName, void *pv)
2022 {
2023     LPSTR tempname;
2024
2025     tempname = HeapAlloc(GetProcessHeap(), 0, MAX_PATH);
2026     GetTempFileNameA(".", "xx", 0, tempname);
2027
2028     if (tempname && (strlen(tempname) < (unsigned)cbTempName))
2029     {
2030         lstrcpyA(pszTempName, tempname);
2031         HeapFree(GetProcessHeap(), 0, tempname);
2032         return TRUE;
2033     }
2034
2035     HeapFree(GetProcessHeap(), 0, tempname);
2036
2037     return FALSE;
2038 }
2039
2040 static INT_PTR CDECL get_open_info(char *pszName, USHORT *pdate, USHORT *ptime,
2041                                    USHORT *pattribs, int *err, void *pv)
2042 {
2043     BY_HANDLE_FILE_INFORMATION finfo;
2044     FILETIME filetime;
2045     HANDLE handle;
2046     DWORD attrs;
2047     BOOL res;
2048
2049     handle = CreateFile(pszName, GENERIC_READ, FILE_SHARE_READ, NULL,
2050                         OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL | FILE_FLAG_SEQUENTIAL_SCAN, NULL);
2051
2052     ok(handle != INVALID_HANDLE_VALUE, "Failed to CreateFile %s\n", pszName);
2053
2054     res = GetFileInformationByHandle(handle, &finfo);
2055     ok(res, "Expected GetFileInformationByHandle to succeed\n");
2056    
2057     FileTimeToLocalFileTime(&finfo.ftLastWriteTime, &filetime);
2058     FileTimeToDosDateTime(&filetime, pdate, ptime);
2059
2060     attrs = GetFileAttributes(pszName);
2061     ok(attrs != INVALID_FILE_ATTRIBUTES, "Failed to GetFileAttributes\n");
2062
2063     return (INT_PTR)handle;
2064 }
2065
2066 static BOOL add_file(HFCI hfci, const char *file, TCOMP compress)
2067 {
2068     char path[MAX_PATH];
2069     char filename[MAX_PATH];
2070
2071     lstrcpyA(path, CURR_DIR);
2072     lstrcatA(path, "\\");
2073     lstrcatA(path, file);
2074
2075     lstrcpyA(filename, file);
2076
2077     return FCIAddFile(hfci, path, filename, FALSE, get_next_cabinet,
2078                       progress, get_open_info, compress);
2079 }
2080
2081 static void set_cab_parameters(PCCAB pCabParams, const CHAR *name, DWORD max_size)
2082 {
2083     ZeroMemory(pCabParams, sizeof(CCAB));
2084
2085     pCabParams->cb = max_size;
2086     pCabParams->cbFolderThresh = FOLDER_THRESHOLD;
2087     pCabParams->setID = 0xbeef;
2088     pCabParams->iCab = 1;
2089     lstrcpyA(pCabParams->szCabPath, CURR_DIR);
2090     lstrcatA(pCabParams->szCabPath, "\\");
2091     lstrcpyA(pCabParams->szCab, name);
2092 }
2093
2094 static void create_cab_file(const CHAR *name, DWORD max_size, const CHAR *files)
2095 {
2096     CCAB cabParams;
2097     LPCSTR ptr;
2098     HFCI hfci;
2099     ERF erf;
2100     BOOL res;
2101
2102     set_cab_parameters(&cabParams, name, max_size);
2103
2104     hfci = FCICreate(&erf, file_placed, mem_alloc, mem_free, fci_open,
2105                       fci_read, fci_write, fci_close, fci_seek, fci_delete,
2106                       get_temp_file, &cabParams, NULL);
2107
2108     ok(hfci != NULL, "Failed to create an FCI context\n");
2109
2110     ptr = files;
2111     while (*ptr)
2112     {
2113         res = add_file(hfci, ptr, tcompTYPE_MSZIP);
2114         ok(res, "Failed to add file: %s\n", ptr);
2115         ptr += lstrlen(ptr) + 1;
2116     }
2117
2118     res = FCIFlushCabinet(hfci, FALSE, get_next_cabinet, progress);
2119     ok(res, "Failed to flush the cabinet\n");
2120
2121     res = FCIDestroy(hfci);
2122     ok(res, "Failed to destroy the cabinet\n");
2123 }
2124
2125 static BOOL get_user_dirs(void)
2126 {
2127     HKEY hkey;
2128     DWORD type, size;
2129
2130     if(RegOpenKey(HKEY_CURRENT_USER,
2131                    "Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders",
2132                    &hkey))
2133         return FALSE;
2134
2135     size = MAX_PATH;
2136     if(RegQueryValueExA(hkey, "AppData", 0, &type, (LPBYTE)APP_DATA_DIR, &size)){
2137         RegCloseKey(hkey);
2138         return FALSE;
2139     }
2140
2141     RegCloseKey(hkey);
2142     return TRUE;
2143 }
2144
2145 static BOOL get_system_dirs(void)
2146 {
2147     HKEY hkey;
2148     DWORD type, size;
2149
2150     if (RegOpenKey(HKEY_LOCAL_MACHINE,
2151                    "Software\\Microsoft\\Windows\\CurrentVersion", &hkey))
2152         return FALSE;
2153
2154     size = MAX_PATH;
2155     if (RegQueryValueExA(hkey, "ProgramFilesDir (x86)", 0, &type, (LPBYTE)PROG_FILES_DIR, &size) &&
2156         RegQueryValueExA(hkey, "ProgramFilesDir", 0, &type, (LPBYTE)PROG_FILES_DIR, &size)) {
2157         RegCloseKey(hkey);
2158         return FALSE;
2159     }
2160
2161     size = MAX_PATH;
2162     if (RegQueryValueExA(hkey, "CommonFilesDir (x86)", 0, &type, (LPBYTE)COMMON_FILES_DIR, &size) &&
2163         RegQueryValueExA(hkey, "CommonFilesDir", 0, &type, (LPBYTE)COMMON_FILES_DIR, &size)) {
2164         RegCloseKey(hkey);
2165         return FALSE;
2166     }
2167
2168     size = MAX_PATH;
2169     if (RegQueryValueExA(hkey, "ProgramFilesDir", 0, &type, (LPBYTE)PROG_FILES_DIR_NATIVE, &size)) {
2170         RegCloseKey(hkey);
2171         return FALSE;
2172     }
2173
2174     RegCloseKey(hkey);
2175
2176     if(GetWindowsDirectoryA(WINDOWS_DIR, MAX_PATH) != ERROR_SUCCESS)
2177         return FALSE;
2178
2179     return TRUE;
2180 }
2181
2182 static void create_file_data(LPCSTR name, LPCSTR data, DWORD size)
2183 {
2184     HANDLE file;
2185     DWORD written;
2186
2187     file = CreateFileA(name, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, 0, NULL);
2188     if (file == INVALID_HANDLE_VALUE)
2189         return;
2190
2191     WriteFile(file, data, strlen(data), &written, NULL);
2192
2193     if (size)
2194     {
2195         SetFilePointer(file, size, NULL, FILE_BEGIN);
2196         SetEndOfFile(file);
2197     }
2198
2199     CloseHandle(file);
2200 }
2201
2202 #define create_file(name, size) create_file_data(name, name, size)
2203
2204 static void create_test_files(void)
2205 {
2206     CreateDirectoryA("msitest", NULL);
2207     create_file("msitest\\one.txt", 100);
2208     CreateDirectoryA("msitest\\first", NULL);
2209     create_file("msitest\\first\\two.txt", 100);
2210     CreateDirectoryA("msitest\\second", NULL);
2211     create_file("msitest\\second\\three.txt", 100);
2212
2213     create_file("four.txt", 100);
2214     create_file("five.txt", 100);
2215     create_cab_file("msitest.cab", MEDIA_SIZE, "four.txt\0five.txt\0");
2216
2217     create_file("msitest\\filename", 100);
2218     create_file("msitest\\service.exe", 100);
2219
2220     DeleteFileA("four.txt");
2221     DeleteFileA("five.txt");
2222 }
2223
2224 static BOOL delete_pf(const CHAR *rel_path, BOOL is_file)
2225 {
2226     CHAR path[MAX_PATH];
2227
2228     lstrcpyA(path, PROG_FILES_DIR);
2229     lstrcatA(path, "\\");
2230     lstrcatA(path, rel_path);
2231
2232     if (is_file)
2233         return DeleteFileA(path);
2234     else
2235         return RemoveDirectoryA(path);
2236 }
2237
2238 static BOOL delete_pf_native(const CHAR *rel_path, BOOL is_file)
2239 {
2240     CHAR path[MAX_PATH];
2241
2242     lstrcpyA(path, PROG_FILES_DIR_NATIVE);
2243     lstrcatA(path, "\\");
2244     lstrcatA(path, rel_path);
2245
2246     if (is_file)
2247         return DeleteFileA(path);
2248     else
2249         return RemoveDirectoryA(path);
2250 }
2251
2252 static BOOL delete_cf(const CHAR *rel_path, BOOL is_file)
2253 {
2254     CHAR path[MAX_PATH];
2255
2256     lstrcpyA(path, COMMON_FILES_DIR);
2257     lstrcatA(path, "\\");
2258     lstrcatA(path, rel_path);
2259
2260     if (is_file)
2261         return DeleteFileA(path);
2262     else
2263         return RemoveDirectoryA(path);
2264 }
2265
2266 static void delete_test_files(void)
2267 {
2268     DeleteFileA("msitest.msi");
2269     DeleteFileA("msitest.cab");
2270     DeleteFileA("msitest\\second\\three.txt");
2271     DeleteFileA("msitest\\first\\two.txt");
2272     DeleteFileA("msitest\\one.txt");
2273     DeleteFileA("msitest\\service.exe");
2274     DeleteFileA("msitest\\filename");
2275     RemoveDirectoryA("msitest\\second");
2276     RemoveDirectoryA("msitest\\first");
2277     RemoveDirectoryA("msitest");
2278 }
2279
2280 static void write_file(const CHAR *filename, const char *data, int data_size)
2281 {
2282     DWORD size;
2283
2284     HANDLE hf = CreateFile(filename, GENERIC_WRITE, 0, NULL,
2285                            CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
2286
2287     WriteFile(hf, data, data_size, &size, NULL);
2288     CloseHandle(hf);
2289 }
2290
2291 static void write_msi_summary_info(MSIHANDLE db, INT version, INT wordcount, const char *template)
2292 {
2293     MSIHANDLE summary;
2294     UINT r;
2295
2296     r = MsiGetSummaryInformationA(db, NULL, 5, &summary);
2297     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2298
2299     r = MsiSummaryInfoSetPropertyA(summary, PID_TEMPLATE, VT_LPSTR, 0, NULL, template);
2300     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2301
2302     r = MsiSummaryInfoSetPropertyA(summary, PID_REVNUMBER, VT_LPSTR, 0, NULL,
2303                                    "{004757CA-5092-49c2-AD20-28E1CE0DF5F2}");
2304     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2305
2306     r = MsiSummaryInfoSetPropertyA(summary, PID_PAGECOUNT, VT_I4, version, NULL, NULL);
2307     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2308
2309     r = MsiSummaryInfoSetPropertyA(summary, PID_WORDCOUNT, VT_I4, wordcount, NULL, NULL);
2310     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2311
2312     r = MsiSummaryInfoSetPropertyA(summary, PID_TITLE, VT_LPSTR, 0, NULL, "MSITEST");
2313     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2314
2315     /* write the summary changes back to the stream */
2316     r = MsiSummaryInfoPersist(summary);
2317     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2318
2319     MsiCloseHandle(summary);
2320 }
2321
2322 #define create_database(name, tables, num_tables) \
2323     create_database_wordcount(name, tables, num_tables, 100, 0, ";1033");
2324
2325 #define create_database_template(name, tables, num_tables, version, template) \
2326     create_database_wordcount(name, tables, num_tables, version, 0, template);
2327
2328 static void create_database_wordcount(const CHAR *name, const msi_table *tables,
2329                                       int num_tables, INT version, INT wordcount,
2330                                       const char *template)
2331 {
2332     MSIHANDLE db;
2333     UINT r;
2334     int j;
2335
2336     r = MsiOpenDatabaseA(name, MSIDBOPEN_CREATE, &db);
2337     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2338
2339     /* import the tables into the database */
2340     for (j = 0; j < num_tables; j++)
2341     {
2342         const msi_table *table = &tables[j];
2343
2344         write_file(table->filename, table->data, (table->size - 1) * sizeof(char));
2345
2346         r = MsiDatabaseImportA(db, CURR_DIR, table->filename);
2347         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2348
2349         DeleteFileA(table->filename);
2350     }
2351
2352     write_msi_summary_info(db, version, wordcount, template);
2353
2354     r = MsiDatabaseCommit(db);
2355     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2356
2357     MsiCloseHandle(db);
2358 }
2359
2360 static void check_service_is_installed(void)
2361 {
2362     SC_HANDLE scm, service;
2363     BOOL res;
2364
2365     scm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
2366     ok(scm != NULL, "Failed to open the SC Manager\n");
2367
2368     service = OpenService(scm, "TestService", SC_MANAGER_ALL_ACCESS);
2369     ok(service != NULL, "Failed to open TestService\n");
2370
2371     res = DeleteService(service);
2372     ok(res, "Failed to delete TestService\n");
2373
2374     CloseServiceHandle(service);
2375     CloseServiceHandle(scm);
2376 }
2377
2378 static BOOL notify_system_change(DWORD event_type, STATEMGRSTATUS *status)
2379 {
2380     RESTOREPOINTINFOA spec;
2381
2382     spec.dwEventType = event_type;
2383     spec.dwRestorePtType = APPLICATION_INSTALL;
2384     spec.llSequenceNumber = status->llSequenceNumber;
2385     lstrcpyA(spec.szDescription, "msitest restore point");
2386
2387     return pSRSetRestorePointA(&spec, status);
2388 }
2389
2390 static void remove_restore_point(DWORD seq_number)
2391 {
2392     DWORD res;
2393
2394     res = pSRRemoveRestorePoint(seq_number);
2395     if (res != ERROR_SUCCESS)
2396         trace("Failed to remove the restore point : %08x\n", res);
2397 }
2398
2399 static LONG delete_key( HKEY key, LPCSTR subkey, REGSAM access )
2400 {
2401     if (pRegDeleteKeyExA)
2402         return pRegDeleteKeyExA( key, subkey, access, 0 );
2403     return RegDeleteKeyA( key, subkey );
2404 }
2405
2406 static void test_MsiInstallProduct(void)
2407 {
2408     UINT r;
2409     CHAR path[MAX_PATH];
2410     LONG res;
2411     HKEY hkey;
2412     DWORD num, size, type;
2413     REGSAM access = KEY_ALL_ACCESS;
2414
2415     if (on_win9x)
2416     {
2417         win_skip("Services are not implemented on Win9x and WinMe\n");
2418         return;
2419     }
2420     if (is_process_limited())
2421     {
2422         skip("process is limited\n");
2423         return;
2424     }
2425
2426     if (is_wow64)
2427         access |= KEY_WOW64_64KEY;
2428
2429     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
2430
2431     /* szPackagePath is NULL */
2432     r = MsiInstallProductA(NULL, "INSTALL=ALL");
2433     ok(r == ERROR_INVALID_PARAMETER,
2434        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
2435
2436     /* both szPackagePath and szCommandLine are NULL */
2437     r = MsiInstallProductA(NULL, NULL);
2438     ok(r == ERROR_INVALID_PARAMETER,
2439        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
2440
2441     /* szPackagePath is empty */
2442     r = MsiInstallProductA("", "INSTALL=ALL");
2443     ok(r == ERROR_PATH_NOT_FOUND,
2444        "Expected ERROR_PATH_NOT_FOUND, got %d\n", r);
2445
2446     create_test_files();
2447     create_database(msifile, tables, sizeof(tables) / sizeof(msi_table));
2448
2449     /* install, don't publish */
2450     r = MsiInstallProductA(msifile, NULL);
2451     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
2452     {
2453         skip("Not enough rights to perform tests\n");
2454         goto error;
2455     }
2456     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2457
2458     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2459     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2460     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2461     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2462     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2463     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2464     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2465     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2466     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2467     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2468     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2469     ok(delete_pf("msitest", FALSE), "File not installed\n");
2470
2471     res = RegOpenKeyEx(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", 0, access, &hkey);
2472     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
2473
2474     size = MAX_PATH;
2475     type = REG_SZ;
2476     res = RegQueryValueExA(hkey, "Name", NULL, &type, (LPBYTE)path, &size);
2477     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
2478     ok(!lstrcmpA(path, "imaname"), "Expected imaname, got %s\n", path);
2479
2480     size = MAX_PATH;
2481     type = REG_SZ;
2482     res = RegQueryValueExA(hkey, "blah", NULL, &type, (LPBYTE)path, &size);
2483     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
2484
2485     size = sizeof(num);
2486     type = REG_DWORD;
2487     res = RegQueryValueExA(hkey, "number", NULL, &type, (LPBYTE)&num, &size);
2488     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
2489     ok(num == 314, "Expected 314, got %d\n", num);
2490
2491     size = MAX_PATH;
2492     type = REG_SZ;
2493     res = RegQueryValueExA(hkey, "OrderTestName", NULL, &type, (LPBYTE)path, &size);
2494     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
2495     ok(!lstrcmpA(path, "OrderTestValue"), "Expected OrderTestValue, got %s\n", path);
2496
2497     check_service_is_installed();
2498
2499     delete_key(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", access);
2500
2501     /* not published, reinstall */
2502     r = MsiInstallProductA(msifile, NULL);
2503     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2504
2505     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2506     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2507     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2508     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2509     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2510     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2511     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2512     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2513     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2514     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2515     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2516     ok(delete_pf("msitest", FALSE), "File not installed\n");
2517
2518     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2519     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
2520     RegDeleteKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest");
2521
2522     create_database(msifile, up_tables, sizeof(up_tables) / sizeof(msi_table));
2523
2524     /* not published, RemovePreviousVersions set */
2525     r = MsiInstallProductA(msifile, NULL);
2526     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2527
2528     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2529     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2530     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2531     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2532     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2533     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2534     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2535     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2536     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2537     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2538     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2539     ok(delete_pf("msitest", FALSE), "File not installed\n");
2540
2541     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2542     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
2543     RegDeleteKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest");
2544
2545     create_database(msifile, up2_tables, sizeof(up2_tables) / sizeof(msi_table));
2546
2547     /* not published, version number bumped */
2548     r = MsiInstallProductA(msifile, NULL);
2549     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2550
2551     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2552     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2553     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2554     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2555     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2556     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2557     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2558     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2559     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2560     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2561     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2562     ok(delete_pf("msitest", FALSE), "File not installed\n");
2563
2564     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2565     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
2566     RegDeleteKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest");
2567
2568     create_database(msifile, up3_tables, sizeof(up3_tables) / sizeof(msi_table));
2569
2570     /* not published, RemovePreviousVersions set and version number bumped */
2571     r = MsiInstallProductA(msifile, NULL);
2572     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2573
2574     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2575     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2576     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2577     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2578     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2579     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2580     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2581     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2582     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2583     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2584     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2585     ok(delete_pf("msitest", FALSE), "File not installed\n");
2586
2587     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2588     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
2589     RegDeleteKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest");
2590
2591     create_database(msifile, up4_tables, sizeof(up4_tables) / sizeof(msi_table));
2592
2593     /* install, publish product */
2594     r = MsiInstallProductA(msifile, "PUBLISH_PRODUCT=1");
2595     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2596
2597     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2598     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2599     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2600     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2601     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2602     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2603     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2604     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2605     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2606     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2607     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2608     ok(delete_pf("msitest", FALSE), "File not installed\n");
2609
2610     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2611     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
2612
2613     create_database(msifile, up4_tables, sizeof(up4_tables) / sizeof(msi_table));
2614
2615     /* published, reinstall */
2616     r = MsiInstallProductA(msifile, NULL);
2617     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2618
2619     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2620     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2621     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2622     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2623     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2624     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2625     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2626     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2627     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2628     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2629     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2630     ok(delete_pf("msitest", FALSE), "File not installed\n");
2631
2632     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2633     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
2634
2635     create_database(msifile, up5_tables, sizeof(up5_tables) / sizeof(msi_table));
2636
2637     /* published product, RemovePreviousVersions set */
2638     r = MsiInstallProductA(msifile, NULL);
2639     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2640
2641     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2642     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2643     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2644     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2645     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2646     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2647     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2648     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2649     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2650     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2651     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2652     ok(delete_pf("msitest", FALSE), "File not installed\n");
2653
2654     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2655     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
2656
2657     create_database(msifile, up6_tables, sizeof(up6_tables) / sizeof(msi_table));
2658
2659     /* published product, version number bumped */
2660     r = MsiInstallProductA(msifile, NULL);
2661     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2662
2663     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2664     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2665     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2666     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2667     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2668     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2669     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2670     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2671     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2672     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2673     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2674     ok(delete_pf("msitest", FALSE), "File not installed\n");
2675
2676     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2677     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
2678
2679     create_database(msifile, up7_tables, sizeof(up7_tables) / sizeof(msi_table));
2680
2681     /* published product, RemovePreviousVersions set and version number bumped */
2682     r = MsiInstallProductA(msifile, NULL);
2683     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2684
2685     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
2686     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
2687     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
2688     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
2689     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
2690     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
2691     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
2692     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
2693     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
2694     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
2695     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
2696     ok(delete_pf("msitest", FALSE), "File not installed\n");
2697
2698     res = RegOpenKeyA(HKEY_CURRENT_USER, "SOFTWARE\\Wine\\msitest", &hkey);
2699     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
2700
2701     r = MsiInstallProductA(msifile, "REMOVE=ALL");
2702     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2703
2704 error:
2705     delete_test_files();
2706     DeleteFileA(msifile);
2707 }
2708
2709 static void test_MsiSetComponentState(void)
2710 {
2711     INSTALLSTATE installed, action;
2712     MSIHANDLE package;
2713     char path[MAX_PATH];
2714     UINT r;
2715
2716     create_database(msifile, tables, sizeof(tables) / sizeof(msi_table));
2717
2718     CoInitialize(NULL);
2719
2720     lstrcpy(path, CURR_DIR);
2721     lstrcat(path, "\\");
2722     lstrcat(path, msifile);
2723
2724     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
2725
2726     r = MsiOpenPackage(path, &package);
2727     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
2728     {
2729         skip("Not enough rights to perform tests\n");
2730         goto error;
2731     }
2732     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2733
2734     r = MsiDoAction(package, "CostInitialize");
2735     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2736
2737     r = MsiDoAction(package, "FileCost");
2738     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2739
2740     r = MsiDoAction(package, "CostFinalize");
2741     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2742
2743     r = MsiGetComponentState(package, "dangler", &installed, &action);
2744     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2745     ok(installed == INSTALLSTATE_ABSENT, "Expected INSTALLSTATE_ABSENT, got %d\n", installed);
2746     ok(action == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", action);
2747
2748     r = MsiSetComponentState(package, "dangler", INSTALLSTATE_SOURCE);
2749     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2750
2751     MsiCloseHandle(package);
2752
2753 error:
2754     CoUninitialize();
2755     DeleteFileA(msifile);
2756 }
2757
2758 static void test_packagecoltypes(void)
2759 {
2760     MSIHANDLE hdb, view, rec;
2761     char path[MAX_PATH];
2762     LPCSTR query;
2763     UINT r, count;
2764
2765     create_database(msifile, tables, sizeof(tables) / sizeof(msi_table));
2766
2767     CoInitialize(NULL);
2768
2769     lstrcpy(path, CURR_DIR);
2770     lstrcat(path, "\\");
2771     lstrcat(path, msifile);
2772
2773     r = MsiOpenDatabase(path, MSIDBOPEN_READONLY, &hdb);
2774     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2775
2776     query = "SELECT * FROM `Media`";
2777     r = MsiDatabaseOpenView( hdb, query, &view );
2778     ok(r == ERROR_SUCCESS, "MsiDatabaseOpenView failed\n");
2779
2780     r = MsiViewGetColumnInfo( view, MSICOLINFO_NAMES, &rec );
2781     count = MsiRecordGetFieldCount( rec );
2782     ok(r == ERROR_SUCCESS, "MsiViewGetColumnInfo failed\n");
2783     ok(count == 6, "Expected 6, got %d\n", count);
2784     ok(check_record(rec, 1, "DiskId"), "wrong column label\n");
2785     ok(check_record(rec, 2, "LastSequence"), "wrong column label\n");
2786     ok(check_record(rec, 3, "DiskPrompt"), "wrong column label\n");
2787     ok(check_record(rec, 4, "Cabinet"), "wrong column label\n");
2788     ok(check_record(rec, 5, "VolumeLabel"), "wrong column label\n");
2789     ok(check_record(rec, 6, "Source"), "wrong column label\n");
2790     MsiCloseHandle(rec);
2791
2792     r = MsiViewGetColumnInfo( view, MSICOLINFO_TYPES, &rec );
2793     count = MsiRecordGetFieldCount( rec );
2794     ok(r == ERROR_SUCCESS, "MsiViewGetColumnInfo failed\n");
2795     ok(count == 6, "Expected 6, got %d\n", count);
2796     ok(check_record(rec, 1, "i2"), "wrong column label\n");
2797     ok(check_record(rec, 2, "i4"), "wrong column label\n");
2798     ok(check_record(rec, 3, "L64"), "wrong column label\n");
2799     ok(check_record(rec, 4, "S255"), "wrong column label\n");
2800     ok(check_record(rec, 5, "S32"), "wrong column label\n");
2801     ok(check_record(rec, 6, "S72"), "wrong column label\n");
2802
2803     MsiCloseHandle(rec);
2804     MsiCloseHandle(view);
2805     MsiCloseHandle(hdb);
2806     CoUninitialize();
2807
2808     DeleteFile(msifile);
2809 }
2810
2811 static void create_cc_test_files(void)
2812 {
2813     CCAB cabParams;
2814     HFCI hfci;
2815     ERF erf;
2816     static CHAR cab_context[] = "test%d.cab";
2817     BOOL res;
2818
2819     create_file("maximus", 500);
2820     create_file("augustus", 50000);
2821     create_file("tiberius", 500);
2822     create_file("caesar", 500);
2823
2824     set_cab_parameters(&cabParams, "test1.cab", 40000);
2825
2826     hfci = FCICreate(&erf, file_placed, mem_alloc, mem_free, fci_open,
2827                       fci_read, fci_write, fci_close, fci_seek, fci_delete,
2828                       get_temp_file, &cabParams, cab_context);
2829     ok(hfci != NULL, "Failed to create an FCI context\n");
2830
2831     res = add_file(hfci, "maximus", tcompTYPE_NONE);
2832     ok(res, "Failed to add file maximus\n");
2833
2834     res = add_file(hfci, "augustus", tcompTYPE_NONE);
2835     ok(res, "Failed to add file augustus\n");
2836
2837     res = add_file(hfci, "tiberius", tcompTYPE_NONE);
2838     ok(res, "Failed to add file tiberius\n");
2839
2840     res = FCIFlushCabinet(hfci, FALSE, get_next_cabinet, progress);
2841     ok(res, "Failed to flush the cabinet\n");
2842
2843     res = FCIDestroy(hfci);
2844     ok(res, "Failed to destroy the cabinet\n");
2845
2846     create_cab_file("test3.cab", MEDIA_SIZE, "caesar\0");
2847
2848     DeleteFile("maximus");
2849     DeleteFile("augustus");
2850     DeleteFile("tiberius");
2851     DeleteFile("caesar");
2852 }
2853
2854 static void delete_cab_files(void)
2855 {
2856     SHFILEOPSTRUCT shfl;
2857     CHAR path[MAX_PATH+10];
2858
2859     lstrcpyA(path, CURR_DIR);
2860     lstrcatA(path, "\\*.cab");
2861     path[strlen(path) + 1] = '\0';
2862
2863     shfl.hwnd = NULL;
2864     shfl.wFunc = FO_DELETE;
2865     shfl.pFrom = path;
2866     shfl.pTo = NULL;
2867     shfl.fFlags = FOF_FILESONLY | FOF_NOCONFIRMATION | FOF_NORECURSION | FOF_SILENT;
2868
2869     SHFileOperation(&shfl);
2870 }
2871
2872 static void test_continuouscabs(void)
2873 {
2874     UINT r;
2875
2876     if (is_process_limited())
2877     {
2878         skip("process is limited\n");
2879         return;
2880     }
2881
2882     create_cc_test_files();
2883     create_database(msifile, cc_tables, sizeof(cc_tables) / sizeof(msi_table));
2884
2885     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
2886
2887     r = MsiInstallProductA(msifile, NULL);
2888     if (r == ERROR_SUCCESS) /* win9x has a problem with this */
2889     {
2890         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2891         ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
2892         ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
2893         ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
2894         ok(delete_pf("msitest", FALSE), "File not installed\n");
2895     }
2896
2897     delete_cab_files();
2898     DeleteFile(msifile);
2899
2900     create_cc_test_files();
2901     create_database(msifile, cc2_tables, sizeof(cc2_tables) / sizeof(msi_table));
2902
2903     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
2904
2905     r = MsiInstallProductA(msifile, NULL);
2906     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
2907     {
2908         skip("Not enough rights to perform tests\n");
2909         goto error;
2910     }
2911     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
2912     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
2913     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
2914     ok(delete_pf("msitest\\tiberius", TRUE), "File not installed\n");
2915     ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
2916     ok(delete_pf("msitest", FALSE), "File not installed\n");
2917
2918 error:
2919     delete_cab_files();
2920     DeleteFile(msifile);
2921 }
2922
2923 static void test_caborder(void)
2924 {
2925     UINT r;
2926
2927     create_file("imperator", 100);
2928     create_file("maximus", 500);
2929     create_file("augustus", 50000);
2930     create_file("caesar", 500);
2931
2932     create_database(msifile, cc_tables, sizeof(cc_tables) / sizeof(msi_table));
2933
2934     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
2935
2936     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
2937     create_cab_file("test2.cab", MEDIA_SIZE, "augustus\0");
2938     create_cab_file("test3.cab", MEDIA_SIZE, "caesar\0");
2939
2940     r = MsiInstallProductA(msifile, NULL);
2941     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
2942     {
2943         skip("Not enough rights to perform tests\n");
2944         goto error;
2945     }
2946     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
2947     ok(!delete_pf("msitest\\augustus", TRUE), "File is installed\n");
2948     ok(!delete_pf("msitest\\caesar", TRUE), "File is installed\n");
2949     todo_wine
2950     {
2951         ok(!delete_pf("msitest\\maximus", TRUE), "File is installed\n");
2952         ok(!delete_pf("msitest", FALSE), "File is installed\n");
2953     }
2954
2955     delete_cab_files();
2956
2957     create_cab_file("test1.cab", MEDIA_SIZE, "imperator\0");
2958     create_cab_file("test2.cab", MEDIA_SIZE, "maximus\0augustus\0");
2959     create_cab_file("test3.cab", MEDIA_SIZE, "caesar\0");
2960
2961     r = MsiInstallProductA(msifile, NULL);
2962     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
2963     ok(!delete_pf("msitest\\maximus", TRUE), "File is installed\n");
2964     ok(!delete_pf("msitest\\augustus", TRUE), "File is installed\n");
2965     ok(!delete_pf("msitest\\caesar", TRUE), "File is installed\n");
2966     ok(!delete_pf("msitest", FALSE), "File is installed\n");
2967
2968     delete_cab_files();
2969     DeleteFile(msifile);
2970
2971     create_cc_test_files();
2972     create_database(msifile, co_tables, sizeof(co_tables) / sizeof(msi_table));
2973
2974     r = MsiInstallProductA(msifile, NULL);
2975     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
2976     ok(!delete_pf("msitest\\caesar", TRUE), "File is installed\n");
2977     ok(!delete_pf("msitest", FALSE), "File is installed\n");
2978     todo_wine
2979     {
2980         ok(!delete_pf("msitest\\augustus", TRUE), "File is installed\n");
2981         ok(!delete_pf("msitest\\maximus", TRUE), "File is installed\n");
2982     }
2983
2984     delete_cab_files();
2985     DeleteFile(msifile);
2986
2987     create_cc_test_files();
2988     create_database(msifile, co2_tables, sizeof(co2_tables) / sizeof(msi_table));
2989
2990     r = MsiInstallProductA(msifile, NULL);
2991     ok(!delete_pf("msitest\\caesar", TRUE), "File is installed\n");
2992     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
2993     todo_wine
2994     {
2995         ok(!delete_pf("msitest\\augustus", TRUE), "File is installed\n");
2996         ok(!delete_pf("msitest\\maximus", TRUE), "File is installed\n");
2997         ok(!delete_pf("msitest", FALSE), "File is installed\n");
2998     }
2999
3000 error:
3001     delete_cab_files();
3002     DeleteFile("imperator");
3003     DeleteFile("maximus");
3004     DeleteFile("augustus");
3005     DeleteFile("caesar");
3006     DeleteFile(msifile);
3007 }
3008
3009 static void test_mixedmedia(void)
3010 {
3011     UINT r;
3012
3013     if (is_process_limited())
3014     {
3015         skip("process is limited\n");
3016         return;
3017     }
3018
3019     CreateDirectoryA("msitest", NULL);
3020     create_file("msitest\\maximus", 500);
3021     create_file("msitest\\augustus", 500);
3022     create_file("caesar", 500);
3023
3024     create_database(msifile, mm_tables, sizeof(mm_tables) / sizeof(msi_table));
3025
3026     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3027
3028     create_cab_file("test1.cab", MEDIA_SIZE, "caesar\0");
3029
3030     r = MsiInstallProductA(msifile, NULL);
3031     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3032     {
3033         skip("Not enough rights to perform tests\n");
3034         goto error;
3035     }
3036     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3037     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
3038     ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
3039     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3040     ok(delete_pf("msitest", FALSE), "File not installed\n");
3041
3042 error:
3043     /* Delete the files in the temp (current) folder */
3044     DeleteFile("msitest\\maximus");
3045     DeleteFile("msitest\\augustus");
3046     RemoveDirectory("msitest");
3047     DeleteFile("caesar");
3048     DeleteFile("test1.cab");
3049     DeleteFile(msifile);
3050 }
3051
3052 static void test_samesequence(void)
3053 {
3054     UINT r;
3055
3056     create_cc_test_files();
3057     create_database(msifile, ss_tables, sizeof(ss_tables) / sizeof(msi_table));
3058
3059     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3060
3061     r = MsiInstallProductA(msifile, NULL);
3062     if (r == ERROR_SUCCESS) /* win9x has a problem with this */
3063     {
3064         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3065         ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
3066         ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
3067         ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3068         ok(delete_pf("msitest", FALSE), "File not installed\n");
3069     }
3070
3071     delete_cab_files();
3072     DeleteFile(msifile);
3073 }
3074
3075 static void test_uiLevelFlags(void)
3076 {
3077     UINT r;
3078
3079     create_cc_test_files();
3080     create_database(msifile, ui_tables, sizeof(ui_tables) / sizeof(msi_table));
3081
3082     MsiSetInternalUI(INSTALLUILEVEL_NONE | INSTALLUILEVEL_SOURCERESONLY, NULL);
3083
3084     r = MsiInstallProductA(msifile, NULL);
3085     if (r == ERROR_SUCCESS) /* win9x has a problem with this */
3086     {
3087         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3088         ok(!delete_pf("msitest\\maximus", TRUE), "UI install occurred, but execute-only was requested.\n");
3089         ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
3090         ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
3091         ok(delete_pf("msitest", FALSE), "File not installed\n");
3092     }
3093
3094     delete_cab_files();
3095     DeleteFile(msifile);
3096 }
3097
3098 static BOOL file_matches(LPSTR path)
3099 {
3100     CHAR buf[MAX_PATH];
3101     HANDLE file;
3102     DWORD size;
3103
3104     file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
3105                       NULL, OPEN_EXISTING, 0, NULL);
3106
3107     ZeroMemory(buf, MAX_PATH);
3108     ReadFile(file, buf, 15, &size, NULL);
3109     CloseHandle(file);
3110
3111     return !lstrcmp(buf, "msitest\\maximus");
3112 }
3113
3114 static void test_readonlyfile(void)
3115 {
3116     UINT r;
3117     DWORD size;
3118     HANDLE file;
3119     CHAR path[MAX_PATH];
3120
3121     if (is_process_limited())
3122     {
3123         skip("process is limited\n");
3124         return;
3125     }
3126
3127     CreateDirectoryA("msitest", NULL);
3128     create_file("msitest\\maximus", 500);
3129     create_database(msifile, rof_tables, sizeof(rof_tables) / sizeof(msi_table));
3130
3131     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3132
3133     lstrcpy(path, PROG_FILES_DIR);
3134     lstrcat(path, "\\msitest");
3135     CreateDirectory(path, NULL);
3136
3137     lstrcat(path, "\\maximus");
3138     file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
3139                       NULL, CREATE_NEW, FILE_ATTRIBUTE_READONLY, NULL);
3140
3141     WriteFile(file, "readonlyfile", strlen("readonlyfile"), &size, NULL);
3142     CloseHandle(file);
3143
3144     r = MsiInstallProductA(msifile, NULL);
3145     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3146     {
3147         skip("Not enough rights to perform tests\n");
3148         goto error;
3149     }
3150     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3151     ok(file_matches(path), "Expected file to be overwritten\n");
3152     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3153     ok(delete_pf("msitest", FALSE), "File not installed\n");
3154
3155 error:
3156     /* Delete the files in the temp (current) folder */
3157     DeleteFile("msitest\\maximus");
3158     RemoveDirectory("msitest");
3159     DeleteFile(msifile);
3160 }
3161
3162 static void test_readonlyfile_cab(void)
3163 {
3164     UINT r;
3165     DWORD size;
3166     HANDLE file;
3167     CHAR path[MAX_PATH];
3168     CHAR buf[16];
3169
3170     if (is_process_limited())
3171     {
3172         skip("process is limited\n");
3173         return;
3174     }
3175
3176     CreateDirectoryA("msitest", NULL);
3177     create_file("maximus", 500);
3178     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
3179     DeleteFile("maximus");
3180
3181     create_database(msifile, rofc_tables, sizeof(rofc_tables) / sizeof(msi_table));
3182
3183     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3184
3185     lstrcpy(path, PROG_FILES_DIR);
3186     lstrcat(path, "\\msitest");
3187     CreateDirectory(path, NULL);
3188
3189     lstrcat(path, "\\maximus");
3190     file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
3191                       NULL, CREATE_NEW, FILE_ATTRIBUTE_READONLY, NULL);
3192
3193     WriteFile(file, "readonlyfile", strlen("readonlyfile"), &size, NULL);
3194     CloseHandle(file);
3195
3196     r = MsiInstallProductA(msifile, NULL);
3197     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3198     {
3199         skip("Not enough rights to perform tests\n");
3200         goto error;
3201     }
3202     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3203
3204     memset( buf, 0, sizeof(buf) );
3205     if ((file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
3206                            NULL, OPEN_EXISTING, 0, NULL)) != INVALID_HANDLE_VALUE)
3207     {
3208         ReadFile(file, buf, sizeof(buf) - 1, &size, NULL);
3209         CloseHandle(file);
3210     }
3211     ok(!memcmp( buf, "maximus", sizeof("maximus")-1 ), "Expected file to be overwritten, got '%s'\n", buf);
3212     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3213     ok(delete_pf("msitest", FALSE), "File not installed\n");
3214
3215 error:
3216     /* Delete the files in the temp (current) folder */
3217     delete_cab_files();
3218     DeleteFile("msitest\\maximus");
3219     RemoveDirectory("msitest");
3220     DeleteFile(msifile);
3221 }
3222
3223 static BOOL add_cabinet_storage(LPCSTR db, LPCSTR cabinet)
3224 {
3225     WCHAR dbW[MAX_PATH], cabinetW[MAX_PATH];
3226     IStorage *stg;
3227     IStream *stm;
3228     HRESULT hr;
3229     HANDLE handle;
3230
3231     MultiByteToWideChar(CP_ACP, 0, db, -1, dbW, MAX_PATH);
3232     hr = StgOpenStorage(dbW, NULL, STGM_DIRECT|STGM_READWRITE|STGM_SHARE_EXCLUSIVE, NULL, 0, &stg);
3233     if (FAILED(hr))
3234         return FALSE;
3235
3236     MultiByteToWideChar(CP_ACP, 0, cabinet, -1, cabinetW, MAX_PATH);
3237     hr = IStorage_CreateStream(stg, cabinetW, STGM_WRITE|STGM_SHARE_EXCLUSIVE, 0, 0, &stm);
3238     if (FAILED(hr))
3239     {
3240         IStorage_Release(stg);
3241         return FALSE;
3242     }
3243
3244     handle = CreateFileW(cabinetW, GENERIC_READ, 0, NULL, OPEN_EXISTING, 0, NULL);
3245     if (handle != INVALID_HANDLE_VALUE)
3246     {
3247         DWORD count;
3248         char buffer[1024];
3249         if (ReadFile(handle, buffer, sizeof(buffer), &count, NULL))
3250             IStream_Write(stm, buffer, count, &count);
3251         CloseHandle(handle);
3252     }
3253
3254     IStream_Release(stm);
3255     IStorage_Release(stg);
3256
3257     return TRUE;
3258 }
3259
3260 static void test_lastusedsource(void)
3261 {
3262     static char prodcode[] = "{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}";
3263
3264     UINT r;
3265     char value[MAX_PATH], path[MAX_PATH];
3266     DWORD size;
3267
3268     if (!pMsiSourceListGetInfoA)
3269     {
3270         win_skip("MsiSourceListGetInfoA is not available\n");
3271         return;
3272     }
3273
3274     CreateDirectoryA("msitest", NULL);
3275     create_file("maximus", 500);
3276     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
3277     DeleteFile("maximus");
3278
3279     create_database("msifile0.msi", lus0_tables, sizeof(lus0_tables) / sizeof(msi_table));
3280     create_database("msifile1.msi", lus1_tables, sizeof(lus1_tables) / sizeof(msi_table));
3281     create_database("msifile2.msi", lus2_tables, sizeof(lus2_tables) / sizeof(msi_table));
3282
3283     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3284
3285     /* no cabinet file */
3286
3287     size = MAX_PATH;
3288     lstrcpyA(value, "aaa");
3289     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
3290                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
3291     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
3292     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
3293
3294     r = MsiInstallProductA("msifile0.msi", "PUBLISH_PRODUCT=1");
3295     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3296     {
3297         skip("Not enough rights to perform tests\n");
3298         goto error;
3299     }
3300     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3301
3302     lstrcpyA(path, CURR_DIR);
3303     lstrcatA(path, "\\");
3304
3305     size = MAX_PATH;
3306     lstrcpyA(value, "aaa");
3307     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
3308                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
3309     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3310     todo_wine
3311     {
3312     ok(!lstrcmpA(value, path), "Expected \"%s\", got \"%s\"\n", path, value);
3313     ok(size == lstrlenA(path), "Expected %d, got %d\n", lstrlenA(path), size);
3314     }
3315
3316     r = MsiInstallProductA("msifile0.msi", "REMOVE=ALL");
3317     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3318
3319     /* separate cabinet file */
3320
3321     size = MAX_PATH;
3322     lstrcpyA(value, "aaa");
3323     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
3324                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
3325     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
3326     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
3327
3328     r = MsiInstallProductA("msifile1.msi", "PUBLISH_PRODUCT=1");
3329     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3330
3331     lstrcpyA(path, CURR_DIR);
3332     lstrcatA(path, "\\");
3333
3334     size = MAX_PATH;
3335     lstrcpyA(value, "aaa");
3336     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
3337                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
3338     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3339     todo_wine
3340     {
3341     ok(!lstrcmpA(value, path), "Expected \"%s\", got \"%s\"\n", path, value);
3342     ok(size == lstrlenA(path), "Expected %d, got %d\n", lstrlenA(path), size);
3343     }
3344
3345     r = MsiInstallProductA("msifile1.msi", "REMOVE=ALL");
3346     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3347
3348     size = MAX_PATH;
3349     lstrcpyA(value, "aaa");
3350     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
3351                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
3352     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
3353     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
3354
3355     /* embedded cabinet stream */
3356
3357     add_cabinet_storage("msifile2.msi", "test1.cab");
3358
3359     r = MsiInstallProductA("msifile2.msi", "PUBLISH_PRODUCT=1");
3360     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3361
3362     size = MAX_PATH;
3363     lstrcpyA(value, "aaa");
3364     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
3365                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
3366     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3367     todo_wine
3368     {
3369     ok(!lstrcmpA(value, path), "Expected \"%s\", got \"%s\"\n", path, value);
3370     ok(size == lstrlenA(path), "Expected %d, got %d\n", lstrlenA(path), size);
3371     }
3372
3373     r = MsiInstallProductA("msifile2.msi", "REMOVE=ALL");
3374     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3375
3376     size = MAX_PATH;
3377     lstrcpyA(value, "aaa");
3378     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
3379                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
3380     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
3381     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
3382
3383 error:
3384     /* Delete the files in the temp (current) folder */
3385     delete_cab_files();
3386     DeleteFile("msitest\\maximus");
3387     RemoveDirectory("msitest");
3388     DeleteFile("msifile0.msi");
3389     DeleteFile("msifile1.msi");
3390     DeleteFile("msifile2.msi");
3391 }
3392
3393 static void test_setdirproperty(void)
3394 {
3395     UINT r;
3396
3397     if (is_process_limited())
3398     {
3399         skip("process is limited\n");
3400         return;
3401     }
3402
3403     CreateDirectoryA("msitest", NULL);
3404     create_file("msitest\\maximus", 500);
3405     create_database(msifile, sdp_tables, sizeof(sdp_tables) / sizeof(msi_table));
3406
3407     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3408
3409     r = MsiInstallProductA(msifile, NULL);
3410     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3411     {
3412         skip("Not enough rights to perform tests\n");
3413         goto error;
3414     }
3415     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3416     ok(delete_cf("msitest\\maximus", TRUE), "File not installed\n");
3417     ok(delete_cf("msitest", FALSE), "File not installed\n");
3418
3419 error:
3420     /* Delete the files in the temp (current) folder */
3421     DeleteFile(msifile);
3422     DeleteFile("msitest\\maximus");
3423     RemoveDirectory("msitest");
3424 }
3425
3426 static void test_cabisextracted(void)
3427 {
3428     UINT r;
3429
3430     if (is_process_limited())
3431     {
3432         skip("process is limited\n");
3433         return;
3434     }
3435
3436     CreateDirectoryA("msitest", NULL);
3437     create_file("msitest\\gaius", 500);
3438     create_file("maximus", 500);
3439     create_file("augustus", 500);
3440     create_file("caesar", 500);
3441
3442     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
3443     create_cab_file("test2.cab", MEDIA_SIZE, "augustus\0");
3444     create_cab_file("test3.cab", MEDIA_SIZE, "caesar\0");
3445
3446     create_database(msifile, cie_tables, sizeof(cie_tables) / sizeof(msi_table));
3447
3448     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3449
3450     r = MsiInstallProductA(msifile, NULL);
3451     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3452     {
3453         skip("Not enough rights to perform tests\n");
3454         goto error;
3455     }
3456     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3457     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3458     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
3459     ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
3460     ok(delete_pf("msitest\\gaius", TRUE), "File not installed\n");
3461     ok(delete_pf("msitest", FALSE), "File not installed\n");
3462
3463 error:
3464     /* Delete the files in the temp (current) folder */
3465     delete_cab_files();
3466     DeleteFile(msifile);
3467     DeleteFile("maximus");
3468     DeleteFile("augustus");
3469     DeleteFile("caesar");
3470     DeleteFile("msitest\\gaius");
3471     RemoveDirectory("msitest");
3472 }
3473
3474 static void test_concurrentinstall(void)
3475 {
3476     UINT r;
3477     CHAR path[MAX_PATH];
3478
3479     if (is_process_limited())
3480     {
3481         skip("process is limited\n");
3482         return;
3483     }
3484
3485     CreateDirectoryA("msitest", NULL);
3486     CreateDirectoryA("msitest\\msitest", NULL);
3487     create_file("msitest\\maximus", 500);
3488     create_file("msitest\\msitest\\augustus", 500);
3489
3490     create_database(msifile, ci_tables, sizeof(ci_tables) / sizeof(msi_table));
3491
3492     lstrcpyA(path, CURR_DIR);
3493     lstrcatA(path, "\\msitest\\concurrent.msi");
3494     create_database(path, ci2_tables, sizeof(ci2_tables) / sizeof(msi_table));
3495
3496     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
3497
3498     r = MsiInstallProductA(msifile, NULL);
3499     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3500     {
3501         skip("Not enough rights to perform tests\n");
3502         DeleteFile(path);
3503         goto error;
3504     }
3505     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3506     if (!delete_pf("msitest\\augustus", TRUE))
3507         trace("concurrent installs not supported\n");
3508     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3509     ok(delete_pf("msitest", FALSE), "File not installed\n");
3510
3511     DeleteFile(path);
3512
3513     r = MsiInstallProductA(msifile, NULL);
3514     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3515     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3516     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
3517     ok(delete_pf("msitest", FALSE), "File not installed\n");
3518
3519 error:
3520     DeleteFile(msifile);
3521     DeleteFile("msitest\\msitest\\augustus");
3522     DeleteFile("msitest\\maximus");
3523     RemoveDirectory("msitest\\msitest");
3524     RemoveDirectory("msitest");
3525 }
3526
3527 static void test_setpropertyfolder(void)
3528 {
3529     UINT r;
3530     CHAR path[MAX_PATH];
3531     DWORD attr;
3532
3533     if (is_process_limited())
3534     {
3535         skip("process is limited\n");
3536         return;
3537     }
3538
3539     lstrcpyA(path, PROG_FILES_DIR);
3540     lstrcatA(path, "\\msitest\\added");
3541
3542     CreateDirectoryA("msitest", NULL);
3543     create_file("msitest\\maximus", 500);
3544
3545     create_database(msifile, spf_tables, sizeof(spf_tables) / sizeof(msi_table));
3546
3547     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
3548
3549     r = MsiInstallProductA(msifile, NULL);
3550     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3551     {
3552         skip("Not enough rights to perform tests\n");
3553         goto error;
3554     }
3555     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3556     attr = GetFileAttributesA(path);
3557     if (attr != INVALID_FILE_ATTRIBUTES && (attr & FILE_ATTRIBUTE_DIRECTORY))
3558     {
3559         ok(delete_pf("msitest\\added\\maximus", TRUE), "File not installed\n");
3560         ok(delete_pf("msitest\\added", FALSE), "File not installed\n");
3561         ok(delete_pf("msitest", FALSE), "File not installed\n");
3562     }
3563     else
3564     {
3565         trace("changing folder property not supported\n");
3566         ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3567         ok(delete_pf("msitest", FALSE), "File not installed\n");
3568     }
3569
3570 error:
3571     /* Delete the files in the temp (current) folder */
3572     DeleteFile(msifile);
3573     DeleteFile("msitest\\maximus");
3574     RemoveDirectory("msitest");
3575 }
3576
3577 static BOOL file_exists(LPCSTR file)
3578 {
3579     return GetFileAttributes(file) != INVALID_FILE_ATTRIBUTES;
3580 }
3581
3582 static BOOL pf_exists(LPCSTR file)
3583 {
3584     CHAR path[MAX_PATH];
3585
3586     lstrcpyA(path, PROG_FILES_DIR);
3587     lstrcatA(path, "\\");
3588     lstrcatA(path, file);
3589
3590     return file_exists(path);
3591 }
3592
3593 static void delete_pfmsitest_files(void)
3594 {
3595     SHFILEOPSTRUCT shfl;
3596     CHAR path[MAX_PATH+11];
3597
3598     lstrcpyA(path, PROG_FILES_DIR);
3599     lstrcatA(path, "\\msitest\\*");
3600     path[strlen(path) + 1] = '\0';
3601
3602     shfl.hwnd = NULL;
3603     shfl.wFunc = FO_DELETE;
3604     shfl.pFrom = path;
3605     shfl.pTo = NULL;
3606     shfl.fFlags = FOF_FILESONLY | FOF_NOCONFIRMATION | FOF_NORECURSION | FOF_SILENT | FOF_NOERRORUI;
3607
3608     SHFileOperation(&shfl);
3609
3610     lstrcpyA(path, PROG_FILES_DIR);
3611     lstrcatA(path, "\\msitest");
3612     RemoveDirectoryA(path);
3613 }
3614
3615 static UINT run_query(MSIHANDLE hdb, MSIHANDLE hrec, const char *query)
3616 {
3617     MSIHANDLE hview = 0;
3618     UINT r;
3619
3620     r = MsiDatabaseOpenView(hdb, query, &hview);
3621     if(r != ERROR_SUCCESS)
3622         return r;
3623
3624     r = MsiViewExecute(hview, hrec);
3625     if(r == ERROR_SUCCESS)
3626         r = MsiViewClose(hview);
3627     MsiCloseHandle(hview);
3628     return r;
3629 }
3630
3631 static void set_transform_summary_info(void)
3632 {
3633     UINT r;
3634     MSIHANDLE suminfo = 0;
3635
3636     /* build summary info */
3637     r = MsiGetSummaryInformation(0, mstfile, 3, &suminfo);
3638     ok(r == ERROR_SUCCESS , "Failed to open summaryinfo\n");
3639
3640     r = MsiSummaryInfoSetProperty(suminfo, PID_TITLE, VT_LPSTR, 0, NULL, "MSITEST");
3641     ok(r == ERROR_SUCCESS, "Failed to set summary info\n");
3642
3643     r = MsiSummaryInfoSetProperty(suminfo, PID_REVNUMBER, VT_LPSTR, 0, NULL,
3644                         "{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}1.1.1;"
3645                         "{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}1.1.1;"
3646                         "{4C0EAA15-0264-4E5A-8758-609EF142B92D}");
3647     ok(r == ERROR_SUCCESS , "Failed to set summary info\n");
3648
3649     r = MsiSummaryInfoSetProperty(suminfo, PID_PAGECOUNT, VT_I4, 100, NULL, NULL);
3650     ok(r == ERROR_SUCCESS, "Failed to set summary info\n");
3651
3652     r = MsiSummaryInfoPersist(suminfo);
3653     ok(r == ERROR_SUCCESS , "Failed to make summary info persist\n");
3654
3655     r = MsiCloseHandle(suminfo);
3656     ok(r == ERROR_SUCCESS , "Failed to close suminfo\n");
3657 }
3658
3659 static void generate_transform(void)
3660 {
3661     MSIHANDLE hdb1, hdb2;
3662     LPCSTR query;
3663     UINT r;
3664
3665     /* start with two identical databases */
3666     CopyFile(msifile, msifile2, FALSE);
3667
3668     r = MsiOpenDatabase(msifile2, MSIDBOPEN_TRANSACT, &hdb1);
3669     ok(r == ERROR_SUCCESS , "Failed to create database\n");
3670
3671     r = MsiDatabaseCommit(hdb1);
3672     ok(r == ERROR_SUCCESS , "Failed to commit database\n");
3673
3674     r = MsiOpenDatabase(msifile, MSIDBOPEN_READONLY, &hdb2);
3675     ok(r == ERROR_SUCCESS , "Failed to create database\n");
3676
3677     query = "INSERT INTO `Property` ( `Property`, `Value` ) VALUES ( 'prop', 'val' )";
3678     r = run_query(hdb1, 0, query);
3679     ok(r == ERROR_SUCCESS, "failed to add property\n");
3680
3681     /* database needs to be committed */
3682     MsiDatabaseCommit(hdb1);
3683
3684     r = MsiDatabaseGenerateTransform(hdb1, hdb2, mstfile, 0, 0);
3685     ok(r == ERROR_SUCCESS, "return code %d, should be ERROR_SUCCESS\n", r);
3686
3687 #if 0  /* not implemented in wine yet */
3688     r = MsiCreateTransformSummaryInfo(hdb2, hdb2, mstfile, 0, 0);
3689     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
3690 #endif
3691
3692     MsiCloseHandle(hdb1);
3693     MsiCloseHandle(hdb2);
3694 }
3695
3696 /* data for generating a transform */
3697
3698 /* tables transform names - encoded as they would be in an msi database file */
3699 static const WCHAR name1[] = { 0x4840, 0x3f3f, 0x4577, 0x446c, 0x3b6a, 0x45e4, 0x4824, 0 }; /* _StringData */
3700 static const WCHAR name2[] = { 0x4840, 0x3f3f, 0x4577, 0x446c, 0x3e6a, 0x44b2, 0x482f, 0 }; /* _StringPool */
3701 static const WCHAR name3[] = { 0x4840, 0x4559, 0x44f2, 0x4568, 0x4737, 0 }; /* Property */
3702
3703 /* data in each table */
3704 static const char data1[] = /* _StringData */
3705     "propval";  /* all the strings squashed together */
3706
3707 static const WCHAR data2[] = { /* _StringPool */
3708 /*  len, refs */
3709     0,   0,    /* string 0 ''     */
3710     4,   1,    /* string 1 'prop' */
3711     3,   1,    /* string 2 'val'  */
3712 };
3713
3714 static const WCHAR data3[] = { /* Property */
3715     0x0201, 0x0001, 0x0002,
3716 };
3717
3718 static const struct {
3719     LPCWSTR name;
3720     const void *data;
3721     DWORD size;
3722 } table_transform_data[] =
3723 {
3724     { name1, data1, sizeof data1 - 1 },
3725     { name2, data2, sizeof data2 },
3726     { name3, data3, sizeof data3 },
3727 };
3728
3729 #define NUM_TRANSFORM_TABLES (sizeof table_transform_data/sizeof table_transform_data[0])
3730
3731 static void generate_transform_manual(void)
3732 {
3733     IStorage *stg = NULL;
3734     IStream *stm;
3735     WCHAR name[0x20];
3736     HRESULT r;
3737     DWORD i, count;
3738     const DWORD mode = STGM_CREATE|STGM_READWRITE|STGM_DIRECT|STGM_SHARE_EXCLUSIVE;
3739
3740     const CLSID CLSID_MsiTransform = { 0xc1082,0,0,{0xc0,0,0,0,0,0,0,0x46}};
3741
3742     MultiByteToWideChar(CP_ACP, 0, mstfile, -1, name, 0x20);
3743
3744     r = StgCreateDocfile(name, mode, 0, &stg);
3745     ok(r == S_OK, "failed to create storage\n");
3746     if (!stg)
3747         return;
3748
3749     r = IStorage_SetClass(stg, &CLSID_MsiTransform);
3750     ok(r == S_OK, "failed to set storage type\n");
3751
3752     for (i=0; i<NUM_TRANSFORM_TABLES; i++)
3753     {
3754         r = IStorage_CreateStream(stg, table_transform_data[i].name,
3755                             STGM_WRITE | STGM_SHARE_EXCLUSIVE, 0, 0, &stm);
3756         if (FAILED(r))
3757         {
3758             ok(0, "failed to create stream %08x\n", r);
3759             continue;
3760         }
3761
3762         r = IStream_Write(stm, table_transform_data[i].data,
3763                           table_transform_data[i].size, &count);
3764         if (FAILED(r) || count != table_transform_data[i].size)
3765             ok(0, "failed to write stream\n");
3766         IStream_Release(stm);
3767     }
3768
3769     IStorage_Release(stg);
3770
3771     set_transform_summary_info();
3772 }
3773
3774 static void test_transformprop(void)
3775 {
3776     UINT r;
3777
3778     if (is_process_limited())
3779     {
3780         skip("process is limited\n");
3781         return;
3782     }
3783
3784     CreateDirectoryA("msitest", NULL);
3785     create_file("msitest\\augustus", 500);
3786
3787     create_database(msifile, tp_tables, sizeof(tp_tables) / sizeof(msi_table));
3788
3789     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3790
3791     r = MsiInstallProductA(msifile, NULL);
3792     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3793     {
3794         skip("Not enough rights to perform tests\n");
3795         goto error;
3796     }
3797     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3798     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
3799     ok(!delete_pf("msitest", FALSE), "File installed\n");
3800
3801     if (0)
3802         generate_transform();
3803     else
3804         generate_transform_manual();
3805
3806     r = MsiInstallProductA(msifile, "TRANSFORMS=winetest.mst");
3807     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3808     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
3809     ok(delete_pf("msitest", FALSE), "File not installed\n");
3810
3811 error:
3812     /* Delete the files in the temp (current) folder */
3813     DeleteFile(msifile);
3814     DeleteFile(msifile2);
3815     DeleteFile(mstfile);
3816     DeleteFile("msitest\\augustus");
3817     RemoveDirectory("msitest");
3818 }
3819
3820 static void test_currentworkingdir(void)
3821 {
3822     UINT r;
3823     CHAR drive[MAX_PATH], path[MAX_PATH];
3824     LPSTR ptr;
3825
3826     if (is_process_limited())
3827     {
3828         skip("process is limited\n");
3829         return;
3830     }
3831
3832     CreateDirectoryA("msitest", NULL);
3833     create_file("msitest\\augustus", 500);
3834
3835     create_database(msifile, cwd_tables, sizeof(cwd_tables) / sizeof(msi_table));
3836
3837     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3838
3839     CreateDirectoryA("diffdir", NULL);
3840     SetCurrentDirectoryA("diffdir");
3841
3842     sprintf(path, "..\\%s", msifile);
3843     r = MsiInstallProductA(path, NULL);
3844     todo_wine
3845     {
3846         ok(r == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %u\n", r);
3847         ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
3848         ok(!delete_pf("msitest", FALSE), "File installed\n");
3849     }
3850
3851     sprintf(path, "%s\\%s", CURR_DIR, msifile);
3852     r = MsiInstallProductA(path, NULL);
3853     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3854     {
3855         skip("Not enough rights to perform tests\n");
3856         goto error;
3857     }
3858     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3859     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
3860     ok(delete_pf("msitest", FALSE), "File not installed\n");
3861
3862     lstrcpyA(drive, CURR_DIR);
3863     drive[2] = '\\';
3864     drive[3] = '\0';
3865     SetCurrentDirectoryA(drive);
3866
3867     lstrcpy(path, CURR_DIR);
3868     if (path[lstrlenA(path) - 1] != '\\')
3869         lstrcatA(path, "\\");
3870     lstrcatA(path, msifile);
3871     ptr = strchr(path, ':');
3872     ptr +=2;
3873
3874     r = MsiInstallProductA(ptr, NULL);
3875     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3876     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
3877     ok(delete_pf("msitest", FALSE), "File not installed\n");
3878
3879 error:
3880     SetCurrentDirectoryA(CURR_DIR);
3881     DeleteFile(msifile);
3882     DeleteFile("msitest\\augustus");
3883     RemoveDirectory("msitest");
3884     RemoveDirectory("diffdir");
3885 }
3886
3887 static void set_admin_summary_info(const CHAR *name)
3888 {
3889     MSIHANDLE db, summary;
3890     UINT r;
3891
3892     r = MsiOpenDatabaseA(name, MSIDBOPEN_DIRECT, &db);
3893     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3894
3895     r = MsiGetSummaryInformationA(db, NULL, 1, &summary);
3896     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3897
3898     r = MsiSummaryInfoSetPropertyA(summary, PID_WORDCOUNT, VT_I4, 5, NULL, NULL);
3899     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3900
3901     /* write the summary changes back to the stream */
3902     r = MsiSummaryInfoPersist(summary);
3903     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3904
3905     MsiCloseHandle(summary);
3906
3907     r = MsiDatabaseCommit(db);
3908     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3909
3910     MsiCloseHandle(db);
3911 }
3912
3913 static void test_admin(void)
3914 {
3915     UINT r;
3916
3917     CreateDirectoryA("msitest", NULL);
3918     create_file("msitest\\augustus", 500);
3919
3920     create_database(msifile, adm_tables, sizeof(adm_tables) / sizeof(msi_table));
3921     set_admin_summary_info(msifile);
3922
3923     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3924
3925     r = MsiInstallProductA(msifile, NULL);
3926     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
3927     {
3928         skip("Not enough rights to perform tests\n");
3929         goto error;
3930     }
3931     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3932     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
3933     ok(!delete_pf("msitest", FALSE), "File installed\n");
3934     ok(!DeleteFile("c:\\msitest\\augustus"), "File installed\n");
3935     ok(!RemoveDirectory("c:\\msitest"), "File installed\n");
3936
3937     r = MsiInstallProductA(msifile, "ACTION=ADMIN");
3938     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3939     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
3940     ok(!delete_pf("msitest", FALSE), "File installed\n");
3941     todo_wine
3942     {
3943         ok(DeleteFile("c:\\msitest\\augustus"), "File not installed\n");
3944         ok(RemoveDirectory("c:\\msitest"), "File not installed\n");
3945     }
3946
3947 error:
3948     DeleteFile(msifile);
3949     DeleteFile("msitest\\augustus");
3950     RemoveDirectory("msitest");
3951 }
3952
3953 static void set_admin_property_stream(LPCSTR file)
3954 {
3955     IStorage *stg;
3956     IStream *stm;
3957     WCHAR fileW[MAX_PATH];
3958     HRESULT hr;
3959     DWORD count;
3960     const DWORD mode = STGM_DIRECT | STGM_READWRITE | STGM_SHARE_EXCLUSIVE;
3961
3962     /* AdminProperties */
3963     static const WCHAR stmname[] = {0x41ca,0x4330,0x3e71,0x44b5,0x4233,0x45f5,0x422c,0x4836,0};
3964     static const WCHAR data[] = {'M','Y','P','R','O','P','=','2','7','1','8',' ',
3965         'M','y','P','r','o','p','=','4','2',0};
3966
3967     MultiByteToWideChar(CP_ACP, 0, file, -1, fileW, MAX_PATH);
3968
3969     hr = StgOpenStorage(fileW, NULL, mode, NULL, 0, &stg);
3970     ok(hr == S_OK, "Expected S_OK, got %d\n", hr);
3971     if (!stg)
3972         return;
3973
3974     hr = IStorage_CreateStream(stg, stmname, STGM_WRITE | STGM_SHARE_EXCLUSIVE, 0, 0, &stm);
3975     ok(hr == S_OK, "Expected S_OK, got %d\n", hr);
3976
3977     hr = IStream_Write(stm, data, sizeof(data), &count);
3978     ok(hr == S_OK, "Expected S_OK, got %d\n", hr);
3979
3980     IStream_Release(stm);
3981     IStorage_Release(stg);
3982 }
3983
3984 static void test_adminprops(void)
3985 {
3986     UINT r;
3987
3988     if (is_process_limited())
3989     {
3990         skip("process is limited\n");
3991         return;
3992     }
3993
3994     CreateDirectoryA("msitest", NULL);
3995     create_file("msitest\\augustus", 500);
3996
3997     create_database(msifile, amp_tables, sizeof(amp_tables) / sizeof(msi_table));
3998     set_admin_summary_info(msifile);
3999     set_admin_property_stream(msifile);
4000
4001     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4002
4003     r = MsiInstallProductA(msifile, NULL);
4004     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
4005     {
4006         skip("Not enough rights to perform tests\n");
4007         goto error;
4008     }
4009     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4010     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
4011     ok(delete_pf("msitest", FALSE), "File installed\n");
4012
4013 error:
4014     DeleteFile(msifile);
4015     DeleteFile("msitest\\augustus");
4016     RemoveDirectory("msitest");
4017 }
4018
4019 static void create_pf_data(LPCSTR file, LPCSTR data, BOOL is_file)
4020 {
4021     CHAR path[MAX_PATH];
4022
4023     lstrcpyA(path, PROG_FILES_DIR);
4024     lstrcatA(path, "\\");
4025     lstrcatA(path, file);
4026
4027     if (is_file)
4028         create_file_data(path, data, 500);
4029     else
4030         CreateDirectoryA(path, NULL);
4031 }
4032
4033 #define create_pf(file, is_file) create_pf_data(file, file, is_file)
4034
4035 static void test_missingcab(void)
4036 {
4037     UINT r;
4038
4039     if (is_process_limited())
4040     {
4041         skip("process is limited\n");
4042         return;
4043     }
4044
4045     CreateDirectoryA("msitest", NULL);
4046     create_file("msitest\\augustus", 500);
4047     create_file("maximus", 500);
4048
4049     create_database(msifile, mc_tables, sizeof(mc_tables) / sizeof(msi_table));
4050
4051     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4052
4053     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
4054
4055     create_pf("msitest", FALSE);
4056     create_pf_data("msitest\\caesar", "abcdefgh", TRUE);
4057
4058     r = MsiInstallProductA(msifile, NULL);
4059     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
4060     {
4061         skip("Not enough rights to perform tests\n");
4062         goto error;
4063     }
4064     ok(r == ERROR_SUCCESS ||
4065        broken(r == ERROR_INSTALL_FAILURE), /* win9x */
4066        "Expected ERROR_SUCCESS, got %u\n", r);
4067     if (r == ERROR_SUCCESS)
4068     {
4069       ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
4070       ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4071     }
4072     ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
4073     ok(!delete_pf("msitest\\gaius", TRUE), "File installed\n");
4074     ok(delete_pf("msitest", FALSE), "File not installed\n");
4075
4076     create_pf("msitest", FALSE);
4077     create_pf_data("msitest\\caesar", "abcdefgh", TRUE);
4078     create_pf("msitest\\gaius", TRUE);
4079
4080     r = MsiInstallProductA(msifile, "GAIUS=1");
4081     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
4082     todo_wine
4083     {
4084         ok(!delete_pf("msitest\\maximus", TRUE), "File installed\n");
4085         ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
4086     }
4087     ok(delete_pf("msitest\\caesar", TRUE), "File removed\n");
4088     ok(delete_pf("msitest\\gaius", TRUE), "File removed\n");
4089     ok(delete_pf("msitest", FALSE), "File not installed\n");
4090
4091 error:
4092     delete_pf("msitest\\caesar", TRUE);
4093     delete_pf("msitest", FALSE);
4094     DeleteFile("msitest\\augustus");
4095     RemoveDirectory("msitest");
4096     DeleteFile("maximus");
4097     DeleteFile("test1.cab");
4098     DeleteFile(msifile);
4099 }
4100
4101 static void test_sourcefolder(void)
4102 {
4103     UINT r;
4104
4105     if (is_process_limited())
4106     {
4107         skip("process is limited\n");
4108         return;
4109     }
4110
4111     CreateDirectoryA("msitest", NULL);
4112     create_file("augustus", 500);
4113
4114     create_database(msifile, sf_tables, sizeof(sf_tables) / sizeof(msi_table));
4115
4116     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4117
4118     r = MsiInstallProductA(msifile, NULL);
4119     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
4120     {
4121         skip("Not enough rights to perform tests\n");
4122         goto error;
4123     }
4124     ok(r == ERROR_INSTALL_FAILURE,
4125        "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
4126     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
4127     todo_wine
4128     {
4129         ok(!delete_pf("msitest", FALSE), "File installed\n");
4130     }
4131
4132     RemoveDirectoryA("msitest");
4133
4134     r = MsiInstallProductA(msifile, NULL);
4135     ok(r == ERROR_INSTALL_FAILURE,
4136        "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
4137     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
4138     todo_wine
4139     {
4140         ok(!delete_pf("msitest", FALSE), "File installed\n");
4141     }
4142
4143 error:
4144     DeleteFile(msifile);
4145     DeleteFile("augustus");
4146 }
4147
4148 static void test_customaction51(void)
4149 {
4150     UINT r;
4151
4152     if (is_process_limited())
4153     {
4154         skip("process is limited\n");
4155         return;
4156     }
4157
4158     CreateDirectoryA("msitest", NULL);
4159     create_file("msitest\\augustus", 500);
4160
4161     create_database(msifile, ca51_tables, sizeof(ca51_tables) / sizeof(msi_table));
4162
4163     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4164
4165     r = MsiInstallProductA(msifile, NULL);
4166     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
4167     {
4168         skip("Not enough rights to perform tests\n");
4169         goto error;
4170     }
4171     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4172     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
4173     ok(delete_pf("msitest", FALSE), "File installed\n");
4174
4175 error:
4176     DeleteFile(msifile);
4177     DeleteFile("msitest\\augustus");
4178     RemoveDirectory("msitest");
4179 }
4180
4181 static void test_installstate(void)
4182 {
4183     UINT r;
4184
4185     if (is_process_limited())
4186     {
4187         skip("process is limited\n");
4188         return;
4189     }
4190
4191     CreateDirectoryA("msitest", NULL);
4192     create_file("msitest\\alpha", 500);
4193     create_file("msitest\\beta", 500);
4194     create_file("msitest\\gamma", 500);
4195     create_file("msitest\\theta", 500);
4196     create_file("msitest\\delta", 500);
4197     create_file("msitest\\epsilon", 500);
4198     create_file("msitest\\zeta", 500);
4199     create_file("msitest\\iota", 500);
4200     create_file("msitest\\eta", 500);
4201     create_file("msitest\\kappa", 500);
4202     create_file("msitest\\lambda", 500);
4203     create_file("msitest\\mu", 500);
4204
4205     create_database(msifile, is_tables, sizeof(is_tables) / sizeof(msi_table));
4206
4207     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4208
4209     r = MsiInstallProductA(msifile, NULL);
4210     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
4211     {
4212         skip("Not enough rights to perform tests\n");
4213         goto error;
4214     }
4215     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4216     ok(delete_pf("msitest\\alpha", TRUE), "File not installed\n");
4217     ok(!delete_pf("msitest\\beta", TRUE), "File installed\n");
4218     ok(delete_pf("msitest\\gamma", TRUE), "File not installed\n");
4219     ok(delete_pf("msitest\\theta", TRUE), "File not installed\n");
4220     ok(!delete_pf("msitest\\delta", TRUE), "File installed\n");
4221     ok(!delete_pf("msitest\\epsilon", TRUE), "File installed\n");
4222     ok(!delete_pf("msitest\\zeta", TRUE), "File installed\n");
4223     ok(!delete_pf("msitest\\iota", TRUE), "File installed\n");
4224     ok(!delete_pf("msitest\\eta", TRUE), "File installed\n");
4225     ok(!delete_pf("msitest\\kappa", TRUE), "File installed\n");
4226     ok(!delete_pf("msitest\\lambda", TRUE), "File installed\n");
4227     ok(!delete_pf("msitest\\mu", TRUE), "File installed\n");
4228     ok(delete_pf("msitest", FALSE), "File not installed\n");
4229
4230     r = MsiInstallProductA(msifile, "ADDLOCAL=\"one,two,three,four\"");
4231     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4232     ok(delete_pf("msitest\\alpha", TRUE), "File not installed\n");
4233     ok(!delete_pf("msitest\\beta", TRUE), "File installed\n");
4234     ok(delete_pf("msitest\\gamma", TRUE), "File not installed\n");
4235     ok(delete_pf("msitest\\theta", TRUE), "File not installed\n");
4236     ok(!delete_pf("msitest\\delta", TRUE), "File installed\n");
4237     ok(delete_pf("msitest\\epsilon", TRUE), "File not installed\n");
4238     ok(delete_pf("msitest\\zeta", TRUE), "File not installed\n");
4239     ok(!delete_pf("msitest\\iota", TRUE), "File installed\n");
4240     ok(delete_pf("msitest\\eta", TRUE), "File not installed\n");
4241     ok(!delete_pf("msitest\\kappa", TRUE), "File installed\n");
4242     ok(!delete_pf("msitest\\lambda", TRUE), "File installed\n");
4243     ok(!delete_pf("msitest\\mu", TRUE), "File installed\n");
4244     ok(delete_pf("msitest", FALSE), "File not installed\n");
4245
4246     r = MsiInstallProductA(msifile, "ADDSOURCE=\"one,two,three,four\"");
4247     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4248     ok(delete_pf("msitest\\alpha", TRUE), "File not installed\n");
4249     ok(!delete_pf("msitest\\beta", TRUE), "File installed\n");
4250     ok(!delete_pf("msitest\\gamma", TRUE), "File installed\n");
4251     ok(delete_pf("msitest\\theta", TRUE), "File not installed\n");
4252     ok(!delete_pf("msitest\\delta", TRUE), "File installed\n");
4253     ok(!delete_pf("msitest\\epsilon", TRUE), "File installed\n");
4254     ok(delete_pf("msitest\\zeta", TRUE), "File not installed\n");
4255     ok(!delete_pf("msitest\\iota", TRUE), "File installed\n");
4256     ok(!delete_pf("msitest\\eta", TRUE), "File installed\n");
4257     ok(!delete_pf("msitest\\kappa", TRUE), "File installed\n");
4258     ok(!delete_pf("msitest\\lambda", TRUE), "File installed\n");
4259     ok(!delete_pf("msitest\\mu", TRUE), "File installed\n");
4260     ok(delete_pf("msitest", FALSE), "File not installed\n");
4261
4262     r = MsiInstallProductA(msifile, "REMOVE=\"one,two,three,four\"");
4263     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4264     ok(!delete_pf("msitest\\alpha", TRUE), "File installed\n");
4265     ok(!delete_pf("msitest\\beta", TRUE), "File installed\n");
4266     ok(!delete_pf("msitest\\gamma", TRUE), "File installed\n");
4267     ok(!delete_pf("msitest\\theta", TRUE), "File installed\n");
4268     ok(!delete_pf("msitest\\delta", TRUE), "File installed\n");
4269     ok(!delete_pf("msitest\\epsilon", TRUE), "File installed\n");
4270     ok(!delete_pf("msitest\\zeta", TRUE), "File installed\n");
4271     ok(!delete_pf("msitest\\iota", TRUE), "File installed\n");
4272     ok(!delete_pf("msitest\\eta", TRUE), "File installed\n");
4273     ok(!delete_pf("msitest\\kappa", TRUE), "File installed\n");
4274     ok(!delete_pf("msitest\\lambda", TRUE), "File installed\n");
4275     ok(!delete_pf("msitest\\mu", TRUE), "File installed\n");
4276     ok(!delete_pf("msitest", FALSE), "File installed\n");
4277
4278 error:
4279     DeleteFile(msifile);
4280     DeleteFile("msitest\\alpha");
4281     DeleteFile("msitest\\beta");
4282     DeleteFile("msitest\\gamma");
4283     DeleteFile("msitest\\theta");
4284     DeleteFile("msitest\\delta");
4285     DeleteFile("msitest\\epsilon");
4286     DeleteFile("msitest\\zeta");
4287     DeleteFile("msitest\\iota");
4288     DeleteFile("msitest\\eta");
4289     DeleteFile("msitest\\kappa");
4290     DeleteFile("msitest\\lambda");
4291     DeleteFile("msitest\\mu");
4292     RemoveDirectory("msitest");
4293 }
4294
4295 static const struct sourcepathmap
4296 {
4297     BOOL sost; /* shortone\shorttwo */
4298     BOOL solt; /* shortone\longtwo */
4299     BOOL lost; /* longone\shorttwo */
4300     BOOL lolt; /* longone\longtwo */
4301     BOOL soste; /* shortone\shorttwo source exists */
4302     BOOL solte; /* shortone\longtwo source exists */
4303     BOOL loste; /* longone\shorttwo source exists */
4304     BOOL lolte; /* longone\longtwo source exists */
4305     UINT err;
4306     DWORD size;
4307 } spmap[256] =
4308 {
4309     {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4310     {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4311     {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4312     {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4313     {TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4314     {TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4315     {TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4316     {TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4317     {TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4318     {TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4319     {TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4320     {TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4321     {TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4322     {TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4323     {TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4324     {TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4325     {TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4326     {TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4327     {TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4328     {TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4329     {TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4330     {TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4331     {TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4332     {TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4333     {TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4334     {TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4335     {TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4336     {TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4337     {TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4338     {TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4339     {TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4340     {TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4341     {TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4342     {TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4343     {TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4344     {TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4345     {TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4346     {TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4347     {TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4348     {TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4349     {TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4350     {TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4351     {TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4352     {TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4353     {TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4354     {TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4355     {TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4356     {TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4357     {TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4358     {TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4359     {TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4360     {TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4361     {TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4362     {TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4363     {TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4364     {TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4365     {TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4366     {TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4367     {TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4368     {TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4369     {TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4370     {TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4371     {TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4372     {TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4373     {TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4374     {TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4375     {TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4376     {TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4377     {TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4378     {TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4379     {TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4380     {TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4381     {TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4382     {TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4383     {TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4384     {TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4385     {TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4386     {TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4387     {TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4388     {TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4389     {TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4390     {TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4391     {TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4392     {TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4393     {TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4394     {TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4395     {TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4396     {TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4397     {TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4398     {TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4399     {TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4400     {TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4401     {TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4402     {TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4403     {TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4404     {TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4405     {TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4406     {TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4407     {TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4408     {TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4409     {TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4410     {TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4411     {TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4412     {TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4413     {TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4414     {TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4415     {TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4416     {TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4417     {TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4418     {TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4419     {TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4420     {TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4421     {TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4422     {TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4423     {TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4424     {TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4425     {TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4426     {TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4427     {TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4428     {TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4429     {TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4430     {TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4431     {TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4432     {TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4433     {TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4434     {TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4435     {TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4436     {TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4437     {FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4438     {FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4439     {FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4440     {FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4441     {FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4442     {FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4443     {FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4444     {FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4445     {FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4446     {FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4447     {FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4448     {FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4449     {FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4450     {FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4451     {FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4452     {FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4453     {FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4454     {FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4455     {FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4456     {FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4457     {FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4458     {FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4459     {FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4460     {FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4461     {FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4462     {FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4463     {FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4464     {FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4465     {FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4466     {FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4467     {FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4468     {FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4469     {FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4470     {FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4471     {FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4472     {FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4473     {FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4474     {FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4475     {FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4476     {FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4477     {FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4478     {FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4479     {FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4480     {FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4481     {FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4482     {FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4483     {FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4484     {FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4485     {FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4486     {FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4487     {FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4488     {FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4489     {FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4490     {FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4491     {FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4492     {FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4493     {FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4494     {FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4495     {FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4496     {FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4497     {FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4498     {FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4499     {FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4500     {FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4501     {FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4502     {FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4503     {FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4504     {FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4505     {FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4506     {FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4507     {FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4508     {FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4509     {FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4510     {FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4511     {FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4512     {FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4513     {FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4514     {FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4515     {FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4516     {FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4517     {FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4518     {FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4519     {FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4520     {FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4521     {FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4522     {FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4523     {FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4524     {FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4525     {FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4526     {FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4527     {FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4528     {FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4529     {FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4530     {FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4531     {FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4532     {FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4533     {FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4534     {FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4535     {FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4536     {FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4537     {FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4538     {FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4539     {FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4540     {FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4541     {FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
4542     {FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4543     {FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
4544     {FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4545     {FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
4546     {FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4547     {FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
4548     {FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4549     {FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4550     {FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4551     {FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4552     {FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4553     {FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4554     {FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4555     {FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4556     {FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4557     {FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4558     {FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4559     {FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4560     {FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4561     {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
4562     {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
4563     {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
4564     {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
4565 };
4566
4567 static DWORD get_pf_file_size(LPCSTR file)
4568 {
4569     CHAR path[MAX_PATH];
4570     HANDLE hfile;
4571     DWORD size;
4572
4573     lstrcpyA(path, PROG_FILES_DIR);
4574     lstrcatA(path, "\\");
4575     lstrcatA(path, file);
4576
4577     hfile = CreateFileA(path, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL);
4578     if (hfile == INVALID_HANDLE_VALUE)
4579         return INVALID_FILE_SIZE;
4580
4581     size = GetFileSize(hfile, NULL);
4582     CloseHandle(hfile);
4583     return size;
4584 }
4585
4586 static void test_sourcepath(void)
4587 {
4588     UINT r, i;
4589
4590     if (!winetest_interactive)
4591     {
4592         skip("Run in interactive mode to run source path tests.\n");
4593         return;
4594     }
4595
4596     create_database(msifile, sp_tables, sizeof(sp_tables) / sizeof(msi_table));
4597
4598     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4599
4600     for (i = 0; i < sizeof(spmap) / sizeof(spmap[0]); i++)
4601     {
4602         if (spmap[i].sost)
4603         {
4604             CreateDirectoryA("shortone", NULL);
4605             CreateDirectoryA("shortone\\shorttwo", NULL);
4606         }
4607
4608         if (spmap[i].solt)
4609         {
4610             CreateDirectoryA("shortone", NULL);
4611             CreateDirectoryA("shortone\\longtwo", NULL);
4612         }
4613
4614         if (spmap[i].lost)
4615         {
4616             CreateDirectoryA("longone", NULL);
4617             CreateDirectoryA("longone\\shorttwo", NULL);
4618         }
4619
4620         if (spmap[i].lolt)
4621         {
4622             CreateDirectoryA("longone", NULL);
4623             CreateDirectoryA("longone\\longtwo", NULL);
4624         }
4625
4626         if (spmap[i].soste)
4627             create_file("shortone\\shorttwo\\augustus", 50);
4628         if (spmap[i].solte)
4629             create_file("shortone\\longtwo\\augustus", 100);
4630         if (spmap[i].loste)
4631             create_file("longone\\shorttwo\\augustus", 150);
4632         if (spmap[i].lolte)
4633             create_file("longone\\longtwo\\augustus", 200);
4634
4635         r = MsiInstallProductA(msifile, NULL);
4636         ok(r == spmap[i].err, "%d: Expected %d, got %d\n", i, spmap[i].err, r);
4637         ok(get_pf_file_size("msitest\\augustus") == spmap[i].size,
4638            "%d: Expected %d, got %d\n", i, spmap[i].size,
4639            get_pf_file_size("msitest\\augustus"));
4640
4641         if (r == ERROR_SUCCESS)
4642         {
4643             ok(delete_pf("msitest\\augustus", TRUE), "%d: File not installed\n", i);
4644             ok(delete_pf("msitest", FALSE), "%d: File not installed\n", i);
4645         }
4646         else
4647         {
4648             ok(!delete_pf("msitest\\augustus", TRUE), "%d: File installed\n", i);
4649             todo_wine ok(!delete_pf("msitest", FALSE), "%d: File installed\n", i);
4650         }
4651
4652         DeleteFileA("shortone\\shorttwo\\augustus");
4653         DeleteFileA("shortone\\longtwo\\augustus");
4654         DeleteFileA("longone\\shorttwo\\augustus");
4655         DeleteFileA("longone\\longtwo\\augustus");
4656         RemoveDirectoryA("shortone\\shorttwo");
4657         RemoveDirectoryA("shortone\\longtwo");
4658         RemoveDirectoryA("longone\\shorttwo");
4659         RemoveDirectoryA("longone\\longtwo");
4660         RemoveDirectoryA("shortone");
4661         RemoveDirectoryA("longone");
4662     }
4663
4664     DeleteFileA(msifile);
4665 }
4666
4667 static void test_MsiConfigureProductEx(void)
4668 {
4669     UINT r;
4670     LONG res;
4671     DWORD type, size;
4672     HKEY props, source;
4673     CHAR keypath[MAX_PATH * 2], localpack[MAX_PATH];
4674     REGSAM access = KEY_ALL_ACCESS;
4675
4676     if (on_win9x)
4677     {
4678         win_skip("Different registry keys on Win9x and WinMe\n");
4679         return;
4680     }
4681     if (is_process_limited())
4682     {
4683         skip("process is limited\n");
4684         return;
4685     }
4686
4687     CreateDirectoryA("msitest", NULL);
4688     create_file("msitest\\hydrogen", 500);
4689     create_file("msitest\\helium", 500);
4690     create_file("msitest\\lithium", 500);
4691
4692     create_database(msifile, mcp_tables, sizeof(mcp_tables) / sizeof(msi_table));
4693
4694     if (is_wow64)
4695         access |= KEY_WOW64_64KEY;
4696
4697     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4698
4699     /* NULL szProduct */
4700     r = MsiConfigureProductExA(NULL, INSTALLLEVEL_DEFAULT,
4701                                INSTALLSTATE_DEFAULT, "PROPVAR=42");
4702     ok(r == ERROR_INVALID_PARAMETER,
4703        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
4704
4705     /* empty szProduct */
4706     r = MsiConfigureProductExA("", INSTALLLEVEL_DEFAULT,
4707                                INSTALLSTATE_DEFAULT, "PROPVAR=42");
4708     ok(r == ERROR_INVALID_PARAMETER,
4709        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
4710
4711     /* garbage szProduct */
4712     r = MsiConfigureProductExA("garbage", INSTALLLEVEL_DEFAULT,
4713                                INSTALLSTATE_DEFAULT, "PROPVAR=42");
4714     ok(r == ERROR_INVALID_PARAMETER,
4715        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
4716
4717     /* guid without brackets */
4718     r = MsiConfigureProductExA("6700E8CF-95AB-4D9C-BC2C-15840DEA7A5D",
4719                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
4720                                "PROPVAR=42");
4721     ok(r == ERROR_INVALID_PARAMETER,
4722        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
4723
4724     /* guid with brackets */
4725     r = MsiConfigureProductExA("{6700E8CF-95AB-4D9C-BC2C-15840DEA7A5D}",
4726                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
4727                                "PROPVAR=42");
4728     ok(r == ERROR_UNKNOWN_PRODUCT,
4729        "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
4730
4731     /* same length as guid, but random */
4732     r = MsiConfigureProductExA("A938G02JF-2NF3N93-VN3-2NNF-3KGKALDNF93",
4733                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
4734                                "PROPVAR=42");
4735     ok(r == ERROR_UNKNOWN_PRODUCT,
4736        "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
4737
4738     /* product not installed yet */
4739     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4740                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
4741                                "PROPVAR=42");
4742     ok(r == ERROR_UNKNOWN_PRODUCT,
4743        "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
4744
4745     /* install the product, per-user unmanaged */
4746     r = MsiInstallProductA(msifile, "INSTALLLEVEL=10 PROPVAR=42");
4747     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
4748     {
4749         skip("Not enough rights to perform tests\n");
4750         goto error;
4751     }
4752     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4753     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
4754     ok(pf_exists("msitest\\helium"), "File not installed\n");
4755     ok(pf_exists("msitest\\lithium"), "File not installed\n");
4756     ok(pf_exists("msitest"), "File not installed\n");
4757
4758     /* product is installed per-user managed, remove it */
4759     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4760                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
4761                                "PROPVAR=42");
4762     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4763     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
4764     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
4765     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
4766     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
4767
4768     /* product has been removed */
4769     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4770                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
4771                                "PROPVAR=42");
4772     ok(r == ERROR_UNKNOWN_PRODUCT,
4773        "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
4774
4775     /* install the product, machine */
4776     r = MsiInstallProductA(msifile, "ALLUSERS=1 INSTALLLEVEL=10 PROPVAR=42");
4777     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4778     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
4779     ok(pf_exists("msitest\\helium"), "File not installed\n");
4780     ok(pf_exists("msitest\\lithium"), "File not installed\n");
4781     ok(pf_exists("msitest"), "File not installed\n");
4782
4783     /* product is installed machine, remove it */
4784     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4785                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
4786                                "PROPVAR=42");
4787     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4788     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
4789     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
4790     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
4791     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
4792
4793     /* product has been removed */
4794     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4795                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
4796                                "PROPVAR=42");
4797     ok(r == ERROR_UNKNOWN_PRODUCT,
4798        "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
4799
4800     /* install the product, machine */
4801     r = MsiInstallProductA(msifile, "ALLUSERS=1 INSTALLLEVEL=10 PROPVAR=42");
4802     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4803     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
4804     ok(pf_exists("msitest\\helium"), "File not installed\n");
4805     ok(pf_exists("msitest\\lithium"), "File not installed\n");
4806     ok(pf_exists("msitest"), "File not installed\n");
4807
4808     DeleteFileA(msifile);
4809
4810     /* local msifile is removed */
4811     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4812                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
4813                                "PROPVAR=42");
4814     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4815     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
4816     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
4817     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
4818     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
4819
4820     create_database(msifile, mcp_tables, sizeof(mcp_tables) / sizeof(msi_table));
4821
4822     /* install the product, machine */
4823     r = MsiInstallProductA(msifile, "ALLUSERS=1 INSTALLLEVEL=10 PROPVAR=42");
4824     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4825     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
4826     ok(pf_exists("msitest\\helium"), "File not installed\n");
4827     ok(pf_exists("msitest\\lithium"), "File not installed\n");
4828     ok(pf_exists("msitest"), "File not installed\n");
4829
4830     DeleteFileA(msifile);
4831
4832     lstrcpyA(keypath, "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\");
4833     lstrcatA(keypath, "Installer\\UserData\\S-1-5-18\\Products\\");
4834     lstrcatA(keypath, "84A88FD7F6998CE40A22FB59F6B9C2BB\\InstallProperties");
4835
4836     res = RegOpenKeyExA(HKEY_LOCAL_MACHINE, keypath, 0, access, &props);
4837     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4838
4839     res = RegSetValueExA(props, "LocalPackage", 0, REG_SZ,
4840                          (const BYTE *)"C:\\idontexist.msi", 18);
4841     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4842
4843     /* LocalPackage is used to find the cached msi package */
4844     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4845                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
4846                                "PROPVAR=42");
4847     ok(r == ERROR_INSTALL_SOURCE_ABSENT,
4848        "Expected ERROR_INSTALL_SOURCE_ABSENT, got %d\n", r);
4849     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
4850     ok(pf_exists("msitest\\helium"), "File not installed\n");
4851     ok(pf_exists("msitest\\lithium"), "File not installed\n");
4852     ok(pf_exists("msitest"), "File not installed\n");
4853
4854     RegCloseKey(props);
4855     create_database(msifile, mcp_tables, sizeof(mcp_tables) / sizeof(msi_table));
4856
4857     /* LastUsedSource (local msi package) can be used as a last resort */
4858     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4859                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
4860                                "PROPVAR=42");
4861     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4862     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
4863     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
4864     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
4865     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
4866
4867     /* install the product, machine */
4868     r = MsiInstallProductA(msifile, "ALLUSERS=1 INSTALLLEVEL=10 PROPVAR=42");
4869     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4870     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
4871     ok(pf_exists("msitest\\helium"), "File not installed\n");
4872     ok(pf_exists("msitest\\lithium"), "File not installed\n");
4873     ok(pf_exists("msitest"), "File not installed\n");
4874
4875     lstrcpyA(keypath, "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\");
4876     lstrcatA(keypath, "Installer\\UserData\\S-1-5-18\\Products\\");
4877     lstrcatA(keypath, "84A88FD7F6998CE40A22FB59F6B9C2BB\\InstallProperties");
4878
4879     res = RegOpenKeyExA(HKEY_LOCAL_MACHINE, keypath, 0, access, &props);
4880     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4881
4882     res = RegSetValueExA(props, "LocalPackage", 0, REG_SZ,
4883                          (const BYTE *)"C:\\idontexist.msi", 18);
4884     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4885
4886     lstrcpyA(keypath, "SOFTWARE\\Classes\\Installer\\Products\\");
4887     lstrcatA(keypath, "84A88FD7F6998CE40A22FB59F6B9C2BB\\SourceList");
4888
4889     res = RegOpenKeyExA(HKEY_LOCAL_MACHINE, keypath, 0, access, &source);
4890     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4891
4892     type = REG_SZ;
4893     size = MAX_PATH;
4894     res = RegQueryValueExA(source, "PackageName", NULL, &type,
4895                            (LPBYTE)localpack, &size);
4896     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4897
4898     res = RegSetValueExA(source, "PackageName", 0, REG_SZ,
4899                          (const BYTE *)"idontexist.msi", 15);
4900     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4901
4902     /* SourceList is altered */
4903     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4904                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
4905                                "PROPVAR=42");
4906     ok(r == ERROR_INSTALL_SOURCE_ABSENT,
4907        "Expected ERROR_INSTALL_SOURCE_ABSENT, got %d\n", r);
4908     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
4909     ok(pf_exists("msitest\\helium"), "File not installed\n");
4910     ok(pf_exists("msitest\\lithium"), "File not installed\n");
4911     ok(pf_exists("msitest"), "File not installed\n");
4912
4913     /* restore the SourceList */
4914     res = RegSetValueExA(source, "PackageName", 0, REG_SZ,
4915                          (const BYTE *)localpack, lstrlenA(localpack) + 1);
4916     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4917
4918     /* finally remove the product */
4919     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
4920                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
4921                                "PROPVAR=42");
4922     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4923     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
4924     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
4925     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
4926     ok(!delete_pf("msitest", FALSE), "File not removed\n");
4927
4928     RegCloseKey(source);
4929     RegCloseKey(props);
4930
4931 error:
4932     DeleteFileA("msitest\\hydrogen");
4933     DeleteFileA("msitest\\helium");
4934     DeleteFileA("msitest\\lithium");
4935     RemoveDirectoryA("msitest");
4936     DeleteFileA(msifile);
4937 }
4938
4939 static void test_missingcomponent(void)
4940 {
4941     UINT r;
4942
4943     if (is_process_limited())
4944     {
4945         skip("process is limited\n");
4946         return;
4947     }
4948
4949     CreateDirectoryA("msitest", NULL);
4950     create_file("msitest\\hydrogen", 500);
4951     create_file("msitest\\helium", 500);
4952     create_file("msitest\\lithium", 500);
4953     create_file("beryllium", 500);
4954
4955     create_database(msifile, mcomp_tables, sizeof(mcomp_tables) / sizeof(msi_table));
4956
4957     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4958
4959     r = MsiInstallProductA(msifile, "INSTALLLEVEL=10 PROPVAR=42");
4960     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
4961     {
4962         skip("Not enough rights to perform tests\n");
4963         goto error;
4964     }
4965     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4966     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
4967     ok(pf_exists("msitest\\helium"), "File not installed\n");
4968     ok(pf_exists("msitest\\lithium"), "File not installed\n");
4969     ok(!pf_exists("msitest\\beryllium"), "File installed\n");
4970     ok(pf_exists("msitest"), "File not installed\n");
4971
4972     r = MsiInstallProductA(msifile, "REMOVE=ALL INSTALLLEVEL=10 PROPVAR=42");
4973     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4974     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
4975     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
4976     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
4977     ok(!pf_exists("msitest\\beryllium"), "File installed\n");
4978     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
4979
4980 error:
4981     DeleteFileA(msifile);
4982     DeleteFileA("msitest\\hydrogen");
4983     DeleteFileA("msitest\\helium");
4984     DeleteFileA("msitest\\lithium");
4985     DeleteFileA("beryllium");
4986     RemoveDirectoryA("msitest");
4987 }
4988
4989 static void test_sourcedirprop(void)
4990 {
4991     UINT r;
4992     CHAR props[MAX_PATH];
4993
4994     if (is_process_limited())
4995     {
4996         skip("process is limited\n");
4997         return;
4998     }
4999
5000     CreateDirectoryA("msitest", NULL);
5001     create_file("msitest\\augustus", 500);
5002
5003     create_database(msifile, ca51_tables, sizeof(ca51_tables) / sizeof(msi_table));
5004
5005     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5006
5007     r = MsiInstallProductA(msifile, NULL);
5008     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5009     {
5010         skip("Not enough rights to perform tests\n");
5011         goto error;
5012     }
5013     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5014     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
5015     ok(delete_pf("msitest", FALSE), "File installed\n");
5016
5017     DeleteFile("msitest\\augustus");
5018     RemoveDirectory("msitest");
5019
5020     CreateDirectoryA("altsource", NULL);
5021     CreateDirectoryA("altsource\\msitest", NULL);
5022     create_file("altsource\\msitest\\augustus", 500);
5023
5024     sprintf(props, "SRCDIR=%s\\altsource\\", CURR_DIR);
5025
5026     r = MsiInstallProductA(msifile, props);
5027     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5028     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
5029     ok(delete_pf("msitest", FALSE), "File installed\n");
5030
5031     DeleteFile("altsource\\msitest\\augustus");
5032     RemoveDirectory("altsource\\msitest");
5033     RemoveDirectory("altsource");
5034
5035 error:
5036     DeleteFile("msitest\\augustus");
5037     RemoveDirectory("msitest");
5038     DeleteFile(msifile);
5039 }
5040
5041 static void test_adminimage(void)
5042 {
5043     UINT r;
5044
5045     if (is_process_limited())
5046     {
5047         skip("process is limited\n");
5048         return;
5049     }
5050
5051     CreateDirectoryA("msitest", NULL);
5052     CreateDirectoryA("msitest\\first", NULL);
5053     CreateDirectoryA("msitest\\second", NULL);
5054     CreateDirectoryA("msitest\\cabout", NULL);
5055     CreateDirectoryA("msitest\\cabout\\new", NULL);
5056     create_file("msitest\\one.txt", 100);
5057     create_file("msitest\\first\\two.txt", 100);
5058     create_file("msitest\\second\\three.txt", 100);
5059     create_file("msitest\\cabout\\four.txt", 100);
5060     create_file("msitest\\cabout\\new\\five.txt", 100);
5061     create_file("msitest\\filename", 100);
5062     create_file("msitest\\service.exe", 100);
5063
5064     create_database_wordcount(msifile, ai_tables,
5065                               sizeof(ai_tables) / sizeof(msi_table),
5066                               100, msidbSumInfoSourceTypeAdminImage, ";1033");
5067
5068     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5069
5070     r = MsiInstallProductA(msifile, NULL);
5071     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5072     {
5073         skip("Not enough rights to perform tests\n");
5074         goto error;
5075     }
5076     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5077
5078     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
5079     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
5080     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
5081     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
5082     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
5083     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
5084     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
5085     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
5086     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
5087     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
5088     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
5089     ok(delete_pf("msitest", FALSE), "File not installed\n");
5090
5091 error:
5092     DeleteFileA("msifile");
5093     DeleteFileA("msitest\\cabout\\new\\five.txt");
5094     DeleteFileA("msitest\\cabout\\four.txt");
5095     DeleteFileA("msitest\\second\\three.txt");
5096     DeleteFileA("msitest\\first\\two.txt");
5097     DeleteFileA("msitest\\one.txt");
5098     DeleteFileA("msitest\\service.exe");
5099     DeleteFileA("msitest\\filename");
5100     RemoveDirectoryA("msitest\\cabout\\new");
5101     RemoveDirectoryA("msitest\\cabout");
5102     RemoveDirectoryA("msitest\\second");
5103     RemoveDirectoryA("msitest\\first");
5104     RemoveDirectoryA("msitest");
5105 }
5106
5107 static void test_propcase(void)
5108 {
5109     UINT r;
5110
5111     if (is_process_limited())
5112     {
5113         skip("process is limited\n");
5114         return;
5115     }
5116
5117     CreateDirectoryA("msitest", NULL);
5118     create_file("msitest\\augustus", 500);
5119
5120     create_database(msifile, pc_tables, sizeof(pc_tables) / sizeof(msi_table));
5121
5122     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5123
5124     r = MsiInstallProductA(msifile, "MyProp=42");
5125     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5126     {
5127         skip("Not enough rights to perform tests\n");
5128         goto error;
5129     }
5130     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5131     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
5132     ok(delete_pf("msitest", FALSE), "File not installed\n");
5133
5134 error:
5135     DeleteFile(msifile);
5136     DeleteFile("msitest\\augustus");
5137     RemoveDirectory("msitest");
5138 }
5139
5140 static void test_int_widths( void )
5141 {
5142     static const char int0[] = "int0\ni0\nint0\tint0\n1";
5143     static const char int1[] = "int1\ni1\nint1\tint1\n1";
5144     static const char int2[] = "int2\ni2\nint2\tint2\n1";
5145     static const char int3[] = "int3\ni3\nint3\tint3\n1";
5146     static const char int4[] = "int4\ni4\nint4\tint4\n1";
5147     static const char int5[] = "int5\ni5\nint5\tint5\n1";
5148     static const char int8[] = "int8\ni8\nint8\tint8\n1";
5149
5150     static const struct
5151     {
5152         const char  *data;
5153         unsigned int size;
5154         UINT         ret;
5155     }
5156     tests[] =
5157     {
5158         { int0, sizeof(int0) - 1, ERROR_SUCCESS },
5159         { int1, sizeof(int1) - 1, ERROR_SUCCESS },
5160         { int2, sizeof(int2) - 1, ERROR_SUCCESS },
5161         { int3, sizeof(int3) - 1, ERROR_FUNCTION_FAILED },
5162         { int4, sizeof(int4) - 1, ERROR_SUCCESS },
5163         { int5, sizeof(int5) - 1, ERROR_FUNCTION_FAILED },
5164         { int8, sizeof(int8) - 1, ERROR_FUNCTION_FAILED }
5165     };
5166
5167     char tmpdir[MAX_PATH], msitable[MAX_PATH], msidb[MAX_PATH];
5168     MSIHANDLE db;
5169     UINT r, i;
5170
5171     GetTempPathA(MAX_PATH, tmpdir);
5172     CreateDirectoryA(tmpdir, NULL);
5173
5174     strcpy(msitable, tmpdir);
5175     strcat(msitable, "\\msitable.idt");
5176
5177     strcpy(msidb, tmpdir);
5178     strcat(msidb, "\\msitest.msi");
5179
5180     r = MsiOpenDatabaseA(msidb, MSIDBOPEN_CREATE, &db);
5181     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5182
5183     for (i = 0; i < sizeof(tests)/sizeof(tests[0]); i++)
5184     {
5185         write_file(msitable, tests[i].data, tests[i].size);
5186
5187         r = MsiDatabaseImportA(db, tmpdir, "msitable.idt");
5188         ok(r == tests[i].ret, " %u expected %u, got %u\n", i, tests[i].ret, r);
5189
5190         r = MsiDatabaseCommit(db);
5191         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5192         DeleteFileA(msitable);
5193     }
5194
5195     MsiCloseHandle(db);
5196     DeleteFileA(msidb);
5197     RemoveDirectoryA(tmpdir);
5198 }
5199
5200 static void test_shortcut(void)
5201 {
5202     UINT r;
5203     HRESULT hr;
5204
5205     if (is_process_limited())
5206     {
5207         skip("process is limited\n");
5208         return;
5209     }
5210
5211     create_test_files();
5212     create_database(msifile, sc_tables, sizeof(sc_tables) / sizeof(msi_table));
5213
5214     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5215
5216     r = MsiInstallProductA(msifile, NULL);
5217     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5218     {
5219         skip("Not enough rights to perform tests\n");
5220         goto error;
5221     }
5222     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5223
5224     hr = CoInitializeEx(NULL, COINIT_MULTITHREADED);
5225     ok(SUCCEEDED(hr), "CoInitialize failed 0x%08x\n", hr);
5226
5227     r = MsiInstallProductA(msifile, NULL);
5228     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5229
5230     CoUninitialize();
5231
5232     hr = CoInitializeEx(NULL, COINIT_APARTMENTTHREADED);
5233     ok(SUCCEEDED(hr), "CoInitialize failed 0x%08x\n", hr);
5234
5235     r = MsiInstallProductA(msifile, NULL);
5236     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5237
5238     CoUninitialize();
5239
5240     delete_pf("msitest\\cabout\\new\\five.txt", TRUE);
5241     delete_pf("msitest\\cabout\\new", FALSE);
5242     delete_pf("msitest\\cabout\\four.txt", TRUE);
5243     delete_pf("msitest\\cabout", FALSE);
5244     delete_pf("msitest\\changed\\three.txt", TRUE);
5245     delete_pf("msitest\\changed", FALSE);
5246     delete_pf("msitest\\first\\two.txt", TRUE);
5247     delete_pf("msitest\\first", FALSE);
5248     delete_pf("msitest\\filename", TRUE);
5249     delete_pf("msitest\\one.txt", TRUE);
5250     delete_pf("msitest\\service.exe", TRUE);
5251     delete_pf("msitest\\Shortcut.lnk", TRUE);
5252     delete_pf("msitest", FALSE);
5253
5254 error:
5255     delete_test_files();
5256     DeleteFile(msifile);
5257 }
5258
5259 static void test_preselected(void)
5260 {
5261     UINT r;
5262
5263     if (is_process_limited())
5264     {
5265         skip("process is limited\n");
5266         return;
5267     }
5268
5269     create_test_files();
5270     create_database(msifile, ps_tables, sizeof(ps_tables) / sizeof(msi_table));
5271
5272     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5273
5274     r = MsiInstallProductA(msifile, "ADDLOCAL=One");
5275     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5276     {
5277         skip("Not enough rights to perform tests\n");
5278         goto error;
5279     }
5280     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5281
5282     ok(!delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File installed\n");
5283     ok(!delete_pf("msitest\\cabout\\new", FALSE), "File installed\n");
5284     ok(!delete_pf("msitest\\cabout\\four.txt", TRUE), "File installed\n");
5285     ok(!delete_pf("msitest\\cabout", FALSE), "File installed\n");
5286     ok(!delete_pf("msitest\\changed\\three.txt", TRUE), "File installed\n");
5287     ok(!delete_pf("msitest\\changed", FALSE), "File installed\n");
5288     ok(!delete_pf("msitest\\first\\two.txt", TRUE), "File installed\n");
5289     ok(!delete_pf("msitest\\first", FALSE), "File installed\n");
5290     ok(!delete_pf("msitest\\filename", TRUE), "File installed\n");
5291     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
5292     ok(!delete_pf("msitest\\service.exe", TRUE), "File installed\n");
5293     ok(delete_pf("msitest", FALSE), "File not installed\n");
5294
5295     r = MsiInstallProductA(msifile, NULL);
5296     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5297
5298     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
5299     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
5300     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
5301     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
5302     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
5303     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
5304     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
5305     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
5306     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
5307     ok(!delete_pf("msitest\\one.txt", TRUE), "File installed\n");
5308     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
5309     ok(delete_pf("msitest", FALSE), "File not installed\n");
5310
5311 error:
5312     delete_test_files();
5313     DeleteFile(msifile);
5314 }
5315
5316 static void test_installed_prop(void)
5317 {
5318     static char prodcode[] = "{7df88a48-996f-4ec8-a022-bf956f9b2cbb}";
5319     UINT r;
5320
5321     if (is_process_limited())
5322     {
5323         skip("process is limited\n");
5324         return;
5325     }
5326
5327     create_test_files();
5328     create_database(msifile, ip_tables, sizeof(ip_tables) / sizeof(msi_table));
5329
5330     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5331
5332     r = MsiInstallProductA(msifile, "FULL=1");
5333     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5334     {
5335         skip("Not enough rights to perform tests\n");
5336         goto error;
5337     }
5338     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5339
5340     r = MsiInstallProductA(msifile, "FULL=1");
5341     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
5342
5343     r = MsiConfigureProductExA(prodcode, INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT, "FULL=1");
5344     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
5345
5346     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
5347     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
5348     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
5349     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
5350     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
5351     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
5352     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
5353     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
5354     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
5355     ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
5356     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
5357     ok(delete_pf("msitest", FALSE), "File not installed\n");
5358
5359     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5360     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5361
5362 error:
5363     delete_test_files();
5364     DeleteFile(msifile);
5365 }
5366
5367 static void test_allusers_prop(void)
5368 {
5369     UINT r;
5370
5371     if (is_process_limited())
5372     {
5373         skip("process is limited\n");
5374         return;
5375     }
5376
5377     create_test_files();
5378     create_database(msifile, aup_tables, sizeof(aup_tables) / sizeof(msi_table));
5379
5380     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5381
5382     /* ALLUSERS property unset */
5383     r = MsiInstallProductA(msifile, "FULL=1");
5384     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5385     {
5386         skip("Not enough rights to perform tests\n");
5387         goto error;
5388     }
5389     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5390
5391     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
5392     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
5393     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
5394     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
5395     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
5396     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
5397     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
5398     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
5399     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
5400     ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
5401     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
5402     ok(delete_pf("msitest", FALSE), "File not installed\n");
5403
5404     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5405     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5406
5407     delete_test_files();
5408
5409     create_test_files();
5410     create_database(msifile, aup2_tables, sizeof(aup2_tables) / sizeof(msi_table));
5411
5412     /* ALLUSERS property set to 1 */
5413     r = MsiInstallProductA(msifile, "FULL=1");
5414     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5415
5416     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
5417     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
5418     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
5419     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
5420     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
5421     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
5422     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
5423     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
5424     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
5425     ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
5426     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
5427     ok(delete_pf("msitest", FALSE), "File not installed\n");
5428
5429     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5430     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5431
5432     delete_test_files();
5433
5434     create_test_files();
5435     create_database(msifile, aup3_tables, sizeof(aup3_tables) / sizeof(msi_table));
5436
5437     /* ALLUSERS property set to 2 */
5438     r = MsiInstallProductA(msifile, "FULL=1");
5439     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5440
5441     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
5442     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
5443     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
5444     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
5445     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
5446     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
5447     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
5448     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
5449     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
5450     ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
5451     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
5452     ok(delete_pf("msitest", FALSE), "File not installed\n");
5453
5454     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5455     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5456
5457     delete_test_files();
5458
5459     create_test_files();
5460     create_database(msifile, aup4_tables, sizeof(aup4_tables) / sizeof(msi_table));
5461
5462     /* ALLUSERS property set to 2, conditioned on ALLUSERS = 1 */
5463     r = MsiInstallProductA(msifile, "FULL=1");
5464     if (r == ERROR_SUCCESS)
5465     {
5466         /* Win9x/WinMe */
5467         win_skip("Win9x and WinMe act differently with respect to ALLUSERS\n");
5468
5469         ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
5470         ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
5471         ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
5472         ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
5473         ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
5474         ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
5475         ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
5476         ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
5477         ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
5478         ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
5479         ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
5480         ok(delete_pf("msitest", FALSE), "File not installed\n");
5481
5482         r = MsiInstallProductA(msifile, "REMOVE=ALL");
5483         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5484
5485         delete_test_files();
5486     }
5487     else
5488         ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
5489
5490 error:
5491     delete_test_files();
5492     DeleteFile(msifile);
5493 }
5494
5495 static char session_manager[] = "System\\CurrentControlSet\\Control\\Session Manager";
5496 static char rename_ops[]      = "PendingFileRenameOperations";
5497
5498 static void process_pending_renames(HKEY hkey)
5499 {
5500     char *buf, *src, *dst, *buf2, *buf2ptr;
5501     DWORD size;
5502     LONG ret;
5503     BOOL found = FALSE;
5504
5505     ret = RegQueryValueExA(hkey, rename_ops, NULL, NULL, NULL, &size);
5506     buf = HeapAlloc(GetProcessHeap(), 0, size + 1);
5507     buf2ptr = buf2 = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, size + 1);
5508
5509     ret = RegQueryValueExA(hkey, rename_ops, NULL, NULL, (LPBYTE)buf, &size);
5510     buf[size] = 0;
5511     ok(!ret, "RegQueryValueExA failed %d\n", ret);
5512     if (ret) return;
5513
5514     for (src = buf; *src; src = dst + strlen(dst) + 1)
5515     {
5516         DWORD flags = MOVEFILE_COPY_ALLOWED;
5517
5518         dst = src + strlen(src) + 1;
5519
5520         if (!strstr(src, "msitest"))
5521         {
5522             lstrcpyA(buf2ptr, src);
5523             buf2ptr += strlen(src) + 1;
5524             if (*dst)
5525             {
5526                 lstrcpyA(buf2ptr, dst);
5527                 buf2ptr += strlen(dst) + 1;
5528             }
5529             buf2ptr++;
5530             continue;
5531         }
5532
5533         found = TRUE;
5534
5535         if (*dst == '!')
5536         {
5537             flags |= MOVEFILE_REPLACE_EXISTING;
5538             dst++;
5539         }
5540         if (src[0] == '\\' && src[1] == '?' && src[2] == '?' && src[3] == '\\') src += 4;
5541         if (*dst)
5542         {
5543             if (dst[0] == '\\' && dst[1] == '?' && dst[2] == '?' && dst[3] == '\\') dst += 4;
5544             ok(MoveFileExA(src, dst, flags), "Failed to move file %s -> %s (%u)\n", src, dst, GetLastError());
5545         }
5546         else
5547             ok(DeleteFileA(src), "Failed to delete file %s (%u)\n", src, GetLastError());
5548     }
5549
5550     ok(found, "Expected a 'msitest' entry\n");
5551
5552     if (*buf2)
5553         RegSetValueExA(hkey, rename_ops, 0, REG_MULTI_SZ, (LPBYTE)buf2, buf2ptr + 1 - buf2);
5554     else
5555         RegDeleteValueA(hkey, rename_ops);
5556
5557     HeapFree(GetProcessHeap(), 0, buf);
5558     HeapFree(GetProcessHeap(), 0, buf2);
5559 }
5560
5561 static BOOL file_matches_data(LPCSTR file, LPCSTR data)
5562 {
5563     DWORD len, data_len = strlen(data);
5564     HANDLE handle;
5565     char buf[128];
5566
5567     handle = CreateFile(file, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL);
5568     ok(handle != INVALID_HANDLE_VALUE, "failed to open %s (%u)\n", file, GetLastError());
5569
5570     if (ReadFile(handle, buf, sizeof(buf), &len, NULL) && len >= data_len)
5571     {
5572         CloseHandle(handle);
5573         return !memcmp(buf, data, data_len);
5574     }
5575     CloseHandle(handle);
5576     return FALSE;
5577 }
5578
5579 static void test_file_in_use(void)
5580 {
5581     UINT r;
5582     HANDLE file;
5583     HKEY hkey;
5584     char path[MAX_PATH];
5585
5586     if (on_win9x)
5587     {
5588         win_skip("Pending file renaming is implemented differently on Win9x and WinMe\n");
5589         return;
5590     }
5591     if (is_process_limited())
5592     {
5593         skip("process is limited\n");
5594         return;
5595     }
5596
5597     RegOpenKeyExA(HKEY_LOCAL_MACHINE, session_manager, 0, KEY_ALL_ACCESS, &hkey);
5598
5599     CreateDirectoryA("msitest", NULL);
5600     create_file("msitest\\maximus", 500);
5601     create_database(msifile, fiu_tables, sizeof(fiu_tables) / sizeof(msi_table));
5602
5603     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5604
5605     lstrcpy(path, PROG_FILES_DIR);
5606     lstrcat(path, "\\msitest");
5607     CreateDirectoryA(path, NULL);
5608
5609     lstrcat(path, "\\maximus");
5610     file = CreateFileA(path, GENERIC_READ, FILE_SHARE_READ, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
5611
5612     r = MsiInstallProductA(msifile, "REBOOT=ReallySuppress FULL=1");
5613     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5614     {
5615         skip("Not enough rights to perform tests\n");
5616         goto error;
5617     }
5618     ok(r == ERROR_SUCCESS_REBOOT_REQUIRED, "Expected ERROR_SUCCESS_REBOOT_REQUIRED got %u\n", r);
5619     ok(!file_matches_data(path, "msitest\\maximus"), "Expected file not to match\n");
5620     CloseHandle(file);
5621     ok(!file_matches_data(path, "msitest\\maximus"), "Expected file not to match\n");
5622
5623     process_pending_renames(hkey);
5624     RegCloseKey(hkey);
5625
5626     ok(file_matches_data(path, "msitest\\maximus"), "Expected file to match\n");
5627     ok(delete_pf("msitest\\maximus", TRUE), "File not present\n");
5628     ok(delete_pf("msitest", FALSE), "Directory not present or not empty\n");
5629
5630     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5631     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5632
5633 error:
5634     RegCloseKey(hkey);
5635
5636     delete_pf("msitest\\maximus", TRUE);
5637     delete_pf("msitest", FALSE);
5638     DeleteFileA("msitest\\maximus");
5639     delete_test_files();
5640     DeleteFile(msifile);
5641 }
5642
5643 static void test_file_in_use_cab(void)
5644 {
5645     UINT r;
5646     HANDLE file;
5647     HKEY hkey;
5648     char path[MAX_PATH];
5649
5650     if (on_win9x)
5651     {
5652         win_skip("Pending file renaming is implemented differently on Win9x and WinMe\n");
5653         return;
5654     }
5655     if (is_process_limited())
5656     {
5657         skip("process is limited\n");
5658         return;
5659     }
5660
5661     RegOpenKeyExA(HKEY_LOCAL_MACHINE, session_manager, 0, KEY_ALL_ACCESS, &hkey);
5662
5663     CreateDirectoryA("msitest", NULL);
5664     create_file("maximus", 500);
5665     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
5666     DeleteFile("maximus");
5667
5668     create_database(msifile, fiuc_tables, sizeof(fiuc_tables) / sizeof(msi_table));
5669
5670     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5671
5672     lstrcpy(path, PROG_FILES_DIR);
5673     lstrcat(path, "\\msitest");
5674     CreateDirectoryA(path, NULL);
5675
5676     lstrcat(path, "\\maximus");
5677     file = CreateFileA(path, GENERIC_READ, FILE_SHARE_READ, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
5678
5679     r = MsiInstallProductA(msifile, "REBOOT=ReallySuppress FULL=1");
5680     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5681     {
5682         skip("Not enough rights to perform tests\n");
5683         goto error;
5684     }
5685     ok(r == ERROR_SUCCESS_REBOOT_REQUIRED, "Expected ERROR_SUCCESS_REBOOT_REQUIRED got %u\n", r);
5686     ok(!file_matches_data(path, "maximus"), "Expected file not to match\n");
5687     CloseHandle(file);
5688     ok(!file_matches_data(path, "maximus"), "Expected file not to match\n");
5689
5690     process_pending_renames(hkey);
5691     RegCloseKey(hkey);
5692
5693     ok(file_matches_data(path, "maximus"), "Expected file to match\n");
5694     ok(delete_pf("msitest\\maximus", TRUE), "File not present\n");
5695     ok(delete_pf("msitest", FALSE), "Directory not present or not empty\n");
5696
5697     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5698     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5699
5700 error:
5701     RegCloseKey(hkey);
5702
5703     delete_pf("msitest\\maximus", TRUE);
5704     delete_pf("msitest", FALSE);
5705     DeleteFileA("msitest\\maximus");
5706     delete_cab_files();
5707     delete_test_files();
5708     DeleteFile(msifile);
5709 }
5710
5711 static INT CALLBACK handler_a(LPVOID context, UINT type, LPCSTR msg)
5712 {
5713     return IDOK;
5714 }
5715
5716 static INT CALLBACK handler_w(LPVOID context, UINT type, LPCWSTR msg)
5717 {
5718     return IDOK;
5719 }
5720
5721 static INT CALLBACK handler_record(LPVOID context, UINT type, MSIHANDLE record)
5722 {
5723     return IDOK;
5724 }
5725
5726 static void test_MsiSetExternalUI(void)
5727 {
5728     INSTALLUI_HANDLERA ret_a;
5729     INSTALLUI_HANDLERW ret_w;
5730     INSTALLUI_HANDLER_RECORD prev;
5731     UINT error;
5732
5733     ret_a = MsiSetExternalUIA(handler_a, INSTALLLOGMODE_ERROR, NULL);
5734     ok(ret_a == NULL, "expected NULL, got %p\n", ret_a);
5735
5736     ret_a = MsiSetExternalUIA(NULL, 0, NULL);
5737     ok(ret_a == handler_a, "expected %p, got %p\n", handler_a, ret_a);
5738
5739     /* Not present before Installer 3.1 */
5740     if (!pMsiSetExternalUIRecord) {
5741         win_skip("MsiSetExternalUIRecord is not available\n");
5742         return;
5743     }
5744
5745     error = pMsiSetExternalUIRecord(handler_record, INSTALLLOGMODE_ERROR, NULL, &prev);
5746     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
5747     ok(prev == NULL, "expected NULL, got %p\n", prev);
5748
5749     prev = (INSTALLUI_HANDLER_RECORD)0xdeadbeef;
5750     error = pMsiSetExternalUIRecord(NULL, INSTALLLOGMODE_ERROR, NULL, &prev);
5751     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
5752     ok(prev == handler_record, "expected %p, got %p\n", handler_record, prev);
5753
5754     ret_w = MsiSetExternalUIW(handler_w, INSTALLLOGMODE_ERROR, NULL);
5755     ok(ret_w == NULL, "expected NULL, got %p\n", ret_w);
5756
5757     ret_w = MsiSetExternalUIW(NULL, 0, NULL);
5758     ok(ret_w == handler_w, "expected %p, got %p\n", handler_w, ret_w);
5759
5760     ret_a = MsiSetExternalUIA(handler_a, INSTALLLOGMODE_ERROR, NULL);
5761     ok(ret_a == NULL, "expected NULL, got %p\n", ret_a);
5762
5763     ret_w = MsiSetExternalUIW(handler_w, INSTALLLOGMODE_ERROR, NULL);
5764     ok(ret_w == NULL, "expected NULL, got %p\n", ret_w);
5765
5766     prev = (INSTALLUI_HANDLER_RECORD)0xdeadbeef;
5767     error = pMsiSetExternalUIRecord(handler_record, INSTALLLOGMODE_ERROR, NULL, &prev);
5768     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
5769     ok(prev == NULL, "expected NULL, got %p\n", prev);
5770
5771     ret_a = MsiSetExternalUIA(NULL, 0, NULL);
5772     ok(ret_a == NULL, "expected NULL, got %p\n", ret_a);
5773
5774     ret_w = MsiSetExternalUIW(NULL, 0, NULL);
5775     ok(ret_w == NULL, "expected NULL, got %p\n", ret_w);
5776
5777     prev = (INSTALLUI_HANDLER_RECORD)0xdeadbeef;
5778     error = pMsiSetExternalUIRecord(NULL, 0, NULL, &prev);
5779     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
5780     ok(prev == handler_record, "expected %p, got %p\n", handler_record, prev);
5781
5782     error = pMsiSetExternalUIRecord(handler_record, INSTALLLOGMODE_ERROR, NULL, NULL);
5783     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
5784
5785     error = pMsiSetExternalUIRecord(NULL, 0, NULL, NULL);
5786     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
5787 }
5788
5789 static void test_feature_override(void)
5790 {
5791     UINT r;
5792     REGSAM access = KEY_ALL_ACCESS;
5793
5794     if (is_process_limited())
5795     {
5796         skip("process is limited\n");
5797         return;
5798     }
5799
5800     create_test_files();
5801     create_file("msitest\\override.txt", 1000);
5802     create_file("msitest\\preselected.txt", 1000);
5803     create_file("msitest\\notpreselected.txt", 1000);
5804     create_database(msifile, fo_tables, sizeof(fo_tables) / sizeof(msi_table));
5805
5806     if (is_wow64)
5807         access |= KEY_WOW64_64KEY;
5808
5809     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5810
5811     r = MsiInstallProductA(msifile, "ADDLOCAL=override");
5812     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
5813     {
5814         skip("Not enough rights to perform tests\n");
5815         goto error;
5816     }
5817     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5818
5819     ok(pf_exists("msitest\\override.txt"), "file not installed\n");
5820     ok(!pf_exists("msitest\\preselected.txt"), "file installed\n");
5821     ok(!pf_exists("msitest\\notpreselected.txt"), "file installed\n");
5822
5823     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5824     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5825
5826     ok(!delete_pf("msitest\\override.txt", TRUE), "file not removed\n");
5827
5828     r = MsiInstallProductA(msifile, "preselect=1");
5829     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5830
5831     ok(pf_exists("msitest\\override.txt"), "file not installed\n");
5832     ok(pf_exists("msitest\\preselected.txt"), "file not installed\n");
5833     ok(!pf_exists("msitest\\notpreselected.txt"), "file installed\n");
5834
5835     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5836     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5837
5838     ok(!delete_pf("msitest\\override.txt", TRUE), "file not removed\n");
5839     todo_wine {
5840     ok(delete_pf("msitest\\preselected.txt", TRUE), "file removed\n");
5841     ok(delete_pf("msitest", FALSE), "directory removed\n");
5842     }
5843
5844     r = MsiInstallProductA(msifile, NULL);
5845     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5846
5847     ok(pf_exists("msitest\\override.txt"), "file not installed\n");
5848     ok(pf_exists("msitest\\preselected.txt"), "file not installed\n");
5849     ok(!pf_exists("msitest\\notpreselected.txt"), "file installed\n");
5850
5851     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5852     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5853
5854     ok(!delete_pf("msitest\\override.txt", TRUE), "file not removed\n");
5855     todo_wine {
5856     ok(delete_pf("msitest\\preselected.txt", TRUE), "file removed\n");
5857     ok(delete_pf("msitest", FALSE), "directory removed\n");
5858     }
5859
5860     delete_key(HKEY_LOCAL_MACHINE, "Software\\Wine\\msitest", access);
5861
5862 error:
5863     DeleteFileA("msitest\\override.txt");
5864     DeleteFileA("msitest\\preselected.txt");
5865     DeleteFileA("msitest\\notpreselected.txt");
5866     delete_test_files();
5867     DeleteFile(msifile);
5868 }
5869
5870 static void test_icon_table(void)
5871 {
5872     MSIHANDLE hdb = 0, record;
5873     LPCSTR query;
5874     UINT res;
5875     CHAR path[MAX_PATH], win9xpath[MAX_PATH];
5876     static const char prodcode[] = "{7DF88A49-996F-4EC8-A022-BF956F9B2CBB}";
5877
5878     if (is_process_limited())
5879     {
5880         skip("process is limited\n");
5881         return;
5882     }
5883
5884     create_database(msifile, icon_base_tables, sizeof(icon_base_tables) / sizeof(msi_table));
5885
5886     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
5887
5888     res = MsiOpenDatabase(msifile, MSIDBOPEN_TRANSACT, &hdb);
5889     ok(res == ERROR_SUCCESS, "failed to open db: %d\n", res);
5890
5891     query = "CREATE TABLE `Icon` (`Name` CHAR(72) NOT NULL, `Data` OBJECT NOT NULL  PRIMARY KEY `Name`)";
5892     res = run_query( hdb, 0, query );
5893     ok(res == ERROR_SUCCESS, "Can't create Icon table: %d\n", res);
5894
5895     create_file("icon.ico", 100);
5896     record = MsiCreateRecord(1);
5897     res = MsiRecordSetStream(record, 1, "icon.ico");
5898     ok(res == ERROR_SUCCESS, "Failed to add stream data to record: %d\n", res);
5899
5900     query = "INSERT INTO `Icon` (`Name`, `Data`) VALUES ('testicon', ?)";
5901     res = run_query(hdb, record, query);
5902     ok(res == ERROR_SUCCESS, "Insert into Icon table failed: %d\n", res);
5903
5904     res = MsiCloseHandle(record);
5905     ok(res == ERROR_SUCCESS, "Failed to close record handle: %d\n", res);
5906     /* Delete the icon file after the handle is closed to make sure it's deleted on Win9x */
5907     DeleteFileA("icon.ico");
5908     res = MsiDatabaseCommit(hdb);
5909     ok(res == ERROR_SUCCESS, "Failed to commit database: %d\n", res);
5910     res = MsiCloseHandle(hdb);
5911     ok(res == ERROR_SUCCESS, "Failed to close database: %d\n", res);
5912
5913     /* per-user */
5914     res = MsiInstallProductA(msifile, "PUBLISH_PRODUCT=1");
5915     if (res == ERROR_INSTALL_PACKAGE_REJECTED)
5916     {
5917         skip("Not enough rights to perform tests\n");
5918         DeleteFile(msifile);
5919         return;
5920     }
5921     ok(res == ERROR_SUCCESS, "Failed to do per-user install: %d\n", res);
5922
5923     lstrcpyA(path, APP_DATA_DIR);
5924     lstrcatA(path, "\\");
5925     lstrcatA(path, "Microsoft\\Installer\\");
5926     lstrcatA(path, prodcode);
5927     lstrcatA(path, "\\testicon");
5928     ok(file_exists(path), "Per-user icon file isn't where it's expected (%s)\n", path);
5929
5930     res = MsiInstallProductA(msifile, "REMOVE=ALL");
5931     ok(res == ERROR_SUCCESS, "Failed to uninstall per-user\n");
5932
5933     /* system-wide */
5934     res = MsiInstallProductA(msifile, "PUBLISH_PRODUCT=1 ALLUSERS=1");
5935     ok(res == ERROR_SUCCESS, "Failed to system-wide install: %d\n", res);
5936
5937     /* win9x with MSI 2.0 installs the icon to a different folder, same as above */
5938     lstrcpyA(win9xpath, APP_DATA_DIR);
5939     lstrcatA(win9xpath, "\\");
5940     lstrcatA(win9xpath, "Microsoft\\Installer\\");
5941     lstrcatA(win9xpath, prodcode);
5942     lstrcatA(win9xpath, "\\testicon");
5943
5944     lstrcpyA(path, WINDOWS_DIR);
5945     lstrcatA(path, "\\");
5946     lstrcatA(path, "Installer\\");
5947     lstrcatA(path, prodcode);
5948     lstrcatA(path, "\\testicon");
5949     ok(file_exists(path) || file_exists(win9xpath),
5950             "System-wide icon file isn't where it's expected (%s)\n", path);
5951
5952     res = MsiInstallProductA(msifile, "REMOVE=ALL");
5953     ok(res == ERROR_SUCCESS, "Failed to uninstall system-wide\n");
5954
5955     delete_pfmsitest_files();
5956     DeleteFile(msifile);
5957 }
5958
5959 static void test_sourcedir_props(void)
5960 {
5961     UINT r;
5962
5963     if (on_win9x)
5964     {
5965         win_skip("skipping sourcedir tests on win9x\n");
5966         return;
5967     }
5968     if (is_process_limited())
5969     {
5970         skip("process is limited\n");
5971         return;
5972     }
5973
5974     create_test_files();
5975     create_file("msitest\\sourcedir.txt", 1000);
5976     create_database(msifile, sd_tables, sizeof(sd_tables) / sizeof(msi_table));
5977
5978     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
5979
5980     /* full UI, no ResolveSource action */
5981     r = MsiInstallProductA(msifile, NULL);
5982     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5983
5984     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5985     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5986
5987     ok(!delete_pf("msitest\\sourcedir.txt", TRUE), "file not removed\n");
5988     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
5989
5990     /* full UI, ResolveSource action */
5991     r = MsiInstallProductA(msifile, "ResolveSource=1");
5992     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5993
5994     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5995     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5996
5997     ok(!delete_pf("msitest\\sourcedir.txt", TRUE), "file not removed\n");
5998     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
5999
6000     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6001
6002     /* no UI, no ResolveSource action */
6003     r = MsiInstallProductA(msifile, NULL);
6004     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6005
6006     r = MsiInstallProductA(msifile, "REMOVE=ALL");
6007     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6008
6009     ok(!delete_pf("msitest\\sourcedir.txt", TRUE), "file not removed\n");
6010     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
6011
6012     /* no UI, ResolveSource action */
6013     r = MsiInstallProductA(msifile, "ResolveSource=1");
6014     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6015
6016     r = MsiInstallProductA(msifile, "REMOVE=ALL");
6017     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6018
6019     ok(!delete_pf("msitest\\sourcedir.txt", TRUE), "file not removed\n");
6020     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
6021
6022     DeleteFileA("msitest\\sourcedir.txt");
6023     DeleteFile(msifile);
6024 }
6025
6026 static void test_package_validation(void)
6027 {
6028     UINT r;
6029
6030     if (is_process_limited())
6031     {
6032         skip("process is limited\n");
6033         return;
6034     }
6035
6036     CreateDirectoryA("msitest", NULL);
6037     create_file("msitest\\maximus", 500);
6038     create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "Intel;1033");
6039
6040     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6041
6042     r = MsiInstallProductA(msifile, NULL);
6043     if (r == ERROR_INSTALL_PACKAGE_REJECTED)
6044     {
6045         skip("Not enough rights to perform tests\n");
6046         goto error;
6047     }
6048     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6049     ok(delete_pf("msitest\\maximus", TRUE), "file does not exist\n");
6050     ok(delete_pf("msitest", FALSE), "directory does not exist\n");
6051
6052     DeleteFile(msifile);
6053     create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "Intel;9999");
6054
6055     r = MsiInstallProductA(msifile, NULL);
6056     ok(r == ERROR_INSTALL_LANGUAGE_UNSUPPORTED, "Expected ERROR_INSTALL_LANGUAGE_UNSUPPORTED, got %u\n", r);
6057     ok(!delete_pf("msitest\\maximus", TRUE), "file exists\n");
6058     ok(!delete_pf("msitest", FALSE), "directory exists\n");
6059
6060     DeleteFile(msifile);
6061     create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "Intel32;0");
6062
6063     r = MsiInstallProductA(msifile, NULL);
6064     ok(r == ERROR_INSTALL_PLATFORM_UNSUPPORTED, "Expected ERROR_INSTALL_PLATFORM_UNSUPPORTED, got %u\n", r);
6065     ok(!delete_pf("msitest\\maximus", TRUE), "file exists\n");
6066     ok(!delete_pf("msitest", FALSE), "directory exists\n");
6067
6068     if (is_64bit && !is_wow64)
6069     {
6070         DeleteFile(msifile);
6071         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "Intel;0");
6072
6073         r = MsiInstallProductA(msifile, NULL);
6074         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6075         ok(delete_pf("msitest\\maximus", TRUE), "file does not exist\n");
6076         ok(delete_pf("msitest", FALSE), "directory does not exist\n");
6077
6078         DeleteFile(msifile);
6079         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "x64;0");
6080
6081         r = MsiInstallProductA(msifile, NULL);
6082         ok(r == ERROR_INSTALL_PACKAGE_INVALID, "Expected ERROR_INSTALL_PACKAGE_INVALID, got %u\n", r);
6083         ok(!delete_pf("msitest\\maximus", TRUE), "file exists\n");
6084         ok(!delete_pf("msitest", FALSE), "directory exists\n");
6085
6086         DeleteFile(msifile);
6087         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 200, "x64;0");
6088
6089         r = MsiInstallProductA(msifile, NULL);
6090         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6091         ok(delete_pf("msitest\\maximus", TRUE), "file does not exist\n");
6092         ok(delete_pf("msitest", FALSE), "directory does not exist\n");
6093     }
6094     else if (is_wow64)
6095     {
6096         DeleteFile(msifile);
6097         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "Intel;0");
6098
6099         r = MsiInstallProductA(msifile, NULL);
6100         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6101         ok(delete_pf("msitest\\maximus", TRUE), "file does not exist\n");
6102         ok(delete_pf("msitest", FALSE), "directory does not exist\n");
6103
6104         DeleteFile(msifile);
6105         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "x64;0");
6106
6107         r = MsiInstallProductA(msifile, NULL);
6108         ok(r == ERROR_INSTALL_PACKAGE_INVALID, "Expected ERROR_INSTALL_PACKAGE_INVALID, got %u\n", r);
6109         ok(!delete_pf_native("msitest\\maximus", TRUE), "file exists\n");
6110         ok(!delete_pf_native("msitest", FALSE), "directory exists\n");
6111
6112         DeleteFile(msifile);
6113         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 200, "x64;0");
6114
6115         r = MsiInstallProductA(msifile, NULL);
6116         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6117         ok(delete_pf_native("msitest\\maximus", TRUE), "file exists\n");
6118         ok(delete_pf_native("msitest", FALSE), "directory exists\n");
6119     }
6120     else
6121     {
6122         DeleteFile(msifile);
6123         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "Intel;0");
6124
6125         r = MsiInstallProductA(msifile, NULL);
6126         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6127         ok(delete_pf("msitest\\maximus", TRUE), "file does not exist\n");
6128         ok(delete_pf("msitest", FALSE), "directory does not exist\n");
6129
6130         DeleteFile(msifile);
6131         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 100, "x64;0");
6132
6133         r = MsiInstallProductA(msifile, NULL);
6134         ok(r == ERROR_INSTALL_PLATFORM_UNSUPPORTED, "Expected ERROR_INSTALL_PLATFORM_UNSUPPORTED, got %u\n", r);
6135         ok(!delete_pf("msitest\\maximus", TRUE), "file exists\n");
6136         ok(!delete_pf("msitest", FALSE), "directory exists\n");
6137
6138         DeleteFile(msifile);
6139         create_database_template(msifile, pv_tables, sizeof(pv_tables)/sizeof(msi_table), 200, "x64;0");
6140
6141         r = MsiInstallProductA(msifile, NULL);
6142         ok(r == ERROR_INSTALL_PLATFORM_UNSUPPORTED, "Expected ERROR_INSTALL_PLATFORM_UNSUPPORTED, got %u\n", r);
6143         ok(!delete_pf("msitest\\maximus", TRUE), "file exists\n");
6144         ok(!delete_pf("msitest", FALSE), "directory exists\n");
6145     }
6146
6147 error:
6148     /* Delete the files in the temp (current) folder */
6149     DeleteFile(msifile);
6150     DeleteFile("msitest\\maximus");
6151     RemoveDirectory("msitest");
6152 }
6153
6154 START_TEST(install)
6155 {
6156     DWORD len;
6157     char temp_path[MAX_PATH], prev_path[MAX_PATH], log_file[MAX_PATH];
6158     STATEMGRSTATUS status;
6159     BOOL ret = FALSE;
6160
6161     init_functionpointers();
6162
6163     on_win9x = check_win9x();
6164
6165     if (pIsWow64Process)
6166         pIsWow64Process(GetCurrentProcess(), &is_wow64);
6167
6168     GetCurrentDirectoryA(MAX_PATH, prev_path);
6169     GetTempPath(MAX_PATH, temp_path);
6170     SetCurrentDirectoryA(temp_path);
6171
6172     lstrcpyA(CURR_DIR, temp_path);
6173     len = lstrlenA(CURR_DIR);
6174
6175     if(len && (CURR_DIR[len - 1] == '\\'))
6176         CURR_DIR[len - 1] = 0;
6177
6178     get_system_dirs();
6179     get_user_dirs();
6180
6181     /* Create a restore point ourselves so we circumvent the multitude of restore points
6182      * that would have been created by all the installation and removal tests.
6183      *
6184      * This is not needed on version 5.0 where setting MSIFASTINSTALL prevents the
6185      * creation of restore points.
6186      */
6187     if (pSRSetRestorePointA && !pMsiGetComponentPathExA)
6188     {
6189         memset(&status, 0, sizeof(status));
6190         ret = notify_system_change(BEGIN_NESTED_SYSTEM_CHANGE, &status);
6191     }
6192
6193     /* Create only one log file and don't append. We have to pass something
6194      * for the log mode for this to work. The logfile needs to have an absolute
6195      * path otherwise we still end up with some extra logfiles as some tests
6196      * change the current directory.
6197      */
6198     lstrcpyA(log_file, temp_path);
6199     lstrcatA(log_file, "\\msitest.log");
6200     MsiEnableLogA(INSTALLLOGMODE_FATALEXIT, log_file, 0);
6201
6202     test_MsiInstallProduct();
6203     test_MsiSetComponentState();
6204     test_packagecoltypes();
6205     test_continuouscabs();
6206     test_caborder();
6207     test_mixedmedia();
6208     test_samesequence();
6209     test_uiLevelFlags();
6210     test_readonlyfile();
6211     test_readonlyfile_cab();
6212     test_setdirproperty();
6213     test_cabisextracted();
6214     test_concurrentinstall();
6215     test_setpropertyfolder();
6216     test_transformprop();
6217     test_currentworkingdir();
6218     test_admin();
6219     test_adminprops();
6220     test_missingcab();
6221     test_sourcefolder();
6222     test_customaction51();
6223     test_installstate();
6224     test_sourcepath();
6225     test_MsiConfigureProductEx();
6226     test_missingcomponent();
6227     test_sourcedirprop();
6228     test_adminimage();
6229     test_propcase();
6230     test_int_widths();
6231     test_shortcut();
6232     test_lastusedsource();
6233     test_preselected();
6234     test_installed_prop();
6235     test_file_in_use();
6236     test_file_in_use_cab();
6237     test_MsiSetExternalUI();
6238     test_allusers_prop();
6239     test_feature_override();
6240     test_icon_table();
6241     test_sourcedir_props();
6242     test_package_validation();
6243
6244     DeleteFileA(log_file);
6245
6246     if (pSRSetRestorePointA && !pMsiGetComponentPathExA && ret)
6247     {
6248         ret = notify_system_change(END_NESTED_SYSTEM_CHANGE, &status);
6249         if (ret)
6250             remove_restore_point(status.llSequenceNumber);
6251     }
6252     FreeLibrary(hsrclient);
6253
6254     SetCurrentDirectoryA(prev_path);
6255 }