[NtUser]
[reactos.git] / reactos / base / applications / setup16 / main.c
1 #define WIN32_NO_STATUS
2 #define WIN32_LEAN_AND_MEAN
3 #include <windows.h>
4 #include <shellapi.h>
5 #include <shlobj.h>
6 #include <setupapi.h>
7
8 #define NT_PARAMS L"NT3.51 Intel Params"
9 #define MSSETUP_PATH L"~MSSETUP.T\\"
10
11 static UINT WINAPI ExtCabCallback(PVOID Context, UINT Notification, UINT_PTR Param1, UINT_PTR Param2)
12 {
13 FILE_IN_CABINET_INFO_W *pInfo;
14 FILEPATHS_W *pFilePaths;
15
16 DBG_UNREFERENCED_LOCAL_VARIABLE(pFilePaths);
17
18 switch(Notification)
19 {
20 case SPFILENOTIFY_FILEINCABINET:
21 pInfo = (FILE_IN_CABINET_INFO_W*)Param1;
22 wcscpy(pInfo->FullTargetName, (LPCWSTR)Context);
23 wcscat(pInfo->FullTargetName, pInfo->NameInCabinet);
24 return FILEOP_DOIT;
25 case SPFILENOTIFY_FILEEXTRACTED:
26 pFilePaths = (FILEPATHS_W*)Param1;
27 return NO_ERROR;
28 }
29 return NO_ERROR;
30 }
31
32 BOOL DeleteDirectory(LPWSTR lpszDir)
33 {
34 SHFILEOPSTRUCT fileop;
35 DWORD len = wcslen(lpszDir);
36 WCHAR *pszFrom = HeapAlloc(GetProcessHeap(), 0, (len + 2) * sizeof(WCHAR));
37 int ret;
38
39 wcscpy(pszFrom, lpszDir);
40 pszFrom[len] = 0;
41 pszFrom[len+1] = 0;
42
43 fileop.hwnd = NULL;
44 fileop.wFunc = FO_DELETE;
45 fileop.pFrom = pszFrom;
46 fileop.pTo = NULL;
47 fileop.fFlags = FOF_NOCONFIRMATION|FOF_SILENT;
48 fileop.fAnyOperationsAborted = FALSE;
49 fileop.lpszProgressTitle = NULL;
50 fileop.hNameMappings = NULL;
51
52 ret = SHFileOperation(&fileop);
53 HeapFree(GetProcessHeap(), 0, pszFrom);
54 return (ret == 0);
55 }
56
57 VOID GetSystemDrive(LPWSTR lpszDrive)
58 {
59 WCHAR szWindir[MAX_PATH];
60 GetWindowsDirectoryW(szWindir, MAX_PATH);
61 _wsplitpath(szWindir, lpszDrive, NULL, NULL, NULL);
62 wcscat(lpszDrive, L"\\");
63 }
64
65 int APIENTRY wWinMain(HINSTANCE hInstance,
66 HINSTANCE hPrevInstance,
67 LPWSTR lpCmdLine,
68 int nCmdShow)
69 {
70 WCHAR szSetupPath[MAX_PATH];
71 WCHAR szFileName[MAX_PATH];
72 WCHAR szCabFileName[MAX_PATH];
73 WCHAR szCabFilePath[MAX_PATH];
74 WCHAR szTempDirName[50];
75 WCHAR szCmdLine[MAX_PATH];
76 WCHAR szTempCmdLine[MAX_PATH];
77 WCHAR szTempPath[MAX_PATH];
78 WCHAR szFullTempPath[MAX_PATH];
79 WCHAR szDrive[4];
80 DWORD dwAttrib;
81 PROCESS_INFORMATION processInfo;
82 STARTUPINFO startupInfo;
83 UNREFERENCED_PARAMETER(hPrevInstance);
84 UNREFERENCED_PARAMETER(nCmdShow);
85
86 GetCurrentDirectory(MAX_PATH, szSetupPath);
87 wcscat(szSetupPath, L"\\");
88 wcscpy(szFileName, szSetupPath);
89 wcscat(szFileName, L"setup.lst");
90
91 if (GetFileAttributes(szFileName) == INVALID_FILE_ATTRIBUTES)
92 {
93 MessageBoxW(0, L"Cannot find Setup.lst file", L"Error", MB_OK | MB_ICONERROR);
94 return 1;
95 }
96
97 /* read information from setup.lst */
98 GetPrivateProfileStringW(NT_PARAMS, L"CabinetFile", NULL, szCabFileName, MAX_PATH, szFileName);
99 GetPrivateProfileStringW(NT_PARAMS, L"TmpDirName", NULL, szTempDirName, 50, szFileName);
100 GetPrivateProfileStringW(NT_PARAMS, L"CmdLine", NULL, szCmdLine, MAX_PATH, szFileName);
101
102 wcscpy(szCabFilePath, szSetupPath);
103 wcscat(szCabFilePath, szCabFileName);
104
105 /* ceate temp directory */
106 GetSystemDrive(szDrive);
107 wcscpy(szTempPath, szDrive);
108 wcscat(szTempPath, MSSETUP_PATH);
109 wcscpy(szFullTempPath, szTempPath);
110 wcscat(szFullTempPath, szTempDirName);
111 wcscat(szFullTempPath, L"\\");
112
113 if (SHCreateDirectoryEx(0, szFullTempPath, NULL) != ERROR_SUCCESS)
114 {
115 MessageBoxW(0, L"Could not create Temp Directory.", L"Error", MB_OK | MB_ICONERROR);
116 return 1;
117 }
118
119 dwAttrib = GetFileAttributes(szTempPath);
120 SetFileAttributes(szTempPath, dwAttrib | FILE_ATTRIBUTE_HIDDEN);
121
122 /* extract files */
123 if (!SetupIterateCabinetW(szCabFilePath, 0, ExtCabCallback, szFullTempPath))
124 {
125 MessageBoxW(0, L"Could not extract cab file", L"Error", MB_OK | MB_ICONERROR);
126 DeleteDirectory(szTempPath);
127 return 1;
128 }
129
130 /* prepare command line */
131 wsprintf(szTempCmdLine, szCmdLine, szFullTempPath, lpCmdLine);
132 wcscpy(szCmdLine, szFullTempPath);
133 wcscat(szCmdLine, szTempCmdLine);
134
135 /* execute the 32-Bit installer */
136 ZeroMemory(&processInfo, sizeof(processInfo));
137 ZeroMemory(&startupInfo, sizeof(startupInfo));
138 startupInfo.cb = sizeof(startupInfo);
139 if (CreateProcessW(NULL, szCmdLine, NULL, NULL, FALSE, NORMAL_PRIORITY_CLASS, NULL, szFullTempPath, &startupInfo, &processInfo))
140 {
141 WaitForSingleObject(processInfo.hProcess, INFINITE);
142 CloseHandle(processInfo.hProcess);
143 CloseHandle(processInfo.hThread);
144 }
145 else
146 {
147 WCHAR szMsg[MAX_PATH];
148 wsprintf(szMsg, L"Failed to load the installer. Error %lu", GetLastError());
149 MessageBoxW(0, szMsg, L"Error", MB_OK | MB_ICONERROR);
150 DeleteDirectory(szTempPath);
151 return 1;
152 }
153
154 /* cleanup */
155 DeleteDirectory(szTempPath);
156
157 return 0;
158 }
159
160 /* EOF */