ReactOS 0.4.17-dev-966-gf06eace
msiexec.c
Go to the documentation of this file.
1/*
2 * msiexec.exe implementation
3 *
4 * Copyright 2004 Vincent Béron
5 * Copyright 2005 Mike McCormack
6 *
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
11 *
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
16 *
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
20 */
21
22#define WIN32_LEAN_AND_MEAN
23
24#include <windows.h>
25#include <commctrl.h>
26#include <msi.h>
27#include <winsvc.h>
28#include <objbase.h>
29
30#include "wine/debug.h"
31#include "msiexec_internal.h"
32
33#include "initguid.h"
34DEFINE_GUID(GUID_NULL,0,0,0,0,0,0,0,0,0,0,0);
35
37
40
41DWORD DoService(void);
42static BOOL silent;
43
44struct string_list
45{
46 struct string_list *next;
48};
49
50void report_error(const char* msg, ...)
51{
52 char buffer[2048];
53 va_list va_args;
54
55 va_start(va_args, msg);
56 vsnprintf(buffer, sizeof(buffer), msg, va_args);
57 va_end(va_args);
58
59 if (silent)
60 MESSAGE("%s", buffer);
61 else
62 MsiMessageBoxA(NULL, buffer, "MsiExec", 0, GetUserDefaultLangID(), 0);
63}
64
65static void ShowUsage(int ExitCode)
66{
67 WCHAR msiexec_version[40];
69 LPWSTR msi_res;
70 LPWSTR msiexec_help;
71 HMODULE hmsi = GetModuleHandleA("msi.dll");
72 DWORD len;
73 DWORD res;
74
75 /* MsiGetFileVersion need the full path */
76 *filename = 0;
78 if (!res)
79 WINE_ERR("GetModuleFileName failed: %ld\n", GetLastError());
80
81 len = ARRAY_SIZE(msiexec_version);
82 *msiexec_version = 0;
83 res = MsiGetFileVersionW(filename, msiexec_version, &len, NULL, NULL);
84 if (res)
85 WINE_ERR("MsiGetFileVersion failed with %ld\n", res);
86
87 /* Return the length of the resource.
88 No typo: The LPWSTR parameter must be a LPWSTR * for this mode */
89 len = LoadStringW(hmsi, 10, (LPWSTR) &msi_res, 0);
90
91 msi_res = malloc((len + 1) * sizeof(WCHAR));
92 msiexec_help = malloc((len + 1) * sizeof(WCHAR) + sizeof(msiexec_version));
93 if (msi_res && msiexec_help) {
94 *msi_res = 0;
95 LoadStringW(hmsi, 10, msi_res, len + 1);
96
97 swprintf(msiexec_help, len + 1 + ARRAY_SIZE(msiexec_version), msi_res, msiexec_version);
98 MsiMessageBoxW(0, msiexec_help, NULL, 0, GetUserDefaultLangID(), 0);
99 }
100 free(msi_res);
101 free(msiexec_help);
102 ExitProcess(ExitCode);
103}
104
106{
107 GUID ProductCode;
108
109 if(lstrlenW(str) != 38)
110 return FALSE;
111 return ( (CLSIDFromString(str, &ProductCode) == NOERROR) );
112
113}
114
116{
117 struct string_list *entry;
118
120 if(!entry)
121 {
122 WINE_ERR("Out of memory!\n");
123 ExitProcess(1);
124 }
125 lstrcpyW(entry->str, str);
126 entry->next = NULL;
127
128 /*
129 * Ignoring o(n^2) time complexity to add n strings for simplicity,
130 * add the string to the end of the list to preserve the order.
131 */
132 while( *list )
133 list = &(*list)->next;
134 *list = entry;
135}
136
137static LPWSTR build_properties(struct string_list *property_list)
138{
139 struct string_list *list;
140 LPWSTR ret, p, value;
141 DWORD len;
142 BOOL needs_quote;
143
144 if(!property_list)
145 return NULL;
146
147 /* count the space we need */
148 len = 1;
149 for(list = property_list; list; list = list->next)
150 len += lstrlenW(list->str) + 3;
151
152 ret = malloc(len * sizeof(WCHAR));
153
154 /* add a space before each string, and quote the value */
155 p = ret;
156 for(list = property_list; list; list = list->next)
157 {
158 value = wcschr(list->str,'=');
159 if(!value)
160 continue;
161 len = value - list->str;
162 *p++ = ' ';
163 memcpy(p, list->str, len * sizeof(WCHAR));
164 p += len;
165 *p++ = '=';
166
167 /* check if the value contains spaces and maybe quote it */
168 value++;
169 needs_quote = *value != '"' && wcschr(value, ' ');
170 if(needs_quote)
171 *p++ = '"';
172 len = lstrlenW(value);
173 memcpy(p, value, len * sizeof(WCHAR));
174 p += len;
175 if(needs_quote)
176 *p++ = '"';
177 }
178 *p = 0;
179
180 WINE_TRACE("properties -> %s\n", wine_dbgstr_w(ret) );
181
182 return ret;
183}
184
185static LPWSTR build_transforms(struct string_list *transform_list)
186{
187 struct string_list *list;
188 LPWSTR ret, p;
189 DWORD len;
190
191 /* count the space we need */
192 len = 1;
193 for(list = transform_list; list; list = list->next)
194 len += lstrlenW(list->str) + 1;
195
196 ret = malloc(len * sizeof(WCHAR));
197
198 /* add all the transforms with a semicolon between each one */
199 p = ret;
200 for(list = transform_list; list; list = list->next)
201 {
202 len = lstrlenW(list->str);
203 lstrcpynW(p, list->str, len );
204 p += len;
205 if(list->next)
206 *p++ = ';';
207 }
208 *p = 0;
209
210 return ret;
211}
212
214{
215 DWORD ret = 0;
216 while(*str >= '0' && *str <= '9')
217 {
218 ret *= 10;
219 ret += (*str - '0');
220 str++;
221 }
222 return ret;
223}
224
225/* str1 is the same as str2, ignoring case */
227{
228 DWORD len, ret;
229 LPWSTR strW;
230
231 len = MultiByteToWideChar( CP_ACP, 0, str2, -1, NULL, 0);
232 if( !len )
233 return FALSE;
234 if( lstrlenW(str1) != (len-1) )
235 return FALSE;
236 strW = malloc(sizeof(WCHAR) * len);
239 free(strW);
240 return (ret == CSTR_EQUAL);
241}
242
243/* prefix is hyphen or dash, and str1 is the same as str2, ignoring case */
245{
246 if (str1[0] != '/' && str1[0] != '-')
247 return FALSE;
248
249 /* skip over the hyphen or slash */
250 return msi_strequal(str1 + 1, str2);
251}
252
253/* str2 is at the beginning of str1, ignoring case */
255{
256 DWORD len, ret;
257 LPWSTR strW;
258
259 len = MultiByteToWideChar( CP_ACP, 0, str2, -1, NULL, 0);
260 if( !len )
261 return FALSE;
262 if( lstrlenW(str1) < (len-1) )
263 return FALSE;
264 strW = malloc(sizeof(WCHAR) * len);
267 free(strW);
268 return (ret == CSTR_EQUAL);
269}
270
271/* prefix is hyphen or dash, and str2 is at the beginning of str1, ignoring case */
273{
274 if (str1[0] != '/' && str1[0] != '-')
275 return FALSE;
276
277 /* skip over the hyphen or slash */
278 return msi_strprefix(str1 + 1, str2);
279}
280
281static VOID *LoadProc(LPCWSTR DllName, LPCSTR ProcName, HMODULE* DllHandle)
282{
283 VOID* (*proc)(void);
284
285 *DllHandle = LoadLibraryExW(DllName, NULL, LOAD_WITH_ALTERED_SEARCH_PATH);
286 if(!*DllHandle)
287 {
288 report_error("Unable to load dll %s\n", wine_dbgstr_w(DllName));
289 ExitProcess(1);
290 }
291 proc = (VOID *) GetProcAddress(*DllHandle, ProcName);
292 if(!proc)
293 {
294 report_error("Dll %s does not implement function %s\n",
295 wine_dbgstr_w(DllName), ProcName);
296 FreeLibrary(*DllHandle);
297 ExitProcess(1);
298 }
299
300 return proc;
301}
302
304{
305 HRESULT hr;
306 DLLREGISTERSERVER pfDllRegisterServer = NULL;
307 HMODULE DllHandle = NULL;
308
309 pfDllRegisterServer = LoadProc(DllName, "DllRegisterServer", &DllHandle);
310
311 hr = pfDllRegisterServer();
312 if(FAILED(hr))
313 {
314 report_error("Failed to register dll %s\n", wine_dbgstr_w(DllName));
315 return 1;
316 }
317 MESSAGE("Successfully registered dll %s\n", wine_dbgstr_w(DllName));
318 if(DllHandle)
319 FreeLibrary(DllHandle);
320 return 0;
321}
322
324{
325 HRESULT hr;
326 DLLUNREGISTERSERVER pfDllUnregisterServer = NULL;
327 HMODULE DllHandle = NULL;
328
329 pfDllUnregisterServer = LoadProc(DllName, "DllUnregisterServer", &DllHandle);
330
331 hr = pfDllUnregisterServer();
332 if(FAILED(hr))
333 {
334 report_error("Failed to unregister dll %s\n", wine_dbgstr_w(DllName));
335 return 1;
336 }
337 MESSAGE("Successfully unregistered dll %s\n", wine_dbgstr_w(DllName));
338 if(DllHandle)
339 FreeLibrary(DllHandle);
340 return 0;
341}
342
343static DWORD DoRegServer(void)
344{
345 SC_HANDLE scm, service;
346 WCHAR path[MAX_PATH+12];
347 DWORD len, ret = 0;
348
350 {
351 report_error("Failed to open the service control manager.\n");
352 return 1;
353 }
355 lstrcpyW(path + len, L"\\msiexec /V");
356 if ((service = CreateServiceW(scm, L"MSIServer", L"MSIServer", GENERIC_ALL,
359 {
360 CloseServiceHandle(service);
361 }
363 {
364 report_error("Failed to create MSI service\n");
365 ret = 1;
366 }
368 return ret;
369}
370
372{
373 SC_HANDLE scm, service;
374 DWORD ret = 0;
375
377 {
378 report_error("Failed to open service control manager\n");
379 return 1;
380 }
381 if ((service = OpenServiceW(scm, L"MSIServer", DELETE)))
382 {
383 if (!DeleteService(service))
384 {
385 report_error("Failed to delete MSI service\n");
386 ret = 1;
387 }
388 CloseServiceHandle(service);
389 }
391 {
392 report_error("Failed to open MSI service\n");
393 ret = 1;
394 }
396 return ret;
397}
398
400
402
404{
405 GUID guid = *(GUID *)arg;
406 free(arg);
408}
409
411{
412 GUID guid, *thread_guid;
413 DWORD64 thread64;
414 WCHAR buffer[24];
416 HANDLE pipe;
417 DWORD size;
418
419 TRACE("%s\n", debugstr_w(arg));
420
421 if (!(client_pid = wcstol(arg, NULL, 10)))
422 {
423 ERR("Invalid parameter %s\n", debugstr_w(arg));
424 return 1;
425 }
426
427#ifdef __REACTOS__
428 swprintf(buffer, ARRAY_SIZE(buffer), L"\\\\.\\pipe\\msica_%x_%d", client_pid, (int)(sizeof(void *) * 8));
429#else
430 swprintf(buffer, ARRAY_SIZE(buffer), L"\\\\.\\pipe\\msica_%x_%d", client_pid, sizeof(void *) * 8);
431#endif
433 if (pipe == INVALID_HANDLE_VALUE)
434 {
435 ERR("Failed to create custom action server pipe: %lu\n", GetLastError());
436 return GetLastError();
437 }
438
439 /* We need this to unmarshal streams, and some apps expect it to be present. */
441
442 while (ReadFile(pipe, &guid, sizeof(guid), &size, NULL) && size == sizeof(guid))
443 {
444 if (IsEqualGUID(&guid, &GUID_NULL))
445 {
446 /* package closed; time to shut down */
448 return 0;
449 }
450
451 thread_guid = malloc(sizeof(GUID));
452 memcpy(thread_guid, &guid, sizeof(GUID));
453 thread = CreateThread(NULL, 0, custom_action_thread, thread_guid, 0, NULL);
454
455 /* give the thread handle to the client to wait on, since we might have
456 * to run a nested action and can't block during this one */
457 thread64 = (DWORD_PTR)thread;
458 if (!WriteFile(pipe, &thread64, sizeof(thread64), &size, NULL) || size != sizeof(thread64))
459 {
460 ERR("Failed to write to custom action server pipe: %lu\n", GetLastError());
462 return GetLastError();
463 }
464 }
465 ERR("Failed to read from custom action server pipe: %lu\n", GetLastError());
467 return GetLastError();
468}
469
470/*
471 * state machine to break up the command line properly
472 */
473
475{
480
481static int chomp( const WCHAR *in, WCHAR *out )
482{
484 const WCHAR *p;
485 int count = 1;
486 BOOL ignore;
487
488 for (p = in; *p; p++)
489 {
490 ignore = TRUE;
491 switch (state)
492 {
493 case CS_WHITESPACE:
494 switch (*p)
495 {
496 case ' ':
497 break;
498 case '"':
499 state = CS_QUOTE;
500 count++;
501 ignore = FALSE;
502 break;
503 default:
504 count++;
505 ignore = FALSE;
506 state = CS_TOKEN;
507 }
508 break;
509
510 case CS_TOKEN:
511 switch (*p)
512 {
513 case '"':
514 state = CS_QUOTE;
515 ignore = FALSE;
516 break;
517 case ' ':
519 if (out) *out++ = 0;
520 break;
521 default:
522 if (p > in && p[-1] == '"')
523 {
524 if (out) *out++ = 0;
525 count++;
526 }
527 ignore = FALSE;
528 }
529 break;
530
531 case CS_QUOTE:
532 switch (*p)
533 {
534 case '"':
535 state = CS_TOKEN;
536 ignore = FALSE;
537 break;
538 default:
539 ignore = FALSE;
540 }
541 break;
542 }
543 if (!ignore && out) *out++ = *p;
544 }
545 if (out) *out = 0;
546 return count;
547}
548
549static void process_args( WCHAR *cmdline, int *pargc, WCHAR ***pargv )
550{
551 WCHAR **argv, *p;
552 int i, count;
553
554 *pargc = 0;
555 *pargv = NULL;
556
557 count = chomp( cmdline, NULL );
558 if (!(p = malloc( (wcslen(cmdline) + count + 1) * sizeof(WCHAR) )))
559 return;
560
561 count = chomp( cmdline, p );
562 if (!(argv = malloc( (count + 1) * sizeof(WCHAR *) )))
563 {
564 free( p );
565 return;
566 }
567 for (i = 0; i < count; i++)
568 {
569 argv[i] = p;
570 p += lstrlenW( p ) + 1;
571 }
572 argv[i] = NULL;
573
574 *pargc = count;
575 *pargv = argv;
576}
577
578static BOOL process_args_from_reg( const WCHAR *ident, int *pargc, WCHAR ***pargv )
579{
580 LONG r;
581 HKEY hkey;
582 DWORD sz = 0, type = 0;
583 WCHAR *buf;
584 BOOL ret = FALSE;
585
587 L"Software\\Microsoft\\Windows\\CurrentVersion\\Installer\\RunOnceEntries", &hkey);
588 if(r != ERROR_SUCCESS)
589 return FALSE;
590 r = RegQueryValueExW(hkey, ident, 0, &type, 0, &sz);
591 if(r == ERROR_SUCCESS && type == REG_SZ)
592 {
593 int len = lstrlenW( *pargv[0] );
594 if (!(buf = malloc( (len + 1) * sizeof(WCHAR) )))
595 {
596 RegCloseKey( hkey );
597 return FALSE;
598 }
599 memcpy( buf, *pargv[0], len * sizeof(WCHAR) );
600 buf[len++] = ' ';
601 r = RegQueryValueExW(hkey, ident, 0, &type, (LPBYTE)(buf + len), &sz);
602 if( r == ERROR_SUCCESS )
603 {
604 process_args(buf, pargc, pargv);
605 ret = TRUE;
606 }
607 free(buf);
608 }
609 RegCloseKey(hkey);
610 return ret;
611}
612
613static WCHAR *get_path_with_extension(const WCHAR *package_name)
614{
615 static const WCHAR ext[] = L".msi";
616 unsigned int p;
617 WCHAR *path;
618
619 if (!(path = malloc(wcslen(package_name) * sizeof(WCHAR) + sizeof(ext))))
620 {
621 WINE_ERR("No memory.\n");
622 return NULL;
623 }
624
625 lstrcpyW(path, package_name);
626 p = lstrlenW(path);
627 while (p && path[p] != '.' && path[p] != L'\\' && path[p] != '/')
628 --p;
629 if (path[p] == '.')
630 {
631 free(path);
632 return NULL;
633 }
634 lstrcatW(path, ext);
635 return path;
636}
637
639{
640 const WCHAR *ptr = filename;
641 int len = wcslen( filename );
642 WCHAR *ret;
643
644 if (!(ret = malloc( (len + 1) * sizeof(WCHAR) ))) return NULL;
645 if (*ptr == '"')
646 {
647 ptr++;
648 len--;
649 }
650 wcscpy( ret, ptr );
651 if (len && ret[len - 1] == '"') ret[len - 1] = 0;
652 return ret;
653}
654
655int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
656{
657 int i;
658 BOOL FunctionInstall = FALSE;
659 BOOL FunctionInstallAdmin = FALSE;
660 BOOL FunctionRepair = FALSE;
661 BOOL FunctionAdvertise = FALSE;
662 BOOL FunctionPatch = FALSE;
663 BOOL FunctionDllRegisterServer = FALSE;
664 BOOL FunctionDllUnregisterServer = FALSE;
665 BOOL FunctionRegServer = FALSE;
666 BOOL FunctionUnregServer = FALSE;
667 BOOL FunctionServer = FALSE;
668 BOOL FunctionUnknown = FALSE;
669
670 LPWSTR PackageName = NULL;
671 LPWSTR Properties = NULL;
672 struct string_list *property_list = NULL;
673
674 DWORD RepairMode = 0;
675
676 DWORD_PTR AdvertiseMode = 0;
677 struct string_list *transform_list = NULL;
678 LANGID Language = 0;
679
680 DWORD LogMode = 0;
681 DWORD LogAttributes = 0;
682
683 LPWSTR PatchFileName = NULL;
684 INSTALLTYPE InstallType = INSTALLTYPE_DEFAULT;
685
686 INSTALLUILEVEL InstallUILevel = INSTALLUILEVEL_FULL;
687
688 LPWSTR DllName = NULL;
689 DWORD ReturnCode;
690 int argc;
691 LPWSTR *argvW = NULL;
692 WCHAR *path, *package_unquoted = NULL, *dll_unquoted = NULL, *patch_unquoted = NULL, *log_unquoted;
693
695
696 /* parse the command line */
697 process_args( GetCommandLineW(), &argc, &argvW );
698
699 /*
700 * If the args begin with /@ IDENT then we need to load the real
701 * command line out of the RunOnceEntries key in the registry.
702 * We do that before starting to process the real commandline,
703 * then overwrite the commandline again.
704 */
705 if(argc>1 && msi_option_equal(argvW[1], "@"))
706 {
707 if(!process_args_from_reg( argvW[2], &argc, &argvW ))
708 return 1;
709 }
710
711 if (argc == 3 && msi_option_equal(argvW[1], "Embedding"))
712 return custom_action_server(argvW[2]);
713
714 for(i = 1; i < argc; i++)
715 {
716 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
717
718 if (msi_option_equal(argvW[i], "regserver"))
719 {
720 FunctionRegServer = TRUE;
721 }
722 else if (msi_option_equal(argvW[i], "unregserver") || msi_option_equal(argvW[i], "unregister")
723 || msi_option_equal(argvW[i], "unreg"))
724 {
725 FunctionUnregServer = TRUE;
726 }
727 else if(msi_option_prefix(argvW[i], "i") || msi_option_prefix(argvW[i], "package"))
728 {
729 LPWSTR argvWi = argvW[i];
730 int argLen = (msi_option_prefix(argvW[i], "i") ? 2 : 8);
731 FunctionInstall = TRUE;
732 if(lstrlenW(argvW[i]) > argLen)
733 argvWi += argLen;
734 else
735 {
736 i++;
737 if(i >= argc)
738 ShowUsage(1);
739 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
740 argvWi = argvW[i];
741 }
742 PackageName = argvWi;
743 }
744 else if(msi_option_equal(argvW[i], "a"))
745 {
746 FunctionInstall = TRUE;
747 FunctionInstallAdmin = TRUE;
748 InstallType = INSTALLTYPE_NETWORK_IMAGE;
749 i++;
750 if(i >= argc)
751 ShowUsage(1);
752 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
753 PackageName = argvW[i];
754 StringListAppend(&property_list, L"ACTION=ADMIN");
755 }
756 else if(msi_option_prefix(argvW[i], "f"))
757 {
758 int j;
759 int len = lstrlenW(argvW[i]);
760 FunctionRepair = TRUE;
761 for(j = 2; j < len; j++)
762 {
763 switch(argvW[i][j])
764 {
765 case 'P':
766 case 'p':
767 RepairMode |= REINSTALLMODE_FILEMISSING;
768 break;
769 case 'O':
770 case 'o':
771 RepairMode |= REINSTALLMODE_FILEOLDERVERSION;
772 break;
773 case 'E':
774 case 'e':
775 RepairMode |= REINSTALLMODE_FILEEQUALVERSION;
776 break;
777 case 'D':
778 case 'd':
779 RepairMode |= REINSTALLMODE_FILEEXACT;
780 break;
781 case 'C':
782 case 'c':
783 RepairMode |= REINSTALLMODE_FILEVERIFY;
784 break;
785 case 'A':
786 case 'a':
787 RepairMode |= REINSTALLMODE_FILEREPLACE;
788 break;
789 case 'U':
790 case 'u':
791 RepairMode |= REINSTALLMODE_USERDATA;
792 break;
793 case 'M':
794 case 'm':
795 RepairMode |= REINSTALLMODE_MACHINEDATA;
796 break;
797 case 'S':
798 case 's':
799 RepairMode |= REINSTALLMODE_SHORTCUT;
800 break;
801 case 'V':
802 case 'v':
803 RepairMode |= REINSTALLMODE_PACKAGE;
804 break;
805 default:
806 report_error("Unknown option \"%c\" in Repair mode\n", argvW[i][j]);
807 break;
808 }
809 }
810 if(len == 2)
811 {
812 RepairMode = REINSTALLMODE_FILEMISSING |
817 }
818 i++;
819 if(i >= argc)
820 ShowUsage(1);
821 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
822 PackageName = argvW[i];
823 }
824 else if(msi_option_prefix(argvW[i], "x") || msi_option_equal(argvW[i], "uninstall"))
825 {
826 FunctionInstall = TRUE;
827 if(msi_option_prefix(argvW[i], "x")) PackageName = argvW[i]+2;
828 if(!PackageName || !PackageName[0])
829 {
830 i++;
831 if (i >= argc)
832 ShowUsage(1);
833 PackageName = argvW[i];
834 }
835 WINE_TRACE("PackageName = %s\n", wine_dbgstr_w(PackageName));
836 StringListAppend(&property_list, L"REMOVE=ALL");
837 }
838 else if(msi_option_prefix(argvW[i], "j"))
839 {
840 int j;
841 int len = lstrlenW(argvW[i]);
842 FunctionAdvertise = TRUE;
843 for(j = 2; j < len; j++)
844 {
845 switch(argvW[i][j])
846 {
847 case 'U':
848 case 'u':
849 AdvertiseMode = ADVERTISEFLAGS_USERASSIGN;
850 break;
851 case 'M':
852 case 'm':
853 AdvertiseMode = ADVERTISEFLAGS_MACHINEASSIGN;
854 break;
855 default:
856 report_error("Unknown option \"%c\" in Advertise mode\n", argvW[i][j]);
857 break;
858 }
859 }
860 i++;
861 if(i >= argc)
862 ShowUsage(1);
863 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
864 PackageName = argvW[i];
865 }
866 else if(msi_strequal(argvW[i], "u"))
867 {
868 FunctionAdvertise = TRUE;
869 AdvertiseMode = ADVERTISEFLAGS_USERASSIGN;
870 i++;
871 if(i >= argc)
872 ShowUsage(1);
873 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
874 PackageName = argvW[i];
875 }
876 else if(msi_strequal(argvW[i], "m"))
877 {
878 FunctionAdvertise = TRUE;
879 AdvertiseMode = ADVERTISEFLAGS_MACHINEASSIGN;
880 i++;
881 if(i >= argc)
882 ShowUsage(1);
883 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
884 PackageName = argvW[i];
885 }
886 else if(msi_option_equal(argvW[i], "t"))
887 {
888 i++;
889 if(i >= argc)
890 ShowUsage(1);
891 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
892 StringListAppend(&transform_list, argvW[i]);
893 }
894 else if(msi_option_equal(argvW[i], "g"))
895 {
896 i++;
897 if(i >= argc)
898 ShowUsage(1);
899 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
900 Language = msi_atou(argvW[i]);
901 }
902 else if(msi_option_prefix(argvW[i], "l"))
903 {
904 int j;
905 int len = lstrlenW(argvW[i]);
906 for(j = 2; j < len; j++)
907 {
908 switch(argvW[i][j])
909 {
910 case 'I':
911 case 'i':
912 LogMode |= INSTALLLOGMODE_INFO;
913 break;
914 case 'W':
915 case 'w':
916 LogMode |= INSTALLLOGMODE_WARNING;
917 break;
918 case 'E':
919 case 'e':
920 LogMode |= INSTALLLOGMODE_ERROR;
921 break;
922 case 'A':
923 case 'a':
925 break;
926 case 'R':
927 case 'r':
928 LogMode |= INSTALLLOGMODE_ACTIONDATA;
929 break;
930 case 'U':
931 case 'u':
932 LogMode |= INSTALLLOGMODE_USER;
933 break;
934 case 'C':
935 case 'c':
936 LogMode |= INSTALLLOGMODE_COMMONDATA;
937 break;
938 case 'M':
939 case 'm':
940 LogMode |= INSTALLLOGMODE_FATALEXIT;
941 break;
942 case 'O':
943 case 'o':
945 break;
946 case 'P':
947 case 'p':
949 break;
950 case 'V':
951 case 'v':
952 LogMode |= INSTALLLOGMODE_VERBOSE;
953 break;
954 case '*':
955 LogMode = INSTALLLOGMODE_FATALEXIT |
970 break;
971 case '+':
972 LogAttributes |= INSTALLLOGATTRIBUTES_APPEND;
973 break;
974 case '!':
975 LogAttributes |= INSTALLLOGATTRIBUTES_FLUSHEACHLINE;
976 break;
977 default:
978 break;
979 }
980 }
981 i++;
982 if(i >= argc)
983 ShowUsage(1);
984 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
985 if (!(log_unquoted = remove_quotes(argvW[i]))) return 1;
986 if (MsiEnableLogW(LogMode, log_unquoted, LogAttributes) != ERROR_SUCCESS)
987 {
988 report_error("Logging in %s (0x%08lx, %lu) failed\n",
989 wine_dbgstr_w(log_unquoted), LogMode, LogAttributes);
990 ExitProcess(1);
991 }
992 }
993 else if(msi_option_equal(argvW[i], "p") || msi_option_equal(argvW[i], "update"))
994 {
995 FunctionPatch = TRUE;
996 i++;
997 if(i >= argc)
998 ShowUsage(1);
999 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
1000 PatchFileName = argvW[i];
1001 }
1002 else if(msi_option_prefix(argvW[i], "q"))
1003 {
1004 if(lstrlenW(argvW[i]) == 2 || msi_strequal(argvW[i]+2, "n") ||
1005 msi_strequal(argvW[i] + 2, "uiet"))
1006 {
1007 silent = TRUE;
1008 InstallUILevel = INSTALLUILEVEL_NONE;
1009 }
1010 else if(msi_strequal(argvW[i]+2, "r"))
1011 {
1012 InstallUILevel = INSTALLUILEVEL_REDUCED;
1013 }
1014 else if(msi_strequal(argvW[i]+2, "f"))
1015 {
1017 }
1018 else if(msi_strequal(argvW[i]+2, "n+"))
1019 {
1021 }
1022 else if(msi_strprefix(argvW[i]+2, "b"))
1023 {
1024 const WCHAR *ptr = argvW[i] + 3;
1025
1026 InstallUILevel = INSTALLUILEVEL_BASIC;
1027
1028 while (*ptr)
1029 {
1030 if (msi_strprefix(ptr, "+"))
1031 InstallUILevel |= INSTALLUILEVEL_ENDDIALOG;
1032 if (msi_strprefix(ptr, "-"))
1033 InstallUILevel |= INSTALLUILEVEL_PROGRESSONLY;
1034 if (msi_strprefix(ptr, "!"))
1035 {
1036 WINE_FIXME("Unhandled modifier: !\n");
1037 InstallUILevel |= INSTALLUILEVEL_HIDECANCEL;
1038 }
1039 ptr++;
1040 }
1041 }
1042 else
1043 {
1044 report_error("Unknown option \"%s\" for UI level\n",
1045 wine_dbgstr_w(argvW[i]+2));
1046 }
1047 }
1048 else if(msi_option_equal(argvW[i], "passive"))
1049 {
1051 StringListAppend(&property_list, L"REBOOTPROMPT=\"S\"");
1052 }
1053 else if(msi_option_equal(argvW[i], "y"))
1054 {
1055 FunctionDllRegisterServer = TRUE;
1056 i++;
1057 if(i >= argc)
1058 ShowUsage(1);
1059 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
1060 DllName = argvW[i];
1061 }
1062 else if(msi_option_equal(argvW[i], "z"))
1063 {
1064 FunctionDllUnregisterServer = TRUE;
1065 i++;
1066 if(i >= argc)
1067 ShowUsage(1);
1068 WINE_TRACE("argvW[%d] = %s\n", i, wine_dbgstr_w(argvW[i]));
1069 DllName = argvW[i];
1070 }
1071 else if(msi_option_equal(argvW[i], "help") || msi_option_equal(argvW[i], "?"))
1072 {
1073 ShowUsage(0);
1074 }
1075 else if(msi_option_equal(argvW[i], "m"))
1076 {
1077 FunctionUnknown = TRUE;
1078 WINE_FIXME("Unknown parameter /m\n");
1079 }
1080 else if(msi_option_equal(argvW[i], "D"))
1081 {
1082 FunctionUnknown = TRUE;
1083 WINE_FIXME("Unknown parameter /D\n");
1084 }
1085 else if (msi_option_equal(argvW[i], "V"))
1086 {
1087 FunctionServer = TRUE;
1088 }
1089 else
1090 StringListAppend(&property_list, argvW[i]);
1091 }
1092
1093 /* start the GUI */
1094 MsiSetInternalUI(InstallUILevel, NULL);
1095
1096 Properties = build_properties( property_list );
1097
1098 if(FunctionInstallAdmin && FunctionPatch)
1099 FunctionInstall = FALSE;
1100
1101 if (PackageName && !(package_unquoted = remove_quotes(PackageName))) return 1;
1102 if (PatchFileName && !(patch_unquoted = remove_quotes(PatchFileName))) return 1;
1103 if (DllName && !(dll_unquoted = remove_quotes(DllName))) return 1;
1104
1105 ReturnCode = 1;
1106 if(FunctionInstall)
1107 {
1108 if(IsProductCode(package_unquoted))
1109 ReturnCode = MsiConfigureProductExW(package_unquoted, 0, INSTALLSTATE_DEFAULT, Properties);
1110 else
1111 {
1112 if ((ReturnCode = MsiInstallProductW(package_unquoted, Properties)) == ERROR_FILE_NOT_FOUND
1113 && (path = get_path_with_extension(package_unquoted)))
1114 {
1115 ReturnCode = MsiInstallProductW(path, Properties);
1116 free(path);
1117 }
1118 }
1119 }
1120 else if(FunctionRepair)
1121 {
1122 if(IsProductCode(package_unquoted))
1123 WINE_FIXME("Product code treatment not implemented yet\n");
1124 else
1125 {
1126 if ((ReturnCode = MsiReinstallProductW(package_unquoted, RepairMode)) == ERROR_FILE_NOT_FOUND
1127 && (path = get_path_with_extension(package_unquoted)))
1128 {
1129 ReturnCode = MsiReinstallProductW(path, RepairMode);
1130 free(path);
1131 }
1132 }
1133 }
1134 else if(FunctionAdvertise)
1135 {
1136 LPWSTR Transforms = build_transforms( property_list );
1137 ReturnCode = MsiAdvertiseProductW(package_unquoted, (LPWSTR) AdvertiseMode, Transforms, Language);
1138 }
1139 else if(FunctionPatch)
1140 {
1141 ReturnCode = MsiApplyPatchW(patch_unquoted, package_unquoted, InstallType, Properties);
1142 }
1143 else if(FunctionDllRegisterServer)
1144 {
1145 ReturnCode = DoDllRegisterServer(dll_unquoted);
1146 }
1147 else if(FunctionDllUnregisterServer)
1148 {
1149 ReturnCode = DoDllUnregisterServer(dll_unquoted);
1150 }
1151 else if (FunctionRegServer)
1152 {
1153 ReturnCode = DoRegServer();
1154 }
1155 else if (FunctionUnregServer)
1156 {
1157 ReturnCode = DoUnregServer();
1158 }
1159 else if (FunctionServer)
1160 {
1161 ReturnCode = DoService();
1162 }
1163 else if (FunctionUnknown)
1164 {
1165 WINE_FIXME( "Unknown function, ignoring\n" );
1166 }
1167 else
1168 ShowUsage(1);
1169
1170 return ReturnCode;
1171}
#define vsnprintf
Definition: acwin.h:108
#define REG_SZ
Definition: layer.c:22
static int state
Definition: maze.c:121
#define msg(x)
Definition: auth_time.c:54
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
#define ARRAY_SIZE(A)
Definition: main.h:20
#define ERR(fmt,...)
Definition: precomp.h:57
static HANDLE thread
Definition: service.c:33
#define RegCloseKey(hKey)
Definition: registry.h:49
HINSTANCE hInstance
Definition: charmap.c:19
Definition: list.h:39
struct list * next
Definition: list.h:40
VOID WINAPI InitCommonControls(void)
Definition: commctrl.c:874
#define free
Definition: debug_ros.c:5
#define malloc
Definition: debug_ros.c:4
HRESULT hr
Definition: delayimp.cpp:582
#define ERROR_SUCCESS
Definition: deptool.c:10
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
LONG WINAPI RegOpenKeyW(HKEY hKey, LPCWSTR lpSubKey, PHKEY phkResult)
Definition: reg.c:3268
LONG WINAPI RegQueryValueExW(_In_ HKEY hkeyorg, _In_ LPCWSTR name, _In_ LPDWORD reserved, _In_ LPDWORD type, _In_ LPBYTE data, _In_ LPDWORD count)
Definition: reg.c:4103
HRESULT WINAPI DECLSPEC_HOTPATCH CoInitializeEx(void *reserved, DWORD model)
Definition: combase.c:2803
void WINAPI DECLSPEC_HOTPATCH CoUninitialize(void)
Definition: combase.c:2842
HRESULT WINAPI CLSIDFromString(LPCOLESTR str, LPCLSID clsid)
Definition: combase.c:1470
#define CDECL
Definition: compat.h:29
#define wcschr
Definition: compat.h:17
#define CP_ACP
Definition: compat.h:109
#define OPEN_EXISTING
Definition: compat.h:775
#define ReadFile(a, b, c, d, e)
Definition: compat.h:742
#define GetProcAddress(x, y)
Definition: compat.h:753
#define INVALID_HANDLE_VALUE
Definition: compat.h:731
#define FreeLibrary(x)
Definition: compat.h:748
#define GENERIC_READ
Definition: compat.h:135
#define MAX_PATH
Definition: compat.h:34
#define CreateFileW
Definition: compat.h:741
#define CALLBACK
Definition: compat.h:35
#define lstrcpyW
Definition: compat.h:749
#define MultiByteToWideChar
Definition: compat.h:110
#define lstrcpynW
Definition: compat.h:738
#define lstrlenW
Definition: compat.h:750
static const WCHAR *const ext[]
Definition: module.c:53
BOOL WINAPI WriteFile(_In_ HANDLE hFile, _In_reads_bytes_opt_(nNumberOfBytesToWrite) LPCVOID lpBuffer, _In_ DWORD nNumberOfBytesToWrite, _Out_opt_ LPDWORD lpNumberOfBytesWritten, _Inout_opt_ LPOVERLAPPED lpOverlapped)
Definition: rw.c:25
DWORD WINAPI GetModuleFileNameW(HINSTANCE hModule, LPWSTR lpFilename, DWORD nSize)
Definition: loader.c:600
HINSTANCE WINAPI DECLSPEC_HOTPATCH LoadLibraryExW(LPCWSTR lpLibFileName, HANDLE hFile, DWORD dwFlags)
Definition: loader.c:288
HMODULE WINAPI DECLSPEC_HOTPATCH GetModuleHandleA(LPCSTR lpModuleName)
Definition: loader.c:812
UINT WINAPI GetSystemDirectoryW(OUT LPWSTR lpBuffer, IN UINT uSize)
Definition: path.c:2331
VOID WINAPI ExitProcess(IN UINT uExitCode)
Definition: proc.c:1380
HANDLE WINAPI DECLSPEC_HOTPATCH CreateThread(IN LPSECURITY_ATTRIBUTES lpThreadAttributes, IN DWORD dwStackSize, IN LPTHREAD_START_ROUTINE lpStartAddress, IN LPVOID lpParameter, IN DWORD dwCreationFlags, OUT LPDWORD lpThreadId)
Definition: thread.c:137
LCID WINAPI GetThreadLocale(void)
Definition: locale.c:2803
INT WINAPI CompareStringW(LCID lcid, DWORD flags, LPCWSTR str1, INT len1, LPCWSTR str2, INT len2)
Definition: locale.c:3946
LANGID WINAPI GetUserDefaultLangID(void)
Definition: locale.c:1182
LPWSTR WINAPI GetCommandLineW(void)
Definition: process.c:1356
GUID guid
Definition: version.c:147
MonoAssembly int argc
Definition: metahost.c:107
UINT WINAPI MsiGetFileVersionW(const WCHAR *path, WCHAR *verbuf, DWORD *verlen, WCHAR *langbuf, DWORD *langlen)
Definition: msi.c:3208
UINT WINAPI MsiConfigureProductExW(LPCWSTR szProduct, int iInstallLevel, INSTALLSTATE eInstallState, LPCWSTR szCommandLine)
Definition: msi.c:831
UINT WINAPI MsiMessageBoxW(HWND hWnd, const WCHAR *lpText, const WCHAR *lpCaption, UINT uType, WORD wLanguageId, DWORD f)
Definition: msi.c:2458
UINT WINAPI MsiEnableLogW(DWORD dwLogMode, const WCHAR *szLogFile, DWORD attributes)
Definition: msi.c:1900
UINT WINAPI MsiInstallProductW(LPCWSTR szPackagePath, LPCWSTR szCommandLine)
Definition: msi.c:228
UINT WINAPI MsiMessageBoxA(HWND hWnd, const char *lpText, const char *lpCaption, UINT uType, WORD wLanguageId, DWORD f)
Definition: msi.c:2451
INSTALLUILEVEL WINAPI MsiSetInternalUI(INSTALLUILEVEL dwUILevel, HWND *phWnd)
Definition: msi.c:2281
UINT WINAPI MsiAdvertiseProductW(LPCWSTR szPackagePath, LPCWSTR szScriptfilePath, LPCWSTR szTransforms, LANGID lgidLanguage)
Definition: msi.c:174
UINT WINAPI MsiApplyPatchW(LPCWSTR szPatchPackage, LPCWSTR szInstallPackage, INSTALLTYPE eInstallType, LPCWSTR szCommandLine)
Definition: msi.c:408
UINT WINAPI MsiReinstallProductW(const WCHAR *szProduct, DWORD dwReinstallMode)
Definition: msi.c:279
_ACRTIMP __msvcrt_long __cdecl wcstol(const wchar_t *, wchar_t **, int)
Definition: wcs.c:2752
_ACRTIMP size_t __cdecl wcslen(const wchar_t *)
Definition: wcs.c:2988
#define va_end(v)
Definition: stdarg.h:28
#define va_start(v, l)
Definition: stdarg.h:26
char * va_list
Definition: vadefs.h:50
#define swprintf
Definition: precomp.h:40
return ret
Definition: mutex.c:147
#define L(x)
Definition: resources.c:13
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
GLuint GLuint GLsizei count
Definition: gl.h:1545
GLuint GLuint GLsizei GLenum type
Definition: gl.h:1545
GLdouble GLdouble GLdouble r
Definition: gl.h:2055
GLuint res
Definition: glext.h:9613
GLuint buffer
Definition: glext.h:5915
GLsizeiptr size
Definition: glext.h:5919
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
GLuint in
Definition: glext.h:9616
GLfloat GLfloat p
Definition: glext.h:8902
GLenum GLsizei len
Definition: glext.h:6722
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint GLint GLint j
Definition: glfuncs.h:250
unsigned int UINT
Definition: sysinfo.c:13
#define FAILED(hr)
Definition: intsafe.h:51
const char * filename
Definition: ioapi.h:137
uint32_t entry
Definition: isohybrid.c:63
#define debugstr_w
Definition: kernel32.h:32
#define wine_dbgstr_w
Definition: kernel32.h:34
#define GUID_NULL
Definition: ks.h:106
USHORT LANGID
Definition: mui.h:9
LPWSTR WINAPI lstrcatW(LPWSTR lpString1, LPCWSTR lpString2)
Definition: lstring.c:274
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
#define MESSAGE
Definition: options.h:86
#define ERROR_FILE_NOT_FOUND
Definition: disk.h:79
static PVOID ptr
Definition: dispmode.c:27
WCHAR strW[12]
Definition: clipboard.c:2216
#define argv
Definition: mplay32.c:18
enum tagINSTALLTYPE INSTALLTYPE
@ INSTALLLOGATTRIBUTES_FLUSHEACHLINE
Definition: msi.h:157
@ INSTALLLOGATTRIBUTES_APPEND
Definition: msi.h:156
@ ADVERTISEFLAGS_USERASSIGN
Definition: msi.h:172
@ ADVERTISEFLAGS_MACHINEASSIGN
Definition: msi.h:171
@ INSTALLLOGMODE_VERBOSE
Definition: msi.h:145
@ INSTALLLOGMODE_ACTIONDATA
Definition: msi.h:140
@ INSTALLLOGMODE_ACTIONSTART
Definition: msi.h:139
@ INSTALLLOGMODE_FATALEXIT
Definition: msi.h:131
@ INSTALLLOGMODE_PROPERTYDUMP
Definition: msi.h:142
@ INSTALLLOGMODE_RESOLVESOURCE
Definition: msi.h:137
@ INSTALLLOGMODE_COMMONDATA
Definition: msi.h:143
@ INSTALLLOGMODE_WARNING
Definition: msi.h:133
@ INSTALLLOGMODE_INITIALIZE
Definition: msi.h:144
@ INSTALLLOGMODE_TERMINATE
Definition: msi.h:146
@ INSTALLLOGMODE_OUTOFDISKSPACE
Definition: msi.h:138
@ INSTALLLOGMODE_ERROR
Definition: msi.h:132
@ INSTALLLOGMODE_INFO
Definition: msi.h:135
@ INSTALLLOGMODE_PROGRESS
Definition: msi.h:141
@ INSTALLLOGMODE_SHOWDIALOG
Definition: msi.h:148
@ INSTALLLOGMODE_USER
Definition: msi.h:134
@ INSTALLTYPE_DEFAULT
Definition: msi.h:189
@ INSTALLTYPE_NETWORK_IMAGE
Definition: msi.h:190
@ REINSTALLMODE_MACHINEDATA
Definition: msi.h:123
@ REINSTALLMODE_FILEREPLACE
Definition: msi.h:122
@ REINSTALLMODE_FILEOLDERVERSION
Definition: msi.h:118
@ REINSTALLMODE_FILEEXACT
Definition: msi.h:120
@ REINSTALLMODE_FILEEQUALVERSION
Definition: msi.h:119
@ REINSTALLMODE_USERDATA
Definition: msi.h:124
@ REINSTALLMODE_PACKAGE
Definition: msi.h:126
@ REINSTALLMODE_FILEVERIFY
Definition: msi.h:121
@ REINSTALLMODE_SHORTCUT
Definition: msi.h:125
@ REINSTALLMODE_FILEMISSING
Definition: msi.h:117
@ INSTALLSTATE_DEFAULT
Definition: msi.h:48
enum tagINSTALLUILEVEL INSTALLUILEVEL
@ INSTALLUILEVEL_ENDDIALOG
Definition: msi.h:72
@ INSTALLUILEVEL_FULL
Definition: msi.h:69
@ INSTALLUILEVEL_BASIC
Definition: msi.h:67
@ INSTALLUILEVEL_HIDECANCEL
Definition: msi.h:70
@ INSTALLUILEVEL_REDUCED
Definition: msi.h:68
@ INSTALLUILEVEL_NONE
Definition: msi.h:66
@ INSTALLUILEVEL_PROGRESSONLY
Definition: msi.h:71
static BOOL IsProductCode(LPWSTR str)
Definition: msiexec.c:105
HRESULT(WINAPI * DLLUNREGISTERSERVER)(void)
Definition: msiexec.c:39
static BOOL msi_strprefix(LPCWSTR str1, LPCSTR str2)
Definition: msiexec.c:254
static DWORD DoUnregServer(void)
Definition: msiexec.c:371
static DWORD DoDllRegisterServer(LPCWSTR DllName)
Definition: msiexec.c:303
void report_error(const char *msg,...)
Definition: msiexec.c:50
static void ShowUsage(int ExitCode)
Definition: msiexec.c:65
static VOID * LoadProc(LPCWSTR DllName, LPCSTR ProcName, HMODULE *DllHandle)
Definition: msiexec.c:281
static int chomp(const WCHAR *in, WCHAR *out)
Definition: msiexec.c:481
static LPWSTR build_transforms(struct string_list *transform_list)
Definition: msiexec.c:185
chomp_state
Definition: msiexec.c:475
@ CS_TOKEN
Definition: msiexec.c:477
@ CS_WHITESPACE
Definition: msiexec.c:476
@ CS_QUOTE
Definition: msiexec.c:478
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
Definition: msiexec.c:655
static int custom_action_server(const WCHAR *arg)
Definition: msiexec.c:410
static DWORD client_pid
Definition: msiexec.c:401
UINT CDECL __wine_msi_call_dll_function(DWORD client_pid, const GUID *guid)
Definition: custom.c:507
static BOOL msi_strequal(LPCWSTR str1, LPCSTR str2)
Definition: msiexec.c:226
static BOOL silent
Definition: msiexec.c:42
static LPWSTR build_properties(struct string_list *property_list)
Definition: msiexec.c:137
static WCHAR * get_path_with_extension(const WCHAR *package_name)
Definition: msiexec.c:613
static BOOL msi_option_prefix(LPCWSTR str1, LPCSTR str2)
Definition: msiexec.c:272
DWORD DoService(void)
Definition: service.c:155
static VOID StringListAppend(struct string_list **list, LPCWSTR str)
Definition: msiexec.c:115
static WCHAR * remove_quotes(const WCHAR *filename)
Definition: msiexec.c:638
static BOOL msi_option_equal(LPCWSTR str1, LPCSTR str2)
Definition: msiexec.c:244
static DWORD DoDllUnregisterServer(LPCWSTR DllName)
Definition: msiexec.c:323
static void process_args(WCHAR *cmdline, int *pargc, WCHAR ***pargv)
Definition: msiexec.c:549
static DWORD DoRegServer(void)
Definition: msiexec.c:343
static DWORD CALLBACK custom_action_thread(void *arg)
Definition: msiexec.c:403
HRESULT(WINAPI * DLLREGISTERSERVER)(void)
Definition: msiexec.c:38
static BOOL process_args_from_reg(const WCHAR *ident, int *pargc, WCHAR ***pargv)
Definition: msiexec.c:578
static DWORD msi_atou(LPCWSTR str)
Definition: msiexec.c:213
#define GENERIC_ALL
Definition: nt_native.h:92
#define DELETE
Definition: nt_native.h:57
#define GENERIC_WRITE
Definition: nt_native.h:90
@ COINIT_MULTITHREADED
Definition: objbase.h:280
static HANDLE proc()
Definition: pdb.c:32
short WCHAR
Definition: pedump.c:58
long LONG
Definition: pedump.c:60
#define DEFINE_GUID(name, l, w1, w2, b1, b2, b3, b4, b5, b6, b7, b8)
Definition: guiddef.h:68
#define IsEqualGUID(rguid1, rguid2)
Definition: guiddef.h:147
#define SC_MANAGER_CREATE_SERVICE
Definition: winsvc.h:15
#define SC_MANAGER_CONNECT
Definition: winsvc.h:14
#define SERVICES_ACTIVE_DATABASEW
Definition: winsvc.h:8
#define list
Definition: rosglue.h:35
const WCHAR * str
BOOL WINAPI DeleteService(SC_HANDLE hService)
Definition: scm.c:921
SC_HANDLE WINAPI OpenSCManagerW(LPCWSTR lpMachineName, LPCWSTR lpDatabaseName, DWORD dwDesiredAccess)
Definition: scm.c:2107
SC_HANDLE WINAPI OpenServiceW(SC_HANDLE hSCManager, LPCWSTR lpServiceName, DWORD dwDesiredAccess)
Definition: scm.c:2199
SC_HANDLE WINAPI CreateServiceW(SC_HANDLE hSCManager, LPCWSTR lpServiceName, LPCWSTR lpDisplayName, DWORD dwDesiredAccess, DWORD dwServiceType, DWORD dwStartType, DWORD dwErrorControl, LPCWSTR lpBinaryPathName, LPCWSTR lpLoadOrderGroup, LPDWORD lpdwTagId, LPCWSTR lpDependencies, LPCWSTR lpServiceStartName, LPCWSTR lpPassword)
Definition: scm.c:812
BOOL WINAPI CloseServiceHandle(SC_HANDLE hSCObject)
Definition: scm.c:580
wcscpy
#define WINE_TRACE
Definition: debug.h:357
#define WINE_FIXME
Definition: debug.h:369
#define WINE_ERR
Definition: debug.h:374
XML_HIDDEN void xmlParserErrors const char const xmlChar const xmlChar * str2
Definition: parser.h:35
XML_HIDDEN void xmlParserErrors const char const xmlChar * str1
Definition: parser.h:35
#define LoadStringW
Definition: utils.h:64
#define TRACE(s)
Definition: solgame.cpp:4
TCHAR * cmdline
Definition: stretchblt.cpp:32
struct string_list * next
Definition: dhcpd.h:121
WCHAR str[1]
Definition: msiexec.c:47
#define DWORD_PTR
Definition: treelist.c:76
const char * LPCSTR
Definition: typedefs.h:52
const uint16_t * LPCWSTR
Definition: typedefs.h:57
uint32_t DWORD_PTR
Definition: typedefs.h:65
#define FIELD_OFFSET(t, f)
Definition: typedefs.h:255
unsigned char * LPBYTE
Definition: typedefs.h:53
uint16_t * LPWSTR
Definition: typedefs.h:56
uint64_t DWORD64
Definition: typedefs.h:67
char * LPSTR
Definition: typedefs.h:51
Definition: pdh_main.c:64
wchar_t tm const _CrtWcstime_Writes_and_advances_ptr_ count wchar_t ** out
Definition: wcsftime.cpp:383
DWORD WINAPI GetLastError(void)
Definition: except.c:1042
#define LOAD_WITH_ALTERED_SEARCH_PATH
Definition: winbase.h:340
_In_ ULONG _In_ ULONG_PTR ident
Definition: winddi.h:3994
#define HRESULT
Definition: msvc.h:7
#define WINAPI
Definition: msvc.h:6
#define ERROR_SERVICE_DOES_NOT_EXIST
Definition: winerror.h:935
#define NOERROR
Definition: winerror.h:3448
#define ERROR_SERVICE_EXISTS
Definition: winerror.h:948
#define NORM_IGNORECASE
Definition: winnls.h:191
#define CSTR_EQUAL
Definition: winnls.h:508
#define HKEY_LOCAL_MACHINE
Definition: winreg.h:12
#define SERVICE_DEMAND_START
Definition: cmtypes.h:979
#define SERVICE_WIN32_SHARE_PROCESS
Definition: cmtypes.h:964
#define SERVICE_ERROR_NORMAL
Definition: cmtypes.h:983