msi: Add more tests for feature overrides.
[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
34 #include "wine/test.h"
35
36 static UINT (WINAPI *pMsiQueryComponentStateA)
37     (LPCSTR, LPCSTR, MSIINSTALLCONTEXT, LPCSTR, INSTALLSTATE*);
38 static UINT (WINAPI *pMsiSetExternalUIRecord)
39     (INSTALLUI_HANDLER_RECORD, DWORD, LPVOID, PINSTALLUI_HANDLER_RECORD);
40 static UINT (WINAPI *pMsiSourceListEnumSourcesA)
41     (LPCSTR, LPCSTR, MSIINSTALLCONTEXT, DWORD, DWORD, LPSTR, LPDWORD);
42 static UINT (WINAPI *pMsiSourceListGetInfoA)
43     (LPCSTR, LPCSTR, MSIINSTALLCONTEXT, DWORD, LPCSTR, LPSTR, LPDWORD);
44
45 static BOOL (WINAPI *pConvertSidToStringSidA)(PSID, LPSTR*);
46
47 static HMODULE hsrclient = 0;
48 static BOOL (WINAPI *pSRRemoveRestorePoint)(DWORD);
49 static BOOL (WINAPI *pSRSetRestorePointA)(RESTOREPOINTINFOA*, STATEMGRSTATUS*);
50
51 static BOOL on_win9x = FALSE;
52
53 static const char *msifile = "msitest.msi";
54 static const char *msifile2 = "winetest2.msi";
55 static const char *mstfile = "winetest.mst";
56 static CHAR CURR_DIR[MAX_PATH];
57 static CHAR PROG_FILES_DIR[MAX_PATH];
58 static CHAR COMMON_FILES_DIR[MAX_PATH];
59
60 /* msi database data */
61
62 static const CHAR component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
63                                     "s72\tS38\ts72\ti2\tS255\tS72\n"
64                                     "Component\tComponent\n"
65                                     "Five\t{8CC92E9D-14B2-4CA4-B2AA-B11D02078087}\tNEWDIR\t2\t\tfive.txt\n"
66                                     "Four\t{FD37B4EA-7209-45C0-8917-535F35A2F080}\tCABOUTDIR\t2\t\tfour.txt\n"
67                                     "One\t{783B242E-E185-4A56-AF86-C09815EC053C}\tMSITESTDIR\t2\tNOT REINSTALL\tone.txt\n"
68                                     "Three\t{010B6ADD-B27D-4EDD-9B3D-34C4F7D61684}\tCHANGEDDIR\t2\t\tthree.txt\n"
69                                     "Two\t{BF03D1A6-20DA-4A65-82F3-6CAC995915CE}\tFIRSTDIR\t2\t\ttwo.txt\n"
70                                     "dangler\t{6091DF25-EF96-45F1-B8E9-A9B1420C7A3C}\tTARGETDIR\t4\t\tregdata\n"
71                                     "component\t\tMSITESTDIR\t0\t1\tfile\n"
72                                     "service_comp\t\tMSITESTDIR\t0\t1\tservice_file";
73
74 static const CHAR directory_dat[] = "Directory\tDirectory_Parent\tDefaultDir\n"
75                                     "s72\tS72\tl255\n"
76                                     "Directory\tDirectory\n"
77                                     "CABOUTDIR\tMSITESTDIR\tcabout\n"
78                                     "CHANGEDDIR\tMSITESTDIR\tchanged:second\n"
79                                     "FIRSTDIR\tMSITESTDIR\tfirst\n"
80                                     "MSITESTDIR\tProgramFilesFolder\tmsitest\n"
81                                     "NEWDIR\tCABOUTDIR\tnew\n"
82                                     "ProgramFilesFolder\tTARGETDIR\t.\n"
83                                     "TARGETDIR\t\tSourceDir";
84
85 static const CHAR feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
86                                   "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
87                                   "Feature\tFeature\n"
88                                   "Five\t\tFive\tThe Five Feature\t5\t3\tNEWDIR\t0\n"
89                                   "Four\t\tFour\tThe Four Feature\t4\t3\tCABOUTDIR\t0\n"
90                                   "One\t\tOne\tThe One Feature\t1\t3\tMSITESTDIR\t0\n"
91                                   "Three\t\tThree\tThe Three Feature\t3\t3\tCHANGEDDIR\t0\n"
92                                   "Two\t\tTwo\tThe Two Feature\t2\t3\tFIRSTDIR\t0\n"
93                                   "feature\t\t\t\t2\t1\tTARGETDIR\t0\n"
94                                   "service_feature\t\t\t\t2\t1\tTARGETDIR\t0";
95
96 static const CHAR feature_comp_dat[] = "Feature_\tComponent_\n"
97                                        "s38\ts72\n"
98                                        "FeatureComponents\tFeature_\tComponent_\n"
99                                        "Five\tFive\n"
100                                        "Four\tFour\n"
101                                        "One\tOne\n"
102                                        "Three\tThree\n"
103                                        "Two\tTwo\n"
104                                        "feature\tcomponent\n"
105                                        "service_feature\tservice_comp\n";
106
107 static const CHAR file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
108                                "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
109                                "File\tFile\n"
110                                "five.txt\tFive\tfive.txt\t1000\t\t\t16384\t5\n"
111                                "four.txt\tFour\tfour.txt\t1000\t\t\t16384\t4\n"
112                                "one.txt\tOne\tone.txt\t1000\t\t\t0\t1\n"
113                                "three.txt\tThree\tthree.txt\t1000\t\t\t0\t3\n"
114                                "two.txt\tTwo\ttwo.txt\t1000\t\t\t0\t2\n"
115                                "file\tcomponent\tfilename\t100\t\t\t8192\t1\n"
116                                "service_file\tservice_comp\tservice.exe\t100\t\t\t8192\t1";
117
118 static const CHAR install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
119                                            "s72\tS255\tI2\n"
120                                            "InstallExecuteSequence\tAction\n"
121                                            "AllocateRegistrySpace\tNOT Installed\t1550\n"
122                                            "CostFinalize\t\t1000\n"
123                                            "CostInitialize\t\t800\n"
124                                            "FileCost\t\t900\n"
125                                            "ResolveSource\t\t950\n"
126                                            "MoveFiles\t\t1700\n"
127                                            "InstallFiles\t\t4000\n"
128                                            "DuplicateFiles\t\t4500\n"
129                                            "WriteEnvironmentStrings\t\t4550\n"
130                                            "CreateShortcuts\t\t4600\n"
131                                            "InstallServices\t\t5000\n"
132                                            "InstallFinalize\t\t6600\n"
133                                            "InstallInitialize\t\t1500\n"
134                                            "InstallValidate\t\t1400\n"
135                                            "LaunchConditions\t\t100\n"
136                                            "WriteRegistryValues\tSourceDir And SOURCEDIR\t5000";
137
138 static const CHAR media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
139                                 "i2\ti4\tL64\tS255\tS32\tS72\n"
140                                 "Media\tDiskId\n"
141                                 "1\t3\t\t\tDISK1\t\n"
142                                 "2\t5\t\tmsitest.cab\tDISK2\t\n";
143
144 static const CHAR property_dat[] = "Property\tValue\n"
145                                    "s72\tl0\n"
146                                    "Property\tProperty\n"
147                                    "DefaultUIFont\tDlgFont8\n"
148                                    "HASUIRUN\t0\n"
149                                    "INSTALLLEVEL\t3\n"
150                                    "InstallMode\tTypical\n"
151                                    "Manufacturer\tWine\n"
152                                    "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
153                                    "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
154                                    "ProductID\tnone\n"
155                                    "ProductLanguage\t1033\n"
156                                    "ProductName\tMSITEST\n"
157                                    "ProductVersion\t1.1.1\n"
158                                    "PROMPTROLLBACKCOST\tP\n"
159                                    "Setup\tSetup\n"
160                                    "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
161                                    "AdminProperties\tPOSTADMIN\n"
162                                    "ROOTDRIVE\tC:\\\n"
163                                    "SERVNAME\tTestService\n"
164                                    "SERVDISP\tTestServiceDisp\n";
165
166 static const CHAR aup_property_dat[] = "Property\tValue\n"
167                                        "s72\tl0\n"
168                                        "Property\tProperty\n"
169                                        "DefaultUIFont\tDlgFont8\n"
170                                        "HASUIRUN\t0\n"
171                                        "ALLUSERS\t1\n"
172                                        "INSTALLLEVEL\t3\n"
173                                        "InstallMode\tTypical\n"
174                                        "Manufacturer\tWine\n"
175                                        "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
176                                        "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
177                                        "ProductID\tnone\n"
178                                        "ProductLanguage\t1033\n"
179                                        "ProductName\tMSITEST\n"
180                                        "ProductVersion\t1.1.1\n"
181                                        "PROMPTROLLBACKCOST\tP\n"
182                                        "Setup\tSetup\n"
183                                        "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
184                                        "AdminProperties\tPOSTADMIN\n"
185                                        "ROOTDRIVE\tC:\\\n"
186                                        "SERVNAME\tTestService\n"
187                                        "SERVDISP\tTestServiceDisp\n";
188
189 static const CHAR aup2_property_dat[] = "Property\tValue\n"
190                                         "s72\tl0\n"
191                                         "Property\tProperty\n"
192                                         "DefaultUIFont\tDlgFont8\n"
193                                         "HASUIRUN\t0\n"
194                                         "ALLUSERS\t2\n"
195                                         "INSTALLLEVEL\t3\n"
196                                         "InstallMode\tTypical\n"
197                                         "Manufacturer\tWine\n"
198                                         "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
199                                         "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
200                                         "ProductID\tnone\n"
201                                         "ProductLanguage\t1033\n"
202                                         "ProductName\tMSITEST\n"
203                                         "ProductVersion\t1.1.1\n"
204                                         "PROMPTROLLBACKCOST\tP\n"
205                                         "Setup\tSetup\n"
206                                         "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
207                                         "AdminProperties\tPOSTADMIN\n"
208                                         "ROOTDRIVE\tC:\\\n"
209                                         "SERVNAME\tTestService\n"
210                                         "SERVDISP\tTestServiceDisp\n";
211
212 static const CHAR shortcut_dat[] = "Shortcut\tDirectory_\tName\tComponent_\tTarget\tArguments\tDescription\tHotkey\tIcon_\tIconIndex\tShowCmd\tWkDir\n"
213                                    "s72\ts72\tl128\ts72\ts72\tS255\tL255\tI2\tS72\tI2\tI2\tS72\n"
214                                    "Shortcut\tShortcut\n"
215                                    "Shortcut\tMSITESTDIR\tShortcut\tcomponent\tShortcut\t\tShortcut\t\t\t\t\t\n";
216
217 static const CHAR environment_dat[] = "Environment\tName\tValue\tComponent_\n"
218                                       "s72\tl255\tL255\ts72\n"
219                                       "Environment\tEnvironment\n"
220                                       "Var1\t=-MSITESTVAR1\t1\tOne\n"
221                                       "Var2\tMSITESTVAR2\t1\tOne\n"
222                                       "Var3\t=-MSITESTVAR3\t1\tOne\n"
223                                       "Var4\tMSITESTVAR4\t1\tOne\n"
224                                       "Var5\t-MSITESTVAR5\t\tOne\n"
225                                       "Var6\tMSITESTVAR6\t\tOne\n"
226                                       "Var7\t!-MSITESTVAR7\t\tOne\n"
227                                       "Var8\t!-*MSITESTVAR8\t\tOne\n"
228                                       "Var9\t=-MSITESTVAR9\t\tOne\n"
229                                       "Var10\t=MSITESTVAR10\t\tOne\n"
230                                       "Var11\t+-MSITESTVAR11\t[~];1\tOne\n"
231                                       "Var12\t+-MSITESTVAR11\t[~];2\tOne\n"
232                                       "Var13\t+-MSITESTVAR12\t[~];1\tOne\n"
233                                       "Var14\t=MSITESTVAR13\t[~];1\tOne\n"
234                                       "Var15\t=MSITESTVAR13\t[~];2\tOne\n"
235                                       "Var16\t=MSITESTVAR14\t;1;\tOne\n"
236                                       "Var17\t=MSITESTVAR15\t;;1;;\tOne\n"
237                                       "Var18\t=MSITESTVAR16\t 1 \tOne\n"
238                                       "Var19\t+-MSITESTVAR17\t1\tOne\n"
239                                       "Var20\t+-MSITESTVAR17\t;;2;;[~]\tOne\n"
240                                       "Var21\t+-MSITESTVAR18\t1\tOne\n"
241                                       "Var22\t+-MSITESTVAR18\t[~];;2;;\tOne\n"
242                                       "Var23\t+-MSITESTVAR19\t1\tOne\n"
243                                       "Var24\t+-MSITESTVAR19\t[~]2\tOne\n"
244                                       "Var25\t+-MSITESTVAR20\t1\tOne\n"
245                                       "Var26\t+-MSITESTVAR20\t2[~]\tOne\n";
246
247 /* Expected results, starting from MSITESTVAR11 onwards */
248 static const CHAR *environment_dat_results[] = {"1;2",    /*MSITESTVAR11*/
249                                                 "1",      /*MSITESTVAR12*/
250                                                 "1;2",    /*MSITESTVAR13*/
251                                                 ";1;",    /*MSITESTVAR14*/
252                                                 ";;1;;",  /*MSITESTVAR15*/
253                                                 " 1 ",    /*MSITESTVAR16*/
254                                                 ";;2;;1", /*MSITESTVAR17*/
255                                                 "1;;2;;", /*MSITESTVAR18*/
256                                                 "1",      /*MSITESTVAR19*/
257                                                 "1",      /*MSITESTVAR20*/
258                                                 NULL};
259
260 static const CHAR condition_dat[] = "Feature_\tLevel\tCondition\n"
261                                     "s38\ti2\tS255\n"
262                                     "Condition\tFeature_\tLevel\n"
263                                     "One\t4\t1\n";
264
265 static const CHAR up_property_dat[] = "Property\tValue\n"
266                                       "s72\tl0\n"
267                                       "Property\tProperty\n"
268                                       "DefaultUIFont\tDlgFont8\n"
269                                       "HASUIRUN\t0\n"
270                                       "INSTALLLEVEL\t3\n"
271                                       "InstallMode\tTypical\n"
272                                       "Manufacturer\tWine\n"
273                                       "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
274                                       "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
275                                       "ProductID\tnone\n"
276                                       "ProductLanguage\t1033\n"
277                                       "ProductName\tMSITEST\n"
278                                       "ProductVersion\t1.1.1\n"
279                                       "PROMPTROLLBACKCOST\tP\n"
280                                       "Setup\tSetup\n"
281                                       "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
282                                       "AdminProperties\tPOSTADMIN\n"
283                                       "ROOTDRIVE\tC:\\\n"
284                                       "SERVNAME\tTestService\n"
285                                       "SERVDISP\tTestServiceDisp\n"
286                                       "RemovePreviousVersions\t1\n";
287
288 static const CHAR up2_property_dat[] = "Property\tValue\n"
289                                        "s72\tl0\n"
290                                        "Property\tProperty\n"
291                                        "DefaultUIFont\tDlgFont8\n"
292                                        "HASUIRUN\t0\n"
293                                        "INSTALLLEVEL\t3\n"
294                                        "InstallMode\tTypical\n"
295                                        "Manufacturer\tWine\n"
296                                        "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
297                                        "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
298                                        "ProductID\tnone\n"
299                                        "ProductLanguage\t1033\n"
300                                        "ProductName\tMSITEST\n"
301                                        "ProductVersion\t1.1.2\n"
302                                        "PROMPTROLLBACKCOST\tP\n"
303                                        "Setup\tSetup\n"
304                                        "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
305                                        "AdminProperties\tPOSTADMIN\n"
306                                        "ROOTDRIVE\tC:\\\n"
307                                        "SERVNAME\tTestService\n"
308                                        "SERVDISP\tTestServiceDisp\n";
309
310 static const CHAR up3_property_dat[] = "Property\tValue\n"
311                                        "s72\tl0\n"
312                                        "Property\tProperty\n"
313                                        "DefaultUIFont\tDlgFont8\n"
314                                        "HASUIRUN\t0\n"
315                                        "INSTALLLEVEL\t3\n"
316                                        "InstallMode\tTypical\n"
317                                        "Manufacturer\tWine\n"
318                                        "PIDTemplate\t12345<###-%%%%%%%>@@@@@\n"
319                                        "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
320                                        "ProductID\tnone\n"
321                                        "ProductLanguage\t1033\n"
322                                        "ProductName\tMSITEST\n"
323                                        "ProductVersion\t1.1.2\n"
324                                        "PROMPTROLLBACKCOST\tP\n"
325                                        "Setup\tSetup\n"
326                                        "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n"
327                                        "AdminProperties\tPOSTADMIN\n"
328                                        "ROOTDRIVE\tC:\\\n"
329                                        "SERVNAME\tTestService\n"
330                                        "SERVDISP\tTestServiceDisp\n"
331                                        "RemovePreviousVersions\t1\n";
332
333 static const CHAR registry_dat[] = "Registry\tRoot\tKey\tName\tValue\tComponent_\n"
334                                    "s72\ti2\tl255\tL255\tL0\ts72\n"
335                                    "Registry\tRegistry\n"
336                                    "Apples\t2\tSOFTWARE\\Wine\\msitest\tName\timaname\tOne\n"
337                                    "Oranges\t2\tSOFTWARE\\Wine\\msitest\tnumber\t#314\tTwo\n"
338                                    "regdata\t2\tSOFTWARE\\Wine\\msitest\tblah\tbad\tdangler\n"
339                                    "OrderTest\t2\tSOFTWARE\\Wine\\msitest\tOrderTestName\tOrderTestValue\tcomponent";
340
341 static const CHAR service_install_dat[] = "ServiceInstall\tName\tDisplayName\tServiceType\tStartType\tErrorControl\t"
342                                           "LoadOrderGroup\tDependencies\tStartName\tPassword\tArguments\tComponent_\tDescription\n"
343                                           "s72\ts255\tL255\ti4\ti4\ti4\tS255\tS255\tS255\tS255\tS255\ts72\tL255\n"
344                                           "ServiceInstall\tServiceInstall\n"
345                                           "TestService\t[SERVNAME]\t[SERVDISP]\t2\t3\t0\t\t\tTestService\t\t\tservice_comp\t\t";
346
347 static const CHAR service_control_dat[] = "ServiceControl\tName\tEvent\tArguments\tWait\tComponent_\n"
348                                           "s72\tl255\ti2\tL255\tI2\ts72\n"
349                                           "ServiceControl\tServiceControl\n"
350                                           "ServiceControl\tTestService\t8\t\t0\tservice_comp";
351
352 static const CHAR sss_service_control_dat[] = "ServiceControl\tName\tEvent\tArguments\tWait\tComponent_\n"
353                                               "s72\tl255\ti2\tL255\tI2\ts72\n"
354                                               "ServiceControl\tServiceControl\n"
355                                               "ServiceControl\tSpooler\t1\t\t0\tservice_comp";
356
357 static const CHAR sss_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
358                                                "s72\tS255\tI2\n"
359                                                "InstallExecuteSequence\tAction\n"
360                                                "CostFinalize\t\t1000\n"
361                                                "CostInitialize\t\t800\n"
362                                                "FileCost\t\t900\n"
363                                                "ResolveSource\t\t950\n"
364                                                "MoveFiles\t\t1700\n"
365                                                "InstallFiles\t\t4000\n"
366                                                "DuplicateFiles\t\t4500\n"
367                                                "WriteEnvironmentStrings\t\t4550\n"
368                                                "CreateShortcuts\t\t4600\n"
369                                                "StartServices\t\t5000\n"
370                                                "DeleteServices\t\t5500\n"
371                                                "InstallFinalize\t\t6600\n"
372                                                "InstallInitialize\t\t1500\n"
373                                                "InstallValidate\t\t1400\n"
374                                                "LaunchConditions\t\t100\n";
375
376 /* tables for test_continuouscabs */
377 static const CHAR cc_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
378                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
379                                        "Component\tComponent\n"
380                                        "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n"
381                                        "augustus\t\tMSITESTDIR\t0\t1\taugustus\n"
382                                        "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n";
383
384 static const CHAR cc2_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
385                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
386                                         "Component\tComponent\n"
387                                         "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n"
388                                         "augustus\t\tMSITESTDIR\t0\t0\taugustus\n"
389                                         "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n";
390
391 static const CHAR cc_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
392                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
393                                      "Feature\tFeature\n"
394                                      "feature\t\t\t\t2\t1\tTARGETDIR\t0";
395
396 static const CHAR cc_feature_comp_dat[] = "Feature_\tComponent_\n"
397                                           "s38\ts72\n"
398                                           "FeatureComponents\tFeature_\tComponent_\n"
399                                           "feature\tmaximus\n"
400                                           "feature\taugustus\n"
401                                           "feature\tcaesar";
402
403 static const CHAR cc_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
404                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
405                                   "File\tFile\n"
406                                   "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
407                                   "augustus\taugustus\taugustus\t50000\t\t\t16384\t2\n"
408                                   "caesar\tcaesar\tcaesar\t500\t\t\t16384\t12";
409
410 static const CHAR cc2_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
411                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
412                                    "File\tFile\n"
413                                    "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
414                                    "augustus\taugustus\taugustus\t50000\t\t\t16384\t2\n"
415                                    "tiberius\tmaximus\ttiberius\t500\t\t\t16384\t3\n"
416                                    "caesar\tcaesar\tcaesar\t500\t\t\t16384\t12";
417
418 static const CHAR cc_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
419                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
420                                    "Media\tDiskId\n"
421                                    "1\t10\t\ttest1.cab\tDISK1\t\n"
422                                    "2\t2\t\ttest2.cab\tDISK2\t\n"
423                                    "3\t12\t\ttest3.cab\tDISK3\t\n";
424
425 static const CHAR co_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
426                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
427                                   "File\tFile\n"
428                                   "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
429                                   "augustus\taugustus\taugustus\t50000\t\t\t16384\t2\n"
430                                   "caesar\tcaesar\tcaesar\t500\t\t\t16384\t3";
431
432 static const CHAR co_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
433                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
434                                    "Media\tDiskId\n"
435                                    "1\t10\t\ttest1.cab\tDISK1\t\n"
436                                    "2\t2\t\ttest2.cab\tDISK2\t\n"
437                                    "3\t3\t\ttest3.cab\tDISK3\t\n";
438
439 static const CHAR co2_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
440                                     "i2\ti4\tL64\tS255\tS32\tS72\n"
441                                     "Media\tDiskId\n"
442                                     "1\t10\t\ttest1.cab\tDISK1\t\n"
443                                     "2\t12\t\ttest3.cab\tDISK3\t\n"
444                                     "3\t2\t\ttest2.cab\tDISK2\t\n";
445
446 static const CHAR mm_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
447                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
448                                   "File\tFile\n"
449                                   "maximus\tmaximus\tmaximus\t500\t\t\t512\t1\n"
450                                   "augustus\taugustus\taugustus\t500\t\t\t512\t2\n"
451                                   "caesar\tcaesar\tcaesar\t500\t\t\t16384\t3";
452
453 static const CHAR mm_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
454                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
455                                    "Media\tDiskId\n"
456                                    "1\t3\t\ttest1.cab\tDISK1\t\n";
457
458 static const CHAR ss_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
459                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
460                                    "Media\tDiskId\n"
461                                    "1\t2\t\ttest1.cab\tDISK1\t\n"
462                                    "2\t2\t\ttest2.cab\tDISK2\t\n"
463                                    "3\t12\t\ttest3.cab\tDISK3\t\n";
464
465 /* tables for test_uiLevelFlags */
466 static const CHAR ui_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
467                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
468                                        "Component\tComponent\n"
469                                        "maximus\t\tMSITESTDIR\t0\tHASUIRUN=1\tmaximus\n"
470                                        "augustus\t\tMSITESTDIR\t0\t1\taugustus\n"
471                                        "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n";
472
473 static const CHAR ui_install_ui_seq_dat[] = "Action\tCondition\tSequence\n"
474                                            "s72\tS255\tI2\n"
475                                            "InstallUISequence\tAction\n"
476                                            "SetUIProperty\t\t5\n"
477                                            "ExecuteAction\t\t1100\n";
478
479 static const CHAR ui_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
480                                            "s72\ti2\tS64\tS0\tS255\n"
481                                            "CustomAction\tAction\n"
482                                            "SetUIProperty\t51\tHASUIRUN\t1\t\n";
483
484 static const CHAR rof_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
485                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
486                                         "Component\tComponent\n"
487                                         "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n";
488
489 static const CHAR rof_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
490                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
491                                       "Feature\tFeature\n"
492                                       "feature\t\tFeature\tFeature\t2\t1\tTARGETDIR\t0\n"
493                                       "montecristo\t\tFeature\tFeature\t2\t1\tTARGETDIR\t0";
494
495 static const CHAR rof_feature_comp_dat[] = "Feature_\tComponent_\n"
496                                            "s38\ts72\n"
497                                            "FeatureComponents\tFeature_\tComponent_\n"
498                                            "feature\tmaximus\n"
499                                            "montecristo\tmaximus";
500
501 static const CHAR rof_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
502                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
503                                    "File\tFile\n"
504                                    "maximus\tmaximus\tmaximus\t500\t\t\t8192\t1";
505
506 static const CHAR rof_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
507                                     "i2\ti4\tL64\tS255\tS32\tS72\n"
508                                     "Media\tDiskId\n"
509                                     "1\t1\t\t\tDISK1\t\n";
510
511 static const CHAR rofc_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
512                                     "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
513                                     "File\tFile\n"
514                                     "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1";
515
516 static const CHAR rofc_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
517                                      "i2\ti4\tL64\tS255\tS32\tS72\n"
518                                      "Media\tDiskId\n"
519                                      "1\t1\t\ttest1.cab\tDISK1\t\n";
520
521 static const CHAR lus2_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
522                                      "i2\ti4\tL64\tS255\tS32\tS72\n"
523                                      "Media\tDiskId\n"
524                                      "1\t1\t\t#test1.cab\tDISK1\t\n";
525
526 static const CHAR sdp_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
527                                                "s72\tS255\tI2\n"
528                                                "InstallExecuteSequence\tAction\n"
529                                                "AllocateRegistrySpace\tNOT Installed\t1550\n"
530                                                "CostFinalize\t\t1000\n"
531                                                "CostInitialize\t\t800\n"
532                                                "FileCost\t\t900\n"
533                                                "InstallFiles\t\t4000\n"
534                                                "InstallFinalize\t\t6600\n"
535                                                "InstallInitialize\t\t1500\n"
536                                                "InstallValidate\t\t1400\n"
537                                                "LaunchConditions\t\t100\n"
538                                                "SetDirProperty\t\t950";
539
540 static const CHAR sdp_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
541                                             "s72\ti2\tS64\tS0\tS255\n"
542                                             "CustomAction\tAction\n"
543                                             "SetDirProperty\t51\tMSITESTDIR\t[CommonFilesFolder]msitest\\\t\n";
544
545 static const CHAR cie_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
546                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
547                                         "Component\tComponent\n"
548                                         "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n"
549                                         "augustus\t\tMSITESTDIR\t0\t1\taugustus\n"
550                                         "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n"
551                                         "gaius\t\tMSITESTDIR\t0\t1\tgaius\n";
552
553 static const CHAR cie_feature_comp_dat[] = "Feature_\tComponent_\n"
554                                            "s38\ts72\n"
555                                            "FeatureComponents\tFeature_\tComponent_\n"
556                                            "feature\tmaximus\n"
557                                            "feature\taugustus\n"
558                                            "feature\tcaesar\n"
559                                            "feature\tgaius";
560
561 static const CHAR cie_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
562                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
563                                    "File\tFile\n"
564                                    "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
565                                    "augustus\taugustus\taugustus\t50000\t\t\t16384\t2\n"
566                                    "caesar\tcaesar\tcaesar\t500\t\t\t16384\t12\n"
567                                    "gaius\tgaius\tgaius\t500\t\t\t8192\t11";
568
569 static const CHAR cie_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
570                                     "i2\ti4\tL64\tS255\tS32\tS72\n"
571                                     "Media\tDiskId\n"
572                                     "1\t1\t\ttest1.cab\tDISK1\t\n"
573                                     "2\t2\t\ttest2.cab\tDISK2\t\n"
574                                     "3\t12\t\ttest3.cab\tDISK3\t\n";
575
576 static const CHAR ci_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
577                                               "s72\tS255\tI2\n"
578                                               "InstallExecuteSequence\tAction\n"
579                                               "CostFinalize\t\t1000\n"
580                                               "CostInitialize\t\t800\n"
581                                               "FileCost\t\t900\n"
582                                               "InstallFiles\t\t4000\n"
583                                               "InstallServices\t\t5000\n"
584                                               "InstallFinalize\t\t6600\n"
585                                               "InstallInitialize\t\t1500\n"
586                                               "RunInstall\t\t1600\n"
587                                               "InstallValidate\t\t1400\n"
588                                               "LaunchConditions\t\t100";
589
590 static const CHAR ci_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
591                                             "s72\ti2\tS64\tS0\tS255\n"
592                                             "CustomAction\tAction\n"
593                                             "RunInstall\t87\tmsitest\\concurrent.msi\tMYPROP=[UILevel]\t\n";
594
595 static const CHAR ci_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
596                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
597                                        "Component\tComponent\n"
598                                        "maximus\t{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}\tMSITESTDIR\t0\tUILevel=5\tmaximus\n";
599
600 static const CHAR ci2_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
601                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
602                                         "Component\tComponent\n"
603                                         "augustus\t\tMSITESTDIR\t0\tUILevel=3 AND MYPROP=5\taugustus\n";
604
605 static const CHAR ci2_feature_comp_dat[] = "Feature_\tComponent_\n"
606                                            "s38\ts72\n"
607                                            "FeatureComponents\tFeature_\tComponent_\n"
608                                            "feature\taugustus";
609
610 static const CHAR ci2_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
611                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
612                                    "File\tFile\n"
613                                    "augustus\taugustus\taugustus\t500\t\t\t8192\t1";
614
615 static const CHAR spf_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
616                                             "s72\ti2\tS64\tS0\tS255\n"
617                                             "CustomAction\tAction\n"
618                                             "SetFolderProp\t51\tMSITESTDIR\t[ProgramFilesFolder]\\msitest\\added\t\n";
619
620 static const CHAR spf_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
621                                                "s72\tS255\tI2\n"
622                                                "InstallExecuteSequence\tAction\n"
623                                                "CostFinalize\t\t1000\n"
624                                                "CostInitialize\t\t800\n"
625                                                "FileCost\t\t900\n"
626                                                "SetFolderProp\t\t950\n"
627                                                "InstallFiles\t\t4000\n"
628                                                "InstallServices\t\t5000\n"
629                                                "InstallFinalize\t\t6600\n"
630                                                "InstallInitialize\t\t1500\n"
631                                                "InstallValidate\t\t1400\n"
632                                                "LaunchConditions\t\t100";
633
634 static const CHAR spf_install_ui_seq_dat[] = "Action\tCondition\tSequence\n"
635                                              "s72\tS255\tI2\n"
636                                              "InstallUISequence\tAction\n"
637                                              "CostInitialize\t\t800\n"
638                                              "FileCost\t\t900\n"
639                                              "CostFinalize\t\t1000\n"
640                                              "ExecuteAction\t\t1100\n";
641
642 static const CHAR pp_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
643                                               "s72\tS255\tI2\n"
644                                               "InstallExecuteSequence\tAction\n"
645                                               "ValidateProductID\t\t700\n"
646                                               "CostInitialize\t\t800\n"
647                                               "FileCost\t\t900\n"
648                                               "CostFinalize\t\t1000\n"
649                                               "InstallValidate\t\t1400\n"
650                                               "InstallInitialize\t\t1500\n"
651                                               "ProcessComponents\tPROCESS_COMPONENTS=1 Or FULL=1\t1600\n"
652                                               "UnpublishFeatures\tUNPUBLISH_FEATURES=1 Or FULL=1\t1800\n"
653                                               "RemoveFiles\t\t3500\n"
654                                               "InstallFiles\t\t4000\n"
655                                               "RegisterUser\tREGISTER_USER=1 Or FULL=1\t6000\n"
656                                               "RegisterProduct\tREGISTER_PRODUCT=1 Or FULL=1\t6100\n"
657                                               "PublishFeatures\tPUBLISH_FEATURES=1 Or FULL=1\t6300\n"
658                                               "PublishProduct\tPUBLISH_PRODUCT=1 Or FULL=1\t6400\n"
659                                               "InstallFinalize\t\t6600";
660
661 static const CHAR ppc_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
662                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
663                                         "Component\tComponent\n"
664                                         "maximus\t{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}\tMSITESTDIR\t0\tUILevel=5\tmaximus\n"
665                                         "augustus\t{5AD3C142-CEF8-490D-B569-784D80670685}\tMSITESTDIR\t1\t\taugustus\n";
666
667 static const CHAR ppc_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
668                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
669                                    "File\tFile\n"
670                                    "maximus\tmaximus\tmaximus\t500\t\t\t8192\t1\n"
671                                    "augustus\taugustus\taugustus\t500\t\t\t8192\t2";
672
673 static const CHAR ppc_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
674                                     "i2\ti4\tL64\tS255\tS32\tS72\n"
675                                     "Media\tDiskId\n"
676                                     "1\t2\t\t\tDISK1\t\n";
677
678 static const CHAR ppc_feature_comp_dat[] = "Feature_\tComponent_\n"
679                                            "s38\ts72\n"
680                                            "FeatureComponents\tFeature_\tComponent_\n"
681                                            "feature\tmaximus\n"
682                                            "feature\taugustus\n"
683                                            "montecristo\tmaximus";
684
685 static const CHAR tp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
686                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
687                                        "Component\tComponent\n"
688                                        "augustus\t\tMSITESTDIR\t0\tprop=\"val\"\taugustus\n";
689
690 static const CHAR cwd_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
691                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
692                                         "Component\tComponent\n"
693                                         "augustus\t\tMSITESTDIR\t0\t\taugustus\n";
694
695 static const CHAR adm_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
696                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
697                                         "Component\tComponent\n"
698                                         "augustus\t\tMSITESTDIR\t0\tPOSTADMIN=1\taugustus";
699
700 static const CHAR adm_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
701                                             "s72\ti2\tS64\tS0\tS255\n"
702                                             "CustomAction\tAction\n"
703                                             "SetPOSTADMIN\t51\tPOSTADMIN\t1\t\n";
704
705 static const CHAR adm_admin_exec_seq_dat[] = "Action\tCondition\tSequence\n"
706                                              "s72\tS255\tI2\n"
707                                              "AdminExecuteSequence\tAction\n"
708                                              "CostFinalize\t\t1000\n"
709                                              "CostInitialize\t\t800\n"
710                                              "FileCost\t\t900\n"
711                                              "SetPOSTADMIN\t\t950\n"
712                                              "InstallFiles\t\t4000\n"
713                                              "InstallFinalize\t\t6600\n"
714                                              "InstallInitialize\t\t1500\n"
715                                              "InstallValidate\t\t1400\n"
716                                              "LaunchConditions\t\t100";
717
718 static const CHAR amp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
719                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
720                                         "Component\tComponent\n"
721                                         "augustus\t\tMSITESTDIR\t0\tMYPROP=2718 and MyProp=42\taugustus\n";
722
723 static const CHAR rem_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
724                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
725                                         "Component\tComponent\n"
726                                         "hydrogen\t{C844BD1E-1907-4C00-8BC9-150BD70DF0A1}\tMSITESTDIR\t0\t\thydrogen\n"
727                                         "helium\t{5AD3C142-CEF8-490D-B569-784D80670685}\tMSITESTDIR\t1\t\thelium\n"
728                                         "lithium\t\tMSITESTDIR\t2\t\tlithium\n";
729
730 static const CHAR rem_feature_comp_dat[] = "Feature_\tComponent_\n"
731                                            "s38\ts72\n"
732                                            "FeatureComponents\tFeature_\tComponent_\n"
733                                            "feature\thydrogen\n"
734                                            "feature\thelium\n"
735                                            "feature\tlithium";
736
737 static const CHAR rem_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
738                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
739                                    "File\tFile\n"
740                                    "hydrogen\thydrogen\thydrogen\t0\t\t\t8192\t1\n"
741                                    "helium\thelium\thelium\t0\t\t\t8192\t1\n"
742                                    "lithium\tlithium\tlithium\t0\t\t\t8192\t1";
743
744 static const CHAR rem_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
745                                                "s72\tS255\tI2\n"
746                                                "InstallExecuteSequence\tAction\n"
747                                                "ValidateProductID\t\t700\n"
748                                                "CostInitialize\t\t800\n"
749                                                "FileCost\t\t900\n"
750                                                "CostFinalize\t\t1000\n"
751                                                "InstallValidate\t\t1400\n"
752                                                "InstallInitialize\t\t1500\n"
753                                                "ProcessComponents\t\t1600\n"
754                                                "UnpublishFeatures\t\t1800\n"
755                                                "RemoveFiles\t\t3500\n"
756                                                "InstallFiles\t\t4000\n"
757                                                "RegisterProduct\t\t6100\n"
758                                                "PublishFeatures\t\t6300\n"
759                                                "PublishProduct\t\t6400\n"
760                                                "InstallFinalize\t\t6600";
761
762 static const CHAR rem_remove_files_dat[] = "FileKey\tComponent_\tFileName\tDirProperty\tInstallMode\n"
763                                            "s72\ts72\tS255\ts72\tI2\n"
764                                            "RemoveFile\tFileKey\n"
765                                            "furlong\thydrogen\tfurlong\tMSITESTDIR\t1\n"
766                                            "firkin\thelium\tfirkin\tMSITESTDIR\t1\n"
767                                            "fortnight\tlithium\tfortnight\tMSITESTDIR\t1\n"
768                                            "becquerel\thydrogen\tbecquerel\tMSITESTDIR\t2\n"
769                                            "dioptre\thelium\tdioptre\tMSITESTDIR\t2\n"
770                                            "attoparsec\tlithium\tattoparsec\tMSITESTDIR\t2\n"
771                                            "storeys\thydrogen\tstoreys\tMSITESTDIR\t3\n"
772                                            "block\thelium\tblock\tMSITESTDIR\t3\n"
773                                            "siriometer\tlithium\tsiriometer\tMSITESTDIR\t3\n"
774                                            "nanoacre\thydrogen\t\tCABOUTDIR\t3\n";
775
776 static const CHAR mov_move_file_dat[] = "FileKey\tComponent_\tSourceName\tDestName\tSourceFolder\tDestFolder\tOptions\n"
777                                         "s72\ts72\tS255\tS255\tS72\ts72\ti2\n"
778                                         "MoveFile\tFileKey\n"
779                                         "abkhazia\taugustus\tnonexistent\tdest\tSourceDir\tMSITESTDIR\t0\n"
780                                         "bahamas\taugustus\tnonexistent\tdest\tSourceDir\tMSITESTDIR\t1\n"
781                                         "cambodia\taugustus\tcameroon\tcanada\tSourceDir\tMSITESTDIR\t0\n"
782                                         "denmark\taugustus\tdjibouti\tdominica\tSourceDir\tMSITESTDIR\t1\n"
783                                         "ecuador\taugustus\tegypt\telsalvador\tNotAProp\tMSITESTDIR\t1\n"
784                                         "fiji\taugustus\tfinland\tfrance\tSourceDir\tNotAProp\t1\n"
785                                         "gabon\taugustus\tgambia\tgeorgia\tSOURCEFULL\tMSITESTDIR\t1\n"
786                                         "haiti\taugustus\thonduras\thungary\tSourceDir\tDESTFULL\t1\n"
787                                         "iceland\taugustus\tindia\tindonesia\tMSITESTDIR\tMSITESTDIR\t1\n"
788                                         "jamaica\taugustus\tjapan\tjordan\tFILEPATHBAD\tMSITESTDIR\t1\n"
789                                         "kazakhstan\taugustus\t\tkiribati\tFILEPATHGOOD\tMSITESTDIR\t1\n"
790                                         "laos\taugustus\tlatvia\tlebanon\tSourceDir\tMSITESTDIR\t1\n"
791                                         "namibia\taugustus\tnauru\tkiribati\tSourceDir\tMSITESTDIR\t1\n"
792                                         "pakistan\taugustus\tperu\tsfn|poland\tSourceDir\tMSITESTDIR\t1\n"
793                                         "wildcard\taugustus\tapp*\twildcard\tSourceDir\tMSITESTDIR\t1\n"
794                                         "single\taugustus\tf?o\tsingle\tSourceDir\tMSITESTDIR\t1\n"
795                                         "wildcardnodest\taugustus\tbudd*\t\tSourceDir\tMSITESTDIR\t1\n"
796                                         "singlenodest\taugustus\tb?r\t\tSourceDir\tMSITESTDIR\t1\n";
797
798 static const CHAR mc_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
799                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
800                                         "Component\tComponent\n"
801                                         "maximus\t\tMSITESTDIR\t0\t1\tmaximus\n"
802                                         "augustus\t\tMSITESTDIR\t0\t1\taugustus\n"
803                                         "caesar\t\tMSITESTDIR\t0\t1\tcaesar\n"
804                                         "gaius\t\tMSITESTDIR\t0\tGAIUS=1\tgaius\n";
805
806 static const CHAR mc_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
807                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
808                                   "File\tFile\n"
809                                   "maximus\tmaximus\tmaximus\t500\t\t\t16384\t1\n"
810                                   "augustus\taugustus\taugustus\t500\t\t\t0\t2\n"
811                                   "caesar\tcaesar\tcaesar\t500\t\t\t16384\t3\n"
812                                   "gaius\tgaius\tgaius\t500\t\t\t16384\t4";
813
814 static const CHAR mc_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
815                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
816                                    "Media\tDiskId\n"
817                                    "1\t1\t\ttest1.cab\tDISK1\t\n"
818                                    "2\t2\t\ttest2.cab\tDISK2\t\n"
819                                    "3\t3\t\ttest3.cab\tDISK3\t\n"
820                                    "4\t4\t\ttest3.cab\tDISK3\t\n";
821
822 static const CHAR mc_file_hash_dat[] = "File_\tOptions\tHashPart1\tHashPart2\tHashPart3\tHashPart4\n"
823                                        "s72\ti2\ti4\ti4\ti4\ti4\n"
824                                        "MsiFileHash\tFile_\n"
825                                        "caesar\t0\t850433704\t-241429251\t675791761\t-1221108824";
826
827 static const CHAR df_directory_dat[] = "Directory\tDirectory_Parent\tDefaultDir\n"
828                                        "s72\tS72\tl255\n"
829                                        "Directory\tDirectory\n"
830                                        "THIS\tMSITESTDIR\tthis\n"
831                                        "DOESNOT\tTHIS\tdoesnot\n"
832                                        "NONEXISTENT\tDOESNOT\texist\n"
833                                        "MSITESTDIR\tProgramFilesFolder\tmsitest\n"
834                                        "ProgramFilesFolder\tTARGETDIR\t.\n"
835                                        "TARGETDIR\t\tSourceDir";
836
837 static const CHAR df_duplicate_file_dat[] = "FileKey\tComponent_\tFile_\tDestName\tDestFolder\n"
838                                             "s72\ts72\ts72\tS255\tS72\n"
839                                             "DuplicateFile\tFileKey\n"
840                                             "maximus\tmaximus\tmaximus\taugustus\t\n"
841                                             "caesar\tmaximus\tmaximus\t\tNONEXISTENT\n"
842                                             "augustus\tnosuchcomponent\tmaximus\t\tMSITESTDIR\n";
843
844 static const CHAR wrv_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
845                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
846                                         "Component\tComponent\n"
847                                         "augustus\t\tMSITESTDIR\t0\t\taugustus\n";
848
849 static const CHAR wrv_registry_dat[] = "Registry\tRoot\tKey\tName\tValue\tComponent_\n"
850                                        "s72\ti2\tl255\tL255\tL0\ts72\n"
851                                        "Registry\tRegistry\n"
852                                        "regdata\t2\tSOFTWARE\\Wine\\msitest\tValue\t[~]one[~]two[~]three\taugustus";
853
854 static const CHAR ca51_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
855                                          "s72\tS38\ts72\ti2\tS255\tS72\n"
856                                          "Component\tComponent\n"
857                                          "augustus\t\tMSITESTDIR\t0\tMYPROP=42\taugustus\n";
858
859 static const CHAR ca51_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
860                                                 "s72\tS255\tI2\n"
861                                                 "InstallExecuteSequence\tAction\n"
862                                                 "ValidateProductID\t\t700\n"
863                                                 "GoodSetProperty\t\t725\n"
864                                                 "BadSetProperty\t\t750\n"
865                                                 "CostInitialize\t\t800\n"
866                                                 "ResolveSource\t\t810\n"
867                                                 "FileCost\t\t900\n"
868                                                 "SetSourceDir\tSRCDIR\t910\n"
869                                                 "CostFinalize\t\t1000\n"
870                                                 "InstallValidate\t\t1400\n"
871                                                 "InstallInitialize\t\t1500\n"
872                                                 "InstallFiles\t\t4000\n"
873                                                 "InstallFinalize\t\t6600";
874
875 static const CHAR ca51_custom_action_dat[] = "Action\tType\tSource\tTarget\n"
876                                              "s72\ti2\tS64\tS0\n"
877                                              "CustomAction\tAction\n"
878                                              "GoodSetProperty\t51\tMYPROP\t42\n"
879                                              "BadSetProperty\t51\t\tMYPROP\n"
880                                              "SetSourceDir\t51\tSourceDir\t[SRCDIR]\n";
881
882 static const CHAR is_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
883                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
884                                      "Feature\tFeature\n"
885                                      "one\t\t\t\t2\t1\t\t0\n" /* favorLocal */
886                                      "two\t\t\t\t2\t1\t\t1\n" /* favorSource */
887                                      "three\t\t\t\t2\t1\t\t4\n" /* favorAdvertise */
888                                      "four\t\t\t\t2\t0\t\t0"; /* disabled */
889
890 static const CHAR is_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
891                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
892                                        "Component\tComponent\n"
893                                        "alpha\t\tMSITESTDIR\t0\t\talpha_file\n" /* favorLocal:Local */
894                                        "beta\t\tMSITESTDIR\t1\t\tbeta_file\n" /* favorLocal:Source */
895                                        "gamma\t\tMSITESTDIR\t2\t\tgamma_file\n" /* favorLocal:Optional */
896                                        "theta\t\tMSITESTDIR\t0\t\ttheta_file\n" /* favorSource:Local */
897                                        "delta\t\tMSITESTDIR\t1\t\tdelta_file\n" /* favorSource:Source */
898                                        "epsilon\t\tMSITESTDIR\t2\t\tepsilon_file\n" /* favorSource:Optional */
899                                        "zeta\t\tMSITESTDIR\t0\t\tzeta_file\n" /* favorAdvertise:Local */
900                                        "iota\t\tMSITESTDIR\t1\t\tiota_file\n" /* favorAdvertise:Source */
901                                        "eta\t\tMSITESTDIR\t2\t\teta_file\n" /* favorAdvertise:Optional */
902                                        "kappa\t\tMSITESTDIR\t0\t\tkappa_file\n" /* disabled:Local */
903                                        "lambda\t\tMSITESTDIR\t1\t\tlambda_file\n" /* disabled:Source */
904                                        "mu\t\tMSITESTDIR\t2\t\tmu_file\n"; /* disabled:Optional */
905
906 static const CHAR is_feature_comp_dat[] = "Feature_\tComponent_\n"
907                                           "s38\ts72\n"
908                                           "FeatureComponents\tFeature_\tComponent_\n"
909                                           "one\talpha\n"
910                                           "one\tbeta\n"
911                                           "one\tgamma\n"
912                                           "two\ttheta\n"
913                                           "two\tdelta\n"
914                                           "two\tepsilon\n"
915                                           "three\tzeta\n"
916                                           "three\tiota\n"
917                                           "three\teta\n"
918                                           "four\tkappa\n"
919                                           "four\tlambda\n"
920                                           "four\tmu";
921
922 static const CHAR is_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
923                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
924                                   "File\tFile\n"
925                                   "alpha_file\talpha\talpha\t500\t\t\t8192\t1\n"
926                                   "beta_file\tbeta\tbeta\t500\t\t\t8291\t2\n"
927                                   "gamma_file\tgamma\tgamma\t500\t\t\t8192\t3\n"
928                                   "theta_file\ttheta\ttheta\t500\t\t\t8192\t4\n"
929                                   "delta_file\tdelta\tdelta\t500\t\t\t8192\t5\n"
930                                   "epsilon_file\tepsilon\tepsilon\t500\t\t\t8192\t6\n"
931                                   "zeta_file\tzeta\tzeta\t500\t\t\t8192\t7\n"
932                                   "iota_file\tiota\tiota\t500\t\t\t8192\t8\n"
933                                   "eta_file\teta\teta\t500\t\t\t8192\t9\n"
934                                   "kappa_file\tkappa\tkappa\t500\t\t\t8192\t10\n"
935                                   "lambda_file\tlambda\tlambda\t500\t\t\t8192\t11\n"
936                                   "mu_file\tmu\tmu\t500\t\t\t8192\t12";
937
938 static const CHAR is_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
939                                    "i2\ti4\tL64\tS255\tS32\tS72\n"
940                                    "Media\tDiskId\n"
941                                    "1\t12\t\t\tDISK1\t\n";
942
943 static const CHAR sp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
944                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
945                                         "Component\tComponent\n"
946                                         "augustus\t\tTWODIR\t0\t\taugustus\n";
947
948 static const CHAR sp_directory_dat[] = "Directory\tDirectory_Parent\tDefaultDir\n"
949                                        "s72\tS72\tl255\n"
950                                        "Directory\tDirectory\n"
951                                        "TARGETDIR\t\tSourceDir\n"
952                                        "ProgramFilesFolder\tTARGETDIR\t.\n"
953                                        "MSITESTDIR\tProgramFilesFolder\tmsitest:.\n"
954                                        "ONEDIR\tMSITESTDIR\t.:shortone|longone\n"
955                                        "TWODIR\tONEDIR\t.:shorttwo|longtwo";
956
957 static const CHAR mcp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
958                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
959                                         "Component\tComponent\n"
960                                         "hydrogen\t{C844BD1E-1907-4C00-8BC9-150BD70DF0A1}\tMSITESTDIR\t2\t\thydrogen\n"
961                                         "helium\t{5AD3C142-CEF8-490D-B569-784D80670685}\tMSITESTDIR\t2\t\thelium\n"
962                                         "lithium\t{4AF28FFC-71C7-4307-BDE4-B77C5338F56F}\tMSITESTDIR\t2\tPROPVAR=42\tlithium\n";
963
964 static const CHAR mcp_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
965                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
966                                       "Feature\tFeature\n"
967                                       "hydroxyl\t\thydroxyl\thydroxyl\t2\t1\tTARGETDIR\t0\n"
968                                       "heliox\t\theliox\theliox\t2\t5\tTARGETDIR\t0\n"
969                                       "lithia\t\tlithia\tlithia\t2\t10\tTARGETDIR\t0";
970
971 static const CHAR mcp_feature_comp_dat[] = "Feature_\tComponent_\n"
972                                            "s38\ts72\n"
973                                            "FeatureComponents\tFeature_\tComponent_\n"
974                                            "hydroxyl\thydrogen\n"
975                                            "heliox\thelium\n"
976                                            "lithia\tlithium";
977
978 static const CHAR mcomp_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
979                                      "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
980                                      "File\tFile\n"
981                                      "hydrogen\thydrogen\thydrogen\t0\t\t\t8192\t1\n"
982                                      "helium\thelium\thelium\t0\t\t\t8192\t1\n"
983                                      "lithium\tlithium\tlithium\t0\t\t\t8192\t1\n"
984                                      "beryllium\tmissingcomp\tberyllium\t0\t\t\t8192\t1";
985
986 static const CHAR ai_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
987                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
988                                   "File\tFile\n"
989                                   "five.txt\tFive\tfive.txt\t1000\t\t\t16384\t5\n"
990                                   "four.txt\tFour\tfour.txt\t1000\t\t\t16384\t4\n"
991                                   "one.txt\tOne\tone.txt\t1000\t\t\t16384\t1\n"
992                                   "three.txt\tThree\tthree.txt\t1000\t\t\t16384\t3\n"
993                                   "two.txt\tTwo\ttwo.txt\t1000\t\t\t16384\t2\n"
994                                   "file\tcomponent\tfilename\t100\t\t\t8192\t1\n"
995                                   "service_file\tservice_comp\tservice.exe\t100\t\t\t8192\t1";
996
997 static const CHAR ip_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
998                                               "s72\tS255\tI2\n"
999                                               "InstallExecuteSequence\tAction\n"
1000                                               "CostFinalize\t\t1000\n"
1001                                               "ValidateProductID\t\t700\n"
1002                                               "CostInitialize\t\t800\n"
1003                                               "FileCost\t\t900\n"
1004                                               "RemoveFiles\t\t3500\n"
1005                                               "InstallFiles\t\t4000\n"
1006                                               "RegisterUser\t\t6000\n"
1007                                               "RegisterProduct\t\t6100\n"
1008                                               "PublishFeatures\t\t6300\n"
1009                                               "PublishProduct\t\t6400\n"
1010                                               "InstallFinalize\t\t6600\n"
1011                                               "InstallInitialize\t\t1500\n"
1012                                               "ProcessComponents\t\t1600\n"
1013                                               "UnpublishFeatures\t\t1800\n"
1014                                               "InstallValidate\t\t1400\n"
1015                                               "LaunchConditions\t\t100\n"
1016                                               "TestInstalledProp\tInstalled AND NOT REMOVE\t950\n";
1017
1018 static const CHAR ip_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
1019                                            "s72\ti2\tS64\tS0\tS255\n"
1020                                            "CustomAction\tAction\n"
1021                                            "TestInstalledProp\t19\t\tTest failed\t\n";
1022
1023 static const CHAR aup_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1024                                                "s72\tS255\tI2\n"
1025                                                "InstallExecuteSequence\tAction\n"
1026                                                "CostFinalize\t\t1000\n"
1027                                                "ValidateProductID\t\t700\n"
1028                                                "CostInitialize\t\t800\n"
1029                                                "FileCost\t\t900\n"
1030                                                "RemoveFiles\t\t3500\n"
1031                                                "InstallFiles\t\t4000\n"
1032                                                "RegisterUser\t\t6000\n"
1033                                                "RegisterProduct\t\t6100\n"
1034                                                "PublishFeatures\t\t6300\n"
1035                                                "PublishProduct\t\t6400\n"
1036                                                "InstallFinalize\t\t6600\n"
1037                                                "InstallInitialize\t\t1500\n"
1038                                                "ProcessComponents\t\t1600\n"
1039                                                "UnpublishFeatures\t\t1800\n"
1040                                                "InstallValidate\t\t1400\n"
1041                                                "LaunchConditions\t\t100\n"
1042                                                "TestAllUsersProp\tALLUSERS AND NOT REMOVE\t50\n";
1043
1044 static const CHAR aup2_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1045                                                 "s72\tS255\tI2\n"
1046                                                 "InstallExecuteSequence\tAction\n"
1047                                                 "CostFinalize\t\t1000\n"
1048                                                 "ValidateProductID\t\t700\n"
1049                                                 "CostInitialize\t\t800\n"
1050                                                 "FileCost\t\t900\n"
1051                                                 "RemoveFiles\t\t3500\n"
1052                                                 "InstallFiles\t\t4000\n"
1053                                                 "RegisterUser\t\t6000\n"
1054                                                 "RegisterProduct\t\t6100\n"
1055                                                 "PublishFeatures\t\t6300\n"
1056                                                 "PublishProduct\t\t6400\n"
1057                                                 "InstallFinalize\t\t6600\n"
1058                                                 "InstallInitialize\t\t1500\n"
1059                                                 "ProcessComponents\t\t1600\n"
1060                                                 "UnpublishFeatures\t\t1800\n"
1061                                                 "InstallValidate\t\t1400\n"
1062                                                 "LaunchConditions\t\t100\n"
1063                                                 "TestAllUsersProp\tALLUSERS=2 AND NOT REMOVE\t50\n";
1064
1065 static const CHAR aup3_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1066                                                 "s72\tS255\tI2\n"
1067                                                 "InstallExecuteSequence\tAction\n"
1068                                                 "CostFinalize\t\t1000\n"
1069                                                 "ValidateProductID\t\t700\n"
1070                                                 "CostInitialize\t\t800\n"
1071                                                 "FileCost\t\t900\n"
1072                                                 "RemoveFiles\t\t3500\n"
1073                                                 "InstallFiles\t\t4000\n"
1074                                                 "RegisterUser\t\t6000\n"
1075                                                 "RegisterProduct\t\t6100\n"
1076                                                 "PublishFeatures\t\t6300\n"
1077                                                 "PublishProduct\t\t6400\n"
1078                                                 "InstallFinalize\t\t6600\n"
1079                                                 "InstallInitialize\t\t1500\n"
1080                                                 "ProcessComponents\t\t1600\n"
1081                                                 "UnpublishFeatures\t\t1800\n"
1082                                                 "InstallValidate\t\t1400\n"
1083                                                 "LaunchConditions\t\t100\n"
1084                                                 "TestAllUsersProp\tALLUSERS=1 AND NOT REMOVE\t50\n";
1085
1086 static const CHAR aup_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
1087                                             "s72\ti2\tS64\tS0\tS255\n"
1088                                             "CustomAction\tAction\n"
1089                                             "TestAllUsersProp\t19\t\tTest failed\t\n";
1090
1091 static const CHAR cf_create_folders_dat[] = "Directory_\tComponent_\n"
1092                                             "s72\ts72\n"
1093                                             "CreateFolder\tDirectory_\tComponent_\n"
1094                                             "FIRSTDIR\tOne\n";
1095
1096 static const CHAR cf_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1097                                               "s72\tS255\tI2\n"
1098                                               "InstallExecuteSequence\tAction\n"
1099                                               "CostFinalize\t\t1000\n"
1100                                               "ValidateProductID\t\t700\n"
1101                                               "CostInitialize\t\t800\n"
1102                                               "FileCost\t\t900\n"
1103                                               "RemoveFiles\t\t3500\n"
1104                                               "CreateFolders\t\t3700\n"
1105                                               "InstallExecute\t\t3800\n"
1106                                               "TestCreateFolders\t\t3900\n"
1107                                               "InstallFiles\t\t4000\n"
1108                                               "RegisterUser\t\t6000\n"
1109                                               "RegisterProduct\t\t6100\n"
1110                                               "PublishFeatures\t\t6300\n"
1111                                               "PublishProduct\t\t6400\n"
1112                                               "InstallFinalize\t\t6600\n"
1113                                               "InstallInitialize\t\t1500\n"
1114                                               "ProcessComponents\t\t1600\n"
1115                                               "UnpublishFeatures\t\t1800\n"
1116                                               "InstallValidate\t\t1400\n"
1117                                               "LaunchConditions\t\t100\n";
1118
1119 static const CHAR cf_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
1120                                            "s72\ti2\tS64\tS0\tS255\n"
1121                                            "CustomAction\tAction\n"
1122                                            "TestCreateFolders\t19\t\tHalts installation\t\n";
1123
1124 static const CHAR rf_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1125                                               "s72\tS255\tI2\n"
1126                                               "InstallExecuteSequence\tAction\n"
1127                                               "CostFinalize\t\t1000\n"
1128                                               "ValidateProductID\t\t700\n"
1129                                               "CostInitialize\t\t800\n"
1130                                               "FileCost\t\t900\n"
1131                                               "RemoveFiles\t\t3500\n"
1132                                               "CreateFolders\t\t3600\n"
1133                                               "RemoveFolders\t\t3700\n"
1134                                               "InstallExecute\t\t3800\n"
1135                                               "TestCreateFolders\t\t3900\n"
1136                                               "InstallFiles\t\t4000\n"
1137                                               "RegisterUser\t\t6000\n"
1138                                               "RegisterProduct\t\t6100\n"
1139                                               "PublishFeatures\t\t6300\n"
1140                                               "PublishProduct\t\t6400\n"
1141                                               "InstallFinalize\t\t6600\n"
1142                                               "InstallInitialize\t\t1500\n"
1143                                               "ProcessComponents\t\t1600\n"
1144                                               "UnpublishFeatures\t\t1800\n"
1145                                               "InstallValidate\t\t1400\n"
1146                                               "LaunchConditions\t\t100\n";
1147
1148
1149 static const CHAR sr_selfreg_dat[] = "File_\tCost\n"
1150                                      "s72\tI2\n"
1151                                      "SelfReg\tFile_\n"
1152                                      "one.txt\t1\n";
1153
1154 static const CHAR sr_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1155                                               "s72\tS255\tI2\n"
1156                                               "InstallExecuteSequence\tAction\n"
1157                                               "CostFinalize\t\t1000\n"
1158                                               "CostInitialize\t\t800\n"
1159                                               "FileCost\t\t900\n"
1160                                               "ResolveSource\t\t950\n"
1161                                               "MoveFiles\t\t1700\n"
1162                                               "SelfUnregModules\t\t3900\n"
1163                                               "InstallFiles\t\t4000\n"
1164                                               "DuplicateFiles\t\t4500\n"
1165                                               "WriteEnvironmentStrings\t\t4550\n"
1166                                               "CreateShortcuts\t\t4600\n"
1167                                               "InstallFinalize\t\t6600\n"
1168                                               "InstallInitialize\t\t1500\n"
1169                                               "InstallValidate\t\t1400\n"
1170                                               "LaunchConditions\t\t100\n";
1171
1172 static const CHAR font_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
1173                                      "i2\ti4\tL64\tS255\tS32\tS72\n"
1174                                      "Media\tDiskId\n"
1175                                      "1\t3\t\t\tDISK1\t\n";
1176
1177 static const CHAR font_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1178                                     "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1179                                     "File\tFile\n"
1180                                     "font.ttf\tfonts\tfont.ttf\t1000\t\t\t8192\t1\n";
1181
1182 static const CHAR font_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1183                                        "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1184                                        "Feature\tFeature\n"
1185                                        "fonts\t\t\tfont feature\t1\t2\tMSITESTDIR\t0\n";
1186
1187 static const CHAR font_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1188                                          "s72\tS38\ts72\ti2\tS255\tS72\n"
1189                                          "Component\tComponent\n"
1190                                          "fonts\t{F5920ED0-1183-4B8F-9330-86CE56557C05}\tMSITESTDIR\t0\t\tfont.ttf\n";
1191
1192 static const CHAR font_feature_comp_dat[] = "Feature_\tComponent_\n"
1193                                             "s38\ts72\n"
1194                                             "FeatureComponents\tFeature_\tComponent_\n"
1195                                             "fonts\tfonts\n";
1196
1197 static const CHAR font_dat[] = "File_\tFontTitle\n"
1198                                "s72\tS128\n"
1199                                "Font\tFile_\n"
1200                                "font.ttf\tmsi test font\n";
1201
1202 static const CHAR font_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1203                                                 "s72\tS255\tI2\n"
1204                                                 "InstallExecuteSequence\tAction\n"
1205                                                 "ValidateProductID\t\t700\n"
1206                                                 "CostInitialize\t\t800\n"
1207                                                 "FileCost\t\t900\n"
1208                                                 "CostFinalize\t\t1000\n"
1209                                                 "InstallValidate\t\t1400\n"
1210                                                 "InstallInitialize\t\t1500\n"
1211                                                 "ProcessComponents\t\t1600\n"
1212                                                 "UnpublishFeatures\t\t1800\n"
1213                                                 "RemoveFiles\t\t3500\n"
1214                                                 "InstallFiles\t\t4000\n"
1215                                                 "RegisterFonts\t\t4100\n"
1216                                                 "UnregisterFonts\t\t4200\n"
1217                                                 "RegisterUser\t\t6000\n"
1218                                                 "RegisterProduct\t\t6100\n"
1219                                                 "PublishFeatures\t\t6300\n"
1220                                                 "PublishProduct\t\t6400\n"
1221                                                 "InstallFinalize\t\t6600";
1222
1223 static const CHAR vp_property_dat[] = "Property\tValue\n"
1224                                       "s72\tl0\n"
1225                                       "Property\tProperty\n"
1226                                       "HASUIRUN\t0\n"
1227                                       "INSTALLLEVEL\t3\n"
1228                                       "InstallMode\tTypical\n"
1229                                       "Manufacturer\tWine\n"
1230                                       "PIDTemplate\t###-#######\n"
1231                                       "ProductCode\t{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}\n"
1232                                       "ProductLanguage\t1033\n"
1233                                       "ProductName\tMSITEST\n"
1234                                       "ProductVersion\t1.1.1\n"
1235                                       "UpgradeCode\t{4C0EAA15-0264-4E5A-8758-609EF142B92D}\n";
1236
1237 static const CHAR vp_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
1238                                            "s72\ti2\tS64\tS0\tS255\n"
1239                                            "CustomAction\tAction\n"
1240                                            "SetProductID1\t51\tProductID\t1\t\n"
1241                                            "SetProductID2\t51\tProductID\t2\t\n"
1242                                            "TestProductID1\t19\t\t\tHalts installation\n"
1243                                            "TestProductID2\t19\t\t\tHalts installation\n";
1244
1245 static const CHAR vp_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1246                                               "s72\tS255\tI2\n"
1247                                               "InstallExecuteSequence\tAction\n"
1248                                               "LaunchConditions\t\t100\n"
1249                                               "CostInitialize\t\t800\n"
1250                                               "FileCost\t\t900\n"
1251                                               "CostFinalize\t\t1000\n"
1252                                               "InstallValidate\t\t1400\n"
1253                                               "InstallInitialize\t\t1500\n"
1254                                               "SetProductID1\tSET_PRODUCT_ID=1\t3000\n"
1255                                               "SetProductID2\tSET_PRODUCT_ID=2\t3100\n"
1256                                               "ValidateProductID\t\t3200\n"
1257                                               "InstallExecute\t\t3300\n"
1258                                               "TestProductID1\tProductID=1\t3400\n"
1259                                               "TestProductID2\tProductID=\"123-1234567\"\t3500\n"
1260                                               "InstallFiles\t\t4000\n"
1261                                               "InstallFinalize\t\t6000\n";
1262
1263 static const CHAR odbc_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1264                                     "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1265                                     "File\tFile\n"
1266                                     "ODBCdriver.dll\todbc\tODBCdriver.dll\t1000\t\t\t8192\t1\n"
1267                                     "ODBCdriver2.dll\todbc\tODBCdriver2.dll\t1000\t\t\t8192\t2\n"
1268                                     "ODBCtranslator.dll\todbc\tODBCtranslator.dll\t1000\t\t\t8192\t3\n"
1269                                     "ODBCtranslator2.dll\todbc\tODBCtranslator2.dll\t1000\t\t\t8192\t4\n"
1270                                     "ODBCsetup.dll\todbc\tODBCsetup.dll\t1000\t\t\t8192\t5\n";
1271
1272 static const CHAR odbc_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1273                                        "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1274                                        "Feature\tFeature\n"
1275                                        "odbc\t\t\todbc feature\t1\t2\tMSITESTDIR\t0\n";
1276
1277 static const CHAR odbc_feature_comp_dat[] = "Feature_\tComponent_\n"
1278                                             "s38\ts72\n"
1279                                             "FeatureComponents\tFeature_\tComponent_\n"
1280                                             "odbc\todbc\n";
1281
1282 static const CHAR odbc_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1283                                          "s72\tS38\ts72\ti2\tS255\tS72\n"
1284                                          "Component\tComponent\n"
1285                                          "odbc\t{B6F3E4AE-35D1-4B72-9044-989F03E20A43}\tMSITESTDIR\t0\t\tODBCdriver.dll\n";
1286
1287 static const CHAR odbc_driver_dat[] = "Driver\tComponent_\tDescription\tFile_\tFile_Setup\n"
1288                                       "s72\ts72\ts255\ts72\tS72\n"
1289                                       "ODBCDriver\tDriver\n"
1290                                       "ODBC test driver\todbc\tODBC test driver\tODBCdriver.dll\t\n"
1291                                       "ODBC test driver2\todbc\tODBC test driver2\tODBCdriver2.dll\tODBCsetup.dll\n";
1292
1293 static const CHAR odbc_translator_dat[] = "Translator\tComponent_\tDescription\tFile_\tFile_Setup\n"
1294                                           "s72\ts72\ts255\ts72\tS72\n"
1295                                           "ODBCTranslator\tTranslator\n"
1296                                           "ODBC test translator\todbc\tODBC test translator\tODBCtranslator.dll\t\n"
1297                                           "ODBC test translator2\todbc\tODBC test translator2\tODBCtranslator2.dll\tODBCsetup.dll\n";
1298
1299 static const CHAR odbc_datasource_dat[] = "DataSource\tComponent_\tDescription\tDriverDescription\tRegistration\n"
1300                                           "s72\ts72\ts255\ts255\ti2\n"
1301                                           "ODBCDataSource\tDataSource\n"
1302                                           "ODBC data source\todbc\tODBC data source\tODBC driver\t0\n";
1303
1304 static const CHAR odbc_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1305                                                 "s72\tS255\tI2\n"
1306                                                 "InstallExecuteSequence\tAction\n"
1307                                                 "LaunchConditions\t\t100\n"
1308                                                 "CostInitialize\t\t800\n"
1309                                                 "FileCost\t\t900\n"
1310                                                 "CostFinalize\t\t1000\n"
1311                                                 "InstallValidate\t\t1400\n"
1312                                                 "InstallInitialize\t\t1500\n"
1313                                                 "ProcessComponents\t\t1600\n"
1314                                                 "InstallODBC\t\t3000\n"
1315                                                 "RemoveODBC\t\t3100\n"
1316                                                 "RemoveFiles\t\t3900\n"
1317                                                 "InstallFiles\t\t4000\n"
1318                                                 "RegisterProduct\t\t5000\n"
1319                                                 "PublishFeatures\t\t5100\n"
1320                                                 "PublishProduct\t\t5200\n"
1321                                                 "InstallFinalize\t\t6000\n";
1322
1323 static const CHAR odbc_media_dat[] = "DiskId\tLastSequence\tDiskPrompt\tCabinet\tVolumeLabel\tSource\n"
1324                                      "i2\ti4\tL64\tS255\tS32\tS72\n"
1325                                      "Media\tDiskId\n"
1326                                      "1\t5\t\t\tDISK1\t\n";
1327
1328 static const CHAR tl_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1329                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1330                                   "File\tFile\n"
1331                                   "typelib.dll\ttypelib\ttypelib.dll\t1000\t\t\t8192\t1\n";
1332
1333 static const CHAR tl_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1334                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1335                                      "Feature\tFeature\n"
1336                                      "typelib\t\t\ttypelib feature\t1\t2\tMSITESTDIR\t0\n";
1337
1338 static const CHAR tl_feature_comp_dat[] = "Feature_\tComponent_\n"
1339                                           "s38\ts72\n"
1340                                           "FeatureComponents\tFeature_\tComponent_\n"
1341                                           "typelib\ttypelib\n";
1342
1343 static const CHAR tl_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1344                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
1345                                        "Component\tComponent\n"
1346                                        "typelib\t{BB4C26FD-89D8-4E49-AF1C-DB4DCB5BF1B0}\tMSITESTDIR\t0\t\ttypelib.dll\n";
1347
1348 static const CHAR tl_typelib_dat[] = "LibID\tLanguage\tComponent_\tVersion\tDescription\tDirectory_\tFeature_\tCost\n"
1349                                      "s38\ti2\ts72\tI4\tL128\tS72\ts38\tI4\n"
1350                                      "TypeLib\tLibID\tLanguage\tComponent_\n"
1351                                      "{EAC5166A-9734-4D91-878F-1DD02304C66C}\t0\ttypelib\t1793\t\tMSITESTDIR\ttypelib\t\n";
1352
1353 static const CHAR tl_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1354                                               "s72\tS255\tI2\n"
1355                                               "InstallExecuteSequence\tAction\n"
1356                                               "LaunchConditions\t\t100\n"
1357                                               "CostInitialize\t\t800\n"
1358                                               "FileCost\t\t900\n"
1359                                               "CostFinalize\t\t1000\n"
1360                                               "InstallValidate\t\t1400\n"
1361                                               "InstallInitialize\t\t1500\n"
1362                                               "ProcessComponents\t\t1600\n"
1363                                               "RemoveFiles\t\t1700\n"
1364                                               "InstallFiles\t\t2000\n"
1365                                               "RegisterTypeLibraries\tREGISTER_TYPELIB=1\t3000\n"
1366                                               "UnregisterTypeLibraries\t\t3100\n"
1367                                               "RegisterProduct\t\t5100\n"
1368                                               "PublishFeatures\t\t5200\n"
1369                                               "PublishProduct\t\t5300\n"
1370                                               "InstallFinalize\t\t6000\n";
1371
1372 static const CHAR crs_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1373                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1374                                    "File\tFile\n"
1375                                    "target.txt\tshortcut\ttarget.txt\t1000\t\t\t8192\t1\n";
1376
1377 static const CHAR crs_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1378                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1379                                       "Feature\tFeature\n"
1380                                       "shortcut\t\t\tshortcut feature\t1\t2\tMSITESTDIR\t0\n";
1381
1382 static const CHAR crs_feature_comp_dat[] = "Feature_\tComponent_\n"
1383                                            "s38\ts72\n"
1384                                            "FeatureComponents\tFeature_\tComponent_\n"
1385                                            "shortcut\tshortcut\n";
1386
1387 static const CHAR crs_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1388                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1389                                         "Component\tComponent\n"
1390                                         "shortcut\t{5D20E3C6-7206-498F-AC28-87AF2F9AD4CC}\tMSITESTDIR\t0\t\ttarget.txt\n";
1391
1392 static const CHAR crs_shortcut_dat[] = "Shortcut\tDirectory_\tName\tComponent_\tTarget\tArguments\tDescription\tHotkey\tIcon_\tIconIndex\tShowCmd\tWkDir\n"
1393                                        "s72\ts72\tl128\ts72\ts72\tL255\tL255\tI2\tS72\tI2\tI2\tS72\n"
1394                                        "Shortcut\tShortcut\n"
1395                                        "shortcut\tMSITESTDIR\tshortcut\tshortcut\t[MSITESTDIR]target.txt\t\t\t\t\t\t\t\n";
1396
1397 static const CHAR crs_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1398                                                "s72\tS255\tI2\n"
1399                                                "InstallExecuteSequence\tAction\n"
1400                                                "LaunchConditions\t\t100\n"
1401                                                "CostInitialize\t\t800\n"
1402                                                "FileCost\t\t900\n"
1403                                                "CostFinalize\t\t1000\n"
1404                                                "InstallValidate\t\t1400\n"
1405                                                "InstallInitialize\t\t1500\n"
1406                                                "ProcessComponents\t\t1600\n"
1407                                                "RemoveFiles\t\t1700\n"
1408                                                "InstallFiles\t\t2000\n"
1409                                                "RemoveShortcuts\t\t3000\n"
1410                                                "CreateShortcuts\t\t3100\n"
1411                                                "RegisterProduct\t\t5000\n"
1412                                                "PublishFeatures\t\t5100\n"
1413                                                "PublishProduct\t\t5200\n"
1414                                                "InstallFinalize\t\t6000\n";
1415
1416 static const CHAR fo_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1417                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1418                                   "File\tFile\n"
1419                                   "override.txt\toverride\toverride.txt\t1000\t\t\t8192\t1\n"
1420                                   "preselected.txt\tpreselected\tpreselected.txt\t1000\t\t\t8192\t2\n"
1421                                   "notpreselected.txt\tnotpreselected\tnotpreselected.txt\t1000\t\t\t8192\t3\n";
1422
1423 static const CHAR fo_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1424                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1425                                      "Feature\tFeature\n"
1426                                      "override\t\t\toverride feature\t1\t1\tMSITESTDIR\t0\n"
1427                                      "preselected\t\t\tpreselected feature\t1\t1\tMSITESTDIR\t0\n"
1428                                      "notpreselected\t\t\tnotpreselected feature\t1\t1\tMSITESTDIR\t0\n";
1429
1430 static const CHAR fo_condition_dat[] = "Feature_\tLevel\tCondition\n"
1431                                        "s38\ti2\tS255\n"
1432                                        "Condition\tFeature_\tLevel\n"
1433                                        "preselected\t0\tPreselected\n"
1434                                        "notpreselected\t0\tNOT Preselected\n";
1435
1436 static const CHAR fo_feature_comp_dat[] = "Feature_\tComponent_\n"
1437                                           "s38\ts72\n"
1438                                           "FeatureComponents\tFeature_\tComponent_\n"
1439                                           "override\toverride\n"
1440                                           "preselected\tpreselected\n"
1441                                           "notpreselected\tnotpreselected\n";
1442
1443 static const CHAR fo_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1444                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
1445                                        "Component\tComponent\n"
1446                                        "override\t{0A00FB1D-97B0-4B42-ADF0-BB8913416623}\tMSITESTDIR\t0\t\toverride.txt\n"
1447                                        "preselected\t{44E1DB75-605A-43DD-8CF5-CAB17F1BBD60}\tMSITESTDIR\t0\t\tpreselected.txt\n"
1448                                        "notpreselected\t{E1647733-5E75-400A-A92E-5E60B4D4EF9F}\tMSITESTDIR\t0\t\tnotpreselected.txt\n";
1449
1450 static const CHAR fo_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
1451                                            "s72\ti2\tS64\tS0\tS255\n"
1452                                            "CustomAction\tAction\n"
1453                                            "SetPreselected\t51\tPreselected\t1\t\n";
1454
1455 static const CHAR fo_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1456                                               "s72\tS255\tI2\n"
1457                                               "InstallExecuteSequence\tAction\n"
1458                                               "LaunchConditions\t\t100\n"
1459                                               "SetPreselected\tpreselect=1\t200\n"
1460                                               "CostInitialize\t\t800\n"
1461                                               "FileCost\t\t900\n"
1462                                               "CostFinalize\t\t1000\n"
1463                                               "InstallValidate\t\t1400\n"
1464                                               "InstallInitialize\t\t1500\n"
1465                                               "ProcessComponents\t\t1600\n"
1466                                               "RemoveFiles\t\t1700\n"
1467                                               "InstallFiles\t\t2000\n"
1468                                               "RegisterProduct\t\t5000\n"
1469                                               "PublishFeatures\t\t5100\n"
1470                                               "PublishProduct\t\t5200\n"
1471                                               "InstallFinalize\t\t6000\n";
1472
1473 static const CHAR pub_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1474                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1475                                    "File\tFile\n"
1476                                    "english.txt\tpublish\tenglish.txt\t1000\t\t\t8192\t1\n";
1477
1478 static const CHAR pub_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1479                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1480                                       "Feature\tFeature\n"
1481                                       "publish\t\t\tpublish feature\t1\t2\tMSITESTDIR\t0\n";
1482
1483 static const CHAR pub_feature_comp_dat[] = "Feature_\tComponent_\n"
1484                                            "s38\ts72\n"
1485                                            "FeatureComponents\tFeature_\tComponent_\n"
1486                                            "publish\tpublish\n";
1487
1488 static const CHAR pub_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1489                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1490                                         "Component\tComponent\n"
1491                                         "publish\t{B4EA0ACF-6238-426E-9C6D-7869F0F9C768}\tMSITESTDIR\t0\t\tenglish.txt\n";
1492
1493 static const CHAR pub_publish_component_dat[] = "ComponentId\tQualifier\tComponent_\tAppData\tFeature_\n"
1494                                                 "s38\ts255\ts72\tL255\ts38\n"
1495                                                 "PublishComponent\tComponentId\tQualifier\tComponent_\n"
1496                                                 "{92AFCBC0-9CA6-4270-8454-47C5EE2B8FAA}\tenglish.txt\tpublish\t\tpublish\n";
1497
1498 static const CHAR pub_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1499                                                "s72\tS255\tI2\n"
1500                                                "InstallExecuteSequence\tAction\n"
1501                                                "LaunchConditions\t\t100\n"
1502                                                "CostInitialize\t\t800\n"
1503                                                "FileCost\t\t900\n"
1504                                                "CostFinalize\t\t1000\n"
1505                                                "InstallValidate\t\t1400\n"
1506                                                "InstallInitialize\t\t1500\n"
1507                                                "ProcessComponents\t\t1600\n"
1508                                                "RemoveFiles\t\t1700\n"
1509                                                "InstallFiles\t\t2000\n"
1510                                                "PublishComponents\t\t3000\n"
1511                                                "UnpublishComponents\t\t3100\n"
1512                                                "RegisterProduct\t\t5000\n"
1513                                                "PublishFeatures\t\t5100\n"
1514                                                "PublishProduct\t\t5200\n"
1515                                                "InstallFinalize\t\t6000\n";
1516
1517 static const CHAR rd_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1518                                   "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1519                                   "File\tFile\n"
1520                                   "original.txt\tduplicate\toriginal.txt\t1000\t\t\t8192\t1\n"
1521                                   "original2.txt\tduplicate\toriginal2.txt\t1000\t\t\t8192\t2\n"
1522                                   "original3.txt\tduplicate2\toriginal3.txt\t1000\t\t\t8192\t3\n";
1523
1524 static const CHAR rd_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1525                                      "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1526                                      "Feature\tFeature\n"
1527                                      "duplicate\t\t\tduplicate feature\t1\t2\tMSITESTDIR\t0\n";
1528
1529 static const CHAR rd_feature_comp_dat[] = "Feature_\tComponent_\n"
1530                                           "s38\ts72\n"
1531                                           "FeatureComponents\tFeature_\tComponent_\n"
1532                                           "duplicate\tduplicate\n";
1533
1534 static const CHAR rd_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1535                                        "s72\tS38\ts72\ti2\tS255\tS72\n"
1536                                        "Component\tComponent\n"
1537                                        "duplicate\t{EB45D06A-ADFE-44E3-8D41-B7DE150E41AD}\tMSITESTDIR\t0\t\toriginal.txt\n"
1538                                        "duplicate2\t{B8BA60E0-B2E9-488E-9D0E-E60F25F04F97}\tMSITESTDIR\t0\tDUPLICATE2=1\toriginal3.txt\n";
1539
1540 static const CHAR rd_duplicate_file_dat[] = "FileKey\tComponent_\tFile_\tDestName\tDestFolder\n"
1541                                             "s72\ts72\ts72\tS255\tS72\n"
1542                                             "DuplicateFile\tFileKey\n"
1543                                             "duplicate\tduplicate\toriginal.txt\tduplicate.txt\t\n"
1544                                             "duplicate2\tduplicate\toriginal2.txt\t\tMSITESTDIR\n"
1545                                             "duplicate3\tduplicate2\toriginal3.txt\tduplicate2.txt\t\n";
1546
1547 static const CHAR rd_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1548                                               "s72\tS255\tI2\n"
1549                                               "InstallExecuteSequence\tAction\n"
1550                                               "LaunchConditions\t\t100\n"
1551                                               "CostInitialize\t\t800\n"
1552                                               "FileCost\t\t900\n"
1553                                               "CostFinalize\t\t1000\n"
1554                                               "InstallValidate\t\t1400\n"
1555                                               "InstallInitialize\t\t1500\n"
1556                                               "ProcessComponents\t\t1600\n"
1557                                               "RemoveDuplicateFiles\t\t1900\n"
1558                                               "InstallFiles\t\t2000\n"
1559                                               "DuplicateFiles\t\t2100\n"
1560                                               "RegisterProduct\t\t5000\n"
1561                                               "PublishFeatures\t\t5100\n"
1562                                               "PublishProduct\t\t5200\n"
1563                                               "InstallFinalize\t\t6000\n";
1564
1565 static const CHAR rrv_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1566                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1567                                    "File\tFile\n"
1568                                    "registry.txt\tregistry\tregistry.txt\t1000\t\t\t8192\t1\n";
1569
1570 static const CHAR rrv_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1571                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1572                                       "Feature\tFeature\n"
1573                                       "registry\t\t\tregistry feature\t1\t2\tMSITESTDIR\t0\n";
1574
1575 static const CHAR rrv_feature_comp_dat[] = "Feature_\tComponent_\n"
1576                                            "s38\ts72\n"
1577                                            "FeatureComponents\tFeature_\tComponent_\n"
1578                                            "registry\tregistry\n";
1579
1580 static const CHAR rrv_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1581                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1582                                         "Component\tComponent\n"
1583                                         "registry\t{DA97585B-962D-45EB-AD32-DA15E60CA9EE}\tMSITESTDIR\t0\t\tregistry.txt\n";
1584
1585 static const CHAR rrv_registry_dat[] = "Registry\tRoot\tKey\tName\tValue\tComponent_\n"
1586                                        "s72\ti2\tl255\tL255\tL0\ts72\n"
1587                                        "Registry\tRegistry\n"
1588                                        "reg1\t2\tSOFTWARE\\Wine\\keyA\t\tA\tregistry\n"
1589                                        "reg2\t2\tSOFTWARE\\Wine\\keyA\tvalueA\tA\tregistry\n"
1590                                        "reg3\t2\tSOFTWARE\\Wine\\key1\t-\t\tregistry\n";
1591
1592 static const CHAR rrv_remove_registry_dat[] = "RemoveRegistry\tRoot\tKey\tName\tComponent_\n"
1593                                               "s72\ti2\tl255\tL255\ts72\n"
1594                                               "RemoveRegistry\tRemoveRegistry\n"
1595                                               "reg1\t2\tSOFTWARE\\Wine\\keyB\t\tregistry\n"
1596                                               "reg2\t2\tSOFTWARE\\Wine\\keyB\tValueB\tregistry\n"
1597                                               "reg3\t2\tSOFTWARE\\Wine\\key2\t-\tregistry\n";
1598
1599 static const CHAR rrv_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1600                                                "s72\tS255\tI2\n"
1601                                                "InstallExecuteSequence\tAction\n"
1602                                                "LaunchConditions\t\t100\n"
1603                                                "CostInitialize\t\t800\n"
1604                                                "FileCost\t\t900\n"
1605                                                "CostFinalize\t\t1000\n"
1606                                                "InstallValidate\t\t1400\n"
1607                                                "InstallInitialize\t\t1500\n"
1608                                                "ProcessComponents\t\t1600\n"
1609                                                "RemoveFiles\t\t1700\n"
1610                                                "InstallFiles\t\t2000\n"
1611                                                "RemoveRegistryValues\t\t3000\n"
1612                                                "RegisterProduct\t\t5000\n"
1613                                                "PublishFeatures\t\t5100\n"
1614                                                "PublishProduct\t\t5200\n"
1615                                                "InstallFinalize\t\t6000\n";
1616
1617 static const CHAR frp_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1618                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1619                                    "File\tFile\n"
1620                                    "product.txt\tproduct\tproduct.txt\t1000\t\t\t8192\t1\n";
1621
1622 static const CHAR frp_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1623                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1624                                       "Feature\tFeature\n"
1625                                       "product\t\t\tproduct feature\t1\t2\tMSITESTDIR\t0\n";
1626
1627 static const CHAR frp_feature_comp_dat[] = "Feature_\tComponent_\n"
1628                                            "s38\ts72\n"
1629                                            "FeatureComponents\tFeature_\tComponent_\n"
1630                                            "product\tproduct\n";
1631
1632 static const CHAR frp_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1633                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1634                                         "Component\tComponent\n"
1635                                         "product\t{44725EE0-EEA8-40BD-8162-A48224A2FEA1}\tMSITESTDIR\t0\t\tproduct.txt\n";
1636
1637 static const CHAR frp_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
1638                                             "s72\ti2\tS64\tS0\tS255\n"
1639                                             "CustomAction\tAction\n"
1640                                             "TestProp\t19\t\t\tPROP set\n";
1641
1642 static const CHAR frp_upgrade_dat[] = "UpgradeCode\tVersionMin\tVersionMax\tLanguage\tAttributes\tRemove\tActionProperty\n"
1643                                       "s38\tS20\tS20\tS255\ti4\tS255\ts72\n"
1644                                       "Upgrade\tUpgradeCode\tVersionMin\tVersionMax\tLanguage\tAttributes\n"
1645                                       "{4C0EAA15-0264-4E5A-8758-609EF142B92D}\t1.1.1\t2.2.2\t\t768\t\tPROP\n";
1646
1647 static const CHAR frp_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1648                                                "s72\tS255\tI2\n"
1649                                                "InstallExecuteSequence\tAction\n"
1650                                                "FindRelatedProducts\t\t50\n"
1651                                                "TestProp\tPROP AND NOT REMOVE\t51\n"
1652                                                "LaunchConditions\t\t100\n"
1653                                                "CostInitialize\t\t800\n"
1654                                                "FileCost\t\t900\n"
1655                                                "CostFinalize\t\t1000\n"
1656                                                "InstallValidate\t\t1400\n"
1657                                                "InstallInitialize\t\t1500\n"
1658                                                "ProcessComponents\t\t1600\n"
1659                                                "RemoveFiles\t\t1700\n"
1660                                                "InstallFiles\t\t2000\n"
1661                                                "RegisterProduct\t\t5000\n"
1662                                                "PublishFeatures\t\t5100\n"
1663                                                "PublishProduct\t\t5200\n"
1664                                                "InstallFinalize\t\t6000\n";
1665
1666 static const CHAR riv_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1667                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1668                                    "File\tFile\n"
1669                                    "inifile.txt\tinifile\tinifile.txt\t1000\t\t\t8192\t1\n";
1670
1671 static const CHAR riv_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1672                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1673                                       "Feature\tFeature\n"
1674                                       "inifile\t\t\tinifile feature\t1\t2\tMSITESTDIR\t0\n";
1675
1676 static const CHAR riv_feature_comp_dat[] = "Feature_\tComponent_\n"
1677                                            "s38\ts72\n"
1678                                            "FeatureComponents\tFeature_\tComponent_\n"
1679                                            "inifile\tinifile\n";
1680
1681 static const CHAR riv_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1682                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1683                                         "Component\tComponent\n"
1684                                         "inifile\t{A0F15705-4F57-4437-88C4-6C8B37ACC6DE}\tMSITESTDIR\t0\t\tinifile.txt\n";
1685
1686 static const CHAR riv_ini_file_dat[] = "IniFile\tFileName\tDirProperty\tSection\tKey\tValue\tAction\tComponent_\n"
1687                                        "s72\tl255\tS72\tl96\tl128\tl255\ti2\ts72\n"
1688                                        "IniFile\tIniFile\n"
1689                                        "inifile1\ttest.ini\tMSITESTDIR\tsection1\tkey1\tvalue1\t0\tinifile\n";
1690
1691 static const CHAR riv_remove_ini_file_dat[] = "RemoveIniFile\tFileName\tDirProperty\tSection\tKey\tValue\tAction\tComponent_\n"
1692                                               "s72\tl255\tS72\tl96\tl128\tL255\ti2\ts72\n"
1693                                               "RemoveIniFile\tRemoveIniFile\n"
1694                                               "inifile1\ttest.ini\tMSITESTDIR\tsectionA\tkeyA\tvalueA\t2\tinifile\n";
1695
1696 static const CHAR riv_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1697                                                "s72\tS255\tI2\n"
1698                                                "InstallExecuteSequence\tAction\n"
1699                                                "LaunchConditions\t\t100\n"
1700                                                "CostInitialize\t\t800\n"
1701                                                "FileCost\t\t900\n"
1702                                                "CostFinalize\t\t1000\n"
1703                                                "InstallValidate\t\t1400\n"
1704                                                "InstallInitialize\t\t1500\n"
1705                                                "ProcessComponents\t\t1600\n"
1706                                                "RemoveFiles\t\t1700\n"
1707                                                "InstallFiles\t\t2000\n"
1708                                                "RemoveIniValues\t\t3000\n"
1709                                                "RegisterProduct\t\t5000\n"
1710                                                "PublishFeatures\t\t5100\n"
1711                                                "PublishProduct\t\t5200\n"
1712                                                "InstallFinalize\t\t6000\n";
1713
1714 static const CHAR res_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1715                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1716                                    "File\tFile\n"
1717                                    "envvar.txt\tenvvar\tenvvar.txt\t1000\t\t\t8192\t1\n";
1718
1719 static const CHAR res_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1720                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1721                                       "Feature\tFeature\n"
1722                                       "envvar\t\t\tenvvar feature\t1\t2\tMSITESTDIR\t0\n";
1723
1724 static const CHAR res_feature_comp_dat[] = "Feature_\tComponent_\n"
1725                                            "s38\ts72\n"
1726                                            "FeatureComponents\tFeature_\tComponent_\n"
1727                                            "envvar\tenvvar\n";
1728
1729 static const CHAR res_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1730                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1731                                         "Component\tComponent\n"
1732                                         "envvar\t{45EE9AF4-E5D1-445F-8BB7-B22D4EEBD29E}\tMSITESTDIR\t0\t\tenvvar.txt\n";
1733
1734 static const CHAR res_environment_dat[] = "Environment\tName\tValue\tComponent_\n"
1735                                           "s72\tl255\tL255\ts72\n"
1736                                           "Environment\tEnvironment\n"
1737                                           "var1\t=-MSITESTVAR1\t1\tenvvar\n"
1738                                           "var2\t=+-MSITESTVAR2\t1\tenvvar\n"
1739                                           "var3\t=MSITESTVAR3\t1\tenvvar\n"
1740                                           "var4\t=-MSITESTVAR4\t\tenvvar\n"
1741                                           "var5\t=MSITESTVAR5\t\tenvvar\n";
1742
1743 static const CHAR res_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1744                                                "s72\tS255\tI2\n"
1745                                                "InstallExecuteSequence\tAction\n"
1746                                                "LaunchConditions\t\t100\n"
1747                                                "CostInitialize\t\t800\n"
1748                                                "FileCost\t\t900\n"
1749                                                "CostFinalize\t\t1000\n"
1750                                                "InstallValidate\t\t1400\n"
1751                                                "InstallInitialize\t\t1500\n"
1752                                                "ProcessComponents\t\t1600\n"
1753                                                "RemoveFiles\t\t1700\n"
1754                                                "InstallFiles\t\t2000\n"
1755                                                "RemoveEnvironmentStrings\t\t3000\n"
1756                                                "RegisterProduct\t\t5000\n"
1757                                                "PublishFeatures\t\t5100\n"
1758                                                "PublishProduct\t\t5200\n"
1759                                                "InstallFinalize\t\t6000\n";
1760
1761 static const CHAR rci_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1762                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1763                                    "File\tFile\n"
1764                                    "class.txt\tclass\tclass.txt\t1000\t\t\t8192\t1\n";
1765
1766 static const CHAR rci_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1767                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1768                                       "Feature\tFeature\n"
1769                                       "class\t\t\tclass feature\t1\t2\tMSITESTDIR\t0\n";
1770
1771 static const CHAR rci_feature_comp_dat[] = "Feature_\tComponent_\n"
1772                                            "s38\ts72\n"
1773                                            "FeatureComponents\tFeature_\tComponent_\n"
1774                                            "class\tclass\n";
1775
1776 static const CHAR rci_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1777                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1778                                         "Component\tComponent\n"
1779                                         "class\t{89A98345-F8A1-422E-A48B-0250B5809F2D}\tMSITESTDIR\t0\t\tclass.txt\n";
1780
1781 static const CHAR rci_appid_dat[] = "AppId\tRemoteServerName\tLocalService\tServiceParameters\tDllSurrogate\tActivateAtStorage\tRunAsInteractiveUser\n"
1782                                     "s38\tS255\tS255\tS255\tS255\tI2\tI2\n"
1783                                     "AppId\tAppId\n"
1784                                     "{CFCC3B38-E683-497D-9AB4-CB40AAFE307F}\t\t\t\t\t\t\n";
1785
1786 static const CHAR rci_class_dat[] = "CLSID\tContext\tComponent_\tProgId_Default\tDescription\tAppId_\tFileTypeMask\tIcon_\tIconIndex\tDefInprocHandler\tArgument\tFeature_\tAttributes\n"
1787                                     "s38\ts32\ts72\tS255\tL255\tS38\tS255\tS72\tI2\tS32\tS255\ts38\tI2\n"
1788                                     "Class\tCLSID\tContext\tComponent_\n"
1789                                     "{110913E7-86D1-4BF3-9922-BA103FCDDDFA}\tLocalServer\tclass\t\tdescription\t{CFCC3B38-E683-497D-9AB4-CB40AAFE307F}\tmask1;mask2\t\t\t2\t\tclass\t\n";
1790
1791 static const CHAR rci_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1792                                                "s72\tS255\tI2\n"
1793                                                "InstallExecuteSequence\tAction\n"
1794                                                "LaunchConditions\t\t100\n"
1795                                                "CostInitialize\t\t800\n"
1796                                                "FileCost\t\t900\n"
1797                                                "CostFinalize\t\t1000\n"
1798                                                "InstallValidate\t\t1400\n"
1799                                                "InstallInitialize\t\t1500\n"
1800                                                "ProcessComponents\t\t1600\n"
1801                                                "RemoveFiles\t\t1700\n"
1802                                                "InstallFiles\t\t2000\n"
1803                                                "UnregisterClassInfo\t\t3000\n"
1804                                                "RegisterClassInfo\t\t4000\n"
1805                                                "RegisterProduct\t\t5000\n"
1806                                                "PublishFeatures\t\t5100\n"
1807                                                "PublishProduct\t\t5200\n"
1808                                                "InstallFinalize\t\t6000\n";
1809
1810 static const CHAR rei_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1811                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1812                                    "File\tFile\n"
1813                                    "extension.txt\textension\textension.txt\t1000\t\t\t8192\t1\n";
1814
1815 static const CHAR rei_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1816                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1817                                       "Feature\tFeature\n"
1818                                       "extension\t\t\textension feature\t1\t2\tMSITESTDIR\t0\n";
1819
1820 static const CHAR rei_feature_comp_dat[] = "Feature_\tComponent_\n"
1821                                            "s38\ts72\n"
1822                                            "FeatureComponents\tFeature_\tComponent_\n"
1823                                            "extension\textension\n";
1824
1825 static const CHAR rei_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1826                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1827                                         "Component\tComponent\n"
1828                                         "extension\t{9A3060D4-60BA-4A82-AB55-9FB148AD013C}\tMSITESTDIR\t0\t\textension.txt\n";
1829
1830 static const CHAR rei_extension_dat[] = "Extension\tComponent_\tProgId_\tMIME_\tFeature_\n"
1831                                         "s255\ts72\tS255\tS64\ts38\n"
1832                                         "Extension\tExtension\tComponent_\n"
1833                                         "extension\textension\tProg.Id.1\t\textension\n";
1834
1835 static const CHAR rei_verb_dat[] = "Extension_\tVerb\tSequence\tCommand\tArgument\n"
1836                                    "s255\ts32\tI2\tL255\tL255\n"
1837                                    "Verb\tExtension_\tVerb\n"
1838                                    "extension\tOpen\t1\t&Open\t/argument\n";
1839
1840 static const CHAR rei_progid_dat[] = "ProgId\tProgId_Parent\tClass_\tDescription\tIcon_\tIconIndex\n"
1841                                      "s255\tS255\tS38\tL255\tS72\tI2\n"
1842                                      "ProgId\tProgId\n"
1843                                      "Prog.Id.1\t\t\tdescription\t\t\n";
1844
1845 static const CHAR rei_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1846                                                "s72\tS255\tI2\n"
1847                                                "InstallExecuteSequence\tAction\n"
1848                                                "LaunchConditions\t\t100\n"
1849                                                "CostInitialize\t\t800\n"
1850                                                "FileCost\t\t900\n"
1851                                                "CostFinalize\t\t1000\n"
1852                                                "InstallValidate\t\t1400\n"
1853                                                "InstallInitialize\t\t1500\n"
1854                                                "ProcessComponents\t\t1600\n"
1855                                                "RemoveFiles\t\t1700\n"
1856                                                "InstallFiles\t\t2000\n"
1857                                                "UnregisterExtensionInfo\t\t3000\n"
1858                                                "RegisterExtensionInfo\t\t4000\n"
1859                                                "RegisterProduct\t\t5000\n"
1860                                                "PublishFeatures\t\t5100\n"
1861                                                "PublishProduct\t\t5200\n"
1862                                                "InstallFinalize\t\t6000\n";
1863
1864 static const CHAR rmi_file_dat[] = "File\tComponent_\tFileName\tFileSize\tVersion\tLanguage\tAttributes\tSequence\n"
1865                                    "s72\ts72\tl255\ti4\tS72\tS20\tI2\ti2\n"
1866                                    "File\tFile\n"
1867                                    "mime.txt\tmime\tmime.txt\t1000\t\t\t8192\t1\n";
1868
1869 static const CHAR rmi_feature_dat[] = "Feature\tFeature_Parent\tTitle\tDescription\tDisplay\tLevel\tDirectory_\tAttributes\n"
1870                                       "s38\tS38\tL64\tL255\tI2\ti2\tS72\ti2\n"
1871                                       "Feature\tFeature\n"
1872                                       "mime\t\t\tmime feature\t1\t2\tMSITESTDIR\t0\n";
1873
1874 static const CHAR rmi_feature_comp_dat[] = "Feature_\tComponent_\n"
1875                                            "s38\ts72\n"
1876                                            "FeatureComponents\tFeature_\tComponent_\n"
1877                                            "mime\tmime\n";
1878
1879 static const CHAR rmi_component_dat[] = "Component\tComponentId\tDirectory_\tAttributes\tCondition\tKeyPath\n"
1880                                         "s72\tS38\ts72\ti2\tS255\tS72\n"
1881                                         "Component\tComponent\n"
1882                                         "mime\t{A1D630CE-13A7-4882-AFDD-148E2BBAFC6D}\tMSITESTDIR\t0\t\tmime.txt\n";
1883
1884 static const CHAR rmi_extension_dat[] = "Extension\tComponent_\tProgId_\tMIME_\tFeature_\n"
1885                                         "s255\ts72\tS255\tS64\ts38\n"
1886                                         "Extension\tExtension\tComponent_\n"
1887                                         "mime\tmime\t\tmime/type\tmime\n";
1888
1889 static const CHAR rmi_verb_dat[] = "Extension_\tVerb\tSequence\tCommand\tArgument\n"
1890                                    "s255\ts32\tI2\tL255\tL255\n"
1891                                    "Verb\tExtension_\tVerb\n"
1892                                    "mime\tOpen\t1\t&Open\t/argument\n";
1893
1894 static const CHAR rmi_mime_dat[] = "ContentType\tExtension_\tCLSID\n"
1895                                    "s64\ts255\tS38\n"
1896                                    "MIME\tContentType\n"
1897                                    "mime/type\tmime\t\n";
1898
1899 static const CHAR rmi_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
1900                                                "s72\tS255\tI2\n"
1901                                                "InstallExecuteSequence\tAction\n"
1902                                                "LaunchConditions\t\t100\n"
1903                                                "CostInitialize\t\t800\n"
1904                                                "FileCost\t\t900\n"
1905                                                "CostFinalize\t\t1000\n"
1906                                                "InstallValidate\t\t1400\n"
1907                                                "InstallInitialize\t\t1500\n"
1908                                                "ProcessComponents\t\t1600\n"
1909                                                "RemoveFiles\t\t1700\n"
1910                                                "InstallFiles\t\t2000\n"
1911                                                "UnregisterExtensionInfo\t\t3000\n"
1912                                                "UnregisterMIMEInfo\t\t3500\n"
1913                                                "RegisterExtensionInfo\t\t4000\n"
1914                                                "RegisterMIMEInfo\t\t4500\n"
1915                                                "RegisterProduct\t\t5000\n"
1916                                                "PublishFeatures\t\t5100\n"
1917                                                "PublishProduct\t\t5200\n"
1918                                                "InstallFinalize\t\t6000\n";
1919
1920 typedef struct _msi_table
1921 {
1922     const CHAR *filename;
1923     const CHAR *data;
1924     int size;
1925 } msi_table;
1926
1927 #define ADD_TABLE(x) {#x".idt", x##_dat, sizeof(x##_dat)}
1928
1929 static const msi_table tables[] =
1930 {
1931     ADD_TABLE(component),
1932     ADD_TABLE(directory),
1933     ADD_TABLE(feature),
1934     ADD_TABLE(feature_comp),
1935     ADD_TABLE(file),
1936     ADD_TABLE(install_exec_seq),
1937     ADD_TABLE(media),
1938     ADD_TABLE(property),
1939     ADD_TABLE(registry),
1940     ADD_TABLE(service_install),
1941     ADD_TABLE(service_control)
1942 };
1943
1944 static const msi_table sc_tables[] =
1945 {
1946     ADD_TABLE(component),
1947     ADD_TABLE(directory),
1948     ADD_TABLE(feature),
1949     ADD_TABLE(feature_comp),
1950     ADD_TABLE(file),
1951     ADD_TABLE(install_exec_seq),
1952     ADD_TABLE(media),
1953     ADD_TABLE(property),
1954     ADD_TABLE(shortcut)
1955 };
1956
1957 static const msi_table ps_tables[] =
1958 {
1959     ADD_TABLE(component),
1960     ADD_TABLE(directory),
1961     ADD_TABLE(feature),
1962     ADD_TABLE(feature_comp),
1963     ADD_TABLE(file),
1964     ADD_TABLE(install_exec_seq),
1965     ADD_TABLE(media),
1966     ADD_TABLE(property),
1967     ADD_TABLE(condition)
1968 };
1969
1970 static const msi_table env_tables[] =
1971 {
1972     ADD_TABLE(component),
1973     ADD_TABLE(directory),
1974     ADD_TABLE(feature),
1975     ADD_TABLE(feature_comp),
1976     ADD_TABLE(file),
1977     ADD_TABLE(install_exec_seq),
1978     ADD_TABLE(media),
1979     ADD_TABLE(property),
1980     ADD_TABLE(environment)
1981 };
1982
1983 static const msi_table up_tables[] =
1984 {
1985     ADD_TABLE(component),
1986     ADD_TABLE(directory),
1987     ADD_TABLE(feature),
1988     ADD_TABLE(feature_comp),
1989     ADD_TABLE(file),
1990     ADD_TABLE(install_exec_seq),
1991     ADD_TABLE(media),
1992     ADD_TABLE(up_property),
1993     ADD_TABLE(registry),
1994     ADD_TABLE(service_install),
1995     ADD_TABLE(service_control)
1996 };
1997
1998 static const msi_table up2_tables[] =
1999 {
2000     ADD_TABLE(component),
2001     ADD_TABLE(directory),
2002     ADD_TABLE(feature),
2003     ADD_TABLE(feature_comp),
2004     ADD_TABLE(file),
2005     ADD_TABLE(install_exec_seq),
2006     ADD_TABLE(media),
2007     ADD_TABLE(up2_property),
2008     ADD_TABLE(registry),
2009     ADD_TABLE(service_install),
2010     ADD_TABLE(service_control)
2011 };
2012
2013 static const msi_table up3_tables[] =
2014 {
2015     ADD_TABLE(component),
2016     ADD_TABLE(directory),
2017     ADD_TABLE(feature),
2018     ADD_TABLE(feature_comp),
2019     ADD_TABLE(file),
2020     ADD_TABLE(install_exec_seq),
2021     ADD_TABLE(media),
2022     ADD_TABLE(up3_property),
2023     ADD_TABLE(registry),
2024     ADD_TABLE(service_install),
2025     ADD_TABLE(service_control)
2026 };
2027
2028 static const msi_table up4_tables[] =
2029 {
2030     ADD_TABLE(component),
2031     ADD_TABLE(directory),
2032     ADD_TABLE(feature),
2033     ADD_TABLE(feature_comp),
2034     ADD_TABLE(file),
2035     ADD_TABLE(pp_install_exec_seq),
2036     ADD_TABLE(media),
2037     ADD_TABLE(property),
2038     ADD_TABLE(registry),
2039     ADD_TABLE(service_install),
2040     ADD_TABLE(service_control)
2041 };
2042
2043 static const msi_table up5_tables[] =
2044 {
2045     ADD_TABLE(component),
2046     ADD_TABLE(directory),
2047     ADD_TABLE(feature),
2048     ADD_TABLE(feature_comp),
2049     ADD_TABLE(file),
2050     ADD_TABLE(pp_install_exec_seq),
2051     ADD_TABLE(media),
2052     ADD_TABLE(up_property),
2053     ADD_TABLE(registry),
2054     ADD_TABLE(service_install),
2055     ADD_TABLE(service_control)
2056 };
2057
2058 static const msi_table up6_tables[] =
2059 {
2060     ADD_TABLE(component),
2061     ADD_TABLE(directory),
2062     ADD_TABLE(feature),
2063     ADD_TABLE(feature_comp),
2064     ADD_TABLE(file),
2065     ADD_TABLE(pp_install_exec_seq),
2066     ADD_TABLE(media),
2067     ADD_TABLE(up2_property),
2068     ADD_TABLE(registry),
2069     ADD_TABLE(service_install),
2070     ADD_TABLE(service_control)
2071 };
2072
2073 static const msi_table up7_tables[] =
2074 {
2075     ADD_TABLE(component),
2076     ADD_TABLE(directory),
2077     ADD_TABLE(feature),
2078     ADD_TABLE(feature_comp),
2079     ADD_TABLE(file),
2080     ADD_TABLE(pp_install_exec_seq),
2081     ADD_TABLE(media),
2082     ADD_TABLE(up3_property),
2083     ADD_TABLE(registry),
2084     ADD_TABLE(service_install),
2085     ADD_TABLE(service_control)
2086 };
2087
2088 static const msi_table cc_tables[] =
2089 {
2090     ADD_TABLE(cc_component),
2091     ADD_TABLE(directory),
2092     ADD_TABLE(cc_feature),
2093     ADD_TABLE(cc_feature_comp),
2094     ADD_TABLE(cc_file),
2095     ADD_TABLE(install_exec_seq),
2096     ADD_TABLE(cc_media),
2097     ADD_TABLE(property),
2098 };
2099
2100 static const msi_table cc2_tables[] =
2101 {
2102     ADD_TABLE(cc2_component),
2103     ADD_TABLE(directory),
2104     ADD_TABLE(cc_feature),
2105     ADD_TABLE(cc_feature_comp),
2106     ADD_TABLE(cc2_file),
2107     ADD_TABLE(install_exec_seq),
2108     ADD_TABLE(cc_media),
2109     ADD_TABLE(property),
2110 };
2111
2112 static const msi_table co_tables[] =
2113 {
2114     ADD_TABLE(cc_component),
2115     ADD_TABLE(directory),
2116     ADD_TABLE(cc_feature),
2117     ADD_TABLE(cc_feature_comp),
2118     ADD_TABLE(co_file),
2119     ADD_TABLE(install_exec_seq),
2120     ADD_TABLE(co_media),
2121     ADD_TABLE(property),
2122 };
2123
2124 static const msi_table co2_tables[] =
2125 {
2126     ADD_TABLE(cc_component),
2127     ADD_TABLE(directory),
2128     ADD_TABLE(cc_feature),
2129     ADD_TABLE(cc_feature_comp),
2130     ADD_TABLE(cc_file),
2131     ADD_TABLE(install_exec_seq),
2132     ADD_TABLE(co2_media),
2133     ADD_TABLE(property),
2134 };
2135
2136 static const msi_table mm_tables[] =
2137 {
2138     ADD_TABLE(cc_component),
2139     ADD_TABLE(directory),
2140     ADD_TABLE(cc_feature),
2141     ADD_TABLE(cc_feature_comp),
2142     ADD_TABLE(mm_file),
2143     ADD_TABLE(install_exec_seq),
2144     ADD_TABLE(mm_media),
2145     ADD_TABLE(property),
2146 };
2147
2148 static const msi_table ss_tables[] =
2149 {
2150     ADD_TABLE(cc_component),
2151     ADD_TABLE(directory),
2152     ADD_TABLE(cc_feature),
2153     ADD_TABLE(cc_feature_comp),
2154     ADD_TABLE(cc_file),
2155     ADD_TABLE(install_exec_seq),
2156     ADD_TABLE(ss_media),
2157     ADD_TABLE(property),
2158 };
2159
2160 static const msi_table ui_tables[] =
2161 {
2162     ADD_TABLE(ui_component),
2163     ADD_TABLE(directory),
2164     ADD_TABLE(cc_feature),
2165     ADD_TABLE(cc_feature_comp),
2166     ADD_TABLE(cc_file),
2167     ADD_TABLE(install_exec_seq),
2168     ADD_TABLE(ui_install_ui_seq),
2169     ADD_TABLE(ui_custom_action),
2170     ADD_TABLE(cc_media),
2171     ADD_TABLE(property),
2172 };
2173
2174 static const msi_table rof_tables[] =
2175 {
2176     ADD_TABLE(rof_component),
2177     ADD_TABLE(directory),
2178     ADD_TABLE(rof_feature),
2179     ADD_TABLE(rof_feature_comp),
2180     ADD_TABLE(rof_file),
2181     ADD_TABLE(install_exec_seq),
2182     ADD_TABLE(rof_media),
2183     ADD_TABLE(property),
2184 };
2185
2186 static const msi_table rofc_tables[] =
2187 {
2188     ADD_TABLE(rof_component),
2189     ADD_TABLE(directory),
2190     ADD_TABLE(rof_feature),
2191     ADD_TABLE(rof_feature_comp),
2192     ADD_TABLE(rofc_file),
2193     ADD_TABLE(install_exec_seq),
2194     ADD_TABLE(rofc_media),
2195     ADD_TABLE(property),
2196 };
2197
2198 static const msi_table sdp_tables[] =
2199 {
2200     ADD_TABLE(rof_component),
2201     ADD_TABLE(directory),
2202     ADD_TABLE(rof_feature),
2203     ADD_TABLE(rof_feature_comp),
2204     ADD_TABLE(rof_file),
2205     ADD_TABLE(sdp_install_exec_seq),
2206     ADD_TABLE(sdp_custom_action),
2207     ADD_TABLE(rof_media),
2208     ADD_TABLE(property),
2209 };
2210
2211 static const msi_table cie_tables[] =
2212 {
2213     ADD_TABLE(cie_component),
2214     ADD_TABLE(directory),
2215     ADD_TABLE(cc_feature),
2216     ADD_TABLE(cie_feature_comp),
2217     ADD_TABLE(cie_file),
2218     ADD_TABLE(install_exec_seq),
2219     ADD_TABLE(cie_media),
2220     ADD_TABLE(property),
2221 };
2222
2223 static const msi_table ci_tables[] =
2224 {
2225     ADD_TABLE(ci_component),
2226     ADD_TABLE(directory),
2227     ADD_TABLE(rof_feature),
2228     ADD_TABLE(rof_feature_comp),
2229     ADD_TABLE(rof_file),
2230     ADD_TABLE(ci_install_exec_seq),
2231     ADD_TABLE(rof_media),
2232     ADD_TABLE(property),
2233     ADD_TABLE(ci_custom_action),
2234 };
2235
2236 static const msi_table ci2_tables[] =
2237 {
2238     ADD_TABLE(ci2_component),
2239     ADD_TABLE(directory),
2240     ADD_TABLE(rof_feature),
2241     ADD_TABLE(ci2_feature_comp),
2242     ADD_TABLE(ci2_file),
2243     ADD_TABLE(install_exec_seq),
2244     ADD_TABLE(rof_media),
2245     ADD_TABLE(property),
2246 };
2247
2248 static const msi_table spf_tables[] =
2249 {
2250     ADD_TABLE(ci_component),
2251     ADD_TABLE(directory),
2252     ADD_TABLE(rof_feature),
2253     ADD_TABLE(rof_feature_comp),
2254     ADD_TABLE(rof_file),
2255     ADD_TABLE(spf_install_exec_seq),
2256     ADD_TABLE(rof_media),
2257     ADD_TABLE(property),
2258     ADD_TABLE(spf_custom_action),
2259     ADD_TABLE(spf_install_ui_seq),
2260 };
2261
2262 static const msi_table pp_tables[] =
2263 {
2264     ADD_TABLE(ci_component),
2265     ADD_TABLE(directory),
2266     ADD_TABLE(rof_feature),
2267     ADD_TABLE(rof_feature_comp),
2268     ADD_TABLE(rof_file),
2269     ADD_TABLE(pp_install_exec_seq),
2270     ADD_TABLE(rof_media),
2271     ADD_TABLE(property),
2272 };
2273
2274 static const msi_table ppc_tables[] =
2275 {
2276     ADD_TABLE(ppc_component),
2277     ADD_TABLE(directory),
2278     ADD_TABLE(rof_feature),
2279     ADD_TABLE(ppc_feature_comp),
2280     ADD_TABLE(ppc_file),
2281     ADD_TABLE(pp_install_exec_seq),
2282     ADD_TABLE(ppc_media),
2283     ADD_TABLE(property),
2284 };
2285
2286 static const msi_table lus0_tables[] =
2287 {
2288     ADD_TABLE(ci_component),
2289     ADD_TABLE(directory),
2290     ADD_TABLE(rof_feature),
2291     ADD_TABLE(rof_feature_comp),
2292     ADD_TABLE(rof_file),
2293     ADD_TABLE(pp_install_exec_seq),
2294     ADD_TABLE(rof_media),
2295     ADD_TABLE(property),
2296 };
2297
2298 static const msi_table lus1_tables[] =
2299 {
2300     ADD_TABLE(ci_component),
2301     ADD_TABLE(directory),
2302     ADD_TABLE(rof_feature),
2303     ADD_TABLE(rof_feature_comp),
2304     ADD_TABLE(rof_file),
2305     ADD_TABLE(pp_install_exec_seq),
2306     ADD_TABLE(rofc_media),
2307     ADD_TABLE(property),
2308 };
2309
2310 static const msi_table lus2_tables[] =
2311 {
2312     ADD_TABLE(ci_component),
2313     ADD_TABLE(directory),
2314     ADD_TABLE(rof_feature),
2315     ADD_TABLE(rof_feature_comp),
2316     ADD_TABLE(rof_file),
2317     ADD_TABLE(pp_install_exec_seq),
2318     ADD_TABLE(lus2_media),
2319     ADD_TABLE(property),
2320 };
2321
2322 static const msi_table tp_tables[] =
2323 {
2324     ADD_TABLE(tp_component),
2325     ADD_TABLE(directory),
2326     ADD_TABLE(rof_feature),
2327     ADD_TABLE(ci2_feature_comp),
2328     ADD_TABLE(ci2_file),
2329     ADD_TABLE(install_exec_seq),
2330     ADD_TABLE(rof_media),
2331     ADD_TABLE(property),
2332 };
2333
2334 static const msi_table cwd_tables[] =
2335 {
2336     ADD_TABLE(cwd_component),
2337     ADD_TABLE(directory),
2338     ADD_TABLE(rof_feature),
2339     ADD_TABLE(ci2_feature_comp),
2340     ADD_TABLE(ci2_file),
2341     ADD_TABLE(install_exec_seq),
2342     ADD_TABLE(rof_media),
2343     ADD_TABLE(property),
2344 };
2345
2346 static const msi_table adm_tables[] =
2347 {
2348     ADD_TABLE(adm_component),
2349     ADD_TABLE(directory),
2350     ADD_TABLE(rof_feature),
2351     ADD_TABLE(ci2_feature_comp),
2352     ADD_TABLE(ci2_file),
2353     ADD_TABLE(install_exec_seq),
2354     ADD_TABLE(rof_media),
2355     ADD_TABLE(property),
2356     ADD_TABLE(adm_custom_action),
2357     ADD_TABLE(adm_admin_exec_seq),
2358 };
2359
2360 static const msi_table amp_tables[] =
2361 {
2362     ADD_TABLE(amp_component),
2363     ADD_TABLE(directory),
2364     ADD_TABLE(rof_feature),
2365     ADD_TABLE(ci2_feature_comp),
2366     ADD_TABLE(ci2_file),
2367     ADD_TABLE(install_exec_seq),
2368     ADD_TABLE(rof_media),
2369     ADD_TABLE(property),
2370 };
2371
2372 static const msi_table rem_tables[] =
2373 {
2374     ADD_TABLE(rem_component),
2375     ADD_TABLE(directory),
2376     ADD_TABLE(rof_feature),
2377     ADD_TABLE(rem_feature_comp),
2378     ADD_TABLE(rem_file),
2379     ADD_TABLE(rem_install_exec_seq),
2380     ADD_TABLE(rof_media),
2381     ADD_TABLE(property),
2382     ADD_TABLE(rem_remove_files),
2383 };
2384
2385 static const msi_table mov_tables[] =
2386 {
2387     ADD_TABLE(cwd_component),
2388     ADD_TABLE(directory),
2389     ADD_TABLE(rof_feature),
2390     ADD_TABLE(ci2_feature_comp),
2391     ADD_TABLE(ci2_file),
2392     ADD_TABLE(install_exec_seq),
2393     ADD_TABLE(rof_media),
2394     ADD_TABLE(property),
2395     ADD_TABLE(mov_move_file),
2396 };
2397
2398 static const msi_table mc_tables[] =
2399 {
2400     ADD_TABLE(mc_component),
2401     ADD_TABLE(directory),
2402     ADD_TABLE(cc_feature),
2403     ADD_TABLE(cie_feature_comp),
2404     ADD_TABLE(mc_file),
2405     ADD_TABLE(install_exec_seq),
2406     ADD_TABLE(mc_media),
2407     ADD_TABLE(property),
2408     ADD_TABLE(mc_file_hash),
2409 };
2410
2411 static const msi_table df_tables[] =
2412 {
2413     ADD_TABLE(rof_component),
2414     ADD_TABLE(df_directory),
2415     ADD_TABLE(rof_feature),
2416     ADD_TABLE(rof_feature_comp),
2417     ADD_TABLE(rof_file),
2418     ADD_TABLE(install_exec_seq),
2419     ADD_TABLE(rof_media),
2420     ADD_TABLE(property),
2421     ADD_TABLE(df_duplicate_file),
2422 };
2423
2424 static const msi_table wrv_tables[] =
2425 {
2426     ADD_TABLE(wrv_component),
2427     ADD_TABLE(directory),
2428     ADD_TABLE(rof_feature),
2429     ADD_TABLE(ci2_feature_comp),
2430     ADD_TABLE(ci2_file),
2431     ADD_TABLE(install_exec_seq),
2432     ADD_TABLE(rof_media),
2433     ADD_TABLE(property),
2434     ADD_TABLE(wrv_registry),
2435 };
2436
2437 static const msi_table sf_tables[] =
2438 {
2439     ADD_TABLE(wrv_component),
2440     ADD_TABLE(directory),
2441     ADD_TABLE(rof_feature),
2442     ADD_TABLE(ci2_feature_comp),
2443     ADD_TABLE(ci2_file),
2444     ADD_TABLE(install_exec_seq),
2445     ADD_TABLE(rof_media),
2446     ADD_TABLE(property),
2447 };
2448
2449 static const msi_table ca51_tables[] =
2450 {
2451     ADD_TABLE(ca51_component),
2452     ADD_TABLE(directory),
2453     ADD_TABLE(rof_feature),
2454     ADD_TABLE(ci2_feature_comp),
2455     ADD_TABLE(ci2_file),
2456     ADD_TABLE(ca51_install_exec_seq),
2457     ADD_TABLE(rof_media),
2458     ADD_TABLE(property),
2459     ADD_TABLE(ca51_custom_action),
2460 };
2461
2462 static const msi_table is_tables[] =
2463 {
2464     ADD_TABLE(is_component),
2465     ADD_TABLE(directory),
2466     ADD_TABLE(is_feature),
2467     ADD_TABLE(is_feature_comp),
2468     ADD_TABLE(is_file),
2469     ADD_TABLE(install_exec_seq),
2470     ADD_TABLE(is_media),
2471     ADD_TABLE(property),
2472 };
2473
2474 static const msi_table sp_tables[] =
2475 {
2476     ADD_TABLE(sp_component),
2477     ADD_TABLE(sp_directory),
2478     ADD_TABLE(rof_feature),
2479     ADD_TABLE(ci2_feature_comp),
2480     ADD_TABLE(ci2_file),
2481     ADD_TABLE(install_exec_seq),
2482     ADD_TABLE(rof_media),
2483     ADD_TABLE(property),
2484 };
2485
2486 static const msi_table mcp_tables[] =
2487 {
2488     ADD_TABLE(mcp_component),
2489     ADD_TABLE(directory),
2490     ADD_TABLE(mcp_feature),
2491     ADD_TABLE(mcp_feature_comp),
2492     ADD_TABLE(rem_file),
2493     ADD_TABLE(rem_install_exec_seq),
2494     ADD_TABLE(rof_media),
2495     ADD_TABLE(property),
2496 };
2497
2498 static const msi_table mcomp_tables[] =
2499 {
2500     ADD_TABLE(mcp_component),
2501     ADD_TABLE(directory),
2502     ADD_TABLE(mcp_feature),
2503     ADD_TABLE(mcp_feature_comp),
2504     ADD_TABLE(mcomp_file),
2505     ADD_TABLE(rem_install_exec_seq),
2506     ADD_TABLE(rof_media),
2507     ADD_TABLE(property),
2508 };
2509
2510 static const msi_table ai_tables[] =
2511 {
2512     ADD_TABLE(component),
2513     ADD_TABLE(directory),
2514     ADD_TABLE(feature),
2515     ADD_TABLE(feature_comp),
2516     ADD_TABLE(ai_file),
2517     ADD_TABLE(install_exec_seq),
2518     ADD_TABLE(media),
2519     ADD_TABLE(property)
2520 };
2521
2522 static const msi_table pc_tables[] =
2523 {
2524     ADD_TABLE(ca51_component),
2525     ADD_TABLE(directory),
2526     ADD_TABLE(rof_feature),
2527     ADD_TABLE(ci2_feature_comp),
2528     ADD_TABLE(ci2_file),
2529     ADD_TABLE(install_exec_seq),
2530     ADD_TABLE(rof_media),
2531     ADD_TABLE(property)
2532 };
2533
2534 static const msi_table ip_tables[] =
2535 {
2536     ADD_TABLE(component),
2537     ADD_TABLE(directory),
2538     ADD_TABLE(feature),
2539     ADD_TABLE(feature_comp),
2540     ADD_TABLE(file),
2541     ADD_TABLE(ip_install_exec_seq),
2542     ADD_TABLE(ip_custom_action),
2543     ADD_TABLE(media),
2544     ADD_TABLE(property)
2545 };
2546
2547 static const msi_table aup_tables[] =
2548 {
2549     ADD_TABLE(component),
2550     ADD_TABLE(directory),
2551     ADD_TABLE(feature),
2552     ADD_TABLE(feature_comp),
2553     ADD_TABLE(file),
2554     ADD_TABLE(aup_install_exec_seq),
2555     ADD_TABLE(aup_custom_action),
2556     ADD_TABLE(media),
2557     ADD_TABLE(property)
2558 };
2559
2560 static const msi_table aup2_tables[] =
2561 {
2562     ADD_TABLE(component),
2563     ADD_TABLE(directory),
2564     ADD_TABLE(feature),
2565     ADD_TABLE(feature_comp),
2566     ADD_TABLE(file),
2567     ADD_TABLE(aup2_install_exec_seq),
2568     ADD_TABLE(aup_custom_action),
2569     ADD_TABLE(media),
2570     ADD_TABLE(aup_property)
2571 };
2572
2573 static const msi_table aup3_tables[] =
2574 {
2575     ADD_TABLE(component),
2576     ADD_TABLE(directory),
2577     ADD_TABLE(feature),
2578     ADD_TABLE(feature_comp),
2579     ADD_TABLE(file),
2580     ADD_TABLE(aup2_install_exec_seq),
2581     ADD_TABLE(aup_custom_action),
2582     ADD_TABLE(media),
2583     ADD_TABLE(aup2_property)
2584 };
2585
2586 static const msi_table aup4_tables[] =
2587 {
2588     ADD_TABLE(component),
2589     ADD_TABLE(directory),
2590     ADD_TABLE(feature),
2591     ADD_TABLE(feature_comp),
2592     ADD_TABLE(file),
2593     ADD_TABLE(aup3_install_exec_seq),
2594     ADD_TABLE(aup_custom_action),
2595     ADD_TABLE(media),
2596     ADD_TABLE(aup2_property)
2597 };
2598
2599 static const msi_table fiu_tables[] =
2600 {
2601     ADD_TABLE(rof_component),
2602     ADD_TABLE(directory),
2603     ADD_TABLE(rof_feature),
2604     ADD_TABLE(rof_feature_comp),
2605     ADD_TABLE(rof_file),
2606     ADD_TABLE(pp_install_exec_seq),
2607     ADD_TABLE(rof_media),
2608     ADD_TABLE(property),
2609 };
2610
2611 static const msi_table fiuc_tables[] =
2612 {
2613     ADD_TABLE(rof_component),
2614     ADD_TABLE(directory),
2615     ADD_TABLE(rof_feature),
2616     ADD_TABLE(rof_feature_comp),
2617     ADD_TABLE(rofc_file),
2618     ADD_TABLE(pp_install_exec_seq),
2619     ADD_TABLE(rofc_media),
2620     ADD_TABLE(property),
2621 };
2622
2623 static const msi_table cf_tables[] =
2624 {
2625     ADD_TABLE(component),
2626     ADD_TABLE(directory),
2627     ADD_TABLE(feature),
2628     ADD_TABLE(feature_comp),
2629     ADD_TABLE(file),
2630     ADD_TABLE(cf_create_folders),
2631     ADD_TABLE(cf_install_exec_seq),
2632     ADD_TABLE(cf_custom_action),
2633     ADD_TABLE(media),
2634     ADD_TABLE(property)
2635 };
2636
2637 static const msi_table rf_tables[] =
2638 {
2639     ADD_TABLE(component),
2640     ADD_TABLE(directory),
2641     ADD_TABLE(feature),
2642     ADD_TABLE(feature_comp),
2643     ADD_TABLE(file),
2644     ADD_TABLE(cf_create_folders),
2645     ADD_TABLE(rf_install_exec_seq),
2646     ADD_TABLE(cf_custom_action),
2647     ADD_TABLE(media),
2648     ADD_TABLE(property)
2649 };
2650
2651 static const msi_table sss_tables[] =
2652 {
2653     ADD_TABLE(component),
2654     ADD_TABLE(directory),
2655     ADD_TABLE(feature),
2656     ADD_TABLE(feature_comp),
2657     ADD_TABLE(file),
2658     ADD_TABLE(sss_install_exec_seq),
2659     ADD_TABLE(sss_service_control),
2660     ADD_TABLE(media),
2661     ADD_TABLE(property)
2662 };
2663
2664 static const msi_table sds_tables[] =
2665 {
2666     ADD_TABLE(component),
2667     ADD_TABLE(directory),
2668     ADD_TABLE(feature),
2669     ADD_TABLE(feature_comp),
2670     ADD_TABLE(file),
2671     ADD_TABLE(sss_install_exec_seq),
2672     ADD_TABLE(service_control),
2673     ADD_TABLE(media),
2674     ADD_TABLE(property)
2675 };
2676
2677 static const msi_table sr_tables[] =
2678 {
2679     ADD_TABLE(component),
2680     ADD_TABLE(directory),
2681     ADD_TABLE(feature),
2682     ADD_TABLE(feature_comp),
2683     ADD_TABLE(file),
2684     ADD_TABLE(sr_selfreg),
2685     ADD_TABLE(sr_install_exec_seq),
2686     ADD_TABLE(media),
2687     ADD_TABLE(property)
2688 };
2689
2690 static const msi_table font_tables[] =
2691 {
2692     ADD_TABLE(font_component),
2693     ADD_TABLE(directory),
2694     ADD_TABLE(font_feature),
2695     ADD_TABLE(font_feature_comp),
2696     ADD_TABLE(font_file),
2697     ADD_TABLE(font),
2698     ADD_TABLE(font_install_exec_seq),
2699     ADD_TABLE(font_media),
2700     ADD_TABLE(property)
2701 };
2702
2703 static const msi_table vp_tables[] =
2704 {
2705     ADD_TABLE(component),
2706     ADD_TABLE(directory),
2707     ADD_TABLE(feature),
2708     ADD_TABLE(feature_comp),
2709     ADD_TABLE(file),
2710     ADD_TABLE(vp_custom_action),
2711     ADD_TABLE(vp_install_exec_seq),
2712     ADD_TABLE(media),
2713     ADD_TABLE(vp_property)
2714 };
2715
2716 static const msi_table odbc_tables[] =
2717 {
2718     ADD_TABLE(odbc_component),
2719     ADD_TABLE(directory),
2720     ADD_TABLE(odbc_feature),
2721     ADD_TABLE(odbc_feature_comp),
2722     ADD_TABLE(odbc_file),
2723     ADD_TABLE(odbc_driver),
2724     ADD_TABLE(odbc_translator),
2725     ADD_TABLE(odbc_datasource),
2726     ADD_TABLE(odbc_install_exec_seq),
2727     ADD_TABLE(odbc_media),
2728     ADD_TABLE(property)
2729 };
2730
2731 static const msi_table tl_tables[] =
2732 {
2733     ADD_TABLE(tl_component),
2734     ADD_TABLE(directory),
2735     ADD_TABLE(tl_feature),
2736     ADD_TABLE(tl_feature_comp),
2737     ADD_TABLE(tl_file),
2738     ADD_TABLE(tl_typelib),
2739     ADD_TABLE(tl_install_exec_seq),
2740     ADD_TABLE(media),
2741     ADD_TABLE(property)
2742 };
2743
2744 static const msi_table crs_tables[] =
2745 {
2746     ADD_TABLE(crs_component),
2747     ADD_TABLE(directory),
2748     ADD_TABLE(crs_feature),
2749     ADD_TABLE(crs_feature_comp),
2750     ADD_TABLE(crs_file),
2751     ADD_TABLE(crs_shortcut),
2752     ADD_TABLE(crs_install_exec_seq),
2753     ADD_TABLE(media),
2754     ADD_TABLE(property)
2755 };
2756
2757 static const msi_table pub_tables[] =
2758 {
2759     ADD_TABLE(directory),
2760     ADD_TABLE(pub_component),
2761     ADD_TABLE(pub_feature),
2762     ADD_TABLE(pub_feature_comp),
2763     ADD_TABLE(pub_file),
2764     ADD_TABLE(pub_publish_component),
2765     ADD_TABLE(pub_install_exec_seq),
2766     ADD_TABLE(media),
2767     ADD_TABLE(property)
2768 };
2769
2770 static const msi_table rd_tables[] =
2771 {
2772     ADD_TABLE(directory),
2773     ADD_TABLE(rd_component),
2774     ADD_TABLE(rd_feature),
2775     ADD_TABLE(rd_feature_comp),
2776     ADD_TABLE(rd_file),
2777     ADD_TABLE(rd_duplicate_file),
2778     ADD_TABLE(rd_install_exec_seq),
2779     ADD_TABLE(media),
2780     ADD_TABLE(property)
2781 };
2782
2783 static const msi_table rrv_tables[] =
2784 {
2785     ADD_TABLE(directory),
2786     ADD_TABLE(rrv_component),
2787     ADD_TABLE(rrv_feature),
2788     ADD_TABLE(rrv_feature_comp),
2789     ADD_TABLE(rrv_file),
2790     ADD_TABLE(rrv_registry),
2791     ADD_TABLE(rrv_remove_registry),
2792     ADD_TABLE(rrv_install_exec_seq),
2793     ADD_TABLE(media),
2794     ADD_TABLE(property)
2795 };
2796
2797 static const msi_table frp_tables[] =
2798 {
2799     ADD_TABLE(directory),
2800     ADD_TABLE(frp_component),
2801     ADD_TABLE(frp_feature),
2802     ADD_TABLE(frp_feature_comp),
2803     ADD_TABLE(frp_file),
2804     ADD_TABLE(frp_upgrade),
2805     ADD_TABLE(frp_custom_action),
2806     ADD_TABLE(frp_install_exec_seq),
2807     ADD_TABLE(media),
2808     ADD_TABLE(property)
2809 };
2810
2811 static const msi_table riv_tables[] =
2812 {
2813     ADD_TABLE(directory),
2814     ADD_TABLE(riv_component),
2815     ADD_TABLE(riv_feature),
2816     ADD_TABLE(riv_feature_comp),
2817     ADD_TABLE(riv_file),
2818     ADD_TABLE(riv_ini_file),
2819     ADD_TABLE(riv_remove_ini_file),
2820     ADD_TABLE(riv_install_exec_seq),
2821     ADD_TABLE(media),
2822     ADD_TABLE(property)
2823 };
2824
2825 static const msi_table res_tables[] =
2826 {
2827     ADD_TABLE(directory),
2828     ADD_TABLE(res_component),
2829     ADD_TABLE(res_feature),
2830     ADD_TABLE(res_feature_comp),
2831     ADD_TABLE(res_file),
2832     ADD_TABLE(res_environment),
2833     ADD_TABLE(res_install_exec_seq),
2834     ADD_TABLE(media),
2835     ADD_TABLE(property)
2836 };
2837
2838 static const msi_table rci_tables[] =
2839 {
2840     ADD_TABLE(directory),
2841     ADD_TABLE(rci_component),
2842     ADD_TABLE(rci_feature),
2843     ADD_TABLE(rci_feature_comp),
2844     ADD_TABLE(rci_file),
2845     ADD_TABLE(rci_appid),
2846     ADD_TABLE(rci_class),
2847     ADD_TABLE(rci_install_exec_seq),
2848     ADD_TABLE(media),
2849     ADD_TABLE(property)
2850 };
2851
2852 static const msi_table rei_tables[] =
2853 {
2854     ADD_TABLE(directory),
2855     ADD_TABLE(rei_component),
2856     ADD_TABLE(rei_feature),
2857     ADD_TABLE(rei_feature_comp),
2858     ADD_TABLE(rei_file),
2859     ADD_TABLE(rei_extension),
2860     ADD_TABLE(rei_verb),
2861     ADD_TABLE(rei_progid),
2862     ADD_TABLE(rei_install_exec_seq),
2863     ADD_TABLE(media),
2864     ADD_TABLE(property)
2865 };
2866
2867 static const msi_table rmi_tables[] =
2868 {
2869     ADD_TABLE(directory),
2870     ADD_TABLE(rmi_component),
2871     ADD_TABLE(rmi_feature),
2872     ADD_TABLE(rmi_feature_comp),
2873     ADD_TABLE(rmi_file),
2874     ADD_TABLE(rmi_extension),
2875     ADD_TABLE(rmi_verb),
2876     ADD_TABLE(rmi_mime),
2877     ADD_TABLE(rmi_install_exec_seq),
2878     ADD_TABLE(media),
2879     ADD_TABLE(property)
2880 };
2881
2882 static const msi_table fo_tables[] =
2883 {
2884     ADD_TABLE(directory),
2885     ADD_TABLE(fo_file),
2886     ADD_TABLE(fo_component),
2887     ADD_TABLE(fo_feature),
2888     ADD_TABLE(fo_condition),
2889     ADD_TABLE(fo_feature_comp),
2890     ADD_TABLE(fo_custom_action),
2891     ADD_TABLE(fo_install_exec_seq),
2892     ADD_TABLE(media),
2893     ADD_TABLE(property)
2894 };
2895
2896 /* cabinet definitions */
2897
2898 /* make the max size large so there is only one cab file */
2899 #define MEDIA_SIZE          0x7FFFFFFF
2900 #define FOLDER_THRESHOLD    900000
2901
2902 /* the FCI callbacks */
2903
2904 static void * CDECL mem_alloc(ULONG cb)
2905 {
2906     return HeapAlloc(GetProcessHeap(), 0, cb);
2907 }
2908
2909 static void CDECL mem_free(void *memory)
2910 {
2911     HeapFree(GetProcessHeap(), 0, memory);
2912 }
2913
2914 static BOOL CDECL get_next_cabinet(PCCAB pccab, ULONG  cbPrevCab, void *pv)
2915 {
2916     sprintf(pccab->szCab, pv, pccab->iCab);
2917     return TRUE;
2918 }
2919
2920 static LONG CDECL progress(UINT typeStatus, ULONG cb1, ULONG cb2, void *pv)
2921 {
2922     return 0;
2923 }
2924
2925 static int CDECL file_placed(PCCAB pccab, char *pszFile, LONG cbFile,
2926                              BOOL fContinuation, void *pv)
2927 {
2928     return 0;
2929 }
2930
2931 static INT_PTR CDECL fci_open(char *pszFile, int oflag, int pmode, int *err, void *pv)
2932 {
2933     HANDLE handle;
2934     DWORD dwAccess = 0;
2935     DWORD dwShareMode = 0;
2936     DWORD dwCreateDisposition = OPEN_EXISTING;
2937     
2938     dwAccess = GENERIC_READ | GENERIC_WRITE;
2939     /* FILE_SHARE_DELETE is not supported by Windows Me/98/95 */
2940     dwShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE;
2941
2942     if (GetFileAttributesA(pszFile) != INVALID_FILE_ATTRIBUTES)
2943         dwCreateDisposition = OPEN_EXISTING;
2944     else
2945         dwCreateDisposition = CREATE_NEW;
2946
2947     handle = CreateFileA(pszFile, dwAccess, dwShareMode, NULL,
2948                          dwCreateDisposition, 0, NULL);
2949
2950     ok(handle != INVALID_HANDLE_VALUE, "Failed to CreateFile %s\n", pszFile);
2951
2952     return (INT_PTR)handle;
2953 }
2954
2955 static UINT CDECL fci_read(INT_PTR hf, void *memory, UINT cb, int *err, void *pv)
2956 {
2957     HANDLE handle = (HANDLE)hf;
2958     DWORD dwRead;
2959     BOOL res;
2960     
2961     res = ReadFile(handle, memory, cb, &dwRead, NULL);
2962     ok(res, "Failed to ReadFile\n");
2963
2964     return dwRead;
2965 }
2966
2967 static UINT CDECL fci_write(INT_PTR hf, void *memory, UINT cb, int *err, void *pv)
2968 {
2969     HANDLE handle = (HANDLE)hf;
2970     DWORD dwWritten;
2971     BOOL res;
2972
2973     res = WriteFile(handle, memory, cb, &dwWritten, NULL);
2974     ok(res, "Failed to WriteFile\n");
2975
2976     return dwWritten;
2977 }
2978
2979 static int CDECL fci_close(INT_PTR hf, int *err, void *pv)
2980 {
2981     HANDLE handle = (HANDLE)hf;
2982     ok(CloseHandle(handle), "Failed to CloseHandle\n");
2983
2984     return 0;
2985 }
2986
2987 static LONG CDECL fci_seek(INT_PTR hf, LONG dist, int seektype, int *err, void *pv)
2988 {
2989     HANDLE handle = (HANDLE)hf;
2990     DWORD ret;
2991     
2992     ret = SetFilePointer(handle, dist, NULL, seektype);
2993     ok(ret != INVALID_SET_FILE_POINTER, "Failed to SetFilePointer\n");
2994
2995     return ret;
2996 }
2997
2998 static int CDECL fci_delete(char *pszFile, int *err, void *pv)
2999 {
3000     BOOL ret = DeleteFileA(pszFile);
3001     ok(ret, "Failed to DeleteFile %s\n", pszFile);
3002
3003     return 0;
3004 }
3005
3006 static void init_functionpointers(void)
3007 {
3008     HMODULE hmsi = GetModuleHandleA("msi.dll");
3009     HMODULE hadvapi32 = GetModuleHandleA("advapi32.dll");
3010
3011 #define GET_PROC(mod, func) \
3012     p ## func = (void*)GetProcAddress(mod, #func); \
3013     if(!p ## func) \
3014       trace("GetProcAddress(%s) failed\n", #func);
3015
3016     GET_PROC(hmsi, MsiQueryComponentStateA);
3017     GET_PROC(hmsi, MsiSetExternalUIRecord);
3018     GET_PROC(hmsi, MsiSourceListEnumSourcesA);
3019     GET_PROC(hmsi, MsiSourceListGetInfoA);
3020
3021     GET_PROC(hadvapi32, ConvertSidToStringSidA);
3022
3023     hsrclient = LoadLibraryA("srclient.dll");
3024     GET_PROC(hsrclient, SRRemoveRestorePoint);
3025     GET_PROC(hsrclient, SRSetRestorePointA);
3026
3027 #undef GET_PROC
3028 }
3029
3030 static BOOL check_win9x(void)
3031 {
3032     SC_HANDLE scm;
3033
3034     scm = OpenSCManager(NULL, NULL, GENERIC_ALL);
3035     if (!scm && (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED))
3036         return TRUE;
3037
3038     CloseServiceHandle(scm);
3039
3040     return FALSE;
3041 }
3042
3043 static LPSTR get_user_sid(LPSTR *usersid)
3044 {
3045     HANDLE token;
3046     BYTE buf[1024];
3047     DWORD size;
3048     PTOKEN_USER user;
3049
3050     if (!pConvertSidToStringSidA)
3051     {
3052         win_skip("ConvertSidToStringSidA is not available\n");
3053         return NULL;
3054     }
3055
3056     *usersid = NULL;
3057     OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &token);
3058     size = sizeof(buf);
3059     GetTokenInformation(token, TokenUser, buf, size, &size);
3060     user = (PTOKEN_USER)buf;
3061     pConvertSidToStringSidA(user->User.Sid, usersid);
3062     ok(*usersid != NULL, "pConvertSidToStringSidA failed lre=%d\n", GetLastError());
3063     CloseHandle(token);
3064     return *usersid;
3065 }
3066
3067 static BOOL check_record(MSIHANDLE rec, UINT field, LPCSTR val)
3068 {
3069     CHAR buffer[0x20];
3070     UINT r;
3071     DWORD sz;
3072
3073     sz = sizeof buffer;
3074     r = MsiRecordGetString(rec, field, buffer, &sz);
3075     return (r == ERROR_SUCCESS ) && !strcmp(val, buffer);
3076 }
3077
3078 static BOOL CDECL get_temp_file(char *pszTempName, int cbTempName, void *pv)
3079 {
3080     LPSTR tempname;
3081
3082     tempname = HeapAlloc(GetProcessHeap(), 0, MAX_PATH);
3083     GetTempFileNameA(".", "xx", 0, tempname);
3084
3085     if (tempname && (strlen(tempname) < (unsigned)cbTempName))
3086     {
3087         lstrcpyA(pszTempName, tempname);
3088         HeapFree(GetProcessHeap(), 0, tempname);
3089         return TRUE;
3090     }
3091
3092     HeapFree(GetProcessHeap(), 0, tempname);
3093
3094     return FALSE;
3095 }
3096
3097 static INT_PTR CDECL get_open_info(char *pszName, USHORT *pdate, USHORT *ptime,
3098                                    USHORT *pattribs, int *err, void *pv)
3099 {
3100     BY_HANDLE_FILE_INFORMATION finfo;
3101     FILETIME filetime;
3102     HANDLE handle;
3103     DWORD attrs;
3104     BOOL res;
3105
3106     handle = CreateFile(pszName, GENERIC_READ, FILE_SHARE_READ, NULL,
3107                         OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL | FILE_FLAG_SEQUENTIAL_SCAN, NULL);
3108
3109     ok(handle != INVALID_HANDLE_VALUE, "Failed to CreateFile %s\n", pszName);
3110
3111     res = GetFileInformationByHandle(handle, &finfo);
3112     ok(res, "Expected GetFileInformationByHandle to succeed\n");
3113    
3114     FileTimeToLocalFileTime(&finfo.ftLastWriteTime, &filetime);
3115     FileTimeToDosDateTime(&filetime, pdate, ptime);
3116
3117     attrs = GetFileAttributes(pszName);
3118     ok(attrs != INVALID_FILE_ATTRIBUTES, "Failed to GetFileAttributes\n");
3119
3120     return (INT_PTR)handle;
3121 }
3122
3123 static BOOL add_file(HFCI hfci, const char *file, TCOMP compress)
3124 {
3125     char path[MAX_PATH];
3126     char filename[MAX_PATH];
3127
3128     lstrcpyA(path, CURR_DIR);
3129     lstrcatA(path, "\\");
3130     lstrcatA(path, file);
3131
3132     lstrcpyA(filename, file);
3133
3134     return FCIAddFile(hfci, path, filename, FALSE, get_next_cabinet,
3135                       progress, get_open_info, compress);
3136 }
3137
3138 static void set_cab_parameters(PCCAB pCabParams, const CHAR *name, DWORD max_size)
3139 {
3140     ZeroMemory(pCabParams, sizeof(CCAB));
3141
3142     pCabParams->cb = max_size;
3143     pCabParams->cbFolderThresh = FOLDER_THRESHOLD;
3144     pCabParams->setID = 0xbeef;
3145     pCabParams->iCab = 1;
3146     lstrcpyA(pCabParams->szCabPath, CURR_DIR);
3147     lstrcatA(pCabParams->szCabPath, "\\");
3148     lstrcpyA(pCabParams->szCab, name);
3149 }
3150
3151 static void create_cab_file(const CHAR *name, DWORD max_size, const CHAR *files)
3152 {
3153     CCAB cabParams;
3154     LPCSTR ptr;
3155     HFCI hfci;
3156     ERF erf;
3157     BOOL res;
3158
3159     set_cab_parameters(&cabParams, name, max_size);
3160
3161     hfci = FCICreate(&erf, file_placed, mem_alloc, mem_free, fci_open,
3162                       fci_read, fci_write, fci_close, fci_seek, fci_delete,
3163                       get_temp_file, &cabParams, NULL);
3164
3165     ok(hfci != NULL, "Failed to create an FCI context\n");
3166
3167     ptr = files;
3168     while (*ptr)
3169     {
3170         res = add_file(hfci, ptr, tcompTYPE_MSZIP);
3171         ok(res, "Failed to add file: %s\n", ptr);
3172         ptr += lstrlen(ptr) + 1;
3173     }
3174
3175     res = FCIFlushCabinet(hfci, FALSE, get_next_cabinet, progress);
3176     ok(res, "Failed to flush the cabinet\n");
3177
3178     res = FCIDestroy(hfci);
3179     ok(res, "Failed to destroy the cabinet\n");
3180 }
3181
3182 static BOOL get_program_files_dir(LPSTR buf, LPSTR buf2)
3183 {
3184     HKEY hkey;
3185     DWORD type, size;
3186
3187     if (RegOpenKey(HKEY_LOCAL_MACHINE,
3188                    "Software\\Microsoft\\Windows\\CurrentVersion", &hkey))
3189         return FALSE;
3190
3191     size = MAX_PATH;
3192     if (RegQueryValueExA(hkey, "ProgramFilesDir", 0, &type, (LPBYTE)buf, &size)) {
3193         RegCloseKey(hkey);
3194         return FALSE;
3195     }
3196
3197     size = MAX_PATH;
3198     if (RegQueryValueExA(hkey, "CommonFilesDir", 0, &type, (LPBYTE)buf2, &size)) {
3199         RegCloseKey(hkey);
3200         return FALSE;
3201     }
3202
3203     RegCloseKey(hkey);
3204     return TRUE;
3205 }
3206
3207 static void create_file_data(LPCSTR name, LPCSTR data, DWORD size)
3208 {
3209     HANDLE file;
3210     DWORD written;
3211
3212     file = CreateFileA(name, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, 0, NULL);
3213     if (file == INVALID_HANDLE_VALUE)
3214         return;
3215
3216     WriteFile(file, data, strlen(data), &written, NULL);
3217
3218     if (size)
3219     {
3220         SetFilePointer(file, size, NULL, FILE_BEGIN);
3221         SetEndOfFile(file);
3222     }
3223
3224     CloseHandle(file);
3225 }
3226
3227 #define create_file(name, size) create_file_data(name, name, size)
3228
3229 static void create_test_files(void)
3230 {
3231     CreateDirectoryA("msitest", NULL);
3232     create_file("msitest\\one.txt", 100);
3233     CreateDirectoryA("msitest\\first", NULL);
3234     create_file("msitest\\first\\two.txt", 100);
3235     CreateDirectoryA("msitest\\second", NULL);
3236     create_file("msitest\\second\\three.txt", 100);
3237
3238     create_file("four.txt", 100);
3239     create_file("five.txt", 100);
3240     create_cab_file("msitest.cab", MEDIA_SIZE, "four.txt\0five.txt\0");
3241
3242     create_file("msitest\\filename", 100);
3243     create_file("msitest\\service.exe", 100);
3244
3245     DeleteFileA("four.txt");
3246     DeleteFileA("five.txt");
3247 }
3248
3249 static BOOL delete_pf(const CHAR *rel_path, BOOL is_file)
3250 {
3251     CHAR path[MAX_PATH];
3252
3253     lstrcpyA(path, PROG_FILES_DIR);
3254     lstrcatA(path, "\\");
3255     lstrcatA(path, rel_path);
3256
3257     if (is_file)
3258         return DeleteFileA(path);
3259     else
3260         return RemoveDirectoryA(path);
3261 }
3262
3263 static BOOL delete_cf(const CHAR *rel_path, BOOL is_file)
3264 {
3265     CHAR path[MAX_PATH];
3266
3267     lstrcpyA(path, COMMON_FILES_DIR);
3268     lstrcatA(path, "\\");
3269     lstrcatA(path, rel_path);
3270
3271     if (is_file)
3272         return DeleteFileA(path);
3273     else
3274         return RemoveDirectoryA(path);
3275 }
3276
3277 static void delete_test_files(void)
3278 {
3279     DeleteFileA("msitest.msi");
3280     DeleteFileA("msitest.cab");
3281     DeleteFileA("msitest\\second\\three.txt");
3282     DeleteFileA("msitest\\first\\two.txt");
3283     DeleteFileA("msitest\\one.txt");
3284     DeleteFileA("msitest\\service.exe");
3285     DeleteFileA("msitest\\filename");
3286     RemoveDirectoryA("msitest\\second");
3287     RemoveDirectoryA("msitest\\first");
3288     RemoveDirectoryA("msitest");
3289 }
3290
3291 static void write_file(const CHAR *filename, const char *data, int data_size)
3292 {
3293     DWORD size;
3294
3295     HANDLE hf = CreateFile(filename, GENERIC_WRITE, 0, NULL,
3296                            CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
3297
3298     WriteFile(hf, data, data_size, &size, NULL);
3299     CloseHandle(hf);
3300 }
3301
3302 static void write_msi_summary_info(MSIHANDLE db, INT wordcount)
3303 {
3304     MSIHANDLE summary;
3305     UINT r;
3306
3307     r = MsiGetSummaryInformationA(db, NULL, 5, &summary);
3308     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3309
3310     r = MsiSummaryInfoSetPropertyA(summary, PID_TEMPLATE, VT_LPSTR, 0, NULL, ";1033");
3311     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3312
3313     r = MsiSummaryInfoSetPropertyA(summary, PID_REVNUMBER, VT_LPSTR, 0, NULL,
3314                                    "{004757CA-5092-49c2-AD20-28E1CE0DF5F2}");
3315     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3316
3317     r = MsiSummaryInfoSetPropertyA(summary, PID_PAGECOUNT, VT_I4, 100, NULL, NULL);
3318     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3319
3320     r = MsiSummaryInfoSetPropertyA(summary, PID_WORDCOUNT, VT_I4, wordcount, NULL, NULL);
3321     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3322
3323     r = MsiSummaryInfoSetPropertyA(summary, PID_TITLE, VT_LPSTR, 0, NULL, "MSITEST");
3324     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3325
3326     /* write the summary changes back to the stream */
3327     r = MsiSummaryInfoPersist(summary);
3328     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3329
3330     MsiCloseHandle(summary);
3331 }
3332
3333 #define create_database(name, tables, num_tables) \
3334     create_database_wordcount(name, tables, num_tables, 0);
3335
3336 static void create_database_wordcount(const CHAR *name, const msi_table *tables,
3337                                       int num_tables, INT wordcount)
3338 {
3339     MSIHANDLE db;
3340     UINT r;
3341     int j;
3342
3343     r = MsiOpenDatabaseA(name, MSIDBOPEN_CREATE, &db);
3344     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3345
3346     /* import the tables into the database */
3347     for (j = 0; j < num_tables; j++)
3348     {
3349         const msi_table *table = &tables[j];
3350
3351         write_file(table->filename, table->data, (table->size - 1) * sizeof(char));
3352
3353         r = MsiDatabaseImportA(db, CURR_DIR, table->filename);
3354         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3355
3356         DeleteFileA(table->filename);
3357     }
3358
3359     write_msi_summary_info(db, wordcount);
3360
3361     r = MsiDatabaseCommit(db);
3362     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3363
3364     MsiCloseHandle(db);
3365 }
3366
3367 static void check_service_is_installed(void)
3368 {
3369     SC_HANDLE scm, service;
3370     BOOL res;
3371
3372     scm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
3373     ok(scm != NULL, "Failed to open the SC Manager\n");
3374
3375     service = OpenService(scm, "TestService", SC_MANAGER_ALL_ACCESS);
3376     ok(service != NULL, "Failed to open TestService\n");
3377
3378     res = DeleteService(service);
3379     ok(res, "Failed to delete TestService\n");
3380
3381     CloseServiceHandle(service);
3382     CloseServiceHandle(scm);
3383 }
3384
3385 static BOOL notify_system_change(DWORD event_type, STATEMGRSTATUS *status)
3386 {
3387     RESTOREPOINTINFOA spec;
3388
3389     spec.dwEventType = event_type;
3390     spec.dwRestorePtType = APPLICATION_INSTALL;
3391     spec.llSequenceNumber = status->llSequenceNumber;
3392     lstrcpyA(spec.szDescription, "msitest restore point");
3393
3394     return pSRSetRestorePointA(&spec, status);
3395 }
3396
3397 static void remove_restore_point(DWORD seq_number)
3398 {
3399     DWORD res;
3400
3401     res = pSRRemoveRestorePoint(seq_number);
3402     if (res != ERROR_SUCCESS)
3403         trace("Failed to remove the restore point : %08x\n", res);
3404 }
3405
3406 static void test_MsiInstallProduct(void)
3407 {
3408     UINT r;
3409     CHAR path[MAX_PATH];
3410     LONG res;
3411     HKEY hkey;
3412     DWORD num, size, type;
3413
3414     if (on_win9x)
3415     {
3416         win_skip("Services are not implemented on Win9x and WinMe\n");
3417         return;
3418     }
3419
3420     /* szPackagePath is NULL */
3421     r = MsiInstallProductA(NULL, "INSTALL=ALL");
3422     ok(r == ERROR_INVALID_PARAMETER,
3423        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
3424
3425     /* both szPackagePath and szCommandLine are NULL */
3426     r = MsiInstallProductA(NULL, NULL);
3427     ok(r == ERROR_INVALID_PARAMETER,
3428        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
3429
3430     /* szPackagePath is empty */
3431     r = MsiInstallProductA("", "INSTALL=ALL");
3432     ok(r == ERROR_PATH_NOT_FOUND,
3433        "Expected ERROR_PATH_NOT_FOUND, got %d\n", r);
3434
3435     create_test_files();
3436     create_database(msifile, tables, sizeof(tables) / sizeof(msi_table));
3437
3438     /* install, don't publish */
3439     r = MsiInstallProductA(msifile, NULL);
3440     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3441
3442     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3443     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3444     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3445     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3446     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3447     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3448     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3449     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3450     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3451     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3452     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3453     ok(delete_pf("msitest", FALSE), "File not installed\n");
3454
3455     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3456     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
3457
3458     size = MAX_PATH;
3459     type = REG_SZ;
3460     res = RegQueryValueExA(hkey, "Name", NULL, &type, (LPBYTE)path, &size);
3461     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
3462     ok(!lstrcmpA(path, "imaname"), "Expected imaname, got %s\n", path);
3463
3464     size = MAX_PATH;
3465     type = REG_SZ;
3466     res = RegQueryValueExA(hkey, "blah", NULL, &type, (LPBYTE)path, &size);
3467     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
3468
3469     size = sizeof(num);
3470     type = REG_DWORD;
3471     res = RegQueryValueExA(hkey, "number", NULL, &type, (LPBYTE)&num, &size);
3472     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
3473     ok(num == 314, "Expected 314, got %d\n", num);
3474
3475     size = MAX_PATH;
3476     type = REG_SZ;
3477     res = RegQueryValueExA(hkey, "OrderTestName", NULL, &type, (LPBYTE)path, &size);
3478     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
3479     ok(!lstrcmpA(path, "OrderTestValue"), "Expected OrderTestValue, got %s\n", path);
3480
3481     check_service_is_installed();
3482
3483     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest");
3484
3485     /* not published, reinstall */
3486     r = MsiInstallProductA(msifile, NULL);
3487     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3488
3489     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3490     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3491     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3492     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3493     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3494     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3495     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3496     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3497     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3498     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3499     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3500     ok(delete_pf("msitest", FALSE), "File not installed\n");
3501
3502     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3503     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
3504     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest");
3505
3506     create_database(msifile, up_tables, sizeof(up_tables) / sizeof(msi_table));
3507
3508     /* not published, RemovePreviousVersions set */
3509     r = MsiInstallProductA(msifile, NULL);
3510     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3511
3512     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3513     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3514     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3515     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3516     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3517     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3518     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3519     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3520     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3521     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3522     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3523     ok(delete_pf("msitest", FALSE), "File not installed\n");
3524
3525     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3526     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
3527     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest");
3528
3529     create_database(msifile, up2_tables, sizeof(up2_tables) / sizeof(msi_table));
3530
3531     /* not published, version number bumped */
3532     r = MsiInstallProductA(msifile, NULL);
3533     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3534
3535     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3536     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3537     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3538     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3539     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3540     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3541     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3542     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3543     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3544     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3545     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3546     ok(delete_pf("msitest", FALSE), "File not installed\n");
3547
3548     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3549     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
3550     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest");
3551
3552     create_database(msifile, up3_tables, sizeof(up3_tables) / sizeof(msi_table));
3553
3554     /* not published, RemovePreviousVersions set and version number bumped */
3555     r = MsiInstallProductA(msifile, NULL);
3556     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3557
3558     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3559     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3560     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3561     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3562     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3563     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3564     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3565     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3566     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3567     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3568     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3569     ok(delete_pf("msitest", FALSE), "File not installed\n");
3570
3571     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3572     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
3573     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest");
3574
3575     create_database(msifile, up4_tables, sizeof(up4_tables) / sizeof(msi_table));
3576
3577     /* install, publish product */
3578     r = MsiInstallProductA(msifile, "PUBLISH_PRODUCT=1");
3579     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3580
3581     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3582     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3583     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3584     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3585     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3586     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3587     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3588     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3589     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3590     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3591     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3592     ok(delete_pf("msitest", FALSE), "File not installed\n");
3593
3594     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3595     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
3596
3597     create_database(msifile, up4_tables, sizeof(up4_tables) / sizeof(msi_table));
3598
3599     /* published, reinstall */
3600     r = MsiInstallProductA(msifile, NULL);
3601     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3602
3603     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3604     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3605     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3606     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3607     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3608     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3609     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3610     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3611     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3612     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3613     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3614     ok(delete_pf("msitest", FALSE), "File not installed\n");
3615
3616     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3617     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
3618
3619     create_database(msifile, up5_tables, sizeof(up5_tables) / sizeof(msi_table));
3620
3621     /* published product, RemovePreviousVersions set */
3622     r = MsiInstallProductA(msifile, NULL);
3623     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3624
3625     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3626     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3627     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3628     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3629     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3630     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3631     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3632     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3633     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3634     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3635     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3636     ok(delete_pf("msitest", FALSE), "File not installed\n");
3637
3638     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3639     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
3640
3641     create_database(msifile, up6_tables, sizeof(up6_tables) / sizeof(msi_table));
3642
3643     /* published product, version number bumped */
3644     r = MsiInstallProductA(msifile, NULL);
3645     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3646
3647     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3648     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3649     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3650     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3651     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3652     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3653     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3654     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3655     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3656     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3657     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3658     ok(delete_pf("msitest", FALSE), "File not installed\n");
3659
3660     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3661     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
3662
3663     create_database(msifile, up7_tables, sizeof(up7_tables) / sizeof(msi_table));
3664
3665     /* published product, RemovePreviousVersions set and version number bumped */
3666     r = MsiInstallProductA(msifile, NULL);
3667     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3668
3669     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
3670     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
3671     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
3672     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
3673     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
3674     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
3675     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
3676     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
3677     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
3678     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
3679     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
3680     ok(delete_pf("msitest", FALSE), "File not installed\n");
3681
3682     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
3683     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
3684
3685     r = MsiInstallProductA(msifile, "REMOVE=ALL");
3686     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3687
3688     delete_test_files();
3689 }
3690
3691 static void test_MsiSetComponentState(void)
3692 {
3693     INSTALLSTATE installed, action;
3694     MSIHANDLE package;
3695     char path[MAX_PATH];
3696     UINT r;
3697
3698     create_database(msifile, tables, sizeof(tables) / sizeof(msi_table));
3699
3700     CoInitialize(NULL);
3701
3702     lstrcpy(path, CURR_DIR);
3703     lstrcat(path, "\\");
3704     lstrcat(path, msifile);
3705
3706     r = MsiOpenPackage(path, &package);
3707     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3708
3709     r = MsiDoAction(package, "CostInitialize");
3710     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3711
3712     r = MsiDoAction(package, "FileCost");
3713     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3714
3715     r = MsiDoAction(package, "CostFinalize");
3716     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3717
3718     r = MsiGetComponentState(package, "dangler", &installed, &action);
3719     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3720     ok(installed == INSTALLSTATE_ABSENT, "Expected INSTALLSTATE_ABSENT, got %d\n", installed);
3721     ok(action == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", action);
3722
3723     r = MsiSetComponentState(package, "dangler", INSTALLSTATE_SOURCE);
3724     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3725
3726     MsiCloseHandle(package);
3727     CoUninitialize();
3728
3729     DeleteFileA(msifile);
3730 }
3731
3732 static void test_packagecoltypes(void)
3733 {
3734     MSIHANDLE hdb, view, rec;
3735     char path[MAX_PATH];
3736     LPCSTR query;
3737     UINT r, count;
3738
3739     create_database(msifile, tables, sizeof(tables) / sizeof(msi_table));
3740
3741     CoInitialize(NULL);
3742
3743     lstrcpy(path, CURR_DIR);
3744     lstrcat(path, "\\");
3745     lstrcat(path, msifile);
3746
3747     r = MsiOpenDatabase(path, MSIDBOPEN_READONLY, &hdb);
3748     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3749
3750     query = "SELECT * FROM `Media`";
3751     r = MsiDatabaseOpenView( hdb, query, &view );
3752     ok(r == ERROR_SUCCESS, "MsiDatabaseOpenView failed\n");
3753
3754     r = MsiViewGetColumnInfo( view, MSICOLINFO_NAMES, &rec );
3755     count = MsiRecordGetFieldCount( rec );
3756     ok(r == ERROR_SUCCESS, "MsiViewGetColumnInfo failed\n");
3757     ok(count == 6, "Expected 6, got %d\n", count);
3758     ok(check_record(rec, 1, "DiskId"), "wrong column label\n");
3759     ok(check_record(rec, 2, "LastSequence"), "wrong column label\n");
3760     ok(check_record(rec, 3, "DiskPrompt"), "wrong column label\n");
3761     ok(check_record(rec, 4, "Cabinet"), "wrong column label\n");
3762     ok(check_record(rec, 5, "VolumeLabel"), "wrong column label\n");
3763     ok(check_record(rec, 6, "Source"), "wrong column label\n");
3764     MsiCloseHandle(rec);
3765
3766     r = MsiViewGetColumnInfo( view, MSICOLINFO_TYPES, &rec );
3767     count = MsiRecordGetFieldCount( rec );
3768     ok(r == ERROR_SUCCESS, "MsiViewGetColumnInfo failed\n");
3769     ok(count == 6, "Expected 6, got %d\n", count);
3770     ok(check_record(rec, 1, "i2"), "wrong column label\n");
3771     ok(check_record(rec, 2, "i4"), "wrong column label\n");
3772     ok(check_record(rec, 3, "L64"), "wrong column label\n");
3773     ok(check_record(rec, 4, "S255"), "wrong column label\n");
3774     ok(check_record(rec, 5, "S32"), "wrong column label\n");
3775     ok(check_record(rec, 6, "S72"), "wrong column label\n");
3776
3777     MsiCloseHandle(rec);
3778     MsiCloseHandle(view);
3779     MsiCloseHandle(hdb);
3780     CoUninitialize();
3781
3782     DeleteFile(msifile);
3783 }
3784
3785 static void create_cc_test_files(void)
3786 {
3787     CCAB cabParams;
3788     HFCI hfci;
3789     ERF erf;
3790     static CHAR cab_context[] = "test%d.cab";
3791     BOOL res;
3792
3793     create_file("maximus", 500);
3794     create_file("augustus", 50000);
3795     create_file("tiberius", 500);
3796     create_file("caesar", 500);
3797
3798     set_cab_parameters(&cabParams, "test1.cab", 40000);
3799
3800     hfci = FCICreate(&erf, file_placed, mem_alloc, mem_free, fci_open,
3801                       fci_read, fci_write, fci_close, fci_seek, fci_delete,
3802                       get_temp_file, &cabParams, cab_context);
3803     ok(hfci != NULL, "Failed to create an FCI context\n");
3804
3805     res = add_file(hfci, "maximus", tcompTYPE_NONE);
3806     ok(res, "Failed to add file maximus\n");
3807
3808     res = add_file(hfci, "augustus", tcompTYPE_NONE);
3809     ok(res, "Failed to add file augustus\n");
3810
3811     res = add_file(hfci, "tiberius", tcompTYPE_NONE);
3812     ok(res, "Failed to add file tiberius\n");
3813
3814     res = FCIFlushCabinet(hfci, FALSE, get_next_cabinet, progress);
3815     ok(res, "Failed to flush the cabinet\n");
3816
3817     res = FCIDestroy(hfci);
3818     ok(res, "Failed to destroy the cabinet\n");
3819
3820     create_cab_file("test3.cab", MEDIA_SIZE, "caesar\0");
3821
3822     DeleteFile("maximus");
3823     DeleteFile("augustus");
3824     DeleteFile("tiberius");
3825     DeleteFile("caesar");
3826 }
3827
3828 static void delete_cab_files(void)
3829 {
3830     SHFILEOPSTRUCT shfl;
3831     CHAR path[MAX_PATH+10];
3832
3833     lstrcpyA(path, CURR_DIR);
3834     lstrcatA(path, "\\*.cab");
3835     path[strlen(path) + 1] = '\0';
3836
3837     shfl.hwnd = NULL;
3838     shfl.wFunc = FO_DELETE;
3839     shfl.pFrom = path;
3840     shfl.pTo = NULL;
3841     shfl.fFlags = FOF_FILESONLY | FOF_NOCONFIRMATION | FOF_NORECURSION | FOF_SILENT;
3842
3843     SHFileOperation(&shfl);
3844 }
3845
3846 static void test_continuouscabs(void)
3847 {
3848     UINT r;
3849
3850     create_cc_test_files();
3851     create_database(msifile, cc_tables, sizeof(cc_tables) / sizeof(msi_table));
3852
3853     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3854
3855     r = MsiInstallProductA(msifile, NULL);
3856     if (r == ERROR_SUCCESS) /* win9x has a problem with this */
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\\caesar", TRUE), "File not installed\n");
3861         ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3862         ok(delete_pf("msitest", FALSE), "File not installed\n");
3863     }
3864
3865     delete_cab_files();
3866     DeleteFile(msifile);
3867
3868     create_cc_test_files();
3869     create_database(msifile, cc2_tables, sizeof(cc2_tables) / sizeof(msi_table));
3870
3871     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3872
3873     r = MsiInstallProductA(msifile, NULL);
3874     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3875     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3876     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
3877     ok(delete_pf("msitest\\tiberius", TRUE), "File not installed\n");
3878     ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
3879     ok(delete_pf("msitest", FALSE), "File not installed\n");
3880
3881     delete_cab_files();
3882     DeleteFile(msifile);
3883 }
3884
3885 static void test_caborder(void)
3886 {
3887     UINT r;
3888
3889     create_file("imperator", 100);
3890     create_file("maximus", 500);
3891     create_file("augustus", 50000);
3892     create_file("caesar", 500);
3893
3894     create_database(msifile, cc_tables, sizeof(cc_tables) / sizeof(msi_table));
3895
3896     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3897
3898     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
3899     create_cab_file("test2.cab", MEDIA_SIZE, "augustus\0");
3900     create_cab_file("test3.cab", MEDIA_SIZE, "caesar\0");
3901
3902     r = MsiInstallProductA(msifile, NULL);
3903     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
3904     ok(!delete_pf("msitest\\augustus", TRUE), "File is installed\n");
3905     ok(!delete_pf("msitest\\caesar", TRUE), "File is installed\n");
3906     todo_wine
3907     {
3908         ok(!delete_pf("msitest\\maximus", TRUE), "File is installed\n");
3909         ok(!delete_pf("msitest", FALSE), "File is installed\n");
3910     }
3911
3912     delete_cab_files();
3913
3914     create_cab_file("test1.cab", MEDIA_SIZE, "imperator\0");
3915     create_cab_file("test2.cab", MEDIA_SIZE, "maximus\0augustus\0");
3916     create_cab_file("test3.cab", MEDIA_SIZE, "caesar\0");
3917
3918     r = MsiInstallProductA(msifile, NULL);
3919     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
3920     ok(!delete_pf("msitest\\maximus", TRUE), "File is installed\n");
3921     ok(!delete_pf("msitest\\augustus", TRUE), "File is installed\n");
3922     ok(!delete_pf("msitest\\caesar", TRUE), "File is installed\n");
3923     todo_wine
3924     {
3925         ok(!delete_pf("msitest", FALSE), "File is installed\n");
3926     }
3927
3928     delete_cab_files();
3929     DeleteFile(msifile);
3930
3931     create_cc_test_files();
3932     create_database(msifile, co_tables, sizeof(co_tables) / sizeof(msi_table));
3933
3934     r = MsiInstallProductA(msifile, NULL);
3935     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
3936     ok(!delete_pf("msitest\\caesar", TRUE), "File is installed\n");
3937     ok(!delete_pf("msitest", FALSE), "File is installed\n");
3938     todo_wine
3939     {
3940         ok(!delete_pf("msitest\\augustus", TRUE), "File is installed\n");
3941         ok(!delete_pf("msitest\\maximus", TRUE), "File is installed\n");
3942     }
3943
3944     delete_cab_files();
3945     DeleteFile(msifile);
3946
3947     create_cc_test_files();
3948     create_database(msifile, co2_tables, sizeof(co2_tables) / sizeof(msi_table));
3949
3950     r = MsiInstallProductA(msifile, NULL);
3951     ok(!delete_pf("msitest\\caesar", TRUE), "File is installed\n");
3952     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
3953     todo_wine
3954     {
3955         ok(!delete_pf("msitest\\augustus", TRUE), "File is installed\n");
3956         ok(!delete_pf("msitest\\maximus", TRUE), "File is installed\n");
3957         ok(!delete_pf("msitest", FALSE), "File is installed\n");
3958     }
3959
3960     delete_cab_files();
3961     DeleteFile("imperator");
3962     DeleteFile("maximus");
3963     DeleteFile("augustus");
3964     DeleteFile("caesar");
3965     DeleteFile(msifile);
3966 }
3967
3968 static void test_mixedmedia(void)
3969 {
3970     UINT r;
3971
3972     CreateDirectoryA("msitest", NULL);
3973     create_file("msitest\\maximus", 500);
3974     create_file("msitest\\augustus", 500);
3975     create_file("caesar", 500);
3976
3977     create_database(msifile, mm_tables, sizeof(mm_tables) / sizeof(msi_table));
3978
3979     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
3980
3981     create_cab_file("test1.cab", MEDIA_SIZE, "caesar\0");
3982
3983     r = MsiInstallProductA(msifile, NULL);
3984     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
3985     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
3986     ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
3987     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
3988     ok(delete_pf("msitest", FALSE), "File not installed\n");
3989
3990     /* Delete the files in the temp (current) folder */
3991     DeleteFile("msitest\\maximus");
3992     DeleteFile("msitest\\augustus");
3993     RemoveDirectory("msitest");
3994     DeleteFile("caesar");
3995     DeleteFile("test1.cab");
3996     DeleteFile(msifile);
3997 }
3998
3999 static void test_samesequence(void)
4000 {
4001     UINT r;
4002
4003     create_cc_test_files();
4004     create_database(msifile, ss_tables, sizeof(ss_tables) / sizeof(msi_table));
4005
4006     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4007
4008     r = MsiInstallProductA(msifile, NULL);
4009     if (r == ERROR_SUCCESS) /* win9x has a problem with this */
4010     {
4011         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4012         ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
4013         ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
4014         ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4015         ok(delete_pf("msitest", FALSE), "File not installed\n");
4016     }
4017
4018     delete_cab_files();
4019     DeleteFile(msifile);
4020 }
4021
4022 static void test_uiLevelFlags(void)
4023 {
4024     UINT r;
4025
4026     create_cc_test_files();
4027     create_database(msifile, ui_tables, sizeof(ui_tables) / sizeof(msi_table));
4028
4029     MsiSetInternalUI(INSTALLUILEVEL_NONE | INSTALLUILEVEL_SOURCERESONLY, NULL);
4030
4031     r = MsiInstallProductA(msifile, NULL);
4032     if (r == ERROR_SUCCESS) /* win9x has a problem with this */
4033     {
4034         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4035         ok(!delete_pf("msitest\\maximus", TRUE), "UI install occurred, but execute-only was requested.\n");
4036         ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
4037         ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
4038         ok(delete_pf("msitest", FALSE), "File not installed\n");
4039     }
4040
4041     delete_cab_files();
4042     DeleteFile(msifile);
4043 }
4044
4045 static BOOL file_matches(LPSTR path)
4046 {
4047     CHAR buf[MAX_PATH];
4048     HANDLE file;
4049     DWORD size;
4050
4051     file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
4052                       NULL, OPEN_EXISTING, 0, NULL);
4053
4054     ZeroMemory(buf, MAX_PATH);
4055     ReadFile(file, buf, 15, &size, NULL);
4056     CloseHandle(file);
4057
4058     return !lstrcmp(buf, "msitest\\maximus");
4059 }
4060
4061 static void test_readonlyfile(void)
4062 {
4063     UINT r;
4064     DWORD size;
4065     HANDLE file;
4066     CHAR path[MAX_PATH];
4067
4068     CreateDirectoryA("msitest", NULL);
4069     create_file("msitest\\maximus", 500);
4070     create_database(msifile, rof_tables, sizeof(rof_tables) / sizeof(msi_table));
4071
4072     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4073
4074     lstrcpy(path, PROG_FILES_DIR);
4075     lstrcat(path, "\\msitest");
4076     CreateDirectory(path, NULL);
4077
4078     lstrcat(path, "\\maximus");
4079     file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
4080                       NULL, CREATE_NEW, FILE_ATTRIBUTE_READONLY, NULL);
4081
4082     WriteFile(file, "readonlyfile", strlen("readonlyfile"), &size, NULL);
4083     CloseHandle(file);
4084
4085     r = MsiInstallProductA(msifile, NULL);
4086     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4087     ok(file_matches(path), "Expected file to be overwritten\n");
4088     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4089     ok(delete_pf("msitest", FALSE), "File not installed\n");
4090
4091     /* Delete the files in the temp (current) folder */
4092     DeleteFile("msitest\\maximus");
4093     RemoveDirectory("msitest");
4094     DeleteFile(msifile);
4095 }
4096
4097 static void test_readonlyfile_cab(void)
4098 {
4099     UINT r;
4100     DWORD size;
4101     HANDLE file;
4102     CHAR path[MAX_PATH];
4103     CHAR buf[16];
4104
4105     CreateDirectoryA("msitest", NULL);
4106     create_file("maximus", 500);
4107     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
4108     DeleteFile("maximus");
4109
4110     create_database(msifile, rofc_tables, sizeof(rofc_tables) / sizeof(msi_table));
4111
4112     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4113
4114     lstrcpy(path, PROG_FILES_DIR);
4115     lstrcat(path, "\\msitest");
4116     CreateDirectory(path, NULL);
4117
4118     lstrcat(path, "\\maximus");
4119     file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
4120                       NULL, CREATE_NEW, FILE_ATTRIBUTE_READONLY, NULL);
4121
4122     WriteFile(file, "readonlyfile", strlen("readonlyfile"), &size, NULL);
4123     CloseHandle(file);
4124
4125     r = MsiInstallProductA(msifile, NULL);
4126     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4127
4128     memset( buf, 0, sizeof(buf) );
4129     if ((file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
4130                            NULL, OPEN_EXISTING, 0, NULL)) != INVALID_HANDLE_VALUE)
4131     {
4132         ReadFile(file, buf, sizeof(buf) - 1, &size, NULL);
4133         CloseHandle(file);
4134     }
4135     ok(!memcmp( buf, "maximus", sizeof("maximus")-1 ), "Expected file to be overwritten, got '%s'\n", buf);
4136     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4137     ok(delete_pf("msitest", FALSE), "File not installed\n");
4138
4139     /* Delete the files in the temp (current) folder */
4140     delete_cab_files();
4141     DeleteFile("msitest\\maximus");
4142     RemoveDirectory("msitest");
4143     DeleteFile(msifile);
4144 }
4145
4146 static BOOL add_cabinet_storage(LPCSTR db, LPCSTR cabinet)
4147 {
4148     WCHAR dbW[MAX_PATH], cabinetW[MAX_PATH];
4149     IStorage *stg;
4150     IStream *stm;
4151     HRESULT hr;
4152     HANDLE handle;
4153
4154     MultiByteToWideChar(CP_ACP, 0, db, -1, dbW, MAX_PATH);
4155     hr = StgOpenStorage(dbW, NULL, STGM_DIRECT|STGM_READWRITE|STGM_SHARE_EXCLUSIVE, NULL, 0, &stg);
4156     if (FAILED(hr))
4157         return FALSE;
4158
4159     MultiByteToWideChar(CP_ACP, 0, cabinet, -1, cabinetW, MAX_PATH);
4160     hr = IStorage_CreateStream(stg, cabinetW, STGM_WRITE|STGM_SHARE_EXCLUSIVE, 0, 0, &stm);
4161     if (FAILED(hr))
4162     {
4163         IStorage_Release(stg);
4164         return FALSE;
4165     }
4166
4167     handle = CreateFileW(cabinetW, GENERIC_READ, 0, NULL, OPEN_EXISTING, 0, NULL);
4168     if (handle != INVALID_HANDLE_VALUE)
4169     {
4170         DWORD count;
4171         char buffer[1024];
4172         if (ReadFile(handle, buffer, sizeof(buffer), &count, NULL))
4173             IStream_Write(stm, buffer, count, &count);
4174         CloseHandle(handle);
4175     }
4176
4177     IStream_Release(stm);
4178     IStorage_Release(stg);
4179
4180     return TRUE;
4181 }
4182
4183 static void test_lastusedsource(void)
4184 {
4185     static char prodcode[] = "{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}";
4186
4187     UINT r;
4188     char value[MAX_PATH], path[MAX_PATH];
4189     DWORD size;
4190
4191     if (!pMsiSourceListGetInfoA)
4192     {
4193         win_skip("MsiSourceListGetInfoA is not available\n");
4194         return;
4195     }
4196
4197     CreateDirectoryA("msitest", NULL);
4198     create_file("maximus", 500);
4199     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
4200     DeleteFile("maximus");
4201
4202     create_database("msifile0.msi", lus0_tables, sizeof(lus0_tables) / sizeof(msi_table));
4203     create_database("msifile1.msi", lus1_tables, sizeof(lus1_tables) / sizeof(msi_table));
4204     create_database("msifile2.msi", lus2_tables, sizeof(lus2_tables) / sizeof(msi_table));
4205
4206     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4207
4208     /* no cabinet file */
4209
4210     size = MAX_PATH;
4211     lstrcpyA(value, "aaa");
4212     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
4213                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
4214     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
4215     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
4216
4217     r = MsiInstallProductA("msifile0.msi", "PUBLISH_PRODUCT=1");
4218     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4219
4220     lstrcpyA(path, CURR_DIR);
4221     lstrcatA(path, "\\");
4222
4223     size = MAX_PATH;
4224     lstrcpyA(value, "aaa");
4225     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
4226                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
4227     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4228     todo_wine
4229     {
4230     ok(!lstrcmpA(value, path), "Expected \"%s\", got \"%s\"\n", path, value);
4231     ok(size == lstrlenA(path), "Expected %d, got %d\n", lstrlenA(path), size);
4232     }
4233
4234     r = MsiInstallProductA("msifile0.msi", "REMOVE=ALL");
4235     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4236
4237     /* separate cabinet file */
4238
4239     size = MAX_PATH;
4240     lstrcpyA(value, "aaa");
4241     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
4242                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
4243     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
4244     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
4245
4246     r = MsiInstallProductA("msifile1.msi", "PUBLISH_PRODUCT=1");
4247     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4248
4249     lstrcpyA(path, CURR_DIR);
4250     lstrcatA(path, "\\");
4251
4252     size = MAX_PATH;
4253     lstrcpyA(value, "aaa");
4254     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
4255                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
4256     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4257     todo_wine
4258     {
4259     ok(!lstrcmpA(value, path), "Expected \"%s\", got \"%s\"\n", path, value);
4260     ok(size == lstrlenA(path), "Expected %d, got %d\n", lstrlenA(path), size);
4261     }
4262
4263     r = MsiInstallProductA("msifile1.msi", "REMOVE=ALL");
4264     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4265
4266     size = MAX_PATH;
4267     lstrcpyA(value, "aaa");
4268     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
4269                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
4270     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
4271     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
4272
4273     /* embedded cabinet stream */
4274
4275     add_cabinet_storage("msifile2.msi", "test1.cab");
4276
4277     r = MsiInstallProductA("msifile2.msi", "PUBLISH_PRODUCT=1");
4278     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4279
4280     size = MAX_PATH;
4281     lstrcpyA(value, "aaa");
4282     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
4283                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
4284     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4285     todo_wine
4286     {
4287     ok(!lstrcmpA(value, path), "Expected \"%s\", got \"%s\"\n", path, value);
4288     ok(size == lstrlenA(path), "Expected %d, got %d\n", lstrlenA(path), size);
4289     }
4290
4291     r = MsiInstallProductA("msifile2.msi", "REMOVE=ALL");
4292     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4293
4294     size = MAX_PATH;
4295     lstrcpyA(value, "aaa");
4296     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
4297                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
4298     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
4299     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
4300
4301     /* Delete the files in the temp (current) folder */
4302     delete_cab_files();
4303     DeleteFile("msitest\\maximus");
4304     RemoveDirectory("msitest");
4305     DeleteFile("msifile0.msi");
4306     DeleteFile("msifile1.msi");
4307     DeleteFile("msifile2.msi");
4308 }
4309
4310 static void test_setdirproperty(void)
4311 {
4312     UINT r;
4313
4314     CreateDirectoryA("msitest", NULL);
4315     create_file("msitest\\maximus", 500);
4316     create_database(msifile, sdp_tables, sizeof(sdp_tables) / sizeof(msi_table));
4317
4318     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4319
4320     r = MsiInstallProductA(msifile, NULL);
4321     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4322     ok(delete_cf("msitest\\maximus", TRUE), "File not installed\n");
4323     ok(delete_cf("msitest", FALSE), "File not installed\n");
4324
4325     /* Delete the files in the temp (current) folder */
4326     DeleteFile(msifile);
4327     DeleteFile("msitest\\maximus");
4328     RemoveDirectory("msitest");
4329 }
4330
4331 static void test_cabisextracted(void)
4332 {
4333     UINT r;
4334
4335     CreateDirectoryA("msitest", NULL);
4336     create_file("msitest\\gaius", 500);
4337     create_file("maximus", 500);
4338     create_file("augustus", 500);
4339     create_file("caesar", 500);
4340
4341     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
4342     create_cab_file("test2.cab", MEDIA_SIZE, "augustus\0");
4343     create_cab_file("test3.cab", MEDIA_SIZE, "caesar\0");
4344
4345     create_database(msifile, cie_tables, sizeof(cie_tables) / sizeof(msi_table));
4346
4347     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
4348
4349     r = MsiInstallProductA(msifile, NULL);
4350     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4351     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4352     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
4353     ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
4354     ok(delete_pf("msitest\\gaius", TRUE), "File not installed\n");
4355     ok(delete_pf("msitest", FALSE), "File not installed\n");
4356
4357     /* Delete the files in the temp (current) folder */
4358     delete_cab_files();
4359     DeleteFile(msifile);
4360     DeleteFile("maximus");
4361     DeleteFile("augustus");
4362     DeleteFile("caesar");
4363     DeleteFile("msitest\\gaius");
4364     RemoveDirectory("msitest");
4365 }
4366
4367 static void test_concurrentinstall(void)
4368 {
4369     UINT r;
4370     CHAR path[MAX_PATH];
4371
4372     CreateDirectoryA("msitest", NULL);
4373     CreateDirectoryA("msitest\\msitest", NULL);
4374     create_file("msitest\\maximus", 500);
4375     create_file("msitest\\msitest\\augustus", 500);
4376
4377     create_database(msifile, ci_tables, sizeof(ci_tables) / sizeof(msi_table));
4378
4379     lstrcpyA(path, CURR_DIR);
4380     lstrcatA(path, "\\msitest\\concurrent.msi");
4381     create_database(path, ci2_tables, sizeof(ci2_tables) / sizeof(msi_table));
4382
4383     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
4384
4385     r = MsiInstallProductA(msifile, NULL);
4386     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4387     if (!delete_pf("msitest\\augustus", TRUE))
4388         trace("concurrent installs not supported\n");
4389     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4390     ok(delete_pf("msitest", FALSE), "File not installed\n");
4391
4392     DeleteFile(path);
4393
4394     r = MsiInstallProductA(msifile, NULL);
4395     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4396     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4397     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
4398     ok(delete_pf("msitest", FALSE), "File not installed\n");
4399
4400     DeleteFile(msifile);
4401     DeleteFile("msitest\\msitest\\augustus");
4402     DeleteFile("msitest\\maximus");
4403     RemoveDirectory("msitest\\msitest");
4404     RemoveDirectory("msitest");
4405 }
4406
4407 static void test_setpropertyfolder(void)
4408 {
4409     UINT r;
4410     CHAR path[MAX_PATH];
4411     DWORD attr;
4412
4413     lstrcpyA(path, PROG_FILES_DIR);
4414     lstrcatA(path, "\\msitest\\added");
4415
4416     CreateDirectoryA("msitest", NULL);
4417     create_file("msitest\\maximus", 500);
4418
4419     create_database(msifile, spf_tables, sizeof(spf_tables) / sizeof(msi_table));
4420
4421     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
4422
4423     r = MsiInstallProductA(msifile, NULL);
4424     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
4425     attr = GetFileAttributesA(path);
4426     if (attr != INVALID_FILE_ATTRIBUTES && (attr & FILE_ATTRIBUTE_DIRECTORY))
4427     {
4428         ok(delete_pf("msitest\\added\\maximus", TRUE), "File not installed\n");
4429         ok(delete_pf("msitest\\added", FALSE), "File not installed\n");
4430         ok(delete_pf("msitest", FALSE), "File not installed\n");
4431     }
4432     else
4433     {
4434         trace("changing folder property not supported\n");
4435         ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4436         ok(delete_pf("msitest", FALSE), "File not installed\n");
4437     }
4438
4439     /* Delete the files in the temp (current) folder */
4440     DeleteFile(msifile);
4441     DeleteFile("msitest\\maximus");
4442     RemoveDirectory("msitest");
4443 }
4444
4445 static BOOL file_exists(LPCSTR file)
4446 {
4447     return GetFileAttributes(file) != INVALID_FILE_ATTRIBUTES;
4448 }
4449
4450 static BOOL pf_exists(LPCSTR file)
4451 {
4452     CHAR path[MAX_PATH];
4453
4454     lstrcpyA(path, PROG_FILES_DIR);
4455     lstrcatA(path, "\\");
4456     lstrcatA(path, file);
4457
4458     return file_exists(path);
4459 }
4460
4461 static void delete_pfmsitest_files(void)
4462 {
4463     SHFILEOPSTRUCT shfl;
4464     CHAR path[MAX_PATH+11];
4465
4466     lstrcpyA(path, PROG_FILES_DIR);
4467     lstrcatA(path, "\\msitest\\*");
4468     path[strlen(path) + 1] = '\0';
4469
4470     shfl.hwnd = NULL;
4471     shfl.wFunc = FO_DELETE;
4472     shfl.pFrom = path;
4473     shfl.pTo = NULL;
4474     shfl.fFlags = FOF_FILESONLY | FOF_NOCONFIRMATION | FOF_NORECURSION | FOF_SILENT;
4475
4476     SHFileOperation(&shfl);
4477
4478     lstrcpyA(path, PROG_FILES_DIR);
4479     lstrcatA(path, "\\msitest");
4480     RemoveDirectoryA(path);
4481 }
4482
4483 static void check_reg_str(HKEY prodkey, LPCSTR name, LPCSTR expected, BOOL bcase, DWORD line)
4484 {
4485     char val[MAX_PATH];
4486     DWORD size, type;
4487     LONG res;
4488
4489     size = MAX_PATH;
4490     val[0] = '\0';
4491     res = RegQueryValueExA(prodkey, name, NULL, &type, (LPBYTE)val, &size);
4492
4493     if (res != ERROR_SUCCESS ||
4494         (type != REG_SZ && type != REG_EXPAND_SZ && type != REG_MULTI_SZ))
4495     {
4496         ok_(__FILE__, line)(FALSE, "Key doesn't exist or wrong type\n");
4497         return;
4498     }
4499
4500     if (!expected)
4501         ok_(__FILE__, line)(lstrlenA(val) == 0, "Expected empty string, got %s\n", val);
4502     else
4503     {
4504         if (bcase)
4505             ok_(__FILE__, line)(!lstrcmpA(val, expected), "Expected %s, got %s\n", expected, val);
4506         else
4507             ok_(__FILE__, line)(!lstrcmpiA(val, expected), "Expected %s, got %s\n", expected, val);
4508     }
4509 }
4510
4511 static void check_reg_dword(HKEY prodkey, LPCSTR name, DWORD expected, DWORD line)
4512 {
4513     DWORD val, size, type;
4514     LONG res;
4515
4516     size = sizeof(DWORD);
4517     res = RegQueryValueExA(prodkey, name, NULL, &type, (LPBYTE)&val, &size);
4518
4519     if (res != ERROR_SUCCESS || type != REG_DWORD)
4520     {
4521         ok_(__FILE__, line)(FALSE, "Key doesn't exist or wrong type\n");
4522         return;
4523     }
4524
4525     ok_(__FILE__, line)(val == expected, "Expected %d, got %d\n", expected, val);
4526 }
4527
4528 static void check_reg_dword2(HKEY prodkey, LPCSTR name, DWORD expected1, DWORD expected2, DWORD line)
4529 {
4530     DWORD val, size, type;
4531     LONG res;
4532
4533     size = sizeof(DWORD);
4534     res = RegQueryValueExA(prodkey, name, NULL, &type, (LPBYTE)&val, &size);
4535
4536     if (res != ERROR_SUCCESS || type != REG_DWORD)
4537     {
4538         ok_(__FILE__, line)(FALSE, "Key doesn't exist or wrong type\n");
4539         return;
4540     }
4541
4542     ok_(__FILE__, line)(val == expected1 || val == expected2, "Expected %d or %d, got %d\n", expected1, expected2, val);
4543 }
4544
4545 static void check_reg_dword3(HKEY prodkey, LPCSTR name, DWORD expected1, DWORD expected2, DWORD expected3, DWORD line)
4546 {
4547     DWORD val, size, type;
4548     LONG res;
4549
4550     size = sizeof(DWORD);
4551     res = RegQueryValueExA(prodkey, name, NULL, &type, (LPBYTE)&val, &size);
4552
4553     if (res != ERROR_SUCCESS || type != REG_DWORD)
4554     {
4555         ok_(__FILE__, line)(FALSE, "Key doesn't exist or wrong type\n");
4556         return;
4557     }
4558
4559     ok_(__FILE__, line)(val == expected1 || val == expected2 || val == expected3,
4560                         "Expected %d, %d or %d, got %d\n", expected1, expected2, expected3, val);
4561 }
4562
4563 #define CHECK_REG_STR(prodkey, name, expected) \
4564     check_reg_str(prodkey, name, expected, TRUE, __LINE__);
4565
4566 #define CHECK_DEL_REG_STR(prodkey, name, expected) \
4567     check_reg_str(prodkey, name, expected, TRUE, __LINE__); \
4568     RegDeleteValueA(prodkey, name);
4569
4570 #define CHECK_REG_ISTR(prodkey, name, expected) \
4571     check_reg_str(prodkey, name, expected, FALSE, __LINE__);
4572
4573 #define CHECK_DEL_REG_ISTR(prodkey, name, expected) \
4574     check_reg_str(prodkey, name, expected, FALSE, __LINE__); \
4575     RegDeleteValueA(prodkey, name);
4576
4577 #define CHECK_REG_DWORD(prodkey, name, expected) \
4578     check_reg_dword(prodkey, name, expected, __LINE__);
4579
4580 #define CHECK_DEL_REG_DWORD(prodkey, name, expected) \
4581     check_reg_dword(prodkey, name, expected, __LINE__); \
4582     RegDeleteValueA(prodkey, name);
4583
4584 #define CHECK_REG_DWORD2(prodkey, name, expected1, expected2) \
4585     check_reg_dword2(prodkey, name, expected1, expected2, __LINE__);
4586
4587 #define CHECK_DEL_REG_DWORD2(prodkey, name, expected1, expected2) \
4588     check_reg_dword2(prodkey, name, expected1, expected2, __LINE__); \
4589     RegDeleteValueA(prodkey, name);
4590
4591 #define CHECK_REG_DWORD3(prodkey, name, expected1, expected2, expected3) \
4592     check_reg_dword3(prodkey, name, expected1, expected2, expected3, __LINE__);
4593
4594 #define CHECK_DEL_REG_DWORD3(prodkey, name, expected1, expected2, expected3) \
4595     check_reg_dword3(prodkey, name, expected1, expected2, expected3, __LINE__); \
4596     RegDeleteValueA(prodkey, name);
4597
4598 static void get_date_str(LPSTR date)
4599 {
4600     SYSTEMTIME systime;
4601
4602     static const char date_fmt[] = "%d%02d%02d";
4603     GetLocalTime(&systime);
4604     sprintf(date, date_fmt, systime.wYear, systime.wMonth, systime.wDay);
4605 }
4606
4607 static void test_publish_registerproduct(void)
4608 {
4609     UINT r;
4610     LONG res;
4611     HKEY hkey;
4612     HKEY props, usage;
4613     LPSTR usersid;
4614     char date[MAX_PATH];
4615     char temp[MAX_PATH];
4616     char keypath[MAX_PATH];
4617
4618     static const CHAR uninstall[] = "Software\\Microsoft\\Windows\\CurrentVersion"
4619                                     "\\Uninstall\\{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}";
4620     static const CHAR userdata[] = "Software\\Microsoft\\Windows\\CurrentVersion\\Installer"
4621                                    "\\UserData\\%s\\Products\\84A88FD7F6998CE40A22FB59F6B9C2BB";
4622     static const CHAR ugkey[] = "Software\\Microsoft\\Windows\\CurrentVersion\\Installer"
4623                                 "\\UpgradeCodes\\51AAE0C44620A5E4788506E91F249BD2";
4624     static const CHAR userugkey[] = "Software\\Microsoft\\Installer\\UpgradeCodes"
4625                                     "\\51AAE0C44620A5E4788506E91F249BD2";
4626
4627     if (!get_user_sid(&usersid))
4628         return;
4629
4630     get_date_str(date);
4631     GetTempPath(MAX_PATH, temp);
4632
4633     CreateDirectoryA("msitest", NULL);
4634     create_file("msitest\\maximus", 500);
4635
4636     create_database(msifile, pp_tables, sizeof(pp_tables) / sizeof(msi_table));
4637
4638     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
4639
4640     /* RegisterProduct */
4641     r = MsiInstallProductA(msifile, "REGISTER_PRODUCT=1");
4642     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4643     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4644     ok(delete_pf("msitest", FALSE), "File not installed\n");
4645
4646     res = RegOpenKeyA(HKEY_CURRENT_USER, userugkey, &hkey);
4647     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
4648
4649     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, uninstall, &hkey);
4650     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4651
4652     CHECK_DEL_REG_STR(hkey, "DisplayName", "MSITEST");
4653     CHECK_DEL_REG_STR(hkey, "DisplayVersion", "1.1.1");
4654     CHECK_DEL_REG_STR(hkey, "InstallDate", date);
4655     CHECK_DEL_REG_STR(hkey, "InstallSource", temp);
4656     CHECK_DEL_REG_ISTR(hkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
4657     CHECK_DEL_REG_STR(hkey, "Publisher", "Wine");
4658     CHECK_DEL_REG_STR(hkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
4659     CHECK_DEL_REG_STR(hkey, "AuthorizedCDFPrefix", NULL);
4660     CHECK_DEL_REG_STR(hkey, "Comments", NULL);
4661     CHECK_DEL_REG_STR(hkey, "Contact", NULL);
4662     CHECK_DEL_REG_STR(hkey, "HelpLink", NULL);
4663     CHECK_DEL_REG_STR(hkey, "HelpTelephone", NULL);
4664     CHECK_DEL_REG_STR(hkey, "InstallLocation", NULL);
4665     CHECK_DEL_REG_STR(hkey, "Readme", NULL);
4666     CHECK_DEL_REG_STR(hkey, "Size", NULL);
4667     CHECK_DEL_REG_STR(hkey, "URLInfoAbout", NULL);
4668     CHECK_DEL_REG_STR(hkey, "URLUpdateInfo", NULL);
4669     CHECK_DEL_REG_DWORD(hkey, "Language", 1033);
4670     CHECK_DEL_REG_DWORD(hkey, "Version", 0x1010001);
4671     CHECK_DEL_REG_DWORD(hkey, "VersionMajor", 1);
4672     CHECK_DEL_REG_DWORD(hkey, "VersionMinor", 1);
4673     CHECK_DEL_REG_DWORD(hkey, "WindowsInstaller", 1);
4674     todo_wine
4675     {
4676         CHECK_DEL_REG_DWORD3(hkey, "EstimatedSize", 12, -12, 4);
4677     }
4678
4679     RegDeleteKeyA(hkey, "");
4680     RegCloseKey(hkey);
4681
4682     sprintf(keypath, userdata, usersid);
4683     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &hkey);
4684     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4685
4686     res = RegOpenKeyA(hkey, "InstallProperties", &props);
4687     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4688
4689     RegDeleteValueA(props, "LocalPackage"); /* LocalPackage is nondeterministic */
4690     CHECK_DEL_REG_STR(props, "DisplayName", "MSITEST");
4691     CHECK_DEL_REG_STR(props, "DisplayVersion", "1.1.1");
4692     CHECK_DEL_REG_STR(props, "InstallDate", date);
4693     CHECK_DEL_REG_STR(props, "InstallSource", temp);
4694     CHECK_DEL_REG_ISTR(props, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
4695     CHECK_DEL_REG_STR(props, "Publisher", "Wine");
4696     CHECK_DEL_REG_STR(props, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
4697     CHECK_DEL_REG_STR(props, "AuthorizedCDFPrefix", NULL);
4698     CHECK_DEL_REG_STR(props, "Comments", NULL);
4699     CHECK_DEL_REG_STR(props, "Contact", NULL);
4700     CHECK_DEL_REG_STR(props, "HelpLink", NULL);
4701     CHECK_DEL_REG_STR(props, "HelpTelephone", NULL);
4702     CHECK_DEL_REG_STR(props, "InstallLocation", NULL);
4703     CHECK_DEL_REG_STR(props, "Readme", NULL);
4704     CHECK_DEL_REG_STR(props, "Size", NULL);
4705     CHECK_DEL_REG_STR(props, "URLInfoAbout", NULL);
4706     CHECK_DEL_REG_STR(props, "URLUpdateInfo", NULL);
4707     CHECK_DEL_REG_DWORD(props, "Language", 1033);
4708     CHECK_DEL_REG_DWORD(props, "Version", 0x1010001);
4709     CHECK_DEL_REG_DWORD(props, "VersionMajor", 1);
4710     CHECK_DEL_REG_DWORD(props, "VersionMinor", 1);
4711     CHECK_DEL_REG_DWORD(props, "WindowsInstaller", 1);
4712     todo_wine
4713     {
4714         CHECK_DEL_REG_DWORD3(props, "EstimatedSize", 12, -12, 4);
4715     }
4716
4717     RegDeleteKeyA(props, "");
4718     RegCloseKey(props);
4719
4720     res = RegOpenKeyA(hkey, "Usage", &usage);
4721     todo_wine
4722     {
4723         ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4724     }
4725
4726     RegDeleteKeyA(usage, "");
4727     RegCloseKey(usage);
4728     RegDeleteKeyA(hkey, "");
4729     RegCloseKey(hkey);
4730
4731     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, ugkey, &hkey);
4732     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4733
4734     CHECK_DEL_REG_STR(hkey, "84A88FD7F6998CE40A22FB59F6B9C2BB", NULL);
4735
4736     RegDeleteKeyA(hkey, "");
4737     RegCloseKey(hkey);
4738
4739     /* RegisterProduct, machine */
4740     r = MsiInstallProductA(msifile, "REGISTER_PRODUCT=1 ALLUSERS=1");
4741     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4742     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4743     ok(delete_pf("msitest", FALSE), "File not installed\n");
4744
4745     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, userugkey, &hkey);
4746     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
4747
4748     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, uninstall, &hkey);
4749     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4750
4751     CHECK_DEL_REG_STR(hkey, "DisplayName", "MSITEST");
4752     CHECK_DEL_REG_STR(hkey, "DisplayVersion", "1.1.1");
4753     CHECK_DEL_REG_STR(hkey, "InstallDate", date);
4754     CHECK_DEL_REG_STR(hkey, "InstallSource", temp);
4755     CHECK_DEL_REG_ISTR(hkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
4756     CHECK_DEL_REG_STR(hkey, "Publisher", "Wine");
4757     CHECK_DEL_REG_STR(hkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
4758     CHECK_DEL_REG_STR(hkey, "AuthorizedCDFPrefix", NULL);
4759     CHECK_DEL_REG_STR(hkey, "Comments", NULL);
4760     CHECK_DEL_REG_STR(hkey, "Contact", NULL);
4761     CHECK_DEL_REG_STR(hkey, "HelpLink", NULL);
4762     CHECK_DEL_REG_STR(hkey, "HelpTelephone", NULL);
4763     CHECK_DEL_REG_STR(hkey, "InstallLocation", NULL);
4764     CHECK_DEL_REG_STR(hkey, "Readme", NULL);
4765     CHECK_DEL_REG_STR(hkey, "Size", NULL);
4766     CHECK_DEL_REG_STR(hkey, "URLInfoAbout", NULL);
4767     CHECK_DEL_REG_STR(hkey, "URLUpdateInfo", NULL);
4768     CHECK_DEL_REG_DWORD(hkey, "Language", 1033);
4769     CHECK_DEL_REG_DWORD(hkey, "Version", 0x1010001);
4770     CHECK_DEL_REG_DWORD(hkey, "VersionMajor", 1);
4771     CHECK_DEL_REG_DWORD(hkey, "VersionMinor", 1);
4772     CHECK_DEL_REG_DWORD(hkey, "WindowsInstaller", 1);
4773     todo_wine
4774     {
4775         CHECK_DEL_REG_DWORD3(hkey, "EstimatedSize", 12, -12, 4);
4776     }
4777
4778     RegDeleteKeyA(hkey, "");
4779     RegCloseKey(hkey);
4780
4781     sprintf(keypath, userdata, "S-1-5-18");
4782     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &hkey);
4783     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4784
4785     res = RegOpenKeyA(hkey, "InstallProperties", &props);
4786     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4787
4788     RegDeleteValueA(props, "LocalPackage"); /* LocalPackage is nondeterministic */
4789     CHECK_DEL_REG_STR(props, "DisplayName", "MSITEST");
4790     CHECK_DEL_REG_STR(props, "DisplayVersion", "1.1.1");
4791     CHECK_DEL_REG_STR(props, "InstallDate", date);
4792     CHECK_DEL_REG_STR(props, "InstallSource", temp);
4793     CHECK_DEL_REG_ISTR(props, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
4794     CHECK_DEL_REG_STR(props, "Publisher", "Wine");
4795     CHECK_DEL_REG_STR(props, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
4796     CHECK_DEL_REG_STR(props, "AuthorizedCDFPrefix", NULL);
4797     CHECK_DEL_REG_STR(props, "Comments", NULL);
4798     CHECK_DEL_REG_STR(props, "Contact", NULL);
4799     CHECK_DEL_REG_STR(props, "HelpLink", NULL);
4800     CHECK_DEL_REG_STR(props, "HelpTelephone", NULL);
4801     CHECK_DEL_REG_STR(props, "InstallLocation", NULL);
4802     CHECK_DEL_REG_STR(props, "Readme", NULL);
4803     CHECK_DEL_REG_STR(props, "Size", NULL);
4804     CHECK_DEL_REG_STR(props, "URLInfoAbout", NULL);
4805     CHECK_DEL_REG_STR(props, "URLUpdateInfo", NULL);
4806     CHECK_DEL_REG_DWORD(props, "Language", 1033);
4807     CHECK_DEL_REG_DWORD(props, "Version", 0x1010001);
4808     CHECK_DEL_REG_DWORD(props, "VersionMajor", 1);
4809     CHECK_DEL_REG_DWORD(props, "VersionMinor", 1);
4810     CHECK_DEL_REG_DWORD(props, "WindowsInstaller", 1);
4811     todo_wine
4812     {
4813         CHECK_DEL_REG_DWORD3(props, "EstimatedSize", 12, -12, 4);
4814     }
4815
4816     RegDeleteKeyA(props, "");
4817     RegCloseKey(props);
4818
4819     res = RegOpenKeyA(hkey, "Usage", &usage);
4820     todo_wine
4821     {
4822         ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4823     }
4824
4825     RegDeleteKeyA(usage, "");
4826     RegCloseKey(usage);
4827     RegDeleteKeyA(hkey, "");
4828     RegCloseKey(hkey);
4829
4830     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, ugkey, &hkey);
4831     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4832
4833     CHECK_DEL_REG_STR(hkey, "84A88FD7F6998CE40A22FB59F6B9C2BB", NULL);
4834
4835     RegDeleteKeyA(hkey, "");
4836     RegCloseKey(hkey);
4837
4838     DeleteFile(msifile);
4839     DeleteFile("msitest\\maximus");
4840     RemoveDirectory("msitest");
4841     HeapFree(GetProcessHeap(), 0, usersid);
4842 }
4843
4844 static void test_publish_publishproduct(void)
4845 {
4846     UINT r;
4847     LONG res;
4848     LPSTR usersid;
4849     HKEY sourcelist, net, props;
4850     HKEY hkey, patches, media;
4851     CHAR keypath[MAX_PATH];
4852     CHAR temp[MAX_PATH];
4853     CHAR path[MAX_PATH];
4854     BOOL old_installer = FALSE;
4855
4856     static const CHAR prodpath[] = "Software\\Microsoft\\Windows\\CurrentVersion"
4857                                    "\\Installer\\UserData\\%s\\Products"
4858                                    "\\84A88FD7F6998CE40A22FB59F6B9C2BB";
4859     static const CHAR cuprodpath[] = "Software\\Microsoft\\Installer\\Products"
4860                                      "\\84A88FD7F6998CE40A22FB59F6B9C2BB";
4861     static const CHAR cuupgrades[] = "Software\\Microsoft\\Installer\\UpgradeCodes"
4862                                      "\\51AAE0C44620A5E4788506E91F249BD2";
4863     static const CHAR badprod[] = "Software\\Microsoft\\Windows\\CurrentVersion"
4864                                   "\\Installer\\Products"
4865                                   "\\84A88FD7F6998CE40A22FB59F6B9C2BB";
4866     static const CHAR machprod[] = "Installer\\Products\\84A88FD7F6998CE40A22FB59F6B9C2BB";
4867     static const CHAR machup[] = "Installer\\UpgradeCodes\\51AAE0C44620A5E4788506E91F249BD2";
4868
4869     if (!get_user_sid(&usersid))
4870         return;
4871
4872     GetTempPath(MAX_PATH, temp);
4873
4874     CreateDirectoryA("msitest", NULL);
4875     create_file("msitest\\maximus", 500);
4876
4877     create_database(msifile, pp_tables, sizeof(pp_tables) / sizeof(msi_table));
4878
4879     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
4880
4881     /* PublishProduct, current user */
4882     r = MsiInstallProductA(msifile, "PUBLISH_PRODUCT=1");
4883     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4884     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4885     ok(delete_pf("msitest", FALSE), "File not installed\n");
4886
4887     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, badprod, &hkey);
4888     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
4889
4890     sprintf(keypath, prodpath, usersid);
4891     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &hkey);
4892     if (res == ERROR_FILE_NOT_FOUND)
4893     {
4894         res = RegOpenKeyA(HKEY_CURRENT_USER, cuprodpath, &hkey);
4895         if (res == ERROR_SUCCESS)
4896         {
4897             win_skip("Windows Installer < 3.0 detected\n");
4898             RegCloseKey(hkey);
4899             old_installer = TRUE;
4900             goto currentuser;
4901         }
4902         else
4903         {
4904             win_skip("Install failed, no need to continue\n");
4905             return;
4906         }
4907     }
4908     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4909
4910     res = RegOpenKeyA(hkey, "InstallProperties", &props);
4911     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
4912
4913     res = RegOpenKeyA(hkey, "Patches", &patches);
4914     todo_wine
4915     {
4916         ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4917
4918         CHECK_DEL_REG_STR(patches, "AllPatches", NULL);
4919     }
4920
4921     RegDeleteKeyA(patches, "");
4922     RegCloseKey(patches);
4923     RegDeleteKeyA(hkey, "");
4924     RegCloseKey(hkey);
4925
4926 currentuser:
4927     res = RegOpenKeyA(HKEY_CURRENT_USER, cuprodpath, &hkey);
4928     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4929
4930     CHECK_DEL_REG_STR(hkey, "ProductName", "MSITEST");
4931     CHECK_DEL_REG_STR(hkey, "PackageCode", "AC75740029052c94DA02821EECD05F2F");
4932     CHECK_DEL_REG_DWORD(hkey, "Language", 1033);
4933     CHECK_DEL_REG_DWORD(hkey, "Version", 0x1010001);
4934     if (!old_installer)
4935         CHECK_DEL_REG_DWORD(hkey, "AuthorizedLUAApp", 0);
4936     CHECK_DEL_REG_DWORD(hkey, "Assignment", 0);
4937     CHECK_DEL_REG_DWORD(hkey, "AdvertiseFlags", 0x184);
4938     CHECK_DEL_REG_DWORD(hkey, "InstanceType", 0);
4939     CHECK_DEL_REG_STR(hkey, "Clients", ":");
4940
4941     res = RegOpenKeyA(hkey, "SourceList", &sourcelist);
4942     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4943
4944     lstrcpyA(path, "n;1;");
4945     lstrcatA(path, temp);
4946     CHECK_DEL_REG_STR(sourcelist, "LastUsedSource", path);
4947     CHECK_DEL_REG_STR(sourcelist, "PackageName", "msitest.msi");
4948
4949     res = RegOpenKeyA(sourcelist, "Net", &net);
4950     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4951
4952     CHECK_DEL_REG_STR(net, "1", temp);
4953
4954     RegDeleteKeyA(net, "");
4955     RegCloseKey(net);
4956
4957     res = RegOpenKeyA(sourcelist, "Media", &media);
4958     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4959
4960     CHECK_DEL_REG_STR(media, "1", "DISK1;");
4961
4962     RegDeleteKeyA(media, "");
4963     RegCloseKey(media);
4964     RegDeleteKeyA(sourcelist, "");
4965     RegCloseKey(sourcelist);
4966     RegDeleteKeyA(hkey, "");
4967     RegCloseKey(hkey);
4968
4969     res = RegOpenKeyA(HKEY_CURRENT_USER, cuupgrades, &hkey);
4970     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4971
4972     CHECK_DEL_REG_STR(hkey, "84A88FD7F6998CE40A22FB59F6B9C2BB", NULL);
4973
4974     RegDeleteKeyA(hkey, "");
4975     RegCloseKey(hkey);
4976
4977     /* PublishProduct, machine */
4978     r = MsiInstallProductA(msifile, "PUBLISH_PRODUCT=1 ALLUSERS=1");
4979     if (old_installer)
4980         goto machprod;
4981     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
4982     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
4983     ok(delete_pf("msitest", FALSE), "File not installed\n");
4984
4985     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, badprod, &hkey);
4986     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
4987
4988     sprintf(keypath, prodpath, "S-1-5-18");
4989     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &hkey);
4990     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4991
4992     res = RegOpenKeyA(hkey, "InstallProperties", &props);
4993     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
4994
4995     res = RegOpenKeyA(hkey, "Patches", &patches);
4996     todo_wine
4997     {
4998         ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
4999
5000         CHECK_DEL_REG_STR(patches, "AllPatches", NULL);
5001     }
5002
5003     RegDeleteKeyA(patches, "");
5004     RegCloseKey(patches);
5005     RegDeleteKeyA(hkey, "");
5006     RegCloseKey(hkey);
5007
5008 machprod:
5009     res = RegOpenKeyA(HKEY_CLASSES_ROOT, machprod, &hkey);
5010     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5011
5012     CHECK_DEL_REG_STR(hkey, "ProductName", "MSITEST");
5013     CHECK_DEL_REG_STR(hkey, "PackageCode", "AC75740029052c94DA02821EECD05F2F");
5014     CHECK_DEL_REG_DWORD(hkey, "Language", 1033);
5015     CHECK_DEL_REG_DWORD(hkey, "Version", 0x1010001);
5016     if (!old_installer)
5017         CHECK_DEL_REG_DWORD(hkey, "AuthorizedLUAApp", 0);
5018     todo_wine CHECK_DEL_REG_DWORD(hkey, "Assignment", 1);
5019     CHECK_DEL_REG_DWORD(hkey, "AdvertiseFlags", 0x184);
5020     CHECK_DEL_REG_DWORD(hkey, "InstanceType", 0);
5021     CHECK_DEL_REG_STR(hkey, "Clients", ":");
5022
5023     res = RegOpenKeyA(hkey, "SourceList", &sourcelist);
5024     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5025
5026     lstrcpyA(path, "n;1;");
5027     lstrcatA(path, temp);
5028     CHECK_DEL_REG_STR(sourcelist, "LastUsedSource", path);
5029     CHECK_DEL_REG_STR(sourcelist, "PackageName", "msitest.msi");
5030
5031     res = RegOpenKeyA(sourcelist, "Net", &net);
5032     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5033
5034     CHECK_DEL_REG_STR(net, "1", temp);
5035
5036     RegDeleteKeyA(net, "");
5037     RegCloseKey(net);
5038
5039     res = RegOpenKeyA(sourcelist, "Media", &media);
5040     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5041
5042     CHECK_DEL_REG_STR(media, "1", "DISK1;");
5043
5044     RegDeleteKeyA(media, "");
5045     RegCloseKey(media);
5046     RegDeleteKeyA(sourcelist, "");
5047     RegCloseKey(sourcelist);
5048     RegDeleteKeyA(hkey, "");
5049     RegCloseKey(hkey);
5050
5051     res = RegOpenKeyA(HKEY_CLASSES_ROOT, machup, &hkey);
5052     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5053
5054     CHECK_DEL_REG_STR(hkey, "84A88FD7F6998CE40A22FB59F6B9C2BB", NULL);
5055
5056     RegDeleteKeyA(hkey, "");
5057     RegCloseKey(hkey);
5058
5059     DeleteFile(msifile);
5060     DeleteFile("msitest\\maximus");
5061     RemoveDirectory("msitest");
5062     HeapFree(GetProcessHeap(), 0, usersid);
5063 }
5064
5065 static void test_publish_publishfeatures(void)
5066 {
5067     UINT r;
5068     LONG res;
5069     HKEY hkey;
5070     LPSTR usersid;
5071     CHAR keypath[MAX_PATH];
5072
5073     static const CHAR cupath[] = "Software\\Microsoft\\Installer\\Features"
5074                                  "\\84A88FD7F6998CE40A22FB59F6B9C2BB";
5075     static const CHAR udpath[] = "Software\\Microsoft\\Windows\\CurrentVersion"
5076                                  "\\Installer\\UserData\\%s\\Products"
5077                                  "\\84A88FD7F6998CE40A22FB59F6B9C2BB\\Features";
5078     static const CHAR featkey[] = "Software\\Microsoft\\Windows\\CurrentVersion"
5079                                   "\\Installer\\Features";
5080     static const CHAR classfeat[] = "Software\\Classes\\Installer\\Features"
5081                                     "\\84A88FD7F6998CE40A22FB59F6B9C2BB";
5082
5083     if (!get_user_sid(&usersid))
5084         return;
5085
5086     CreateDirectoryA("msitest", NULL);
5087     create_file("msitest\\maximus", 500);
5088
5089     create_database(msifile, pp_tables, sizeof(pp_tables) / sizeof(msi_table));
5090
5091     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
5092
5093     /* PublishFeatures, current user */
5094     r = MsiInstallProductA(msifile, "PUBLISH_FEATURES=1");
5095     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5096     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
5097     ok(delete_pf("msitest", FALSE), "File not installed\n");
5098
5099     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, featkey, &hkey);
5100     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5101
5102     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, classfeat, &hkey);
5103     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5104
5105     res = RegOpenKeyA(HKEY_CURRENT_USER, cupath, &hkey);
5106     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5107
5108     CHECK_REG_STR(hkey, "feature", "");
5109     CHECK_REG_STR(hkey, "montecristo", "");
5110
5111     RegDeleteValueA(hkey, "feature");
5112     RegDeleteValueA(hkey, "montecristo");
5113     RegDeleteKeyA(hkey, "");
5114     RegCloseKey(hkey);
5115
5116     sprintf(keypath, udpath, usersid);
5117     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &hkey);
5118     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5119
5120     CHECK_REG_STR(hkey, "feature", "VGtfp^p+,?82@JU1j_KE");
5121     CHECK_REG_STR(hkey, "montecristo", "VGtfp^p+,?82@JU1j_KE");
5122
5123     RegDeleteValueA(hkey, "feature");
5124     RegDeleteValueA(hkey, "montecristo");
5125     RegDeleteKeyA(hkey, "");
5126     RegCloseKey(hkey);
5127
5128     /* PublishFeatures, machine */
5129     r = MsiInstallProductA(msifile, "PUBLISH_FEATURES=1 ALLUSERS=1");
5130     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5131     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
5132     ok(delete_pf("msitest", FALSE), "File not installed\n");
5133
5134     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, featkey, &hkey);
5135     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5136
5137     res = RegOpenKeyA(HKEY_CURRENT_USER, cupath, &hkey);
5138     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5139
5140     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, classfeat, &hkey);
5141     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5142
5143     CHECK_REG_STR(hkey, "feature", "");
5144     CHECK_REG_STR(hkey, "montecristo", "");
5145
5146     RegDeleteValueA(hkey, "feature");
5147     RegDeleteValueA(hkey, "montecristo");
5148     RegDeleteKeyA(hkey, "");
5149     RegCloseKey(hkey);
5150
5151     sprintf(keypath, udpath, "S-1-5-18");
5152     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &hkey);
5153     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5154
5155     CHECK_REG_STR(hkey, "feature", "VGtfp^p+,?82@JU1j_KE");
5156     CHECK_REG_STR(hkey, "montecristo", "VGtfp^p+,?82@JU1j_KE");
5157
5158     RegDeleteValueA(hkey, "feature");
5159     RegDeleteValueA(hkey, "montecristo");
5160     RegDeleteKeyA(hkey, "");
5161     RegCloseKey(hkey);
5162
5163     DeleteFile(msifile);
5164     DeleteFile("msitest\\maximus");
5165     RemoveDirectory("msitest");
5166     HeapFree(GetProcessHeap(), 0, usersid);
5167 }
5168
5169 static LPSTR reg_get_val_str(HKEY hkey, LPCSTR name)
5170 {
5171     DWORD len = 0;
5172     LPSTR val;
5173     LONG r;
5174
5175     r = RegQueryValueExA(hkey, name, NULL, NULL, NULL, &len);
5176     if (r != ERROR_SUCCESS)
5177         return NULL;
5178
5179     len += sizeof (WCHAR);
5180     val = HeapAlloc(GetProcessHeap(), 0, len);
5181     if (!val) return NULL;
5182     val[0] = 0;
5183     RegQueryValueExA(hkey, name, NULL, NULL, (LPBYTE)val, &len);
5184     return val;
5185 }
5186
5187 static void get_owner_company(LPSTR *owner, LPSTR *company)
5188 {
5189     LONG res;
5190     HKEY hkey;
5191
5192     *owner = *company = NULL;
5193
5194     res = RegOpenKeyA(HKEY_CURRENT_USER,
5195                       "Software\\Microsoft\\MS Setup (ACME)\\User Info", &hkey);
5196     if (res == ERROR_SUCCESS)
5197     {
5198         *owner = reg_get_val_str(hkey, "DefName");
5199         *company = reg_get_val_str(hkey, "DefCompany");
5200         RegCloseKey(hkey);
5201     }
5202
5203     if (!*owner || !*company)
5204     {
5205         res = RegOpenKeyA(HKEY_LOCAL_MACHINE,
5206                           "Software\\Microsoft\\Windows\\CurrentVersion", &hkey);
5207         if (res == ERROR_SUCCESS)
5208         {
5209             *owner = reg_get_val_str(hkey, "RegisteredOwner");
5210             *company = reg_get_val_str(hkey, "RegisteredOrganization");
5211             RegCloseKey(hkey);
5212         }
5213     }
5214
5215     if (!*owner || !*company)
5216     {
5217         res = RegOpenKeyA(HKEY_LOCAL_MACHINE,
5218                           "Software\\Microsoft\\Windows NT\\CurrentVersion", &hkey);
5219         if (res == ERROR_SUCCESS)
5220         {
5221             *owner = reg_get_val_str(hkey, "RegisteredOwner");
5222             *company = reg_get_val_str(hkey, "RegisteredOrganization");
5223             RegCloseKey(hkey);
5224         }
5225     }
5226 }
5227
5228 static void test_publish_registeruser(void)
5229 {
5230     UINT r;
5231     LONG res;
5232     HKEY props;
5233     LPSTR usersid;
5234     LPSTR owner, company;
5235     CHAR keypath[MAX_PATH];
5236
5237     static const CHAR keyfmt[] =
5238         "Software\\Microsoft\\Windows\\CurrentVersion\\Installer\\"
5239         "UserData\\%s\\Products\\84A88FD7F6998CE40A22FB59F6B9C2BB\\InstallProperties";
5240
5241     if (!get_user_sid(&usersid))
5242         return;
5243
5244     get_owner_company(&owner, &company);
5245
5246     CreateDirectoryA("msitest", NULL);
5247     create_file("msitest\\maximus", 500);
5248
5249     create_database(msifile, pp_tables, sizeof(pp_tables) / sizeof(msi_table));
5250
5251     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
5252
5253     /* RegisterUser, per-user */
5254     r = MsiInstallProductA(msifile, "REGISTER_USER=1");
5255     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5256     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
5257     ok(delete_pf("msitest", FALSE), "File not installed\n");
5258
5259     sprintf(keypath, keyfmt, usersid);
5260
5261     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &props);
5262     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5263
5264     CHECK_REG_STR(props, "ProductID", "none");
5265     CHECK_REG_STR(props, "RegCompany", company);
5266     CHECK_REG_STR(props, "RegOwner", owner);
5267
5268     RegDeleteValueA(props, "ProductID");
5269     RegDeleteValueA(props, "RegCompany");
5270     RegDeleteValueA(props, "RegOwner");
5271     RegDeleteKeyA(props, "");
5272     RegCloseKey(props);
5273
5274     /* RegisterUser, machine */
5275     r = MsiInstallProductA(msifile, "REGISTER_USER=1 ALLUSERS=1");
5276     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5277     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
5278     ok(delete_pf("msitest", FALSE), "File not installed\n");
5279
5280     sprintf(keypath, keyfmt, "S-1-5-18");
5281
5282     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &props);
5283     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5284
5285     CHECK_REG_STR(props, "ProductID", "none");
5286     CHECK_REG_STR(props, "RegCompany", company);
5287     CHECK_REG_STR(props, "RegOwner", owner);
5288
5289     RegDeleteValueA(props, "ProductID");
5290     RegDeleteValueA(props, "RegCompany");
5291     RegDeleteValueA(props, "RegOwner");
5292     RegDeleteKeyA(props, "");
5293     RegCloseKey(props);
5294
5295     HeapFree(GetProcessHeap(), 0, company);
5296     HeapFree(GetProcessHeap(), 0, owner);
5297
5298     DeleteFile(msifile);
5299     DeleteFile("msitest\\maximus");
5300     RemoveDirectory("msitest");
5301     LocalFree(usersid);
5302 }
5303
5304 static void test_publish_processcomponents(void)
5305 {
5306     UINT r;
5307     LONG res;
5308     DWORD size;
5309     HKEY comp, hkey;
5310     LPSTR usersid;
5311     CHAR val[MAX_PATH];
5312     CHAR keypath[MAX_PATH];
5313     CHAR program_files_maximus[MAX_PATH];
5314
5315     static const CHAR keyfmt[] =
5316         "Software\\Microsoft\\Windows\\CurrentVersion\\Installer\\"
5317         "UserData\\%s\\Components\\%s";
5318     static const CHAR compkey[] =
5319         "Software\\Microsoft\\Windows\\CurrentVersion\\Installer\\Components";
5320
5321     if (!get_user_sid(&usersid))
5322         return;
5323
5324     CreateDirectoryA("msitest", NULL);
5325     create_file("msitest\\maximus", 500);
5326
5327     create_database(msifile, ppc_tables, sizeof(ppc_tables) / sizeof(msi_table));
5328
5329     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
5330
5331     /* ProcessComponents, per-user */
5332     r = MsiInstallProductA(msifile, "PROCESS_COMPONENTS=1");
5333     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5334     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
5335     ok(delete_pf("msitest", FALSE), "File not installed\n");
5336
5337     sprintf(keypath, keyfmt, usersid, "CBABC2FDCCB35E749A8944D8C1C098B5");
5338
5339     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &comp);
5340     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5341
5342     size = MAX_PATH;
5343     res = RegQueryValueExA(comp, "84A88FD7F6998CE40A22FB59F6B9C2BB",
5344                            NULL, NULL, (LPBYTE)val, &size);
5345     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5346
5347     lstrcpyA(program_files_maximus,PROG_FILES_DIR);
5348     lstrcatA(program_files_maximus,"\\msitest\\maximus");
5349
5350     ok(!lstrcmpiA(val, program_files_maximus),
5351        "Expected \"%s\", got \"%s\"\n", program_files_maximus, val);
5352
5353     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, compkey, &hkey);
5354     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5355
5356     RegDeleteValueA(comp, "84A88FD7F6998CE40A22FB59F6B9C2BB");
5357     RegDeleteKeyA(comp, "");
5358     RegCloseKey(comp);
5359
5360     sprintf(keypath, keyfmt, usersid, "241C3DA58FECD0945B9687D408766058");
5361
5362     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &comp);
5363     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5364
5365     size = MAX_PATH;
5366     res = RegQueryValueExA(comp, "84A88FD7F6998CE40A22FB59F6B9C2BB",
5367                            NULL, NULL, (LPBYTE)val, &size);
5368     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5369     ok(!lstrcmpA(val, "01\\msitest\\augustus"),
5370        "Expected \"01\\msitest\\augustus\", got \"%s\"\n", val);
5371
5372     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, compkey, &hkey);
5373     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5374
5375     RegDeleteValueA(comp, "84A88FD7F6998CE40A22FB59F6B9C2BB");
5376     RegDeleteKeyA(comp, "");
5377     RegCloseKey(comp);
5378
5379     /* ProcessComponents, machine */
5380     r = MsiInstallProductA(msifile, "PROCESS_COMPONENTS=1 ALLUSERS=1");
5381     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5382     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
5383     ok(delete_pf("msitest", FALSE), "File not installed\n");
5384
5385     sprintf(keypath, keyfmt, "S-1-5-18", "CBABC2FDCCB35E749A8944D8C1C098B5");
5386
5387     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &comp);
5388     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5389
5390     size = MAX_PATH;
5391     res = RegQueryValueExA(comp, "84A88FD7F6998CE40A22FB59F6B9C2BB",
5392                            NULL, NULL, (LPBYTE)val, &size);
5393     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5394     ok(!lstrcmpiA(val, program_files_maximus),
5395        "Expected \"%s\", got \"%s\"\n", program_files_maximus, val);
5396
5397     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, compkey, &hkey);
5398     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5399
5400     RegDeleteValueA(comp, "84A88FD7F6998CE40A22FB59F6B9C2BB");
5401     RegDeleteKeyA(comp, "");
5402     RegCloseKey(comp);
5403
5404     sprintf(keypath, keyfmt, "S-1-5-18", "241C3DA58FECD0945B9687D408766058");
5405
5406     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &comp);
5407     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5408
5409     size = MAX_PATH;
5410     res = RegQueryValueExA(comp, "84A88FD7F6998CE40A22FB59F6B9C2BB",
5411                            NULL, NULL, (LPBYTE)val, &size);
5412     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5413     ok(!lstrcmpA(val, "01\\msitest\\augustus"),
5414        "Expected \"01\\msitest\\augustus\", got \"%s\"\n", val);
5415
5416     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, compkey, &hkey);
5417     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5418
5419     RegDeleteValueA(comp, "84A88FD7F6998CE40A22FB59F6B9C2BB");
5420     RegDeleteKeyA(comp, "");
5421     RegCloseKey(comp);
5422
5423     DeleteFile(msifile);
5424     DeleteFile("msitest\\maximus");
5425     RemoveDirectory("msitest");
5426     LocalFree(usersid);
5427 }
5428
5429 static void test_publish(void)
5430 {
5431     UINT r;
5432     LONG res;
5433     HKEY uninstall, prodkey;
5434     INSTALLSTATE state;
5435     CHAR prodcode[] = "{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}";
5436     char date[MAX_PATH];
5437     char temp[MAX_PATH];
5438
5439     static const CHAR subkey[] = "Software\\Microsoft\\Windows\\CurrentVersion\\Uninstall";
5440
5441     if (!pMsiQueryComponentStateA)
5442     {
5443         win_skip("MsiQueryComponentStateA is not available\n");
5444         return;
5445     }
5446
5447     get_date_str(date);
5448     GetTempPath(MAX_PATH, temp);
5449
5450     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, subkey, &uninstall);
5451     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5452
5453     CreateDirectoryA("msitest", NULL);
5454     create_file("msitest\\maximus", 500);
5455
5456     create_database(msifile, pp_tables, sizeof(pp_tables) / sizeof(msi_table));
5457
5458     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
5459
5460     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5461     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5462
5463     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5464     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5465
5466     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5467     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5468
5469     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5470                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5471     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5472     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5473
5474     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5475     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5476
5477     /* nothing published */
5478     r = MsiInstallProductA(msifile, NULL);
5479     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5480     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5481     ok(pf_exists("msitest"), "File not installed\n");
5482
5483     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5484     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5485
5486     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5487     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5488
5489     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5490     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5491
5492     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5493                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5494     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5495     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5496
5497     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5498     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5499
5500     /* PublishProduct and RegisterProduct */
5501     r = MsiInstallProductA(msifile, "REGISTER_PRODUCT=1 PUBLISH_PRODUCT=1");
5502     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5503     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5504     ok(pf_exists("msitest"), "File not installed\n");
5505
5506     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5507     ok(state == INSTALLSTATE_DEFAULT, "Expected INSTALLSTATE_DEFAULT, got %d\n", state);
5508
5509     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5510     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5511
5512     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5513     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5514
5515     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5516                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5517     ok(r == ERROR_UNKNOWN_COMPONENT, "Expected ERROR_UNKNOWN_COMPONENT, got %d\n", r);
5518     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5519
5520     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5521     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5522
5523     CHECK_REG_STR(prodkey, "DisplayName", "MSITEST");
5524     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
5525     CHECK_REG_STR(prodkey, "InstallDate", date);
5526     CHECK_REG_STR(prodkey, "InstallSource", temp);
5527     CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5528     CHECK_REG_STR(prodkey, "Publisher", "Wine");
5529     CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5530     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
5531     CHECK_REG_STR(prodkey, "Comments", NULL);
5532     CHECK_REG_STR(prodkey, "Contact", NULL);
5533     CHECK_REG_STR(prodkey, "HelpLink", NULL);
5534     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
5535     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
5536     CHECK_REG_STR(prodkey, "Readme", NULL);
5537     CHECK_REG_STR(prodkey, "Size", NULL);
5538     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
5539     CHECK_REG_STR(prodkey, "URLUpdateInfo", NULL);
5540     CHECK_REG_DWORD(prodkey, "Language", 1033);
5541     CHECK_REG_DWORD(prodkey, "Version", 0x1010001);
5542     CHECK_REG_DWORD(prodkey, "VersionMajor", 1);
5543     CHECK_REG_DWORD(prodkey, "VersionMinor", 1);
5544     CHECK_REG_DWORD(prodkey, "WindowsInstaller", 1);
5545     todo_wine
5546     {
5547         CHECK_REG_DWORD2(prodkey, "EstimatedSize", 12, -12);
5548     }
5549
5550     RegCloseKey(prodkey);
5551
5552     r = MsiInstallProductA(msifile, "FULL=1 REMOVE=ALL");
5553     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5554     ok(pf_exists("msitest\\maximus"), "File deleted\n");
5555     ok(pf_exists("msitest"), "File deleted\n");
5556
5557     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5558     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5559
5560     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5561     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5562
5563     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5564     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5565
5566     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5567                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5568     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5569     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5570
5571     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5572     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5573
5574     /* complete install */
5575     r = MsiInstallProductA(msifile, "FULL=1");
5576     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5577     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5578     ok(pf_exists("msitest"), "File not installed\n");
5579
5580     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5581     ok(state == INSTALLSTATE_DEFAULT, "Expected INSTALLSTATE_DEFAULT, got %d\n", state);
5582
5583     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5584     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5585
5586     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5587     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5588
5589     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5590                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5591     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5592     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5593
5594     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5595     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5596
5597     CHECK_REG_STR(prodkey, "DisplayName", "MSITEST");
5598     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
5599     CHECK_REG_STR(prodkey, "InstallDate", date);
5600     CHECK_REG_STR(prodkey, "InstallSource", temp);
5601     CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5602     CHECK_REG_STR(prodkey, "Publisher", "Wine");
5603     CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5604     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
5605     CHECK_REG_STR(prodkey, "Comments", NULL);
5606     CHECK_REG_STR(prodkey, "Contact", NULL);
5607     CHECK_REG_STR(prodkey, "HelpLink", NULL);
5608     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
5609     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
5610     CHECK_REG_STR(prodkey, "Readme", NULL);
5611     CHECK_REG_STR(prodkey, "Size", NULL);
5612     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
5613     CHECK_REG_STR(prodkey, "URLUpdateInfo", NULL);
5614     CHECK_REG_DWORD(prodkey, "Language", 1033);
5615     CHECK_REG_DWORD(prodkey, "Version", 0x1010001);
5616     CHECK_REG_DWORD(prodkey, "VersionMajor", 1);
5617     CHECK_REG_DWORD(prodkey, "VersionMinor", 1);
5618     CHECK_REG_DWORD(prodkey, "WindowsInstaller", 1);
5619     todo_wine
5620     {
5621         CHECK_REG_DWORD2(prodkey, "EstimatedSize", 12, -12);
5622     }
5623
5624     RegCloseKey(prodkey);
5625
5626     /* no UnpublishFeatures */
5627     r = MsiInstallProductA(msifile, "REMOVE=ALL");
5628     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5629     ok(!pf_exists("msitest\\maximus"), "File not deleted\n");
5630     ok(!pf_exists("msitest"), "Directory not deleted\n");
5631
5632     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5633     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5634
5635     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5636     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5637
5638     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5639     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5640
5641     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5642                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5643     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5644     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5645
5646     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5647     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5648
5649     /* complete install */
5650     r = MsiInstallProductA(msifile, "FULL=1");
5651     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5652     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5653     ok(pf_exists("msitest"), "File not installed\n");
5654
5655     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5656     ok(state == INSTALLSTATE_DEFAULT, "Expected INSTALLSTATE_DEFAULT, got %d\n", state);
5657
5658     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5659     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5660
5661     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5662     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5663
5664     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5665                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5666     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5667     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5668
5669     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5670     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5671
5672     CHECK_REG_STR(prodkey, "DisplayName", "MSITEST");
5673     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
5674     CHECK_REG_STR(prodkey, "InstallDate", date);
5675     CHECK_REG_STR(prodkey, "InstallSource", temp);
5676     CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5677     CHECK_REG_STR(prodkey, "Publisher", "Wine");
5678     CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5679     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
5680     CHECK_REG_STR(prodkey, "Comments", NULL);
5681     CHECK_REG_STR(prodkey, "Contact", NULL);
5682     CHECK_REG_STR(prodkey, "HelpLink", NULL);
5683     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
5684     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
5685     CHECK_REG_STR(prodkey, "Readme", NULL);
5686     CHECK_REG_STR(prodkey, "Size", NULL);
5687     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
5688     CHECK_REG_STR(prodkey, "URLUpdateInfo", NULL);
5689     CHECK_REG_DWORD(prodkey, "Language", 1033);
5690     CHECK_REG_DWORD(prodkey, "Version", 0x1010001);
5691     CHECK_REG_DWORD(prodkey, "VersionMajor", 1);
5692     CHECK_REG_DWORD(prodkey, "VersionMinor", 1);
5693     CHECK_REG_DWORD(prodkey, "WindowsInstaller", 1);
5694     todo_wine
5695     {
5696         CHECK_REG_DWORD2(prodkey, "EstimatedSize", 12, -12);
5697     }
5698
5699     RegCloseKey(prodkey);
5700
5701     /* UnpublishFeatures, only feature removed.  Only works when entire product is removed */
5702     r = MsiInstallProductA(msifile, "UNPUBLISH_FEATURES=1 REMOVE=feature");
5703     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5704     todo_wine ok(pf_exists("msitest\\maximus"), "File deleted\n");
5705     todo_wine ok(pf_exists("msitest"), "Directory deleted\n");
5706
5707     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5708     ok(state == INSTALLSTATE_DEFAULT, "Expected INSTALLSTATE_DEFAULT, got %d\n", state);
5709
5710     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5711     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5712
5713     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5714     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5715
5716     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5717                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5718     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5719     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5720
5721     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5722     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5723
5724     CHECK_REG_STR(prodkey, "DisplayName", "MSITEST");
5725     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
5726     CHECK_REG_STR(prodkey, "InstallDate", date);
5727     CHECK_REG_STR(prodkey, "InstallSource", temp);
5728     CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5729     CHECK_REG_STR(prodkey, "Publisher", "Wine");
5730     CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5731     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
5732     CHECK_REG_STR(prodkey, "Comments", NULL);
5733     CHECK_REG_STR(prodkey, "Contact", NULL);
5734     CHECK_REG_STR(prodkey, "HelpLink", NULL);
5735     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
5736     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
5737     CHECK_REG_STR(prodkey, "Readme", NULL);
5738     CHECK_REG_STR(prodkey, "Size", NULL);
5739     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
5740     CHECK_REG_STR(prodkey, "URLUpdateInfo", NULL);
5741     CHECK_REG_DWORD(prodkey, "Language", 1033);
5742     CHECK_REG_DWORD(prodkey, "Version", 0x1010001);
5743     CHECK_REG_DWORD(prodkey, "VersionMajor", 1);
5744     CHECK_REG_DWORD(prodkey, "VersionMinor", 1);
5745     CHECK_REG_DWORD(prodkey, "WindowsInstaller", 1);
5746     todo_wine
5747     {
5748         CHECK_REG_DWORD2(prodkey, "EstimatedSize", 12, -12);
5749     }
5750
5751     RegCloseKey(prodkey);
5752
5753     /* complete install */
5754     r = MsiInstallProductA(msifile, "FULL=1");
5755     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5756     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5757     ok(pf_exists("msitest"), "File not installed\n");
5758
5759     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5760     ok(state == INSTALLSTATE_DEFAULT, "Expected INSTALLSTATE_DEFAULT, got %d\n", state);
5761
5762     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5763     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5764
5765     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5766     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5767
5768     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5769                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5770     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5771     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5772
5773     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5774     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5775
5776     CHECK_REG_STR(prodkey, "DisplayName", "MSITEST");
5777     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
5778     CHECK_REG_STR(prodkey, "InstallDate", date);
5779     CHECK_REG_STR(prodkey, "InstallSource", temp);
5780     CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5781     CHECK_REG_STR(prodkey, "Publisher", "Wine");
5782     CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5783     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
5784     CHECK_REG_STR(prodkey, "Comments", NULL);
5785     CHECK_REG_STR(prodkey, "Contact", NULL);
5786     CHECK_REG_STR(prodkey, "HelpLink", NULL);
5787     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
5788     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
5789     CHECK_REG_STR(prodkey, "Readme", NULL);
5790     CHECK_REG_STR(prodkey, "Size", NULL);
5791     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
5792     CHECK_REG_STR(prodkey, "URLUpdateInfo", NULL);
5793     CHECK_REG_DWORD(prodkey, "Language", 1033);
5794     CHECK_REG_DWORD(prodkey, "Version", 0x1010001);
5795     CHECK_REG_DWORD(prodkey, "VersionMajor", 1);
5796     CHECK_REG_DWORD(prodkey, "VersionMinor", 1);
5797     CHECK_REG_DWORD(prodkey, "WindowsInstaller", 1);
5798     todo_wine
5799     {
5800         CHECK_REG_DWORD2(prodkey, "EstimatedSize", 12, -20);
5801     }
5802
5803     RegCloseKey(prodkey);
5804
5805     /* UnpublishFeatures, both features removed */
5806     r = MsiInstallProductA(msifile, "UNPUBLISH_FEATURES=1 REMOVE=feature,montecristo");
5807     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5808     ok(!pf_exists("msitest\\maximus"), "File not deleted\n");
5809     ok(!pf_exists("msitest"), "Directory not deleted\n");
5810
5811     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5812     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5813
5814     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5815     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5816
5817     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5818     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5819
5820     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5821                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5822     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5823     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5824
5825     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5826     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5827
5828     /* complete install */
5829     r = MsiInstallProductA(msifile, "FULL=1");
5830     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5831     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5832     ok(pf_exists("msitest"), "File not installed\n");
5833
5834     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5835     ok(state == INSTALLSTATE_DEFAULT, "Expected INSTALLSTATE_DEFAULT, got %d\n", state);
5836
5837     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5838     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5839
5840     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5841     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5842
5843     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5844                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5845     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5846     ok(state == INSTALLSTATE_LOCAL, "Expected INSTALLSTATE_LOCAL, got %d\n", state);
5847
5848     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5849     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
5850
5851     CHECK_REG_STR(prodkey, "DisplayName", "MSITEST");
5852     CHECK_REG_STR(prodkey, "DisplayVersion", "1.1.1");
5853     CHECK_REG_STR(prodkey, "InstallDate", date);
5854     CHECK_REG_STR(prodkey, "InstallSource", temp);
5855     CHECK_REG_ISTR(prodkey, "ModifyPath", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5856     CHECK_REG_STR(prodkey, "Publisher", "Wine");
5857     CHECK_REG_STR(prodkey, "UninstallString", "MsiExec.exe /I{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5858     CHECK_REG_STR(prodkey, "AuthorizedCDFPrefix", NULL);
5859     CHECK_REG_STR(prodkey, "Comments", NULL);
5860     CHECK_REG_STR(prodkey, "Contact", NULL);
5861     CHECK_REG_STR(prodkey, "HelpLink", NULL);
5862     CHECK_REG_STR(prodkey, "HelpTelephone", NULL);
5863     CHECK_REG_STR(prodkey, "InstallLocation", NULL);
5864     CHECK_REG_STR(prodkey, "Readme", NULL);
5865     CHECK_REG_STR(prodkey, "Size", NULL);
5866     CHECK_REG_STR(prodkey, "URLInfoAbout", NULL);
5867     CHECK_REG_STR(prodkey, "URLUpdateInfo", NULL);
5868     CHECK_REG_DWORD(prodkey, "Language", 1033);
5869     CHECK_REG_DWORD(prodkey, "Version", 0x1010001);
5870     CHECK_REG_DWORD(prodkey, "VersionMajor", 1);
5871     CHECK_REG_DWORD(prodkey, "VersionMinor", 1);
5872     CHECK_REG_DWORD(prodkey, "WindowsInstaller", 1);
5873     todo_wine
5874     {
5875         CHECK_REG_DWORD2(prodkey, "EstimatedSize", 12, -12);
5876     }
5877
5878     RegCloseKey(prodkey);
5879
5880     /* complete uninstall */
5881     r = MsiInstallProductA(msifile, "FULL=1 REMOVE=ALL");
5882     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
5883     ok(!pf_exists("msitest\\maximus"), "File not deleted\n");
5884     ok(!pf_exists("msitest"), "Directory not deleted\n");
5885
5886     state = MsiQueryProductState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}");
5887     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5888
5889     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "feature");
5890     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5891
5892     state = MsiQueryFeatureState("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}", "montecristo");
5893     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5894
5895     r = pMsiQueryComponentStateA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5896                                 "{DF2CBABC-3BCC-47E5-A998-448D1C0C895B}", &state);
5897     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5898     ok(state == INSTALLSTATE_UNKNOWN, "Expected INSTALLSTATE_UNKNOWN, got %d\n", state);
5899
5900     res = RegOpenKeyA(uninstall, prodcode, &prodkey);
5901     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
5902
5903     /* make sure 'Program Files\msitest' is removed */
5904     delete_pfmsitest_files();
5905
5906     RegCloseKey(uninstall);
5907     DeleteFile(msifile);
5908     DeleteFile("msitest\\maximus");
5909     RemoveDirectory("msitest");
5910 }
5911
5912 static void test_publishsourcelist(void)
5913 {
5914     UINT r;
5915     DWORD size;
5916     CHAR value[MAX_PATH];
5917     CHAR path[MAX_PATH];
5918     CHAR prodcode[] = "{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}";
5919
5920     if (!pMsiSourceListEnumSourcesA || !pMsiSourceListGetInfoA)
5921     {
5922         win_skip("MsiSourceListEnumSourcesA and/or MsiSourceListGetInfoA are not available\n");
5923         return;
5924     }
5925
5926     CreateDirectoryA("msitest", NULL);
5927     create_file("msitest\\maximus", 500);
5928
5929     create_database(msifile, pp_tables, sizeof(pp_tables) / sizeof(msi_table));
5930
5931     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
5932
5933     r = MsiInstallProductA(msifile, NULL);
5934     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5935     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5936     ok(pf_exists("msitest"), "File not installed\n");
5937
5938     /* nothing published */
5939     size = MAX_PATH;
5940     lstrcpyA(value, "aaa");
5941     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5942                                MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, value, &size);
5943     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5944     ok(size == MAX_PATH, "Expected %d, got %d\n", MAX_PATH, size);
5945     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
5946
5947     size = MAX_PATH;
5948     lstrcpyA(value, "aaa");
5949     r = pMsiSourceListEnumSourcesA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5950                                    MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
5951     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5952     ok(size == MAX_PATH, "Expected %d, got %d\n", MAX_PATH, size);
5953     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
5954
5955     r = MsiInstallProductA(msifile, "REGISTER_PRODUCT=1");
5956     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5957     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5958     ok(pf_exists("msitest"), "File not installed\n");
5959
5960     /* after RegisterProduct */
5961     size = MAX_PATH;
5962     lstrcpyA(value, "aaa");
5963     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5964                                MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, value, &size);
5965     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5966     ok(size == MAX_PATH, "Expected %d, got %d\n", MAX_PATH, size);
5967     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
5968
5969     size = MAX_PATH;
5970     lstrcpyA(value, "aaa");
5971     r = pMsiSourceListEnumSourcesA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5972                                    MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
5973     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5974     ok(size == MAX_PATH, "Expected %d, got %d\n", MAX_PATH, size);
5975     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
5976
5977     r = MsiInstallProductA(msifile, "PROCESS_COMPONENTS=1");
5978     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
5979     ok(pf_exists("msitest\\maximus"), "File not installed\n");
5980     ok(pf_exists("msitest"), "File not installed\n");
5981
5982     /* after ProcessComponents */
5983     size = MAX_PATH;
5984     lstrcpyA(value, "aaa");
5985     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5986                                MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, value, &size);
5987     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5988     ok(size == MAX_PATH, "Expected %d, got %d\n", MAX_PATH, size);
5989     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
5990
5991     size = MAX_PATH;
5992     lstrcpyA(value, "aaa");
5993     r = pMsiSourceListEnumSourcesA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
5994                                    MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
5995     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
5996     ok(size == MAX_PATH, "Expected %d, got %d\n", MAX_PATH, size);
5997     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
5998
5999     r = MsiInstallProductA(msifile, "PUBLISH_FEATURES=1");
6000     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6001     ok(pf_exists("msitest\\maximus"), "File not installed\n");
6002     ok(pf_exists("msitest"), "File not installed\n");
6003
6004     /* after PublishFeatures */
6005     size = MAX_PATH;
6006     lstrcpyA(value, "aaa");
6007     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6008                                MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, value, &size);
6009     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
6010     ok(size == MAX_PATH, "Expected %d, got %d\n", MAX_PATH, size);
6011     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
6012
6013     size = MAX_PATH;
6014     lstrcpyA(value, "aaa");
6015     r = pMsiSourceListEnumSourcesA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6016                                    MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
6017     ok(r == ERROR_UNKNOWN_PRODUCT, "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
6018     ok(size == MAX_PATH, "Expected %d, got %d\n", MAX_PATH, size);
6019     ok(!lstrcmpA(value, "aaa"), "Expected \"aaa\", got \"%s\"\n", value);
6020
6021     r = MsiInstallProductA(msifile, "PUBLISH_PRODUCT=1");
6022     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6023     ok(pf_exists("msitest\\maximus"), "File not installed\n");
6024     ok(pf_exists("msitest"), "File not installed\n");
6025
6026     /* after PublishProduct */
6027     size = MAX_PATH;
6028     lstrcpyA(value, "aaa");
6029     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6030                                MSICODE_PRODUCT, INSTALLPROPERTY_PACKAGENAME, value, &size);
6031     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
6032     ok(!lstrcmpA(value, "msitest.msi"), "Expected 'msitest.msi', got %s\n", value);
6033     ok(size == 11, "Expected 11, got %d\n", size);
6034
6035     size = MAX_PATH;
6036     lstrcpyA(value, "aaa");
6037     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6038                                MSICODE_PRODUCT, INSTALLPROPERTY_MEDIAPACKAGEPATH, value, &size);
6039     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
6040     ok(!lstrcmpA(value, ""), "Expected \"\", got \"%s\"\n", value);
6041     ok(size == 0, "Expected 0, got %d\n", size);
6042
6043     size = MAX_PATH;
6044     lstrcpyA(value, "aaa");
6045     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6046                                MSICODE_PRODUCT, INSTALLPROPERTY_DISKPROMPT, value, &size);
6047     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
6048     ok(!lstrcmpA(value, ""), "Expected \"\", got \"%s\"\n", value);
6049     ok(size == 0, "Expected 0, got %d\n", size);
6050
6051     lstrcpyA(path, CURR_DIR);
6052     lstrcatA(path, "\\");
6053
6054     size = MAX_PATH;
6055     lstrcpyA(value, "aaa");
6056     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6057                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDSOURCE, value, &size);
6058     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
6059     ok(!lstrcmpA(value, path), "Expected \"%s\", got \"%s\"\n", path, value);
6060     ok(size == lstrlenA(path), "Expected %d, got %d\n", lstrlenA(path), size);
6061
6062     size = MAX_PATH;
6063     lstrcpyA(value, "aaa");
6064     r = pMsiSourceListGetInfoA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6065                                MSICODE_PRODUCT, INSTALLPROPERTY_LASTUSEDTYPE, value, &size);
6066     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
6067     ok(!lstrcmpA(value, "n"), "Expected \"n\", got \"%s\"\n", value);
6068     ok(size == 1, "Expected 1, got %d\n", size);
6069
6070     size = MAX_PATH;
6071     lstrcpyA(value, "aaa");
6072     r = pMsiSourceListEnumSourcesA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6073                                    MSICODE_PRODUCT | MSISOURCETYPE_URL, 0, value, &size);
6074     ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
6075     ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
6076     ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
6077
6078     size = MAX_PATH;
6079     lstrcpyA(value, "aaa");
6080     r = pMsiSourceListEnumSourcesA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6081                                    MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 0, value, &size);
6082     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
6083     ok(!lstrcmpA(value, path), "Expected \"%s\", got \"%s\"\n", path, value);
6084     ok(size == lstrlenA(path), "Expected %d, got %d\n", lstrlenA(path), size);
6085
6086     size = MAX_PATH;
6087     lstrcpyA(value, "aaa");
6088     r = pMsiSourceListEnumSourcesA(prodcode, NULL, MSIINSTALLCONTEXT_USERUNMANAGED,
6089                                    MSICODE_PRODUCT | MSISOURCETYPE_NETWORK, 1, value, &size);
6090     ok(r == ERROR_NO_MORE_ITEMS, "Expected ERROR_NO_MORE_ITEMS, got %d\n", r);
6091     ok(!lstrcmpA(value, "aaa"), "Expected value to be unchanged, got %s\n", value);
6092     ok(size == MAX_PATH, "Expected MAX_PATH, got %d\n", size);
6093
6094     /* complete uninstall */
6095     r = MsiInstallProductA(msifile, "FULL=1 REMOVE=ALL");
6096     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
6097     ok(!pf_exists("msitest\\maximus"), "File not deleted\n");
6098     ok(!pf_exists("msitest"), "Directory not deleted\n");
6099
6100     /* make sure 'Program Files\msitest' is removed */
6101     delete_pfmsitest_files();
6102
6103     DeleteFile(msifile);
6104     DeleteFile("msitest\\maximus");
6105     RemoveDirectory("msitest");
6106 }
6107
6108 static UINT run_query(MSIHANDLE hdb, MSIHANDLE hrec, const char *query)
6109 {
6110     MSIHANDLE hview = 0;
6111     UINT r;
6112
6113     r = MsiDatabaseOpenView(hdb, query, &hview);
6114     if(r != ERROR_SUCCESS)
6115         return r;
6116
6117     r = MsiViewExecute(hview, hrec);
6118     if(r == ERROR_SUCCESS)
6119         r = MsiViewClose(hview);
6120     MsiCloseHandle(hview);
6121     return r;
6122 }
6123
6124 static void set_transform_summary_info(void)
6125 {
6126     UINT r;
6127     MSIHANDLE suminfo = 0;
6128
6129     /* build summary info */
6130     r = MsiGetSummaryInformation(0, mstfile, 3, &suminfo);
6131     ok(r == ERROR_SUCCESS , "Failed to open summaryinfo\n");
6132
6133     r = MsiSummaryInfoSetProperty(suminfo, PID_TITLE, VT_LPSTR, 0, NULL, "MSITEST");
6134     ok(r == ERROR_SUCCESS, "Failed to set summary info\n");
6135
6136     r = MsiSummaryInfoSetProperty(suminfo, PID_REVNUMBER, VT_LPSTR, 0, NULL,
6137                         "{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}1.1.1;"
6138                         "{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}1.1.1;"
6139                         "{4C0EAA15-0264-4E5A-8758-609EF142B92D}");
6140     ok(r == ERROR_SUCCESS , "Failed to set summary info\n");
6141
6142     r = MsiSummaryInfoSetProperty(suminfo, PID_PAGECOUNT, VT_I4, 100, NULL, NULL);
6143     ok(r == ERROR_SUCCESS, "Failed to set summary info\n");
6144
6145     r = MsiSummaryInfoPersist(suminfo);
6146     ok(r == ERROR_SUCCESS , "Failed to make summary info persist\n");
6147
6148     r = MsiCloseHandle(suminfo);
6149     ok(r == ERROR_SUCCESS , "Failed to close suminfo\n");
6150 }
6151
6152 static void generate_transform(void)
6153 {
6154     MSIHANDLE hdb1, hdb2;
6155     LPCSTR query;
6156     UINT r;
6157
6158     /* start with two identical databases */
6159     CopyFile(msifile, msifile2, FALSE);
6160
6161     r = MsiOpenDatabase(msifile2, MSIDBOPEN_TRANSACT, &hdb1);
6162     ok(r == ERROR_SUCCESS , "Failed to create database\n");
6163
6164     r = MsiDatabaseCommit(hdb1);
6165     ok(r == ERROR_SUCCESS , "Failed to commit database\n");
6166
6167     r = MsiOpenDatabase(msifile, MSIDBOPEN_READONLY, &hdb2);
6168     ok(r == ERROR_SUCCESS , "Failed to create database\n");
6169
6170     query = "INSERT INTO `Property` ( `Property`, `Value` ) VALUES ( 'prop', 'val' )";
6171     r = run_query(hdb1, 0, query);
6172     ok(r == ERROR_SUCCESS, "failed to add property\n");
6173
6174     /* database needs to be committed */
6175     MsiDatabaseCommit(hdb1);
6176
6177     r = MsiDatabaseGenerateTransform(hdb1, hdb2, mstfile, 0, 0);
6178     ok(r == ERROR_SUCCESS, "return code %d, should be ERROR_SUCCESS\n", r);
6179
6180 #if 0  /* not implemented in wine yet */
6181     r = MsiCreateTransformSummaryInfo(hdb2, hdb2, mstfile, 0, 0);
6182     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
6183 #endif
6184
6185     MsiCloseHandle(hdb1);
6186     MsiCloseHandle(hdb2);
6187 }
6188
6189 /* data for generating a transform */
6190
6191 /* tables transform names - encoded as they would be in an msi database file */
6192 static const WCHAR name1[] = { 0x4840, 0x3f3f, 0x4577, 0x446c, 0x3b6a, 0x45e4, 0x4824, 0 }; /* _StringData */
6193 static const WCHAR name2[] = { 0x4840, 0x3f3f, 0x4577, 0x446c, 0x3e6a, 0x44b2, 0x482f, 0 }; /* _StringPool */
6194 static const WCHAR name3[] = { 0x4840, 0x4559, 0x44f2, 0x4568, 0x4737, 0 }; /* Property */
6195
6196 /* data in each table */
6197 static const char data1[] = /* _StringData */
6198     "propval";  /* all the strings squashed together */
6199
6200 static const WCHAR data2[] = { /* _StringPool */
6201 /*  len, refs */
6202     0,   0,    /* string 0 ''     */
6203     4,   1,    /* string 1 'prop' */
6204     3,   1,    /* string 2 'val'  */
6205 };
6206
6207 static const WCHAR data3[] = { /* Property */
6208     0x0201, 0x0001, 0x0002,
6209 };
6210
6211 static const struct {
6212     LPCWSTR name;
6213     const void *data;
6214     DWORD size;
6215 } table_transform_data[] =
6216 {
6217     { name1, data1, sizeof data1 - 1 },
6218     { name2, data2, sizeof data2 },
6219     { name3, data3, sizeof data3 },
6220 };
6221
6222 #define NUM_TRANSFORM_TABLES (sizeof table_transform_data/sizeof table_transform_data[0])
6223
6224 static void generate_transform_manual(void)
6225 {
6226     IStorage *stg = NULL;
6227     IStream *stm;
6228     WCHAR name[0x20];
6229     HRESULT r;
6230     DWORD i, count;
6231     const DWORD mode = STGM_CREATE|STGM_READWRITE|STGM_DIRECT|STGM_SHARE_EXCLUSIVE;
6232
6233     const CLSID CLSID_MsiTransform = { 0xc1082,0,0,{0xc0,0,0,0,0,0,0,0x46}};
6234
6235     MultiByteToWideChar(CP_ACP, 0, mstfile, -1, name, 0x20);
6236
6237     r = StgCreateDocfile(name, mode, 0, &stg);
6238     ok(r == S_OK, "failed to create storage\n");
6239     if (!stg)
6240         return;
6241
6242     r = IStorage_SetClass(stg, &CLSID_MsiTransform);
6243     ok(r == S_OK, "failed to set storage type\n");
6244
6245     for (i=0; i<NUM_TRANSFORM_TABLES; i++)
6246     {
6247         r = IStorage_CreateStream(stg, table_transform_data[i].name,
6248                             STGM_WRITE | STGM_SHARE_EXCLUSIVE, 0, 0, &stm);
6249         if (FAILED(r))
6250         {
6251             ok(0, "failed to create stream %08x\n", r);
6252             continue;
6253         }
6254
6255         r = IStream_Write(stm, table_transform_data[i].data,
6256                           table_transform_data[i].size, &count);
6257         if (FAILED(r) || count != table_transform_data[i].size)
6258             ok(0, "failed to write stream\n");
6259         IStream_Release(stm);
6260     }
6261
6262     IStorage_Release(stg);
6263
6264     set_transform_summary_info();
6265 }
6266
6267 static void test_transformprop(void)
6268 {
6269     UINT r;
6270
6271     CreateDirectoryA("msitest", NULL);
6272     create_file("msitest\\augustus", 500);
6273
6274     create_database(msifile, tp_tables, sizeof(tp_tables) / sizeof(msi_table));
6275
6276     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6277
6278     r = MsiInstallProductA(msifile, NULL);
6279     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6280     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
6281     ok(!delete_pf("msitest", FALSE), "File installed\n");
6282
6283     if (0)
6284         generate_transform();
6285     else
6286         generate_transform_manual();
6287
6288     r = MsiInstallProductA(msifile, "TRANSFORMS=winetest.mst");
6289     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6290     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
6291     ok(delete_pf("msitest", FALSE), "File not installed\n");
6292
6293     /* Delete the files in the temp (current) folder */
6294     DeleteFile(msifile);
6295     DeleteFile(msifile2);
6296     DeleteFile(mstfile);
6297     DeleteFile("msitest\\augustus");
6298     RemoveDirectory("msitest");
6299 }
6300
6301 static void test_currentworkingdir(void)
6302 {
6303     UINT r;
6304     CHAR drive[MAX_PATH], path[MAX_PATH];
6305     LPSTR ptr;
6306
6307     CreateDirectoryA("msitest", NULL);
6308     create_file("msitest\\augustus", 500);
6309
6310     create_database(msifile, cwd_tables, sizeof(cwd_tables) / sizeof(msi_table));
6311
6312     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6313
6314     CreateDirectoryA("diffdir", NULL);
6315     SetCurrentDirectoryA("diffdir");
6316
6317     sprintf(path, "..\\%s", msifile);
6318     r = MsiInstallProductA(path, NULL);
6319     todo_wine
6320     {
6321         ok(r == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %u\n", r);
6322         ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
6323         ok(!delete_pf("msitest", FALSE), "File installed\n");
6324     }
6325
6326     sprintf(path, "%s\\%s", CURR_DIR, msifile);
6327     r = MsiInstallProductA(path, NULL);
6328     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6329     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
6330     ok(delete_pf("msitest", FALSE), "File not installed\n");
6331
6332     lstrcpyA(drive, CURR_DIR);
6333     drive[2] = '\\';
6334     drive[3] = '\0';
6335     SetCurrentDirectoryA(drive);
6336
6337     lstrcpy(path, CURR_DIR);
6338     if (path[lstrlenA(path) - 1] != '\\')
6339         lstrcatA(path, "\\");
6340     lstrcatA(path, msifile);
6341     ptr = strchr(path, ':');
6342     ptr +=2;
6343
6344     r = MsiInstallProductA(ptr, NULL);
6345     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6346     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
6347     ok(delete_pf("msitest", FALSE), "File not installed\n");
6348
6349     SetCurrentDirectoryA(CURR_DIR);
6350
6351     DeleteFile(msifile);
6352     DeleteFile("msitest\\augustus");
6353     RemoveDirectory("msitest");
6354     RemoveDirectory("diffdir");
6355 }
6356
6357 static void set_admin_summary_info(const CHAR *name)
6358 {
6359     MSIHANDLE db, summary;
6360     UINT r;
6361
6362     r = MsiOpenDatabaseA(name, MSIDBOPEN_DIRECT, &db);
6363     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6364
6365     r = MsiGetSummaryInformationA(db, NULL, 1, &summary);
6366     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6367
6368     r = MsiSummaryInfoSetPropertyA(summary, PID_WORDCOUNT, VT_I4, 5, NULL, NULL);
6369     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6370
6371     /* write the summary changes back to the stream */
6372     r = MsiSummaryInfoPersist(summary);
6373     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6374
6375     MsiCloseHandle(summary);
6376
6377     r = MsiDatabaseCommit(db);
6378     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6379
6380     MsiCloseHandle(db);
6381 }
6382
6383 static void test_admin(void)
6384 {
6385     UINT r;
6386
6387     CreateDirectoryA("msitest", NULL);
6388     create_file("msitest\\augustus", 500);
6389
6390     create_database(msifile, adm_tables, sizeof(adm_tables) / sizeof(msi_table));
6391     set_admin_summary_info(msifile);
6392
6393     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6394
6395     r = MsiInstallProductA(msifile, NULL);
6396     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6397     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
6398     ok(!delete_pf("msitest", FALSE), "File installed\n");
6399     ok(!DeleteFile("c:\\msitest\\augustus"), "File installed\n");
6400     ok(!RemoveDirectory("c:\\msitest"), "File installed\n");
6401
6402     r = MsiInstallProductA(msifile, "ACTION=ADMIN");
6403     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6404     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
6405     ok(!delete_pf("msitest", FALSE), "File installed\n");
6406     todo_wine
6407     {
6408         ok(DeleteFile("c:\\msitest\\augustus"), "File not installed\n");
6409         ok(RemoveDirectory("c:\\msitest"), "File not installed\n");
6410     }
6411
6412     DeleteFile(msifile);
6413     DeleteFile("msitest\\augustus");
6414     RemoveDirectory("msitest");
6415 }
6416
6417 static void set_admin_property_stream(LPCSTR file)
6418 {
6419     IStorage *stg;
6420     IStream *stm;
6421     WCHAR fileW[MAX_PATH];
6422     HRESULT hr;
6423     DWORD count;
6424     const DWORD mode = STGM_DIRECT | STGM_READWRITE | STGM_SHARE_EXCLUSIVE;
6425
6426     /* AdminProperties */
6427     static const WCHAR stmname[] = {0x41ca,0x4330,0x3e71,0x44b5,0x4233,0x45f5,0x422c,0x4836,0};
6428     static const WCHAR data[] = {'M','Y','P','R','O','P','=','2','7','1','8',' ',
6429         'M','y','P','r','o','p','=','4','2',0};
6430
6431     MultiByteToWideChar(CP_ACP, 0, file, -1, fileW, MAX_PATH);
6432
6433     hr = StgOpenStorage(fileW, NULL, mode, NULL, 0, &stg);
6434     ok(hr == S_OK, "Expected S_OK, got %d\n", hr);
6435     if (!stg)
6436         return;
6437
6438     hr = IStorage_CreateStream(stg, stmname, STGM_WRITE | STGM_SHARE_EXCLUSIVE, 0, 0, &stm);
6439     ok(hr == S_OK, "Expected S_OK, got %d\n", hr);
6440
6441     hr = IStream_Write(stm, data, sizeof(data), &count);
6442     ok(hr == S_OK, "Expected S_OK, got %d\n", hr);
6443
6444     IStream_Release(stm);
6445     IStorage_Release(stg);
6446 }
6447
6448 static void test_adminprops(void)
6449 {
6450     UINT r;
6451
6452     CreateDirectoryA("msitest", NULL);
6453     create_file("msitest\\augustus", 500);
6454
6455     create_database(msifile, amp_tables, sizeof(amp_tables) / sizeof(msi_table));
6456     set_admin_summary_info(msifile);
6457     set_admin_property_stream(msifile);
6458
6459     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6460
6461     r = MsiInstallProductA(msifile, NULL);
6462     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6463     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
6464     ok(delete_pf("msitest", FALSE), "File installed\n");
6465
6466     DeleteFile(msifile);
6467     DeleteFile("msitest\\augustus");
6468     RemoveDirectory("msitest");
6469 }
6470
6471 static void create_pf_data(LPCSTR file, LPCSTR data, BOOL is_file)
6472 {
6473     CHAR path[MAX_PATH];
6474
6475     lstrcpyA(path, PROG_FILES_DIR);
6476     lstrcatA(path, "\\");
6477     lstrcatA(path, file);
6478
6479     if (is_file)
6480         create_file_data(path, data, 500);
6481     else
6482         CreateDirectoryA(path, NULL);
6483 }
6484
6485 #define create_pf(file, is_file) create_pf_data(file, file, is_file)
6486
6487 static void test_removefiles(void)
6488 {
6489     UINT r;
6490
6491     CreateDirectoryA("msitest", NULL);
6492     create_file("msitest\\hydrogen", 500);
6493     create_file("msitest\\helium", 500);
6494     create_file("msitest\\lithium", 500);
6495
6496     create_database(msifile, rem_tables, sizeof(rem_tables) / sizeof(msi_table));
6497
6498     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
6499
6500     r = MsiInstallProductA(msifile, NULL);
6501     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6502     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
6503     ok(!pf_exists("msitest\\helium"), "File installed\n");
6504     ok(pf_exists("msitest\\lithium"), "File not installed\n");
6505     ok(pf_exists("msitest"), "File not installed\n");
6506
6507     r = MsiInstallProductA(msifile, "REMOVE=ALL");
6508     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6509     ok(!pf_exists("msitest\\hydrogen"), "File not deleted\n");
6510     ok(!pf_exists("msitest\\helium"), "File not deleted\n");
6511     ok(delete_pf("msitest\\lithium", TRUE), "File deleted\n");
6512     ok(delete_pf("msitest", FALSE), "File deleted\n");
6513
6514     create_pf("msitest", FALSE);
6515     create_pf("msitest\\hydrogen", TRUE);
6516     create_pf("msitest\\helium", TRUE);
6517     create_pf("msitest\\lithium", TRUE);
6518
6519     r = MsiInstallProductA(msifile, NULL);
6520     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6521     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
6522     ok(pf_exists("msitest\\helium"), "File not installed\n");
6523     ok(pf_exists("msitest\\lithium"), "File not installed\n");
6524     ok(pf_exists("msitest"), "File not installed\n");
6525
6526     r = MsiInstallProductA(msifile, "REMOVE=ALL");
6527     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6528     ok(!pf_exists("msitest\\hydrogen"), "File not deleted\n");
6529     ok(delete_pf("msitest\\helium", TRUE), "File deleted\n");
6530     ok(delete_pf("msitest\\lithium", TRUE), "File deleted\n");
6531     ok(delete_pf("msitest", FALSE), "File deleted\n");
6532
6533     create_pf("msitest", FALSE);
6534     create_pf("msitest\\furlong", TRUE);
6535     create_pf("msitest\\firkin", TRUE);
6536     create_pf("msitest\\fortnight", TRUE);
6537     create_pf("msitest\\becquerel", TRUE);
6538     create_pf("msitest\\dioptre", TRUE);
6539     create_pf("msitest\\attoparsec", TRUE);
6540     create_pf("msitest\\storeys", TRUE);
6541     create_pf("msitest\\block", TRUE);
6542     create_pf("msitest\\siriometer", TRUE);
6543     create_pf("msitest\\cabout", FALSE);
6544     create_pf("msitest\\cabout\\blocker", TRUE);
6545
6546     r = MsiInstallProductA(msifile, NULL);
6547     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6548     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
6549     ok(!pf_exists("msitest\\helium"), "File installed\n");
6550     ok(pf_exists("msitest\\lithium"), "File not installed\n");
6551     ok(!pf_exists("msitest\\furlong"), "File not deleted\n");
6552     ok(!pf_exists("msitest\\firkin"), "File not deleted\n");
6553     ok(!pf_exists("msitest\\fortnight"), "File not deleted\n");
6554     ok(pf_exists("msitest\\becquerel"), "File not installed\n");
6555     ok(pf_exists("msitest\\dioptre"), "File not installed\n");
6556     ok(pf_exists("msitest\\attoparsec"), "File not installed\n");
6557     ok(!pf_exists("msitest\\storeys"), "File not deleted\n");
6558     ok(!pf_exists("msitest\\block"), "File not deleted\n");
6559     ok(!pf_exists("msitest\\siriometer"), "File not deleted\n");
6560     ok(pf_exists("msitest\\cabout"), "Directory removed\n");
6561     ok(pf_exists("msitest"), "File not installed\n");
6562
6563     create_pf("msitest\\furlong", TRUE);
6564     create_pf("msitest\\firkin", TRUE);
6565     create_pf("msitest\\fortnight", TRUE);
6566     create_pf("msitest\\storeys", TRUE);
6567     create_pf("msitest\\block", TRUE);
6568     create_pf("msitest\\siriometer", TRUE);
6569
6570     r = MsiInstallProductA(msifile, "REMOVE=ALL");
6571     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6572     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not deleted\n");
6573     ok(!delete_pf("msitest\\helium", TRUE), "File not deleted\n");
6574     ok(delete_pf("msitest\\lithium", TRUE), "File deleted\n");
6575     ok(delete_pf("msitest\\furlong", TRUE), "File deleted\n");
6576     ok(delete_pf("msitest\\firkin", TRUE), "File deleted\n");
6577     ok(delete_pf("msitest\\fortnight", TRUE), "File deleted\n");
6578     ok(!delete_pf("msitest\\becquerel", TRUE), "File not deleted\n");
6579     ok(!delete_pf("msitest\\dioptre", TRUE), "File not deleted\n");
6580     ok(delete_pf("msitest\\attoparsec", TRUE), "File deleted\n");
6581     ok(!delete_pf("msitest\\storeys", TRUE), "File not deleted\n");
6582     ok(!delete_pf("msitest\\block", TRUE), "File not deleted\n");
6583     ok(delete_pf("msitest\\siriometer", TRUE), "File deleted\n");
6584     ok(pf_exists("msitest\\cabout"), "Directory deleted\n");
6585     ok(pf_exists("msitest"), "Directory deleted\n");
6586
6587     r = MsiInstallProductA(msifile, NULL);
6588     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6589     ok(delete_pf("msitest\\hydrogen", TRUE), "File not installed\n");
6590     ok(!delete_pf("msitest\\helium", TRUE), "File installed\n");
6591     ok(delete_pf("msitest\\lithium", TRUE), "File not installed\n");
6592     ok(pf_exists("msitest\\cabout"), "Directory deleted\n");
6593     ok(pf_exists("msitest"), "Directory deleted\n");
6594
6595     delete_pf("msitest\\cabout\\blocker", TRUE);
6596
6597     r = MsiInstallProductA(msifile, "REMOVE=ALL");
6598     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6599     ok(!delete_pf("msitest\\cabout", FALSE), "Directory not deleted\n");
6600     ok(delete_pf("msitest", FALSE), "Directory deleted\n");
6601
6602     DeleteFile(msifile);
6603     DeleteFile("msitest\\hydrogen");
6604     DeleteFile("msitest\\helium");
6605     DeleteFile("msitest\\lithium");
6606     RemoveDirectory("msitest");
6607 }
6608
6609 static void test_movefiles(void)
6610 {
6611     UINT r;
6612     char props[MAX_PATH];
6613
6614     CreateDirectoryA("msitest", NULL);
6615     create_file("msitest\\augustus", 100);
6616     create_file("cameroon", 100);
6617     create_file("djibouti", 100);
6618     create_file("egypt", 100);
6619     create_file("finland", 100);
6620     create_file("gambai", 100);
6621     create_file("honduras", 100);
6622     create_file("msitest\\india", 100);
6623     create_file("japan", 100);
6624     create_file("kenya", 100);
6625     CreateDirectoryA("latvia", NULL);
6626     create_file("nauru", 100);
6627     create_file("peru", 100);
6628     create_file("apple", 100);
6629     create_file("application", 100);
6630     create_file("ape", 100);
6631     create_file("foo", 100);
6632     create_file("fao", 100);
6633     create_file("fbod", 100);
6634     create_file("budding", 100);
6635     create_file("buddy", 100);
6636     create_file("bud", 100);
6637     create_file("bar", 100);
6638     create_file("bur", 100);
6639     create_file("bird", 100);
6640
6641     create_database(msifile, mov_tables, sizeof(mov_tables) / sizeof(msi_table));
6642
6643     MsiSetInternalUI(INSTALLUILEVEL_FULL, NULL);
6644
6645     /* if the source or dest property is not a full path,
6646      * windows tries to access it as a network resource
6647      */
6648
6649     sprintf(props, "SOURCEFULL=\"%s\\\" DESTFULL=\"%s\\msitest\" "
6650             "FILEPATHBAD=\"%s\\japan\" FILEPATHGOOD=\"%s\\kenya\"",
6651             CURR_DIR, PROG_FILES_DIR, CURR_DIR, CURR_DIR);
6652
6653     r = MsiInstallProductA(msifile, props);
6654     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6655     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
6656     ok(!delete_pf("msitest\\dest", TRUE), "File copied\n");
6657     ok(delete_pf("msitest\\canada", TRUE), "File not copied\n");
6658     ok(delete_pf("msitest\\dominica", TRUE), "File not moved\n");
6659     ok(!delete_pf("msitest\\elsalvador", TRUE), "File moved\n");
6660     ok(!delete_pf("msitest\\france", TRUE), "File moved\n");
6661     ok(!delete_pf("msitest\\georgia", TRUE), "File moved\n");
6662     ok(delete_pf("msitest\\hungary", TRUE), "File not moved\n");
6663     ok(!delete_pf("msitest\\indonesia", TRUE), "File moved\n");
6664     ok(!delete_pf("msitest\\jordan", TRUE), "File moved\n");
6665     ok(delete_pf("msitest\\kiribati", TRUE), "File not moved\n");
6666     ok(!delete_pf("msitest\\lebanon", TRUE), "File moved\n");
6667     ok(!delete_pf("msitest\\lebanon", FALSE), "Directory moved\n");
6668     ok(delete_pf("msitest\\poland", TRUE), "File not moved\n");
6669     /* either apple or application will be moved depending on directory order */
6670     if (!delete_pf("msitest\\apple", TRUE))
6671         ok(delete_pf("msitest\\application", TRUE), "File not moved\n");
6672     else
6673         ok(!delete_pf("msitest\\application", TRUE), "File should not exist\n");
6674     ok(delete_pf("msitest\\wildcard", TRUE), "File not moved\n");
6675     ok(!delete_pf("msitest\\ape", TRUE), "File moved\n");
6676     /* either fao or foo will be moved depending on directory order */
6677     if (delete_pf("msitest\\foo", TRUE))
6678         ok(!delete_pf("msitest\\fao", TRUE), "File should not exist\n");
6679     else
6680         ok(delete_pf("msitest\\fao", TRUE), "File not moved\n");
6681     ok(delete_pf("msitest\\single", TRUE), "File not moved\n");
6682     ok(!delete_pf("msitest\\fbod", TRUE), "File moved\n");
6683     ok(delete_pf("msitest\\budding", TRUE), "File not moved\n");
6684     ok(delete_pf("msitest\\buddy", TRUE), "File not moved\n");
6685     ok(!delete_pf("msitest\\bud", TRUE), "File moved\n");
6686     ok(delete_pf("msitest\\bar", TRUE), "File not moved\n");
6687     ok(delete_pf("msitest\\bur", TRUE), "File not moved\n");
6688     ok(!delete_pf("msitest\\bird", TRUE), "File moved\n");
6689     ok(delete_pf("msitest", FALSE), "File not installed\n");
6690     ok(DeleteFileA("cameroon"), "File moved\n");
6691     ok(!DeleteFileA("djibouti"), "File not moved\n");
6692     ok(DeleteFileA("egypt"), "File moved\n");
6693     ok(DeleteFileA("finland"), "File moved\n");
6694     ok(DeleteFileA("gambai"), "File moved\n");
6695     ok(!DeleteFileA("honduras"), "File not moved\n");
6696     ok(DeleteFileA("msitest\\india"), "File moved\n");
6697     ok(DeleteFileA("japan"), "File moved\n");
6698     ok(!DeleteFileA("kenya"), "File not moved\n");
6699     ok(RemoveDirectoryA("latvia"), "Directory moved\n");
6700     ok(!DeleteFileA("nauru"), "File not moved\n");
6701     ok(!DeleteFileA("peru"), "File not moved\n");
6702     ok(!DeleteFileA("apple"), "File not moved\n");
6703     ok(!DeleteFileA("application"), "File not moved\n");
6704     ok(DeleteFileA("ape"), "File moved\n");
6705     ok(!DeleteFileA("foo"), "File not moved\n");
6706     ok(!DeleteFileA("fao"), "File not moved\n");
6707     ok(DeleteFileA("fbod"), "File moved\n");
6708     ok(!DeleteFileA("budding"), "File not moved\n");
6709     ok(!DeleteFileA("buddy"), "File not moved\n");
6710     ok(DeleteFileA("bud"), "File moved\n");
6711     ok(!DeleteFileA("bar"), "File not moved\n");
6712     ok(!DeleteFileA("bur"), "File not moved\n");
6713     ok(DeleteFileA("bird"), "File moved\n");
6714
6715     DeleteFile("msitest\\augustus");
6716     RemoveDirectory("msitest");
6717     DeleteFile(msifile);
6718 }
6719
6720 static void test_missingcab(void)
6721 {
6722     UINT r;
6723
6724     CreateDirectoryA("msitest", NULL);
6725     create_file("msitest\\augustus", 500);
6726     create_file("maximus", 500);
6727
6728     create_database(msifile, mc_tables, sizeof(mc_tables) / sizeof(msi_table));
6729
6730     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6731
6732     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
6733
6734     create_pf("msitest", FALSE);
6735     create_pf_data("msitest\\caesar", "abcdefgh", TRUE);
6736
6737     r = MsiInstallProductA(msifile, NULL);
6738     ok(r == ERROR_SUCCESS ||
6739        broken(r == ERROR_INSTALL_FAILURE), /* win9x */
6740        "Expected ERROR_SUCCESS, got %u\n", r);
6741     if (r == ERROR_SUCCESS)
6742     {
6743       ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
6744       ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
6745     }
6746     ok(delete_pf("msitest\\caesar", TRUE), "File not installed\n");
6747     ok(!delete_pf("msitest\\gaius", TRUE), "File installed\n");
6748     ok(delete_pf("msitest", FALSE), "File not installed\n");
6749
6750     create_pf("msitest", FALSE);
6751     create_pf_data("msitest\\caesar", "abcdefgh", TRUE);
6752     create_pf("msitest\\gaius", TRUE);
6753
6754     r = MsiInstallProductA(msifile, "GAIUS=1");
6755     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
6756     todo_wine
6757     {
6758         ok(!delete_pf("msitest\\maximus", TRUE), "File installed\n");
6759         ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
6760     }
6761     ok(delete_pf("msitest\\caesar", TRUE), "File removed\n");
6762     ok(delete_pf("msitest\\gaius", TRUE), "File removed\n");
6763     ok(delete_pf("msitest", FALSE), "File not installed\n");
6764
6765     DeleteFile("msitest\\augustus");
6766     RemoveDirectory("msitest");
6767     DeleteFile("maximus");
6768     DeleteFile("test1.cab");
6769     DeleteFile(msifile);
6770 }
6771
6772 static void test_duplicatefiles(void)
6773 {
6774     UINT r;
6775
6776     CreateDirectoryA("msitest", NULL);
6777     create_file("msitest\\maximus", 500);
6778     create_database(msifile, df_tables, sizeof(df_tables) / sizeof(msi_table));
6779
6780     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6781
6782     /* fails if the destination folder is not a valid property */
6783
6784     r = MsiInstallProductA(msifile, NULL);
6785     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6786     ok(delete_pf("msitest\\maximus", TRUE), "File not installed\n");
6787     ok(delete_pf("msitest\\augustus", TRUE), "File not duplicated\n");
6788     ok(delete_pf("msitest\\this\\doesnot\\exist\\maximus", TRUE), "File not duplicated\n");
6789     ok(delete_pf("msitest\\this\\doesnot\\exist", FALSE), "File not duplicated\n");
6790     ok(delete_pf("msitest\\this\\doesnot", FALSE), "File not duplicated\n");
6791     ok(delete_pf("msitest\\this", FALSE), "File not duplicated\n");
6792     ok(delete_pf("msitest", FALSE), "File not installed\n");
6793
6794     DeleteFile("msitest\\maximus");
6795     RemoveDirectory("msitest");
6796     DeleteFile(msifile);
6797 }
6798
6799 static void test_writeregistryvalues(void)
6800 {
6801     UINT r;
6802     LONG res;
6803     HKEY hkey;
6804     DWORD type, size;
6805     CHAR path[MAX_PATH];
6806
6807     CreateDirectoryA("msitest", NULL);
6808     create_file("msitest\\augustus", 500);
6809
6810     create_database(msifile, wrv_tables, sizeof(wrv_tables) / sizeof(msi_table));
6811
6812     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6813
6814     r = MsiInstallProductA(msifile, NULL);
6815     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6816     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
6817     ok(delete_pf("msitest", FALSE), "File installed\n");
6818
6819     res = RegOpenKey(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest", &hkey);
6820     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
6821
6822     size = MAX_PATH;
6823     type = REG_MULTI_SZ;
6824     memset(path, 'a', MAX_PATH);
6825     res = RegQueryValueExA(hkey, "Value", NULL, &type, (LPBYTE)path, &size);
6826     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
6827     ok(!memcmp(path, "one\0two\0three\0\0", size), "Wrong multi-sz data\n");
6828     ok(size == 15, "Expected 15, got %d\n", size);
6829     ok(type == REG_MULTI_SZ, "Expected REG_MULTI_SZ, got %d\n", type);
6830
6831     DeleteFile(msifile);
6832     DeleteFile("msitest\\augustus");
6833     RemoveDirectory("msitest");
6834
6835     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine\\msitest");
6836     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "SOFTWARE\\Wine");
6837 }
6838
6839 static void test_sourcefolder(void)
6840 {
6841     UINT r;
6842
6843     CreateDirectoryA("msitest", NULL);
6844     create_file("augustus", 500);
6845
6846     create_database(msifile, sf_tables, sizeof(sf_tables) / sizeof(msi_table));
6847
6848     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6849
6850     r = MsiInstallProductA(msifile, NULL);
6851     ok(r == ERROR_INSTALL_FAILURE,
6852        "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
6853     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
6854     todo_wine
6855     {
6856         ok(!delete_pf("msitest", FALSE), "File installed\n");
6857     }
6858
6859     RemoveDirectoryA("msitest");
6860
6861     r = MsiInstallProductA(msifile, NULL);
6862     ok(r == ERROR_INSTALL_FAILURE,
6863        "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
6864     ok(!delete_pf("msitest\\augustus", TRUE), "File installed\n");
6865     todo_wine
6866     {
6867         ok(!delete_pf("msitest", FALSE), "File installed\n");
6868     }
6869
6870     DeleteFile(msifile);
6871     DeleteFile("augustus");
6872 }
6873
6874 static void test_customaction51(void)
6875 {
6876     UINT r;
6877
6878     CreateDirectoryA("msitest", NULL);
6879     create_file("msitest\\augustus", 500);
6880
6881     create_database(msifile, ca51_tables, sizeof(ca51_tables) / sizeof(msi_table));
6882
6883     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6884
6885     r = MsiInstallProductA(msifile, NULL);
6886     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6887     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
6888     ok(delete_pf("msitest", FALSE), "File installed\n");
6889
6890     DeleteFile(msifile);
6891     DeleteFile("msitest\\augustus");
6892     RemoveDirectory("msitest");
6893 }
6894
6895 static void test_installstate(void)
6896 {
6897     UINT r;
6898
6899     CreateDirectoryA("msitest", NULL);
6900     create_file("msitest\\alpha", 500);
6901     create_file("msitest\\beta", 500);
6902     create_file("msitest\\gamma", 500);
6903     create_file("msitest\\theta", 500);
6904     create_file("msitest\\delta", 500);
6905     create_file("msitest\\epsilon", 500);
6906     create_file("msitest\\zeta", 500);
6907     create_file("msitest\\iota", 500);
6908     create_file("msitest\\eta", 500);
6909     create_file("msitest\\kappa", 500);
6910     create_file("msitest\\lambda", 500);
6911     create_file("msitest\\mu", 500);
6912
6913     create_database(msifile, is_tables, sizeof(is_tables) / sizeof(msi_table));
6914
6915     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
6916
6917     r = MsiInstallProductA(msifile, NULL);
6918     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6919     ok(delete_pf("msitest\\alpha", TRUE), "File not installed\n");
6920     ok(!delete_pf("msitest\\beta", TRUE), "File installed\n");
6921     ok(delete_pf("msitest\\gamma", TRUE), "File not installed\n");
6922     ok(delete_pf("msitest\\theta", TRUE), "File not installed\n");
6923     ok(!delete_pf("msitest\\delta", TRUE), "File installed\n");
6924     ok(!delete_pf("msitest\\epsilon", TRUE), "File installed\n");
6925     ok(!delete_pf("msitest\\zeta", TRUE), "File installed\n");
6926     ok(!delete_pf("msitest\\iota", TRUE), "File installed\n");
6927     ok(!delete_pf("msitest\\eta", TRUE), "File installed\n");
6928     ok(!delete_pf("msitest\\kappa", TRUE), "File installed\n");
6929     ok(!delete_pf("msitest\\lambda", TRUE), "File installed\n");
6930     ok(!delete_pf("msitest\\mu", TRUE), "File installed\n");
6931     ok(delete_pf("msitest", FALSE), "File not installed\n");
6932
6933     r = MsiInstallProductA(msifile, "ADDLOCAL=\"one,two,three,four\"");
6934     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6935     ok(delete_pf("msitest\\alpha", TRUE), "File not installed\n");
6936     ok(!delete_pf("msitest\\beta", TRUE), "File installed\n");
6937     ok(delete_pf("msitest\\gamma", TRUE), "File not installed\n");
6938     ok(delete_pf("msitest\\theta", TRUE), "File not installed\n");
6939     ok(!delete_pf("msitest\\delta", TRUE), "File installed\n");
6940     ok(delete_pf("msitest\\epsilon", TRUE), "File not installed\n");
6941     ok(delete_pf("msitest\\zeta", TRUE), "File not installed\n");
6942     ok(!delete_pf("msitest\\iota", TRUE), "File installed\n");
6943     ok(delete_pf("msitest\\eta", TRUE), "File not installed\n");
6944     ok(!delete_pf("msitest\\kappa", TRUE), "File installed\n");
6945     ok(!delete_pf("msitest\\lambda", TRUE), "File installed\n");
6946     ok(!delete_pf("msitest\\mu", TRUE), "File installed\n");
6947     ok(delete_pf("msitest", FALSE), "File not installed\n");
6948
6949     r = MsiInstallProductA(msifile, "ADDSOURCE=\"one,two,three,four\"");
6950     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6951     ok(delete_pf("msitest\\alpha", TRUE), "File not installed\n");
6952     ok(!delete_pf("msitest\\beta", TRUE), "File installed\n");
6953     ok(!delete_pf("msitest\\gamma", TRUE), "File installed\n");
6954     ok(delete_pf("msitest\\theta", TRUE), "File not installed\n");
6955     ok(!delete_pf("msitest\\delta", TRUE), "File installed\n");
6956     ok(!delete_pf("msitest\\epsilon", TRUE), "File installed\n");
6957     ok(delete_pf("msitest\\zeta", TRUE), "File not installed\n");
6958     ok(!delete_pf("msitest\\iota", TRUE), "File installed\n");
6959     ok(!delete_pf("msitest\\eta", TRUE), "File installed\n");
6960     ok(!delete_pf("msitest\\kappa", TRUE), "File installed\n");
6961     ok(!delete_pf("msitest\\lambda", TRUE), "File installed\n");
6962     ok(!delete_pf("msitest\\mu", TRUE), "File installed\n");
6963     ok(delete_pf("msitest", FALSE), "File not installed\n");
6964
6965     r = MsiInstallProductA(msifile, "REMOVE=\"one,two,three,four\"");
6966     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
6967     ok(!delete_pf("msitest\\alpha", TRUE), "File installed\n");
6968     ok(!delete_pf("msitest\\beta", TRUE), "File installed\n");
6969     ok(!delete_pf("msitest\\gamma", TRUE), "File installed\n");
6970     ok(!delete_pf("msitest\\theta", TRUE), "File installed\n");
6971     ok(!delete_pf("msitest\\delta", TRUE), "File installed\n");
6972     ok(!delete_pf("msitest\\epsilon", TRUE), "File installed\n");
6973     ok(!delete_pf("msitest\\zeta", TRUE), "File installed\n");
6974     ok(!delete_pf("msitest\\iota", TRUE), "File installed\n");
6975     ok(!delete_pf("msitest\\eta", TRUE), "File installed\n");
6976     ok(!delete_pf("msitest\\kappa", TRUE), "File installed\n");
6977     ok(!delete_pf("msitest\\lambda", TRUE), "File installed\n");
6978     ok(!delete_pf("msitest\\mu", TRUE), "File installed\n");
6979     ok(!delete_pf("msitest", FALSE), "File installed\n");
6980
6981     DeleteFile(msifile);
6982     DeleteFile("msitest\\alpha");
6983     DeleteFile("msitest\\beta");
6984     DeleteFile("msitest\\gamma");
6985     DeleteFile("msitest\\theta");
6986     DeleteFile("msitest\\delta");
6987     DeleteFile("msitest\\epsilon");
6988     DeleteFile("msitest\\zeta");
6989     DeleteFile("msitest\\iota");
6990     DeleteFile("msitest\\eta");
6991     DeleteFile("msitest\\kappa");
6992     DeleteFile("msitest\\lambda");
6993     DeleteFile("msitest\\mu");
6994     RemoveDirectory("msitest");
6995 }
6996
6997 struct sourcepathmap
6998 {
6999     BOOL sost; /* shortone\shorttwo */
7000     BOOL solt; /* shortone\longtwo */
7001     BOOL lost; /* longone\shorttwo */
7002     BOOL lolt; /* longone\longtwo */
7003     BOOL soste; /* shortone\shorttwo source exists */
7004     BOOL solte; /* shortone\longtwo source exists */
7005     BOOL loste; /* longone\shorttwo source exists */
7006     BOOL lolte; /* longone\longtwo source exists */
7007     UINT err;
7008     DWORD size;
7009 } spmap[256] =
7010 {
7011     {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7012     {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7013     {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7014     {TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7015     {TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7016     {TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7017     {TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7018     {TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7019     {TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7020     {TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7021     {TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7022     {TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7023     {TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7024     {TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7025     {TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7026     {TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7027     {TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7028     {TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7029     {TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7030     {TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7031     {TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7032     {TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7033     {TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7034     {TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7035     {TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7036     {TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7037     {TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7038     {TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7039     {TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7040     {TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7041     {TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7042     {TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7043     {TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7044     {TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7045     {TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7046     {TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7047     {TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7048     {TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7049     {TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7050     {TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7051     {TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7052     {TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7053     {TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7054     {TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7055     {TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7056     {TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7057     {TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7058     {TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7059     {TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7060     {TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7061     {TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7062     {TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7063     {TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7064     {TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7065     {TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7066     {TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7067     {TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7068     {TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7069     {TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7070     {TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7071     {TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7072     {TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7073     {TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7074     {TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7075     {TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7076     {TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7077     {TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7078     {TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7079     {TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7080     {TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7081     {TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7082     {TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7083     {TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7084     {TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7085     {TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7086     {TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7087     {TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7088     {TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7089     {TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7090     {TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7091     {TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7092     {TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7093     {TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7094     {TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7095     {TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7096     {TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7097     {TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7098     {TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7099     {TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7100     {TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7101     {TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7102     {TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7103     {TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7104     {TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7105     {TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7106     {TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7107     {TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7108     {TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7109     {TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7110     {TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7111     {TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7112     {TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7113     {TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7114     {TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7115     {TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7116     {TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7117     {TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7118     {TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7119     {TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7120     {TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7121     {TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7122     {TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7123     {TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7124     {TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7125     {TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7126     {TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7127     {TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7128     {TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7129     {TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7130     {TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7131     {TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7132     {TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7133     {TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7134     {TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7135     {TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7136     {TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7137     {TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7138     {TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7139     {FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7140     {FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7141     {FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7142     {FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7143     {FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7144     {FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7145     {FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7146     {FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7147     {FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7148     {FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7149     {FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7150     {FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7151     {FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7152     {FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7153     {FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7154     {FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7155     {FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7156     {FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7157     {FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7158     {FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7159     {FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7160     {FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7161     {FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7162     {FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7163     {FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7164     {FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7165     {FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7166     {FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7167     {FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7168     {FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7169     {FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7170     {FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7171     {FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7172     {FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7173     {FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7174     {FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7175     {FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7176     {FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7177     {FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7178     {FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7179     {FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7180     {FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7181     {FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7182     {FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7183     {FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7184     {FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7185     {FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7186     {FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7187     {FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7188     {FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7189     {FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7190     {FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7191     {FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7192     {FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7193     {FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7194     {FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7195     {FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7196     {FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7197     {FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7198     {FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7199     {FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7200     {FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7201     {FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7202     {FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7203     {FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7204     {FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7205     {FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7206     {FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7207     {FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7208     {FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7209     {FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7210     {FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7211     {FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7212     {FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7213     {FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7214     {FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7215     {FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7216     {FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7217     {FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7218     {FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7219     {FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7220     {FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7221     {FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7222     {FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7223     {FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7224     {FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7225     {FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7226     {FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7227     {FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7228     {FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7229     {FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7230     {FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7231     {FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7232     {FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7233     {FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7234     {FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7235     {FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7236     {FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7237     {FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7238     {FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7239     {FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7240     {FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7241     {FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7242     {FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7243     {FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, ERROR_SUCCESS, 200},
7244     {FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7245     {FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, ERROR_SUCCESS, 200},
7246     {FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7247     {FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, TRUE, ERROR_SUCCESS, 200},
7248     {FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7249     {FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, TRUE, ERROR_SUCCESS, 200},
7250     {FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7251     {FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7252     {FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7253     {FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7254     {FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7255     {FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7256     {FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7257     {FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7258     {FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7259     {FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7260     {FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7261     {FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7262     {FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7263     {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, ERROR_INSTALL_FAILURE, 0},
7264     {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, ERROR_INSTALL_FAILURE, 0},
7265     {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, ERROR_INSTALL_FAILURE, 0},
7266     {FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, ERROR_INSTALL_FAILURE, 0},
7267 };
7268
7269 static DWORD get_pf_file_size(LPCSTR file)
7270 {
7271     CHAR path[MAX_PATH];
7272     HANDLE hfile;
7273     DWORD size;
7274
7275     lstrcpyA(path, PROG_FILES_DIR);
7276     lstrcatA(path, "\\");
7277     lstrcatA(path, file);
7278
7279     hfile = CreateFileA(path, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL);
7280     if (hfile == INVALID_HANDLE_VALUE)
7281         return INVALID_FILE_SIZE;
7282
7283     size = GetFileSize(hfile, NULL);
7284     CloseHandle(hfile);
7285     return size;
7286 }
7287
7288 static void test_sourcepath(void)
7289 {
7290     UINT r, i;
7291
7292     if (!winetest_interactive)
7293     {
7294         skip("Run in interactive mode to run source path tests.\n");
7295         return;
7296     }
7297
7298     create_database(msifile, sp_tables, sizeof(sp_tables) / sizeof(msi_table));
7299
7300     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
7301
7302     for (i = 0; i < sizeof(spmap) / sizeof(spmap[0]); i++)
7303     {
7304         if (spmap[i].sost)
7305         {
7306             CreateDirectoryA("shortone", NULL);
7307             CreateDirectoryA("shortone\\shorttwo", NULL);
7308         }
7309
7310         if (spmap[i].solt)
7311         {
7312             CreateDirectoryA("shortone", NULL);
7313             CreateDirectoryA("shortone\\longtwo", NULL);
7314         }
7315
7316         if (spmap[i].lost)
7317         {
7318             CreateDirectoryA("longone", NULL);
7319             CreateDirectoryA("longone\\shorttwo", NULL);
7320         }
7321
7322         if (spmap[i].lolt)
7323         {
7324             CreateDirectoryA("longone", NULL);
7325             CreateDirectoryA("longone\\longtwo", NULL);
7326         }
7327
7328         if (spmap[i].soste)
7329             create_file("shortone\\shorttwo\\augustus", 50);
7330         if (spmap[i].solte)
7331             create_file("shortone\\longtwo\\augustus", 100);
7332         if (spmap[i].loste)
7333             create_file("longone\\shorttwo\\augustus", 150);
7334         if (spmap[i].lolte)
7335             create_file("longone\\longtwo\\augustus", 200);
7336
7337         r = MsiInstallProductA(msifile, NULL);
7338         ok(r == spmap[i].err, "%d: Expected %d, got %d\n", i, spmap[i].err, r);
7339         ok(get_pf_file_size("msitest\\augustus") == spmap[i].size,
7340            "%d: Expected %d, got %d\n", i, spmap[i].size,
7341            get_pf_file_size("msitest\\augustus"));
7342
7343         if (r == ERROR_SUCCESS)
7344         {
7345             ok(delete_pf("msitest\\augustus", TRUE), "%d: File not installed\n", i);
7346             ok(delete_pf("msitest", FALSE), "%d: File not installed\n", i);
7347         }
7348         else
7349         {
7350             ok(!delete_pf("msitest\\augustus", TRUE), "%d: File installed\n", i);
7351             todo_wine ok(!delete_pf("msitest", FALSE), "%d: File installed\n", i);
7352         }
7353
7354         DeleteFileA("shortone\\shorttwo\\augustus");
7355         DeleteFileA("shortone\\longtwo\\augustus");
7356         DeleteFileA("longone\\shorttwo\\augustus");
7357         DeleteFileA("longone\\longtwo\\augustus");
7358         RemoveDirectoryA("shortone\\shorttwo");
7359         RemoveDirectoryA("shortone\\longtwo");
7360         RemoveDirectoryA("longone\\shorttwo");
7361         RemoveDirectoryA("longone\\longtwo");
7362         RemoveDirectoryA("shortone");
7363         RemoveDirectoryA("longone");
7364     }
7365
7366     DeleteFileA(msifile);
7367 }
7368
7369 static void test_MsiConfigureProductEx(void)
7370 {
7371     UINT r;
7372     LONG res;
7373     DWORD type, size;
7374     HKEY props, source;
7375     CHAR keypath[MAX_PATH * 2];
7376     CHAR localpack[MAX_PATH];
7377
7378     if (on_win9x)
7379     {
7380         win_skip("Different registry keys on Win9x and WinMe\n");
7381         return;
7382     }
7383
7384     CreateDirectoryA("msitest", NULL);
7385     create_file("msitest\\hydrogen", 500);
7386     create_file("msitest\\helium", 500);
7387     create_file("msitest\\lithium", 500);
7388
7389     create_database(msifile, mcp_tables, sizeof(mcp_tables) / sizeof(msi_table));
7390
7391     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
7392
7393     /* NULL szProduct */
7394     r = MsiConfigureProductExA(NULL, INSTALLLEVEL_DEFAULT,
7395                                INSTALLSTATE_DEFAULT, "PROPVAR=42");
7396     ok(r == ERROR_INVALID_PARAMETER,
7397        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
7398
7399     /* empty szProduct */
7400     r = MsiConfigureProductExA("", INSTALLLEVEL_DEFAULT,
7401                                INSTALLSTATE_DEFAULT, "PROPVAR=42");
7402     ok(r == ERROR_INVALID_PARAMETER,
7403        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
7404
7405     /* garbage szProduct */
7406     r = MsiConfigureProductExA("garbage", INSTALLLEVEL_DEFAULT,
7407                                INSTALLSTATE_DEFAULT, "PROPVAR=42");
7408     ok(r == ERROR_INVALID_PARAMETER,
7409        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
7410
7411     /* guid without brackets */
7412     r = MsiConfigureProductExA("6700E8CF-95AB-4D9C-BC2C-15840DEA7A5D",
7413                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
7414                                "PROPVAR=42");
7415     ok(r == ERROR_INVALID_PARAMETER,
7416        "Expected ERROR_INVALID_PARAMETER, got %d\n", r);
7417
7418     /* guid with brackets */
7419     r = MsiConfigureProductExA("{6700E8CF-95AB-4D9C-BC2C-15840DEA7A5D}",
7420                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
7421                                "PROPVAR=42");
7422     ok(r == ERROR_UNKNOWN_PRODUCT,
7423        "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
7424
7425     /* same length as guid, but random */
7426     r = MsiConfigureProductExA("A938G02JF-2NF3N93-VN3-2NNF-3KGKALDNF93",
7427                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
7428                                "PROPVAR=42");
7429     ok(r == ERROR_UNKNOWN_PRODUCT,
7430        "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
7431
7432     /* product not installed yet */
7433     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7434                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
7435                                "PROPVAR=42");
7436     ok(r == ERROR_UNKNOWN_PRODUCT,
7437        "Expected ERROR_UNKNOWN_PRODUCT, got %d\n", r);
7438
7439     /* install the product, per-user unmanaged */
7440     r = MsiInstallProductA(msifile, "INSTALLLEVEL=10 PROPVAR=42");
7441     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7442     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
7443     ok(pf_exists("msitest\\helium"), "File not installed\n");
7444     ok(pf_exists("msitest\\lithium"), "File not installed\n");
7445     ok(pf_exists("msitest"), "File not installed\n");
7446
7447     /* product is installed per-user managed, remove it */
7448     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7449                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
7450                                "PROPVAR=42");
7451     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
7452     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
7453     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
7454     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
7455     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
7456
7457     /* product has been removed */
7458     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7459                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
7460                                "PROPVAR=42");
7461     ok(r == ERROR_UNKNOWN_PRODUCT,
7462        "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
7463
7464     /* install the product, machine */
7465     r = MsiInstallProductA(msifile, "ALLUSERS=1 INSTALLLEVEL=10 PROPVAR=42");
7466     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7467     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
7468     ok(pf_exists("msitest\\helium"), "File not installed\n");
7469     ok(pf_exists("msitest\\lithium"), "File not installed\n");
7470     ok(pf_exists("msitest"), "File not installed\n");
7471
7472     /* product is installed machine, remove it */
7473     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7474                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
7475                                "PROPVAR=42");
7476     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
7477     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
7478     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
7479     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
7480     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
7481
7482     /* product has been removed */
7483     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7484                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT,
7485                                "PROPVAR=42");
7486     ok(r == ERROR_UNKNOWN_PRODUCT,
7487        "Expected ERROR_UNKNOWN_PRODUCT, got %u\n", r);
7488
7489     /* install the product, machine */
7490     r = MsiInstallProductA(msifile, "ALLUSERS=1 INSTALLLEVEL=10 PROPVAR=42");
7491     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7492     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
7493     ok(pf_exists("msitest\\helium"), "File not installed\n");
7494     ok(pf_exists("msitest\\lithium"), "File not installed\n");
7495     ok(pf_exists("msitest"), "File not installed\n");
7496
7497     DeleteFileA(msifile);
7498
7499     /* local msifile is removed */
7500     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7501                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
7502                                "PROPVAR=42");
7503     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
7504     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
7505     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
7506     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
7507     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
7508
7509     create_database(msifile, mcp_tables, sizeof(mcp_tables) / sizeof(msi_table));
7510
7511     /* install the product, machine */
7512     r = MsiInstallProductA(msifile, "ALLUSERS=1 INSTALLLEVEL=10 PROPVAR=42");
7513     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7514     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
7515     ok(pf_exists("msitest\\helium"), "File not installed\n");
7516     ok(pf_exists("msitest\\lithium"), "File not installed\n");
7517     ok(pf_exists("msitest"), "File not installed\n");
7518
7519     DeleteFileA(msifile);
7520
7521     lstrcpyA(keypath, "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\");
7522     lstrcatA(keypath, "Installer\\UserData\\S-1-5-18\\Products\\");
7523     lstrcatA(keypath, "84A88FD7F6998CE40A22FB59F6B9C2BB\\InstallProperties");
7524
7525     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &props);
7526     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7527
7528     res = RegSetValueExA(props, "LocalPackage", 0, REG_SZ,
7529                          (const BYTE *)"C:\\idontexist.msi", 18);
7530     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7531
7532     /* LocalPackage is used to find the cached msi package */
7533     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7534                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
7535                                "PROPVAR=42");
7536     ok(r == ERROR_INSTALL_SOURCE_ABSENT,
7537        "Expected ERROR_INSTALL_SOURCE_ABSENT, got %d\n", r);
7538     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
7539     ok(pf_exists("msitest\\helium"), "File not installed\n");
7540     ok(pf_exists("msitest\\lithium"), "File not installed\n");
7541     ok(pf_exists("msitest"), "File not installed\n");
7542
7543     RegCloseKey(props);
7544     create_database(msifile, mcp_tables, sizeof(mcp_tables) / sizeof(msi_table));
7545
7546     /* LastUsedSource (local msi package) can be used as a last resort */
7547     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7548                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
7549                                "PROPVAR=42");
7550     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
7551     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
7552     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
7553     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
7554     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
7555
7556     /* install the product, machine */
7557     r = MsiInstallProductA(msifile, "ALLUSERS=1 INSTALLLEVEL=10 PROPVAR=42");
7558     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7559     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
7560     ok(pf_exists("msitest\\helium"), "File not installed\n");
7561     ok(pf_exists("msitest\\lithium"), "File not installed\n");
7562     ok(pf_exists("msitest"), "File not installed\n");
7563
7564     lstrcpyA(keypath, "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\");
7565     lstrcatA(keypath, "Installer\\UserData\\S-1-5-18\\Products\\");
7566     lstrcatA(keypath, "84A88FD7F6998CE40A22FB59F6B9C2BB\\InstallProperties");
7567
7568     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &props);
7569     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7570
7571     res = RegSetValueExA(props, "LocalPackage", 0, REG_SZ,
7572                          (const BYTE *)"C:\\idontexist.msi", 18);
7573     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7574
7575     lstrcpyA(keypath, "SOFTWARE\\Classes\\Installer\\Products\\");
7576     lstrcatA(keypath, "84A88FD7F6998CE40A22FB59F6B9C2BB\\SourceList");
7577
7578     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, keypath, &source);
7579     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7580
7581     type = REG_SZ;
7582     size = MAX_PATH;
7583     res = RegQueryValueExA(source, "PackageName", NULL, &type,
7584                            (LPBYTE)localpack, &size);
7585     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7586
7587     res = RegSetValueExA(source, "PackageName", 0, REG_SZ,
7588                          (const BYTE *)"idontexist.msi", 15);
7589     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7590
7591     /* SourceList is altered */
7592     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7593                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
7594                                "PROPVAR=42");
7595     ok(r == ERROR_INSTALL_SOURCE_ABSENT,
7596        "Expected ERROR_INSTALL_SOURCE_ABSENT, got %d\n", r);
7597     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
7598     ok(pf_exists("msitest\\helium"), "File not installed\n");
7599     ok(pf_exists("msitest\\lithium"), "File not installed\n");
7600     ok(pf_exists("msitest"), "File not installed\n");
7601
7602     /* restore the SourceList */
7603     res = RegSetValueExA(source, "PackageName", 0, REG_SZ,
7604                          (const BYTE *)localpack, lstrlenA(localpack) + 1);
7605     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7606
7607     /* finally remove the product */
7608     r = MsiConfigureProductExA("{7DF88A48-996F-4EC8-A022-BF956F9B2CBB}",
7609                                INSTALLLEVEL_DEFAULT, INSTALLSTATE_ABSENT,
7610                                "PROPVAR=42");
7611     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", r);
7612     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
7613     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
7614     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
7615     ok(!delete_pf("msitest", FALSE), "File not removed\n");
7616
7617     DeleteFileA(msifile);
7618     RegCloseKey(source);
7619     RegCloseKey(props);
7620     DeleteFileA("msitest\\hydrogen");
7621     DeleteFileA("msitest\\helium");
7622     DeleteFileA("msitest\\lithium");
7623     RemoveDirectoryA("msitest");
7624 }
7625
7626 static void test_missingcomponent(void)
7627 {
7628     UINT r;
7629
7630     CreateDirectoryA("msitest", NULL);
7631     create_file("msitest\\hydrogen", 500);
7632     create_file("msitest\\helium", 500);
7633     create_file("msitest\\lithium", 500);
7634     create_file("beryllium", 500);
7635
7636     create_database(msifile, mcomp_tables, sizeof(mcomp_tables) / sizeof(msi_table));
7637
7638     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
7639
7640     r = MsiInstallProductA(msifile, "INSTALLLEVEL=10 PROPVAR=42");
7641     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7642     ok(pf_exists("msitest\\hydrogen"), "File not installed\n");
7643     ok(pf_exists("msitest\\helium"), "File not installed\n");
7644     ok(pf_exists("msitest\\lithium"), "File not installed\n");
7645     ok(!pf_exists("msitest\\beryllium"), "File installed\n");
7646     ok(pf_exists("msitest"), "File not installed\n");
7647
7648     r = MsiInstallProductA(msifile, "REMOVE=ALL INSTALLLEVEL=10 PROPVAR=42");
7649     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7650     ok(!delete_pf("msitest\\hydrogen", TRUE), "File not removed\n");
7651     ok(!delete_pf("msitest\\helium", TRUE), "File not removed\n");
7652     ok(!delete_pf("msitest\\lithium", TRUE), "File not removed\n");
7653     ok(!pf_exists("msitest\\beryllium"), "File installed\n");
7654     ok(!delete_pf("msitest", FALSE), "Directory not removed\n");
7655
7656     DeleteFileA(msifile);
7657     DeleteFileA("msitest\\hydrogen");
7658     DeleteFileA("msitest\\helium");
7659     DeleteFileA("msitest\\lithium");
7660     DeleteFileA("beryllium");
7661     RemoveDirectoryA("msitest");
7662 }
7663
7664 static void test_sourcedirprop(void)
7665 {
7666     UINT r;
7667     CHAR props[MAX_PATH];
7668
7669     CreateDirectoryA("msitest", NULL);
7670     create_file("msitest\\augustus", 500);
7671
7672     create_database(msifile, ca51_tables, sizeof(ca51_tables) / sizeof(msi_table));
7673
7674     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
7675
7676     r = MsiInstallProductA(msifile, NULL);
7677     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7678     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
7679     ok(delete_pf("msitest", FALSE), "File installed\n");
7680
7681     DeleteFile("msitest\\augustus");
7682     RemoveDirectory("msitest");
7683
7684     CreateDirectoryA("altsource", NULL);
7685     CreateDirectoryA("altsource\\msitest", NULL);
7686     create_file("altsource\\msitest\\augustus", 500);
7687
7688     sprintf(props, "SRCDIR=%s\\altsource\\", CURR_DIR);
7689
7690     r = MsiInstallProductA(msifile, props);
7691     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7692     ok(delete_pf("msitest\\augustus", TRUE), "File installed\n");
7693     ok(delete_pf("msitest", FALSE), "File installed\n");
7694
7695     DeleteFile(msifile);
7696     DeleteFile("altsource\\msitest\\augustus");
7697     RemoveDirectory("altsource\\msitest");
7698     RemoveDirectory("altsource");
7699 }
7700
7701 static void test_adminimage(void)
7702 {
7703     UINT r;
7704
7705     CreateDirectoryA("msitest", NULL);
7706     CreateDirectoryA("msitest\\first", NULL);
7707     CreateDirectoryA("msitest\\second", NULL);
7708     CreateDirectoryA("msitest\\cabout", NULL);
7709     CreateDirectoryA("msitest\\cabout\\new", NULL);
7710     create_file("msitest\\one.txt", 100);
7711     create_file("msitest\\first\\two.txt", 100);
7712     create_file("msitest\\second\\three.txt", 100);
7713     create_file("msitest\\cabout\\four.txt", 100);
7714     create_file("msitest\\cabout\\new\\five.txt", 100);
7715     create_file("msitest\\filename", 100);
7716     create_file("msitest\\service.exe", 100);
7717
7718     create_database_wordcount(msifile, ai_tables,
7719                               sizeof(ai_tables) / sizeof(msi_table),
7720                               msidbSumInfoSourceTypeAdminImage);
7721
7722     r = MsiInstallProductA(msifile, NULL);
7723     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7724
7725     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
7726     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
7727     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
7728     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
7729     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
7730     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
7731     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
7732     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
7733     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
7734     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
7735     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
7736     ok(delete_pf("msitest", FALSE), "File not installed\n");
7737
7738     DeleteFileA("msitest.msi");
7739     DeleteFileA("msitest\\cabout\\new\\five.txt");
7740     DeleteFileA("msitest\\cabout\\four.txt");
7741     DeleteFileA("msitest\\second\\three.txt");
7742     DeleteFileA("msitest\\first\\two.txt");
7743     DeleteFileA("msitest\\one.txt");
7744     DeleteFileA("msitest\\service.exe");
7745     DeleteFileA("msitest\\filename");
7746     RemoveDirectoryA("msitest\\cabout\\new");
7747     RemoveDirectoryA("msitest\\cabout");
7748     RemoveDirectoryA("msitest\\second");
7749     RemoveDirectoryA("msitest\\first");
7750     RemoveDirectoryA("msitest");
7751 }
7752
7753 static void test_propcase(void)
7754 {
7755     UINT r;
7756
7757     CreateDirectoryA("msitest", NULL);
7758     create_file("msitest\\augustus", 500);
7759
7760     create_database(msifile, pc_tables, sizeof(pc_tables) / sizeof(msi_table));
7761
7762     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
7763
7764     r = MsiInstallProductA(msifile, "MyProp=42");
7765     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7766     ok(delete_pf("msitest\\augustus", TRUE), "File not installed\n");
7767     ok(delete_pf("msitest", FALSE), "File not installed\n");
7768
7769     DeleteFile(msifile);
7770     DeleteFile("msitest\\augustus");
7771     RemoveDirectory("msitest");
7772 }
7773
7774 static void test_int_widths( void )
7775 {
7776     static const char int0[] = "int0\ni0\nint0\tint0\n1";
7777     static const char int1[] = "int1\ni1\nint1\tint1\n1";
7778     static const char int2[] = "int2\ni2\nint2\tint2\n1";
7779     static const char int3[] = "int3\ni3\nint3\tint3\n1";
7780     static const char int4[] = "int4\ni4\nint4\tint4\n1";
7781     static const char int5[] = "int5\ni5\nint5\tint5\n1";
7782     static const char int8[] = "int8\ni8\nint8\tint8\n1";
7783
7784     static const struct
7785     {
7786         const char  *data;
7787         unsigned int size;
7788         UINT         ret;
7789     }
7790     tests[] =
7791     {
7792         { int0, sizeof(int0) - 1, ERROR_SUCCESS },
7793         { int1, sizeof(int1) - 1, ERROR_SUCCESS },
7794         { int2, sizeof(int2) - 1, ERROR_SUCCESS },
7795         { int3, sizeof(int3) - 1, ERROR_FUNCTION_FAILED },
7796         { int4, sizeof(int4) - 1, ERROR_SUCCESS },
7797         { int5, sizeof(int5) - 1, ERROR_FUNCTION_FAILED },
7798         { int8, sizeof(int8) - 1, ERROR_FUNCTION_FAILED }
7799     };
7800
7801     char tmpdir[MAX_PATH], msitable[MAX_PATH], msidb[MAX_PATH];
7802     MSIHANDLE db;
7803     UINT r, i;
7804
7805     GetTempPathA(MAX_PATH, tmpdir);
7806     CreateDirectoryA(tmpdir, NULL);
7807
7808     strcpy(msitable, tmpdir);
7809     strcat(msitable, "\\msitable.idt");
7810
7811     strcpy(msidb, tmpdir);
7812     strcat(msidb, "\\msitest.msi");
7813
7814     r = MsiOpenDatabaseA(msidb, MSIDBOPEN_CREATE, &db);
7815     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7816
7817     for (i = 0; i < sizeof(tests)/sizeof(tests[0]); i++)
7818     {
7819         write_file(msitable, tests[i].data, tests[i].size);
7820
7821         r = MsiDatabaseImportA(db, tmpdir, "msitable.idt");
7822         ok(r == tests[i].ret, " %u expected %u, got %u\n", i, tests[i].ret, r);
7823
7824         r = MsiDatabaseCommit(db);
7825         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7826         DeleteFileA(msitable);
7827     }
7828
7829     MsiCloseHandle(db);
7830     DeleteFileA(msidb);
7831     RemoveDirectoryA(tmpdir);
7832 }
7833
7834 static void test_shortcut(void)
7835 {
7836     UINT r;
7837     HRESULT hr;
7838
7839     create_test_files();
7840     create_database(msifile, sc_tables, sizeof(sc_tables) / sizeof(msi_table));
7841
7842     r = MsiInstallProductA(msifile, NULL);
7843     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7844
7845     hr = CoInitializeEx(NULL, COINIT_MULTITHREADED);
7846     ok(SUCCEEDED(hr), "CoInitialize failed 0x%08x\n", hr);
7847
7848     r = MsiInstallProductA(msifile, NULL);
7849     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7850
7851     CoUninitialize();
7852
7853     hr = CoInitializeEx(NULL, COINIT_APARTMENTTHREADED);
7854     ok(SUCCEEDED(hr), "CoInitialize failed 0x%08x\n", hr);
7855
7856     r = MsiInstallProductA(msifile, NULL);
7857     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7858
7859     CoUninitialize();
7860
7861     delete_pf("msitest\\cabout\\new\\five.txt", TRUE);
7862     delete_pf("msitest\\cabout\\new", FALSE);
7863     delete_pf("msitest\\cabout\\four.txt", TRUE);
7864     delete_pf("msitest\\cabout", FALSE);
7865     delete_pf("msitest\\changed\\three.txt", TRUE);
7866     delete_pf("msitest\\changed", FALSE);
7867     delete_pf("msitest\\first\\two.txt", TRUE);
7868     delete_pf("msitest\\first", FALSE);
7869     delete_pf("msitest\\filename", TRUE);
7870     delete_pf("msitest\\one.txt", TRUE);
7871     delete_pf("msitest\\service.exe", TRUE);
7872     delete_pf("msitest\\Shortcut.lnk", TRUE);
7873     delete_pf("msitest", FALSE);
7874     delete_test_files();
7875 }
7876
7877 static void test_envvar(void)
7878 {
7879     UINT r;
7880     HKEY env;
7881     LONG res;
7882     DWORD type, size;
7883     char buffer[16];
7884     UINT i;
7885
7886     if (on_win9x)
7887     {
7888         win_skip("Environment variables are handled differently on Win9x and WinMe\n");
7889         return;
7890     }
7891
7892     create_test_files();
7893     create_database(msifile, env_tables, sizeof(env_tables) / sizeof(msi_table));
7894
7895     res = RegCreateKeyExA(HKEY_CURRENT_USER, "Environment", 0, NULL, 0, KEY_ALL_ACCESS, NULL, &env, NULL);
7896     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7897
7898     res = RegSetValueExA(env, "MSITESTVAR1", 0, REG_SZ, (const BYTE *)"0", 2);
7899     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7900
7901     res = RegSetValueExA(env, "MSITESTVAR2", 0, REG_SZ, (const BYTE *)"0", 2);
7902     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7903
7904     r = MsiInstallProductA(msifile, NULL);
7905     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7906
7907     type = REG_NONE;
7908     size = sizeof(buffer);
7909     buffer[0] = 0;
7910     res = RegQueryValueExA(env, "MSITESTVAR1", NULL, &type, (LPBYTE)buffer, &size);
7911     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7912     ok(type == REG_SZ, "Expected REG_SZ, got %u\n", type);
7913     ok(!lstrcmp(buffer, "1"), "Expected \"1\", got %s\n", buffer);
7914
7915     res = RegDeleteValueA(env, "MSITESTVAR1");
7916     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7917
7918     type = REG_NONE;
7919     size = sizeof(buffer);
7920     buffer[0] = 0;
7921     res = RegQueryValueExA(env, "MSITESTVAR2", NULL, &type, (LPBYTE)buffer, &size);
7922     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7923     ok(type == REG_SZ, "Expected REG_SZ, got %u\n", type);
7924     ok(!lstrcmp(buffer, "1"), "Expected \"1\", got %s\n", buffer);
7925
7926     res = RegDeleteValueA(env, "MSITESTVAR2");
7927     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7928
7929     res = RegDeleteValueA(env, "MSITESTVAR3");
7930     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7931
7932     res = RegDeleteValueA(env, "MSITESTVAR4");
7933     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
7934
7935     res = RegDeleteValueA(env, "MSITESTVAR5");
7936     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
7937
7938     res = RegDeleteValueA(env, "MSITESTVAR6");
7939     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
7940
7941     res = RegDeleteValueA(env, "MSITESTVAR7");
7942     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
7943
7944     res = RegDeleteValueA(env, "MSITESTVAR8");
7945     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
7946
7947     res = RegDeleteValueA(env, "MSITESTVAR9");
7948     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
7949
7950     res = RegDeleteValueA(env, "MSITESTVAR10");
7951     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
7952
7953     i = 11;
7954     while (environment_dat_results[(i-11)]) {
7955         char name[20];
7956         sprintf(name, "MSITESTVAR%d", i);
7957
7958         type = REG_NONE;
7959         size = sizeof(buffer);
7960         buffer[0] = 0;
7961         res = RegQueryValueExA(env, name, NULL, &type, (LPBYTE)buffer, &size);
7962         ok(res == ERROR_SUCCESS, "%d: Expected ERROR_SUCCESS, got %d\n", i, res);
7963         ok(type == REG_SZ, "%d: Expected REG_SZ, got %u\n", i, type);
7964         ok(!lstrcmp(buffer, environment_dat_results[(i-11)]), "%d: Expected %s, got %s\n",
7965            i, environment_dat_results[(i-11)], buffer);
7966
7967         res = RegDeleteValueA(env, name);
7968         ok(res == ERROR_SUCCESS, "%d: Expected ERROR_SUCCESS, got %d\n", i, res);
7969         i++;
7970     }
7971
7972
7973     RegCloseKey(env);
7974     delete_pf("msitest\\cabout\\new\\five.txt", TRUE);
7975     delete_pf("msitest\\cabout\\new", FALSE);
7976     delete_pf("msitest\\cabout\\four.txt", TRUE);
7977     delete_pf("msitest\\cabout", FALSE);
7978     delete_pf("msitest\\changed\\three.txt", TRUE);
7979     delete_pf("msitest\\changed", FALSE);
7980     delete_pf("msitest\\first\\two.txt", TRUE);
7981     delete_pf("msitest\\first", FALSE);
7982     delete_pf("msitest\\filename", TRUE);
7983     delete_pf("msitest\\one.txt", TRUE);
7984     delete_pf("msitest\\service.exe", TRUE);
7985     delete_pf("msitest", FALSE);
7986     delete_test_files();
7987 }
7988
7989 static void test_preselected(void)
7990 {
7991     UINT r;
7992
7993     create_test_files();
7994     create_database(msifile, ps_tables, sizeof(ps_tables) / sizeof(msi_table));
7995
7996     r = MsiInstallProductA(msifile, "ADDLOCAL=One");
7997     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
7998
7999     ok(!delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File installed\n");
8000     ok(!delete_pf("msitest\\cabout\\new", FALSE), "File installed\n");
8001     ok(!delete_pf("msitest\\cabout\\four.txt", TRUE), "File installed\n");
8002     ok(!delete_pf("msitest\\cabout", FALSE), "File installed\n");
8003     ok(!delete_pf("msitest\\changed\\three.txt", TRUE), "File installed\n");
8004     ok(!delete_pf("msitest\\changed", FALSE), "File installed\n");
8005     ok(!delete_pf("msitest\\first\\two.txt", TRUE), "File installed\n");
8006     ok(!delete_pf("msitest\\first", FALSE), "File installed\n");
8007     ok(!delete_pf("msitest\\filename", TRUE), "File installed\n");
8008     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
8009     ok(!delete_pf("msitest\\service.exe", TRUE), "File installed\n");
8010     ok(delete_pf("msitest", FALSE), "File not installed\n");
8011
8012     r = MsiInstallProductA(msifile, NULL);
8013     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8014
8015     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8016     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
8017     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8018     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
8019     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8020     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
8021     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8022     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
8023     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8024     ok(!delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8025     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8026     ok(delete_pf("msitest", FALSE), "File not installed\n");
8027     delete_test_files();
8028 }
8029
8030 static void test_installed_prop(void)
8031 {
8032     static char prodcode[] = "{7df88a48-996f-4ec8-a022-bf956f9b2cbb}";
8033     UINT r;
8034
8035     create_test_files();
8036     create_database(msifile, ip_tables, sizeof(ip_tables) / sizeof(msi_table));
8037
8038     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8039
8040     r = MsiInstallProductA(msifile, "FULL=1");
8041     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8042
8043     r = MsiInstallProductA(msifile, "FULL=1");
8044     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8045
8046     r = MsiConfigureProductExA(prodcode, INSTALLLEVEL_DEFAULT, INSTALLSTATE_DEFAULT, "FULL=1");
8047     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8048
8049     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8050     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
8051     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8052     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
8053     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8054     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
8055     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8056     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
8057     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8058     ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8059     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8060     ok(delete_pf("msitest", FALSE), "File not installed\n");
8061
8062     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8063     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8064
8065     delete_test_files();
8066 }
8067
8068 static void test_allusers_prop(void)
8069 {
8070     UINT r;
8071
8072     create_test_files();
8073     create_database(msifile, aup_tables, sizeof(aup_tables) / sizeof(msi_table));
8074
8075     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8076
8077     /* ALLUSERS property unset */
8078     r = MsiInstallProductA(msifile, "FULL=1");
8079     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8080
8081     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8082     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
8083     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8084     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
8085     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8086     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
8087     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8088     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
8089     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8090     ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8091     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8092     ok(delete_pf("msitest", FALSE), "File not installed\n");
8093
8094     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8095     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8096
8097     delete_test_files();
8098
8099     create_test_files();
8100     create_database(msifile, aup2_tables, sizeof(aup2_tables) / sizeof(msi_table));
8101
8102     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8103
8104     /* ALLUSERS property set to 1 */
8105     r = MsiInstallProductA(msifile, "FULL=1");
8106     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8107
8108     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8109     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
8110     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8111     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
8112     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8113     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
8114     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8115     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
8116     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8117     ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8118     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8119     ok(delete_pf("msitest", FALSE), "File not installed\n");
8120
8121     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8122     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8123
8124     delete_test_files();
8125
8126     create_test_files();
8127     create_database(msifile, aup3_tables, sizeof(aup3_tables) / sizeof(msi_table));
8128
8129     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8130
8131     /* ALLUSERS property set to 2 */
8132     r = MsiInstallProductA(msifile, "FULL=1");
8133     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8134
8135     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8136     ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
8137     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8138     ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
8139     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8140     ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
8141     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8142     ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
8143     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8144     ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8145     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8146     ok(delete_pf("msitest", FALSE), "File not installed\n");
8147
8148     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8149     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8150
8151     delete_test_files();
8152
8153     create_test_files();
8154     create_database(msifile, aup4_tables, sizeof(aup4_tables) / sizeof(msi_table));
8155
8156     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8157
8158     /* ALLUSERS property set to 2, conditioned on ALLUSERS = 1 */
8159     r = MsiInstallProductA(msifile, "FULL=1");
8160     if (r == ERROR_SUCCESS)
8161     {
8162         /* Win9x/WinMe */
8163         win_skip("Win9x and WinMe act differently with respect to ALLUSERS\n");
8164
8165         ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8166         ok(delete_pf("msitest\\cabout\\new", FALSE), "File not installed\n");
8167         ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8168         ok(delete_pf("msitest\\cabout", FALSE), "File not installed\n");
8169         ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8170         ok(delete_pf("msitest\\changed", FALSE), "File not installed\n");
8171         ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8172         ok(delete_pf("msitest\\first", FALSE), "File not installed\n");
8173         ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8174         ok(delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8175         ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8176         ok(delete_pf("msitest", FALSE), "File not installed\n");
8177
8178         r = MsiInstallProductA(msifile, "REMOVE=ALL");
8179         ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8180
8181         delete_test_files();
8182     }
8183     else
8184         ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8185 }
8186
8187 static char session_manager[] = "System\\CurrentControlSet\\Control\\Session Manager";
8188 static char rename_ops[]      = "PendingFileRenameOperations";
8189
8190 static void process_pending_renames(HKEY hkey)
8191 {
8192     char *buf, *src, *dst, *buf2, *buf2ptr;
8193     DWORD size, buf2len = 0;
8194     LONG ret;
8195     BOOL found = FALSE;
8196
8197     ret = RegQueryValueExA(hkey, rename_ops, NULL, NULL, NULL, &size);
8198     buf = HeapAlloc(GetProcessHeap(), 0, size);
8199     buf2ptr = buf2 = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, size);
8200     buf[0] = 0;
8201
8202     ret = RegQueryValueExA(hkey, rename_ops, NULL, NULL, (LPBYTE)buf, &size);
8203     ok(!ret, "RegQueryValueExA failed %d (%u)\n", ret, GetLastError());
8204
8205     for (src = buf; *src; src = dst + strlen(dst) + 1)
8206     {
8207         DWORD flags = MOVEFILE_COPY_ALLOWED;
8208
8209         dst = src + strlen(src) + 1;
8210
8211         if (!strstr(src, "msitest"))
8212         {
8213             lstrcpyA(buf2ptr, src);
8214             buf2len += strlen(src) + 1;
8215             buf2ptr += strlen(src) + 1;
8216             if (*dst)
8217             {
8218                 lstrcpyA(buf2ptr, dst);
8219                 buf2ptr += strlen(dst) + 1;
8220                 buf2len += strlen(dst) + 1;
8221             }
8222             buf2ptr++;
8223             buf2len++;
8224             continue;
8225         }
8226
8227         found = TRUE;
8228
8229         if (*dst == '!')
8230         {
8231             flags |= MOVEFILE_REPLACE_EXISTING;
8232             dst++;
8233         }
8234         if (src[0] == '\\' && src[1] == '?' && src[2] == '?' && src[3] == '\\') src += 4;
8235         if (*dst)
8236         {
8237             if (dst[0] == '\\' && dst[1] == '?' && dst[2] == '?' && dst[3] == '\\') dst += 4;
8238             ok(MoveFileExA(src, dst, flags), "Failed to move file %s -> %s (%u)\n", src, dst, GetLastError());
8239         }
8240         else
8241             ok(DeleteFileA(src), "Failed to delete file %s (%u)\n", src, GetLastError());
8242     }
8243
8244     ok(found, "Expected a 'msitest' entry\n");
8245
8246     if (*buf2)
8247     {
8248         buf2len++;
8249         RegSetValueExA(hkey, rename_ops, 0, REG_MULTI_SZ, (LPBYTE)buf2, buf2len);
8250     }
8251     else
8252         RegDeleteValueA(hkey, rename_ops);
8253
8254     HeapFree(GetProcessHeap(), 0, buf);
8255     HeapFree(GetProcessHeap(), 0, buf2);
8256 }
8257
8258 static BOOL file_matches_data(LPCSTR file, LPCSTR data)
8259 {
8260     DWORD len, data_len = strlen(data);
8261     HANDLE handle;
8262     char buf[128];
8263
8264     handle = CreateFile(file, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL);
8265     ok(handle != INVALID_HANDLE_VALUE, "failed to open %s (%u)\n", file, GetLastError());
8266
8267     if (ReadFile(handle, buf, sizeof(buf), &len, NULL) && len >= data_len)
8268     {
8269         CloseHandle(handle);
8270         return !memcmp(buf, data, data_len);
8271     }
8272     CloseHandle(handle);
8273     return FALSE;
8274 }
8275
8276 static void test_file_in_use(void)
8277 {
8278     UINT r;
8279     HANDLE file;
8280     HKEY hkey;
8281     char path[MAX_PATH];
8282
8283     if (on_win9x)
8284     {
8285         win_skip("Pending file renaming is implemented differently on Win9x and WinMe\n");
8286         return;
8287     }
8288
8289     RegOpenKeyExA(HKEY_LOCAL_MACHINE, session_manager, 0, KEY_ALL_ACCESS, &hkey);
8290
8291     CreateDirectoryA("msitest", NULL);
8292     create_file("msitest\\maximus", 500);
8293     create_database(msifile, fiu_tables, sizeof(fiu_tables) / sizeof(msi_table));
8294
8295     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8296
8297     lstrcpy(path, PROG_FILES_DIR);
8298     lstrcat(path, "\\msitest");
8299     CreateDirectoryA(path, NULL);
8300
8301     lstrcat(path, "\\maximus");
8302     file = CreateFileA(path, GENERIC_READ, FILE_SHARE_READ, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
8303
8304     r = MsiInstallProductA(msifile, "REBOOT=ReallySuppress FULL=1");
8305     ok(r == ERROR_SUCCESS_REBOOT_REQUIRED, "Expected ERROR_SUCCESS_REBOOT_REQUIRED got %u\n", r);
8306     ok(!file_matches_data(path, "msitest\\maximus"), "Expected file not to match\n");
8307     CloseHandle(file);
8308     ok(!file_matches_data(path, "msitest\\maximus"), "Expected file not to match\n");
8309
8310     process_pending_renames(hkey);
8311     RegCloseKey(hkey);
8312
8313     ok(file_matches_data(path, "msitest\\maximus"), "Expected file to match\n");
8314     ok(delete_pf("msitest\\maximus", TRUE), "File not present\n");
8315     ok(delete_pf("msitest", FALSE), "Directory not present or not empty\n");
8316
8317     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8318     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8319
8320     DeleteFileA("msitest\\maximus");
8321     delete_test_files();
8322 }
8323
8324 static void test_file_in_use_cab(void)
8325 {
8326     UINT r;
8327     HANDLE file;
8328     HKEY hkey;
8329     char path[MAX_PATH];
8330
8331     if (on_win9x)
8332     {
8333         win_skip("Pending file renaming is implemented differently on Win9x and WinMe\n");
8334         return;
8335     }
8336
8337     RegOpenKeyExA(HKEY_LOCAL_MACHINE, session_manager, 0, KEY_ALL_ACCESS, &hkey);
8338
8339     CreateDirectoryA("msitest", NULL);
8340     create_file("maximus", 500);
8341     create_cab_file("test1.cab", MEDIA_SIZE, "maximus\0");
8342     DeleteFile("maximus");
8343
8344     create_database(msifile, fiuc_tables, sizeof(fiuc_tables) / sizeof(msi_table));
8345
8346     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8347
8348     lstrcpy(path, PROG_FILES_DIR);
8349     lstrcat(path, "\\msitest");
8350     CreateDirectoryA(path, NULL);
8351
8352     lstrcat(path, "\\maximus");
8353     file = CreateFileA(path, GENERIC_READ, FILE_SHARE_READ, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
8354
8355     r = MsiInstallProductA(msifile, "REBOOT=ReallySuppress FULL=1");
8356     ok(r == ERROR_SUCCESS_REBOOT_REQUIRED, "Expected ERROR_SUCCESS_REBOOT_REQUIRED got %u\n", r);
8357     ok(!file_matches_data(path, "maximus"), "Expected file not to match\n");
8358     CloseHandle(file);
8359     ok(!file_matches_data(path, "maximus"), "Expected file not to match\n");
8360
8361     process_pending_renames(hkey);
8362     RegCloseKey(hkey);
8363
8364     ok(file_matches_data(path, "maximus"), "Expected file to match\n");
8365     ok(delete_pf("msitest\\maximus", TRUE), "File not present\n");
8366     ok(delete_pf("msitest", FALSE), "Directory not present or not empty\n");
8367
8368     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8369     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8370
8371     delete_cab_files();
8372     delete_test_files();
8373 }
8374
8375 static INT CALLBACK handler_a(LPVOID context, UINT type, LPCSTR msg)
8376 {
8377     return IDOK;
8378 }
8379
8380 static INT CALLBACK handler_w(LPVOID context, UINT type, LPCWSTR msg)
8381 {
8382     return IDOK;
8383 }
8384
8385 static INT CALLBACK handler_record(LPVOID context, UINT type, MSIHANDLE record)
8386 {
8387     return IDOK;
8388 }
8389
8390 static void test_MsiSetExternalUI(void)
8391 {
8392     INSTALLUI_HANDLERA ret_a;
8393     INSTALLUI_HANDLERW ret_w;
8394     INSTALLUI_HANDLER_RECORD prev;
8395     UINT error;
8396
8397     ret_a = MsiSetExternalUIA(handler_a, INSTALLLOGMODE_ERROR, NULL);
8398     ok(ret_a == NULL, "expected NULL, got %p\n", ret_a);
8399
8400     ret_a = MsiSetExternalUIA(NULL, 0, NULL);
8401     ok(ret_a == handler_a, "expected %p, got %p\n", handler_a, ret_a);
8402
8403     /* Not present before Installer 3.1 */
8404     if (!pMsiSetExternalUIRecord) {
8405         win_skip("MsiSetExternalUIRecord is not available\n");
8406         return;
8407     }
8408
8409     error = pMsiSetExternalUIRecord(handler_record, INSTALLLOGMODE_ERROR, NULL, &prev);
8410     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
8411     ok(prev == NULL, "expected NULL, got %p\n", prev);
8412
8413     prev = (INSTALLUI_HANDLER_RECORD)0xdeadbeef;
8414     error = pMsiSetExternalUIRecord(NULL, INSTALLLOGMODE_ERROR, NULL, &prev);
8415     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
8416     ok(prev == handler_record, "expected %p, got %p\n", handler_record, prev);
8417
8418     ret_w = MsiSetExternalUIW(handler_w, INSTALLLOGMODE_ERROR, NULL);
8419     ok(ret_w == NULL, "expected NULL, got %p\n", ret_w);
8420
8421     ret_w = MsiSetExternalUIW(NULL, 0, NULL);
8422     ok(ret_w == handler_w, "expected %p, got %p\n", handler_w, ret_w);
8423
8424     ret_a = MsiSetExternalUIA(handler_a, INSTALLLOGMODE_ERROR, NULL);
8425     ok(ret_a == NULL, "expected NULL, got %p\n", ret_a);
8426
8427     ret_w = MsiSetExternalUIW(handler_w, INSTALLLOGMODE_ERROR, NULL);
8428     ok(ret_w == NULL, "expected NULL, got %p\n", ret_w);
8429
8430     prev = (INSTALLUI_HANDLER_RECORD)0xdeadbeef;
8431     error = pMsiSetExternalUIRecord(handler_record, INSTALLLOGMODE_ERROR, NULL, &prev);
8432     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
8433     ok(prev == NULL, "expected NULL, got %p\n", prev);
8434
8435     ret_a = MsiSetExternalUIA(NULL, 0, NULL);
8436     ok(ret_a == NULL, "expected NULL, got %p\n", ret_a);
8437
8438     ret_w = MsiSetExternalUIW(NULL, 0, NULL);
8439     ok(ret_w == NULL, "expected NULL, got %p\n", ret_w);
8440
8441     prev = (INSTALLUI_HANDLER_RECORD)0xdeadbeef;
8442     error = pMsiSetExternalUIRecord(NULL, 0, NULL, &prev);
8443     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
8444     ok(prev == handler_record, "expected %p, got %p\n", handler_record, prev);
8445
8446     error = pMsiSetExternalUIRecord(handler_record, INSTALLLOGMODE_ERROR, NULL, NULL);
8447     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
8448
8449     error = pMsiSetExternalUIRecord(NULL, 0, NULL, NULL);
8450     ok(!error, "MsiSetExternalUIRecord failed %u\n", error);
8451 }
8452
8453 static void test_feature_override(void)
8454 {
8455     UINT r;
8456
8457     create_test_files();
8458     create_file("msitest\\override.txt", 1000);
8459     create_file("msitest\\preselected.txt", 1000);
8460     create_file("msitest\\notpreselected.txt", 1000);
8461     create_database(msifile, fo_tables, sizeof(fo_tables) / sizeof(msi_table));
8462
8463     r = MsiInstallProductA(msifile, "ADDLOCAL=override");
8464     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8465
8466     ok(pf_exists("msitest\\override.txt"), "file not installed\n");
8467     ok(!pf_exists("msitest\\preselected.txt"), "file installed\n");
8468     ok(!pf_exists("msitest\\notpreselected.txt"), "file installed\n");
8469
8470     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8471     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8472
8473     ok(!delete_pf("msitest\\override.txt", TRUE), "file not removed\n");
8474
8475     r = MsiInstallProductA(msifile, "preselect=1");
8476     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8477
8478     ok(pf_exists("msitest\\override.txt"), "file not installed\n");
8479     ok(pf_exists("msitest\\preselected.txt"), "file not installed\n");
8480     ok(!pf_exists("msitest\\notpreselected.txt"), "file installed\n");
8481
8482     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8483     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8484
8485     ok(!delete_pf("msitest\\override.txt", TRUE), "file not removed\n");
8486     todo_wine {
8487     ok(delete_pf("msitest\\preselected.txt", TRUE), "file removed\n");
8488     ok(delete_pf("msitest", FALSE), "directory removed\n");
8489     }
8490
8491     r = MsiInstallProductA(msifile, NULL);
8492     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8493
8494     ok(pf_exists("msitest\\override.txt"), "file not installed\n");
8495     ok(pf_exists("msitest\\preselected.txt"), "file not installed\n");
8496     ok(!pf_exists("msitest\\notpreselected.txt"), "file installed\n");
8497
8498     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8499     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8500
8501     ok(!delete_pf("msitest\\override.txt", TRUE), "file not removed\n");
8502     todo_wine {
8503     ok(delete_pf("msitest\\preselected.txt", TRUE), "file removed\n");
8504     ok(delete_pf("msitest", FALSE), "directory removed\n");
8505     }
8506
8507     DeleteFileA("msitest\\override.txt");
8508     DeleteFileA("msitest\\preselected.txt");
8509     DeleteFileA("msitest\\notpreselected.txt");
8510     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\msitest");
8511     delete_test_files();
8512 }
8513
8514 static void test_create_folder(void)
8515 {
8516     UINT r;
8517
8518     create_test_files();
8519     create_database(msifile, cf_tables, sizeof(cf_tables) / sizeof(msi_table));
8520
8521     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8522
8523     r = MsiInstallProductA(msifile, NULL);
8524     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8525
8526     ok(!delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File installed\n");
8527     ok(!delete_pf("msitest\\cabout\\new", FALSE), "Directory created\n");
8528     ok(!delete_pf("msitest\\cabout\\four.txt", TRUE), "File installed\n");
8529     ok(!delete_pf("msitest\\cabout", FALSE), "Directory created\n");
8530     ok(!delete_pf("msitest\\changed\\three.txt", TRUE), "File installed\n");
8531     ok(!delete_pf("msitest\\changed", FALSE), "Directory created\n");
8532     ok(!delete_pf("msitest\\first\\two.txt", TRUE), "File installed\n");
8533     ok(!delete_pf("msitest\\first", FALSE), "Directory created\n");
8534     ok(!delete_pf("msitest\\filename", TRUE), "File installed\n");
8535     ok(!delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8536     ok(!delete_pf("msitest\\service.exe", TRUE), "File installed\n");
8537     ok(!delete_pf("msitest", FALSE), "Directory created\n");
8538
8539     r = MsiInstallProductA(msifile, "LOCAL=Two");
8540     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8541
8542     ok(!delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File installed\n");
8543     ok(!delete_pf("msitest\\cabout\\new", FALSE), "Directory created\n");
8544     ok(!delete_pf("msitest\\cabout\\four.txt", TRUE), "File installed\n");
8545     ok(!delete_pf("msitest\\cabout", FALSE), "Directory created\n");
8546     ok(!delete_pf("msitest\\changed\\three.txt", TRUE), "File installed\n");
8547     ok(!delete_pf("msitest\\changed", FALSE), "Directory created\n");
8548     ok(!delete_pf("msitest\\first\\two.txt", TRUE), "File installed\n");
8549     ok(!delete_pf("msitest\\first", FALSE), "Directory created\n");
8550     ok(!delete_pf("msitest\\filename", TRUE), "File installed\n");
8551     ok(!delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8552     ok(!delete_pf("msitest\\service.exe", TRUE), "File installed\n");
8553     ok(!delete_pf("msitest", FALSE), "Directory created\n");
8554
8555     delete_test_files();
8556 }
8557
8558 static void test_remove_folder(void)
8559 {
8560     UINT r;
8561
8562     create_test_files();
8563     create_database(msifile, rf_tables, sizeof(rf_tables) / sizeof(msi_table));
8564
8565     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8566
8567     r = MsiInstallProductA(msifile, NULL);
8568     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8569
8570     ok(!delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File installed\n");
8571     ok(!delete_pf("msitest\\cabout\\new", FALSE), "Directory created\n");
8572     ok(!delete_pf("msitest\\cabout\\four.txt", TRUE), "File installed\n");
8573     ok(!delete_pf("msitest\\cabout", FALSE), "Directory created\n");
8574     ok(!delete_pf("msitest\\changed\\three.txt", TRUE), "File installed\n");
8575     ok(!delete_pf("msitest\\changed", FALSE), "Directory created\n");
8576     ok(!delete_pf("msitest\\first\\two.txt", TRUE), "File installed\n");
8577     ok(!delete_pf("msitest\\first", FALSE), "Directory created\n");
8578     ok(!delete_pf("msitest\\filename", TRUE), "File installed\n");
8579     ok(!delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8580     ok(!delete_pf("msitest\\service.exe", TRUE), "File installed\n");
8581     ok(!delete_pf("msitest", FALSE), "Directory created\n");
8582
8583     r = MsiInstallProductA(msifile, "LOCAL=Two");
8584     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8585
8586     ok(!delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File installed\n");
8587     ok(!delete_pf("msitest\\cabout\\new", FALSE), "Directory created\n");
8588     ok(!delete_pf("msitest\\cabout\\four.txt", TRUE), "File installed\n");
8589     ok(!delete_pf("msitest\\cabout", FALSE), "Directory created\n");
8590     ok(!delete_pf("msitest\\changed\\three.txt", TRUE), "File installed\n");
8591     ok(!delete_pf("msitest\\changed", FALSE), "Directory created\n");
8592     ok(!delete_pf("msitest\\first\\two.txt", TRUE), "File installed\n");
8593     ok(!delete_pf("msitest\\first", FALSE), "Directory created\n");
8594     ok(!delete_pf("msitest\\filename", TRUE), "File installed\n");
8595     ok(!delete_pf("msitest\\one.txt", TRUE), "File installed\n");
8596     ok(!delete_pf("msitest\\service.exe", TRUE), "File installed\n");
8597     ok(!delete_pf("msitest", FALSE), "Directory created\n");
8598
8599     delete_test_files();
8600 }
8601
8602 static void test_start_services(void)
8603 {
8604     UINT r;
8605     SC_HANDLE scm, service;
8606     BOOL ret;
8607     DWORD error = ERROR_SUCCESS;
8608
8609     if (on_win9x)
8610     {
8611         win_skip("Services are not implemented on Win9x and WinMe\n");
8612         return;
8613     }
8614     scm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
8615     ok(scm != NULL, "Failed to open the SC Manager\n");
8616     if (!scm) return;
8617
8618     service = OpenService(scm, "Spooler", SC_MANAGER_ALL_ACCESS);
8619     if (!service && GetLastError() == ERROR_SERVICE_DOES_NOT_EXIST)
8620     {
8621         win_skip("The 'Spooler' service does not exist\n");
8622         CloseServiceHandle(scm);
8623         return;
8624     }
8625     ok(service != NULL, "Failed to open Spooler, error %d\n", GetLastError());
8626     if (!service) {
8627         CloseServiceHandle(scm);
8628         return;
8629     }
8630
8631     ret = StartService(service, 0, NULL);
8632     if (!ret && (error = GetLastError()) != ERROR_SERVICE_ALREADY_RUNNING)
8633     {
8634         skip("Terminal service not available, skipping test\n");
8635         CloseServiceHandle(service);
8636         CloseServiceHandle(scm);
8637         return;
8638     }
8639
8640     CloseServiceHandle(service);
8641     CloseServiceHandle(scm);
8642
8643     create_test_files();
8644     create_database(msifile, sss_tables, sizeof(sss_tables) / sizeof(msi_table));
8645
8646     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8647
8648     r = MsiInstallProductA(msifile, NULL);
8649     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8650
8651     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8652     ok(delete_pf("msitest\\cabout\\new", FALSE), "Directory not created\n");
8653     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8654     ok(delete_pf("msitest\\cabout", FALSE), "Directory not created\n");
8655     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8656     ok(delete_pf("msitest\\changed", FALSE), "Directory not created\n");
8657     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8658     ok(delete_pf("msitest\\first", FALSE), "Directory not created\n");
8659     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8660     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
8661     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8662     ok(delete_pf("msitest", FALSE), "Directory not created\n");
8663
8664     delete_test_files();
8665
8666     if (error == ERROR_SUCCESS)
8667     {
8668         SERVICE_STATUS status;
8669
8670         scm = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
8671         service = OpenService(scm, "Spooler", SC_MANAGER_ALL_ACCESS);
8672
8673         ret = ControlService(service, SERVICE_CONTROL_STOP, &status);
8674         ok(ret, "ControlService failed %u\n", GetLastError());
8675
8676         CloseServiceHandle(service);
8677         CloseServiceHandle(scm);
8678     }
8679 }
8680
8681 static void test_delete_services(void)
8682 {
8683     UINT r;
8684
8685     create_test_files();
8686     create_database(msifile, sds_tables, sizeof(sds_tables) / sizeof(msi_table));
8687
8688     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8689
8690     r = MsiInstallProductA(msifile, NULL);
8691     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8692
8693     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8694     ok(delete_pf("msitest\\cabout\\new", FALSE), "Directory not created\n");
8695     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8696     ok(delete_pf("msitest\\cabout", FALSE), "Directory not created\n");
8697     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8698     ok(delete_pf("msitest\\changed", FALSE), "Directory not created\n");
8699     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8700     ok(delete_pf("msitest\\first", FALSE), "Directory not created\n");
8701     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8702     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
8703     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8704     ok(delete_pf("msitest", FALSE), "Directory not created\n");
8705
8706     delete_test_files();
8707 }
8708
8709 static void test_self_registration(void)
8710 {
8711     UINT r;
8712
8713     create_test_files();
8714     create_database(msifile, sr_tables, sizeof(sr_tables) / sizeof(msi_table));
8715
8716     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8717
8718     r = MsiInstallProductA(msifile, NULL);
8719     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8720
8721     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8722     ok(delete_pf("msitest\\cabout\\new", FALSE), "Directory not created\n");
8723     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8724     ok(delete_pf("msitest\\cabout", FALSE), "Directory not created\n");
8725     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8726     ok(delete_pf("msitest\\changed", FALSE), "Directory not created\n");
8727     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8728     ok(delete_pf("msitest\\first", FALSE), "Directory not created\n");
8729     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8730     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
8731     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8732     ok(delete_pf("msitest", FALSE), "Directory not created\n");
8733
8734     delete_test_files();
8735 }
8736
8737 static void test_register_font(void)
8738 {
8739     static const char regfont1[] = "Software\\Microsoft\\Windows NT\\CurrentVersion\\Fonts";
8740     static const char regfont2[] = "Software\\Microsoft\\Windows\\CurrentVersion\\Fonts";
8741     LONG ret;
8742     HKEY key;
8743     UINT r;
8744
8745     create_test_files();
8746     create_file("msitest\\font.ttf", 1000);
8747     create_database(msifile, font_tables, sizeof(font_tables) / sizeof(msi_table));
8748
8749     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8750
8751     r = MsiInstallProductA(msifile, NULL);
8752     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8753
8754     ret = RegOpenKeyA(HKEY_LOCAL_MACHINE, regfont1, &key);
8755     if (ret)
8756         RegOpenKeyA(HKEY_LOCAL_MACHINE, regfont2, &key);
8757
8758     ret = RegQueryValueExA(key, "msi test font", NULL, NULL, NULL, NULL);
8759     ok(ret != ERROR_FILE_NOT_FOUND, "unexpected result %d\n", ret);
8760
8761     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8762     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8763
8764     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
8765
8766     ret = RegQueryValueExA(key, "msi test font", NULL, NULL, NULL, NULL);
8767     ok(ret == ERROR_FILE_NOT_FOUND, "unexpected result %d\n", ret);
8768
8769     RegDeleteValueA(key, "msi test font");
8770     RegCloseKey(key);
8771     DeleteFileA("msitest\\font.ttf");
8772     delete_test_files();
8773 }
8774
8775 static void test_validate_product_id(void)
8776 {
8777     UINT r;
8778
8779     create_test_files();
8780     create_database(msifile, vp_tables, sizeof(vp_tables) / sizeof(msi_table));
8781
8782     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8783
8784     r = MsiInstallProductA(msifile, NULL);
8785     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8786
8787     r = MsiInstallProductA(msifile, "SET_PRODUCT_ID=1");
8788     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8789
8790     r = MsiInstallProductA(msifile, "SET_PRODUCT_ID=2");
8791     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8792
8793     r = MsiInstallProductA(msifile, "PIDKEY=123-1234567");
8794     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8795
8796     ok(delete_pf("msitest\\cabout\\new\\five.txt", TRUE), "File not installed\n");
8797     ok(delete_pf("msitest\\cabout\\new", FALSE), "Directory not created\n");
8798     ok(delete_pf("msitest\\cabout\\four.txt", TRUE), "File not installed\n");
8799     ok(delete_pf("msitest\\cabout", FALSE), "Directory not created\n");
8800     ok(delete_pf("msitest\\changed\\three.txt", TRUE), "File not installed\n");
8801     ok(delete_pf("msitest\\changed", FALSE), "Directory not created\n");
8802     ok(delete_pf("msitest\\first\\two.txt", TRUE), "File not installed\n");
8803     ok(delete_pf("msitest\\first", FALSE), "Directory not created\n");
8804     ok(delete_pf("msitest\\filename", TRUE), "File not installed\n");
8805     ok(delete_pf("msitest\\one.txt", TRUE), "File not installed\n");
8806     ok(delete_pf("msitest\\service.exe", TRUE), "File not installed\n");
8807     ok(delete_pf("msitest", FALSE), "Directory not created\n");
8808
8809     delete_test_files();
8810 }
8811
8812 static void test_install_remove_odbc(void)
8813 {
8814     UINT r;
8815
8816     create_test_files();
8817     create_file("msitest\\ODBCdriver.dll", 1000);
8818     create_file("msitest\\ODBCdriver2.dll", 1000);
8819     create_file("msitest\\ODBCtranslator.dll", 1000);
8820     create_file("msitest\\ODBCtranslator2.dll", 1000);
8821     create_file("msitest\\ODBCsetup.dll", 1000);
8822     create_database(msifile, odbc_tables, sizeof(odbc_tables) / sizeof(msi_table));
8823
8824     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8825
8826     r = MsiInstallProductA(msifile, NULL);
8827     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8828
8829     ok(pf_exists("msitest\\ODBCdriver.dll"), "file not created\n");
8830     ok(pf_exists("msitest\\ODBCdriver2.dll"), "file not created\n");
8831     ok(pf_exists("msitest\\ODBCtranslator.dll"), "file not created\n");
8832     ok(pf_exists("msitest\\ODBCtranslator2.dll"), "file not created\n");
8833     ok(pf_exists("msitest\\ODBCsetup.dll"), "file not created\n");
8834
8835     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8836     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8837
8838     ok(!delete_pf("msitest\\ODBCdriver.dll", TRUE), "file not removed\n");
8839     ok(!delete_pf("msitest\\ODBCdriver2.dll", TRUE), "file not removed\n");
8840     ok(!delete_pf("msitest\\ODBCtranslator.dll", TRUE), "file not removed\n");
8841     ok(!delete_pf("msitest\\ODBCtranslator2.dll", TRUE), "file not removed\n");
8842     ok(!delete_pf("msitest\\ODBCsetup.dll", TRUE), "file not removed\n");
8843     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
8844
8845     DeleteFileA("msitest\\ODBCdriver.dll");
8846     DeleteFileA("msitest\\ODBCdriver2.dll");
8847     DeleteFileA("msitest\\ODBCtranslator.dll");
8848     DeleteFileA("msitest\\ODBCtranslator2.dll");
8849     DeleteFileA("msitest\\ODBCsetup.dll");
8850     delete_test_files();
8851 }
8852
8853 static void test_register_typelib(void)
8854 {
8855     UINT r;
8856
8857     create_test_files();
8858     create_file("msitest\\typelib.dll", 1000);
8859     create_database(msifile, tl_tables, sizeof(tl_tables) / sizeof(msi_table));
8860
8861     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8862
8863     r = MsiInstallProductA(msifile, "REGISTER_TYPELIB=1");
8864     ok(r == ERROR_INSTALL_FAILURE, "Expected ERROR_INSTALL_FAILURE, got %u\n", r);
8865
8866     r = MsiInstallProductA(msifile, NULL);
8867     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8868
8869     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8870     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8871
8872     ok(!delete_pf("msitest\\typelib.dll", TRUE), "file not removed\n");
8873     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
8874
8875     DeleteFileA("msitest\\typelib.dll");
8876     delete_test_files();
8877 }
8878
8879 static void test_create_remove_shortcut(void)
8880 {
8881     UINT r;
8882
8883     create_test_files();
8884     create_file("msitest\\target.txt", 1000);
8885     create_database(msifile, crs_tables, sizeof(crs_tables) / sizeof(msi_table));
8886
8887     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8888
8889     r = MsiInstallProductA(msifile, NULL);
8890     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8891
8892     ok(pf_exists("msitest\\target.txt"), "file not created\n");
8893     ok(pf_exists("msitest\\shortcut.lnk"), "file not created\n");
8894
8895     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8896     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8897
8898     ok(!delete_pf("msitest\\shortcut.lnk", TRUE), "file not removed\n");
8899     ok(!delete_pf("msitest\\target.txt", TRUE), "file not removed\n");
8900     todo_wine ok(!delete_pf("msitest", FALSE), "directory not removed\n");
8901
8902     DeleteFileA("msitest\\target.txt");
8903     delete_test_files();
8904 }
8905
8906 static void test_publish_components(void)
8907 {
8908     static char keypath[] =
8909         "Software\\Microsoft\\Installer\\Components\\0CBCFA296AC907244845745CEEB2F8AA";
8910
8911     UINT r;
8912     LONG res;
8913     HKEY key;
8914
8915     create_test_files();
8916     create_file("msitest\\english.txt", 1000);
8917     create_database(msifile, pub_tables, sizeof(pub_tables) / sizeof(msi_table));
8918
8919     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8920
8921     r = MsiInstallProductA(msifile, NULL);
8922     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8923
8924     res = RegOpenKeyA(HKEY_CURRENT_USER, keypath, &key);
8925     ok(res == ERROR_SUCCESS, "components key not created %d\n", res);
8926
8927     res = RegQueryValueExA(key, "english.txt", NULL, NULL, NULL, NULL);
8928     ok(res == ERROR_SUCCESS, "value not found %d\n", res);
8929     RegCloseKey(key);
8930
8931     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8932     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8933
8934     res = RegOpenKeyA(HKEY_CURRENT_USER, keypath, &key);
8935     ok(res == ERROR_FILE_NOT_FOUND, "unexpected result %d\n", res);
8936
8937     ok(!delete_pf("msitest\\english.txt", TRUE), "file not removed\n");
8938     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
8939
8940     DeleteFileA("msitest\\english.txt");
8941     delete_test_files();
8942 }
8943
8944 static void test_remove_duplicate_files(void)
8945 {
8946     UINT r;
8947
8948     create_test_files();
8949     create_file("msitest\\original.txt", 1000);
8950     create_file("msitest\\original2.txt", 1000);
8951     create_file("msitest\\original3.txt", 1000);
8952     create_database(msifile, rd_tables, sizeof(rd_tables) / sizeof(msi_table));
8953
8954     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8955
8956     r = MsiInstallProductA(msifile, NULL);
8957     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8958
8959     ok(pf_exists("msitest\\original.txt"), "file not created\n");
8960     ok(pf_exists("msitest\\original2.txt"), "file not created\n");
8961     ok(!pf_exists("msitest\\original3.txt"), "file created\n");
8962     ok(pf_exists("msitest\\duplicate.txt"), "file not created\n");
8963     ok(!pf_exists("msitest\\duplicate2.txt"), "file created\n");
8964
8965     r = MsiInstallProductA(msifile, "REMOVE=ALL");
8966     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
8967
8968     ok(delete_pf("msitest\\original.txt", TRUE), "file removed\n");
8969     ok(!delete_pf("msitest\\original2.txt", TRUE), "file not removed\n");
8970     ok(!delete_pf("msitest\\original3.txt", TRUE), "file not removed\n");
8971     ok(!delete_pf("msitest\\duplicate.txt", TRUE), "file not removed\n");
8972     ok(!delete_pf("msitest\\duplicate2.txt", TRUE), "file not removed\n");
8973     ok(delete_pf("msitest", FALSE), "directory removed\n");
8974
8975     DeleteFileA("msitest\\original.txt");
8976     DeleteFileA("msitest\\original2.txt");
8977     DeleteFileA("msitest\\original3.txt");
8978     delete_test_files();
8979 }
8980
8981 static void test_remove_registry_values(void)
8982 {
8983     UINT r;
8984     LONG res;
8985     HKEY key;
8986
8987     create_test_files();
8988     create_file("msitest\\registry.txt", 1000);
8989     create_database(msifile, rrv_tables, sizeof(rrv_tables) / sizeof(msi_table));
8990
8991     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
8992
8993     RegCreateKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\key1", &key);
8994     RegSetValueExA(key, "value1", 0, REG_SZ, (const BYTE *)"1", 2);
8995     RegCloseKey(key);
8996
8997     RegCreateKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\key2", &key);
8998     RegSetValueExA(key, "value2", 0, REG_SZ, (const BYTE *)"2", 2);
8999     RegCloseKey(key);
9000
9001     RegCreateKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\keyA", &key);
9002     RegSetValueExA(key, "", 0, REG_SZ, (const BYTE *)"default", 8);
9003     RegSetValueExA(key, "valueA", 0, REG_SZ, (const BYTE *)"A", 2);
9004     RegSetValueExA(key, "valueB", 0, REG_SZ, (const BYTE *)"B", 2);
9005     RegCloseKey(key);
9006
9007     RegCreateKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\keyB", &key);
9008     RegSetValueExA(key, "", 0, REG_SZ, (const BYTE *)"default", 8);
9009     RegSetValueExA(key, "valueB", 0, REG_SZ, (const BYTE *)"B", 2);
9010     RegCloseKey(key);
9011
9012     r = MsiInstallProductA(msifile, NULL);
9013     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9014
9015     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\key1", &key);
9016     ok(res == ERROR_SUCCESS, "key removed\n");
9017     RegCloseKey(key);
9018
9019     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\key2", &key);
9020     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9021
9022     res = RegCreateKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\key2", &key);
9023     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
9024     RegCloseKey(key);
9025
9026     r = MsiInstallProductA(msifile, "REMOVE=ALL");
9027     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9028
9029     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\key1", &key);
9030     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9031
9032     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\key2", &key);
9033     ok(res == ERROR_SUCCESS, "key removed\n");
9034     RegCloseKey(key);
9035
9036     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\keyA", &key);
9037     ok(res == ERROR_SUCCESS, "key removed\n");
9038     RegCloseKey(key);
9039
9040     res = RegOpenKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\keyB", &key);
9041     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9042
9043     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\keyA");
9044     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine\\key2");
9045     RegDeleteKeyA(HKEY_LOCAL_MACHINE, "Software\\Wine");
9046
9047     ok(!delete_pf("msitest\\registry.txt", TRUE), "file not removed\n");
9048     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
9049
9050     DeleteFileA("msitest\\registry.txt");
9051     delete_test_files();
9052 }
9053
9054 static void test_find_related_products(void)
9055 {
9056     UINT r;
9057
9058     create_test_files();
9059     create_file("msitest\\product.txt", 1000);
9060     create_database(msifile, frp_tables, sizeof(frp_tables) / sizeof(msi_table));
9061
9062     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
9063
9064     r = MsiInstallProductA(msifile, NULL);
9065     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9066
9067     /* install again, so it finds the upgrade code */
9068     r = MsiInstallProductA(msifile, NULL);
9069     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9070
9071     r = MsiInstallProductA(msifile, "REMOVE=ALL");
9072     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9073
9074     ok(!delete_pf("msitest\\product.txt", TRUE), "file not removed\n");
9075     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
9076
9077     DeleteFileA("msitest\\product.txt");
9078     delete_test_files();
9079 }
9080
9081 static void test_remove_ini_values(void)
9082 {
9083     UINT r;
9084     DWORD len;
9085     char inifile[MAX_PATH], buf[0x10];
9086     HANDLE file;
9087     BOOL ret;
9088
9089     create_test_files();
9090     create_file("msitest\\inifile.txt", 1000);
9091     create_database(msifile, riv_tables, sizeof(riv_tables) / sizeof(msi_table));
9092
9093     lstrcpyA(inifile, PROG_FILES_DIR);
9094     lstrcatA(inifile, "\\msitest");
9095     CreateDirectoryA(inifile, NULL);
9096     lstrcatA(inifile, "\\test.ini");
9097     file = CreateFileA(inifile, GENERIC_WRITE|GENERIC_READ, 0, NULL, CREATE_ALWAYS, 0, NULL);
9098     CloseHandle(file);
9099
9100     ret = WritePrivateProfileStringA("section1", "key1", "value1", inifile);
9101     ok(ret, "failed to write profile string %u\n", GetLastError());
9102
9103     ret = WritePrivateProfileStringA("sectionA", "keyA", "valueA", inifile);
9104     ok(ret, "failed to write profile string %u\n", GetLastError());
9105
9106     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
9107
9108     r = MsiInstallProductA(msifile, NULL);
9109     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9110
9111     len = GetPrivateProfileStringA("section1", "key1", NULL, buf, sizeof(buf), inifile);
9112     ok(len == 6, "got %u expected 6\n", len);
9113
9114     len = GetPrivateProfileStringA("sectionA", "keyA", NULL, buf, sizeof(buf), inifile);
9115     ok(!len, "got %u expected 0\n", len);
9116
9117     r = MsiInstallProductA(msifile, "REMOVE=ALL");
9118     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9119
9120     len = GetPrivateProfileStringA("section1", "key1", NULL, buf, sizeof(buf), inifile);
9121     ok(!len, "got %u expected 0\n", len);
9122
9123     len = GetPrivateProfileStringA("sectionA", "keyA", NULL, buf, sizeof(buf), inifile);
9124     ok(!len, "got %u expected 0\n", len);
9125
9126     todo_wine ok(!delete_pf("msitest\\test.ini", TRUE), "file removed\n");
9127     ok(!delete_pf("msitest\\inifile.txt", TRUE), "file not removed\n");
9128     ok(delete_pf("msitest", FALSE), "directory removed\n");
9129
9130     DeleteFileA("msitest\\inifile.txt");
9131     delete_test_files();
9132 }
9133
9134 static void test_remove_env_strings(void)
9135 {
9136     UINT r;
9137     LONG res;
9138     HKEY key;
9139     DWORD type, size;
9140     char buffer[0x10];
9141
9142     if (on_win9x)
9143     {
9144         win_skip("Environment variables are handled differently on win9x and winme\n");
9145         return;
9146     }
9147
9148     create_test_files();
9149     create_file("msitest\\envvar.txt", 1000);
9150     create_database(msifile, res_tables, sizeof(res_tables) / sizeof(msi_table));
9151
9152     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
9153
9154     res = RegOpenKeyA(HKEY_CURRENT_USER, "Environment", &key);
9155     ok(!res, "failed to open environment key %d\n", res);
9156
9157     RegSetValueExA(key, "MSITESTVAR1", 0, REG_SZ, (const BYTE *)"1", 2);
9158     RegSetValueExA(key, "MSITESTVAR2", 0, REG_SZ, (const BYTE *)"1", 2);
9159     RegSetValueExA(key, "MSITESTVAR3", 0, REG_SZ, (const BYTE *)"1", 2);
9160     RegSetValueExA(key, "MSITESTVAR4", 0, REG_SZ, (const BYTE *)"1", 2);
9161     RegSetValueExA(key, "MSITESTVAR5", 0, REG_SZ, (const BYTE *)"1", 2);
9162
9163     RegCloseKey(key);
9164
9165     r = MsiInstallProductA(msifile, NULL);
9166     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9167
9168     res = RegOpenKeyA(HKEY_CURRENT_USER, "Environment", &key);
9169     ok(!res, "failed to open environment key %d\n", res);
9170
9171     type = REG_NONE;
9172     buffer[0] = 0;
9173     size = sizeof(buffer);
9174     res = RegQueryValueExA(key, "MSITESTVAR1", NULL, &type, (LPBYTE)buffer, &size);
9175     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
9176     ok(type == REG_SZ, "expected REG_SZ, got %u\n", type);
9177     ok(!lstrcmp(buffer, "1"), "expected \"1\", got \"%s\"\n", buffer);
9178
9179     type = REG_NONE;
9180     buffer[0] = 0;
9181     size = sizeof(buffer);
9182     res = RegQueryValueExA(key, "MSITESTVAR2", NULL, &type, (LPBYTE)buffer, &size);
9183     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
9184     ok(type == REG_SZ, "expected REG_SZ, got %u\n", type);
9185     ok(!lstrcmp(buffer, "1"), "expected \"1\", got \"%s\"\n", buffer);
9186
9187     type = REG_NONE;
9188     buffer[0] = 0;
9189     size = sizeof(buffer);
9190     res = RegQueryValueExA(key, "MSITESTVAR3", NULL, &type, (LPBYTE)buffer, &size);
9191     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
9192     ok(type == REG_SZ, "expected REG_SZ, got %u\n", type);
9193     ok(!lstrcmp(buffer, "1"), "expected \"1\", got \"%s\"\n", buffer);
9194
9195     type = REG_NONE;
9196     buffer[0] = 0;
9197     size = sizeof(buffer);
9198     res = RegQueryValueExA(key, "MSITESTVAR4", NULL, &type, (LPBYTE)buffer, &size);
9199     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
9200     ok(type == REG_SZ, "expected REG_SZ, got %u\n", type);
9201     ok(!lstrcmp(buffer, "1"), "expected \"1\", got \"%s\"\n", buffer);
9202
9203     type = REG_NONE;
9204     buffer[0] = 0;
9205     size = sizeof(buffer);
9206     res = RegQueryValueExA(key, "MSITESTVAR5", NULL, &type, (LPBYTE)buffer, &size);
9207     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
9208     ok(type == REG_SZ, "expected REG_SZ, got %u\n", type);
9209     ok(!lstrcmp(buffer, "1"), "expected \"1\", got \"%s\"\n", buffer);
9210
9211     RegCloseKey(key);
9212
9213     r = MsiInstallProductA(msifile, "REMOVE=ALL");
9214     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9215
9216     res = RegOpenKeyA(HKEY_CURRENT_USER, "Environment", &key);
9217     ok(!res, "failed to open environment key %d\n", res);
9218
9219     res = RegQueryValueExA(key, "MSITESTVAR1", NULL, NULL, NULL, NULL);
9220     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
9221
9222     res = RegQueryValueExA(key, "MSITESTVAR2", NULL, NULL, NULL, NULL);
9223     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
9224
9225     type = REG_NONE;
9226     buffer[0] = 0;
9227     size = sizeof(buffer);
9228     res = RegQueryValueExA(key, "MSITESTVAR3", NULL, &type, (LPBYTE)buffer, &size);
9229     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
9230     ok(type == REG_SZ, "expected REG_SZ, got %u\n", type);
9231     ok(!lstrcmp(buffer, "1"), "expected \"1\", got \"%s\"\n", buffer);
9232     RegDeleteValueA(key, "MSITESTVAR3");
9233
9234     res = RegQueryValueExA(key, "MSITESTVAR4", NULL, NULL, NULL, NULL);
9235     ok(res == ERROR_FILE_NOT_FOUND, "Expected ERROR_FILE_NOT_FOUND, got %d\n", res);
9236
9237     type = REG_NONE;
9238     buffer[0] = 0;
9239     size = sizeof(buffer);
9240     res = RegQueryValueExA(key, "MSITESTVAR5", NULL, &type, (LPBYTE)buffer, &size);
9241     ok(res == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", res);
9242     ok(type == REG_SZ, "expected REG_SZ, got %u\n", type);
9243     ok(!lstrcmp(buffer, "1"), "expected \"1\", got \"%s\"\n", buffer);
9244     RegDeleteValueA(key, "MSITESTVAR5");
9245
9246     RegCloseKey(key);
9247
9248     ok(!delete_pf("msitest\\envvar.txt", TRUE), "file not removed\n");
9249     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
9250
9251     DeleteFileA("msitest\\envvar.txt");
9252     delete_test_files();
9253 }
9254
9255 static void test_register_class_info(void)
9256 {
9257     UINT r;
9258     LONG res;
9259     HKEY hkey;
9260
9261     create_test_files();
9262     create_file("msitest\\class.txt", 1000);
9263     create_database(msifile, rci_tables, sizeof(rci_tables) / sizeof(msi_table));
9264
9265     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
9266
9267     r = MsiInstallProductA(msifile, NULL);
9268     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9269
9270     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "CLSID\\{110913E7-86D1-4BF3-9922-BA103FCDDDFA}", &hkey);
9271     ok(res == ERROR_SUCCESS, "key not created\n");
9272     RegCloseKey(hkey);
9273
9274     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "FileType\\{110913E7-86D1-4BF3-9922-BA103FCDDDFA}", &hkey);
9275     ok(res == ERROR_SUCCESS, "key not created\n");
9276     RegCloseKey(hkey);
9277
9278     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "AppID\\{CFCC3B38-E683-497D-9AB4-CB40AAFE307F}", &hkey);
9279     ok(res == ERROR_SUCCESS, "key not created\n");
9280     RegCloseKey(hkey);
9281
9282     r = MsiInstallProductA(msifile, "REMOVE=ALL");
9283     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9284
9285     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "CLSID\\{110913E7-86D1-4BF3-9922-BA103FCDDDFA}", &hkey);
9286     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9287
9288     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "FileType\\{110913E7-86D1-4BF3-9922-BA103FCDDDFA}", &hkey);
9289     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9290
9291     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "AppID\\{CFCC3B38-E683-497D-9AB4-CB40AAFE307F}", &hkey);
9292     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9293
9294     ok(!delete_pf("msitest\\class.txt", TRUE), "file not removed\n");
9295     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
9296
9297     DeleteFileA("msitest\\class.txt");
9298     delete_test_files();
9299 }
9300
9301 static void test_register_extension_info(void)
9302 {
9303     UINT r;
9304     LONG res;
9305     HKEY hkey;
9306
9307     create_test_files();
9308     create_file("msitest\\extension.txt", 1000);
9309     create_database(msifile, rei_tables, sizeof(rei_tables) / sizeof(msi_table));
9310
9311     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
9312
9313     r = MsiInstallProductA(msifile, NULL);
9314     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9315
9316     res = RegOpenKeyA(HKEY_CLASSES_ROOT, ".extension", &hkey);
9317     ok(res == ERROR_SUCCESS, "key not created\n");
9318     RegCloseKey(hkey);
9319
9320     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "Prog.Id.1\\shell\\Open\\command", &hkey);
9321     ok(res == ERROR_SUCCESS, "key not created\n");
9322     RegCloseKey(hkey);
9323
9324     r = MsiInstallProductA(msifile, "REMOVE=ALL");
9325     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9326
9327     res = RegOpenKeyA(HKEY_CLASSES_ROOT, ".extension", &hkey);
9328     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9329
9330     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "Prog.Id.1", &hkey);
9331     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9332
9333     ok(!delete_pf("msitest\\extension.txt", TRUE), "file not removed\n");
9334     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
9335
9336     DeleteFileA("msitest\\extension.txt");
9337     delete_test_files();
9338 }
9339
9340 static void test_register_mime_info(void)
9341 {
9342     UINT r;
9343     LONG res;
9344     HKEY hkey;
9345
9346     create_test_files();
9347     create_file("msitest\\mime.txt", 1000);
9348     create_database(msifile, rmi_tables, sizeof(rmi_tables) / sizeof(msi_table));
9349
9350     MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
9351
9352     r = MsiInstallProductA(msifile, NULL);
9353     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9354
9355     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "MIME\\Database\\Content Type\\mime/type", &hkey);
9356     ok(res == ERROR_SUCCESS, "key not created\n");
9357     RegCloseKey(hkey);
9358
9359     r = MsiInstallProductA(msifile, "REMOVE=ALL");
9360     ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
9361
9362     res = RegOpenKeyA(HKEY_CLASSES_ROOT, "MIME\\Database\\Content Type\\mime/type", &hkey);
9363     ok(res == ERROR_FILE_NOT_FOUND, "key not removed\n");
9364
9365     ok(!delete_pf("msitest\\mime.txt", TRUE), "file not removed\n");
9366     ok(!delete_pf("msitest", FALSE), "directory not removed\n");
9367
9368     DeleteFileA("msitest\\mime.txt");
9369     delete_test_files();
9370 }
9371
9372 START_TEST(install)
9373 {
9374     DWORD len;
9375     char temp_path[MAX_PATH], prev_path[MAX_PATH], log_file[MAX_PATH];
9376     STATEMGRSTATUS status;
9377     BOOL ret = FALSE;
9378
9379     init_functionpointers();
9380
9381     on_win9x = check_win9x();
9382
9383     GetCurrentDirectoryA(MAX_PATH, prev_path);
9384     GetTempPath(MAX_PATH, temp_path);
9385     SetCurrentDirectoryA(temp_path);
9386
9387     lstrcpyA(CURR_DIR, temp_path);
9388     len = lstrlenA(CURR_DIR);
9389
9390     if(len && (CURR_DIR[len - 1] == '\\'))
9391         CURR_DIR[len - 1] = 0;
9392
9393     get_program_files_dir(PROG_FILES_DIR, COMMON_FILES_DIR);
9394
9395     /* Create a restore point ourselves so we circumvent the multitude of restore points
9396      * that would have been created by all the installation and removal tests.
9397      */
9398     if (pSRSetRestorePointA)
9399     {
9400         memset(&status, 0, sizeof(status));
9401         ret = notify_system_change(BEGIN_NESTED_SYSTEM_CHANGE, &status);
9402     }
9403
9404     /* Create only one log file and don't append. We have to pass something
9405      * for the log mode for this to work. The logfile needs to have an absolute
9406      * path otherwise we still end up with some extra logfiles as some tests
9407      * change the current directory.
9408      */
9409     lstrcpyA(log_file, temp_path);
9410     lstrcatA(log_file, "\\msitest.log");
9411     MsiEnableLogA(INSTALLLOGMODE_FATALEXIT, log_file, 0);
9412
9413     test_MsiInstallProduct();
9414     test_MsiSetComponentState();
9415     test_packagecoltypes();
9416     test_continuouscabs();
9417     test_caborder();
9418     test_mixedmedia();
9419     test_samesequence();
9420     test_uiLevelFlags();
9421     test_readonlyfile();
9422     test_readonlyfile_cab();
9423     test_setdirproperty();
9424     test_cabisextracted();
9425     test_concurrentinstall();
9426     test_setpropertyfolder();
9427     test_publish_registerproduct();
9428     test_publish_publishproduct();
9429     test_publish_publishfeatures();
9430     test_publish_registeruser();
9431     test_publish_processcomponents();
9432     test_publish();
9433     test_publishsourcelist();
9434     test_transformprop();
9435     test_currentworkingdir();
9436     test_admin();
9437     test_adminprops();
9438     test_removefiles();
9439     test_movefiles();
9440     test_missingcab();
9441     test_duplicatefiles();
9442     test_writeregistryvalues();
9443     test_sourcefolder();
9444     test_customaction51();
9445     test_installstate();
9446     test_sourcepath();
9447     test_MsiConfigureProductEx();
9448     test_missingcomponent();
9449     test_sourcedirprop();
9450     test_adminimage();
9451     test_propcase();
9452     test_int_widths();
9453     test_shortcut();
9454     test_envvar();
9455     test_lastusedsource();
9456     test_preselected();
9457     test_installed_prop();
9458     test_file_in_use();
9459     test_file_in_use_cab();
9460     test_MsiSetExternalUI();
9461     test_allusers_prop();
9462     test_feature_override();
9463     test_create_folder();
9464     test_remove_folder();
9465     test_start_services();
9466     test_delete_services();
9467     test_self_registration();
9468     test_register_font();
9469     test_validate_product_id();
9470     test_install_remove_odbc();
9471     test_register_typelib();
9472     test_create_remove_shortcut();
9473     test_publish_components();
9474     test_remove_duplicate_files();
9475     test_remove_registry_values();
9476     test_find_related_products();
9477     test_remove_ini_values();
9478     test_remove_env_strings();
9479     test_register_class_info();
9480     test_register_extension_info();
9481     test_register_mime_info();
9482
9483     DeleteFileA(log_file);
9484
9485     if (pSRSetRestorePointA && ret)
9486     {
9487         ret = notify_system_change(END_NESTED_SYSTEM_CHANGE, &status);
9488         if (ret)
9489             remove_restore_point(status.llSequenceNumber);
9490     }
9491     FreeLibrary(hsrclient);
9492
9493     SetCurrentDirectoryA(prev_path);
9494 }