[SETUP:REACTOS] Adapt the 1st-stage GUI setup to compile with the setuplib.
authorHermès Bélusca-Maïto <hermes.belusca-maito@reactos.org>
Mon, 14 Aug 2017 17:06:19 +0000 (17:06 +0000)
committerHermès Bélusca-Maïto <hermes.belusca-maito@reactos.org>
Sun, 28 Oct 2018 17:59:47 +0000 (18:59 +0100)
svn path=/branches/setup_improvements/; revision=75544

[SETUP:REACTOS] More interfacing of the 1st-stage GUI installer with the setuplib.

- Add a ConvertNtPathToWin32Path() helper function that allows converting
  NT paths like: \Device\CdRom0\i386\txtsetup.sif file into a Win32 path
  that the Win32 versions of the SetupApi functions (e.g. SetupOpenInfFileW)
  can accept.
  Note that RtlNtPathNameToDosPathName() cannot be used here because this
  function only works for NT paths within the \DosDevices\ (or \??\) NTObj
  directory, and not in other directories.

- Use this helper function in the implementation of SetupOpenInfFileExW.
  Now the txtsetup.sif function can be loaded by setuplib *when being used*
  by the 1st-stage GUI installer!

- Remove deprecated code.

svn path=/branches/setup_improvements/; revision=75668
svn path=/branches/setup_improvements/; revision=75721
svn path=/branches/setup_improvements/; revision=75750

base/setup/reactos/CMakeLists.txt
base/setup/reactos/drivepage.c
base/setup/reactos/inffile.c [new file with mode: 0644]
base/setup/reactos/reactos.c
base/setup/reactos/reactos.h

index 8aaa7ba..0f08c1f 100644 (file)
@@ -1,14 +1,22 @@
 
+include_directories(
+    ${CMAKE_CURRENT_SOURCE_DIR}
+    ${CMAKE_CURRENT_SOURCE_DIR}/../lib
+#    ${REACTOS_SOURCE_DIR}/base/setup/lib
+    ${REACTOS_SOURCE_DIR}/sdk/include/reactos/libs/zlib
+    ${REACTOS_SOURCE_DIR}/sdk/include/reactos/drivers)
+
 list(APPEND SOURCE
     drivepage.c
+    inffile.c
     reactos.c
     reactos.h)
 
 file(GLOB reactos_rc_deps res/*.*)
 add_rc_deps(reactos.rc ${reactos_rc_deps})
 add_executable(reactos ${SOURCE} reactos.rc)
-add_pch(reactos reactos.h SOURCE)
-target_link_libraries(reactos uuid)
 set_module_type(reactos win32gui UNICODE)
+add_pch(reactos reactos.h SOURCE)
+target_link_libraries(reactos uuid setuplib ext2lib vfatlib btrfslib)
 add_importlibs(reactos advapi32 gdi32 user32 comctl32 setupapi msvcrt kernel32 ntdll)
 add_cd_file(TARGET reactos DESTINATION reactos NO_CAB FOR bootcd)
index 5cda85e..e73e7a1 100644 (file)
@@ -57,7 +57,7 @@ MoreOptDlgProc(HWND hwndDlg,
             SendMessage(GetDlgItem(hwndDlg, IDC_PATH),
                         WM_SETTEXT,
                         (WPARAM)0,
-                        (LPARAM)pSetupData->InstallDir);
+                        (LPARAM)pSetupData->USetupData.InstallationDirectory);
             break;
 
         case WM_COMMAND:
@@ -66,8 +66,8 @@ MoreOptDlgProc(HWND hwndDlg,
                 case IDOK:
                     SendMessage(GetDlgItem(hwndDlg, IDC_PATH),
                                 WM_GETTEXT,
-                                (WPARAM)sizeof(pSetupData->InstallDir) / sizeof(TCHAR),
-                                (LPARAM)pSetupData->InstallDir);
+                                (WPARAM)sizeof(pSetupData->USetupData.InstallationDirectory) / sizeof(TCHAR),
+                                (LPARAM)pSetupData->USetupData.InstallationDirectory);
 
                     EndDialog(hwndDlg, IDOK);
                     return TRUE;
diff --git a/base/setup/reactos/inffile.c b/base/setup/reactos/inffile.c
new file mode 100644 (file)
index 0000000..db25b07
--- /dev/null
@@ -0,0 +1,89 @@
+/*
+ * COPYRIGHT:       See COPYING in the top level directory
+ * PROJECT:         ReactOS text-mode setup
+ * FILE:            base/setup/usetup/inffile.c
+ * PURPOSE:         .inf files support functions
+ * PROGRAMMERS:     Hervé Poussineau
+ *                  Hermes Belusca-Maito (hermes.belusca@sfr.fr)
+ */
+
+/* INCLUDES ******************************************************************/
+
+#include "reactos.h"
+
+#define NDEBUG
+#include <debug.h>
+
+/* SETUP* API COMPATIBILITY FUNCTIONS ****************************************/
+
+/* Functions from the INFLIB library */
+
+/* SetupOpenInfFileW with support for a user-provided LCID */
+HINF
+WINAPI
+SetupOpenInfFileExW(
+    IN PCWSTR FileName,
+    IN PCWSTR InfClass,
+    IN DWORD InfStyle,
+    IN LCID LocaleId,
+    OUT PUINT ErrorLine)
+{
+    WCHAR Win32FileName[MAX_PATH];
+
+    UNREFERENCED_PARAMETER(LocaleId);
+
+    /*
+     * SetupOpenInfFileExW is called within setuplib with NT paths, however
+     * the Win32 SetupOpenInfFileW API only takes Win32 paths. We therefore
+     * map the NT path to Win32 path and then call the Win32 API.
+     */
+    if (!ConvertNtPathToWin32Path(Win32FileName,
+                                  _countof(Win32FileName),
+                                  FileName))
+    {
+        return INVALID_HANDLE_VALUE;
+    }
+
+    return SetupOpenInfFileW(Win32FileName,
+                             InfClass,
+                             InfStyle,
+                             ErrorLine);
+}
+
+
+/* HELPER FUNCTIONS **********************************************************/
+
+#if 0
+
+HINF WINAPI
+INF_OpenBufferedFileA(
+    IN PSTR FileBuffer,
+    IN ULONG FileSize,
+    IN PCSTR InfClass,
+    IN DWORD InfStyle,
+    IN LCID LocaleId,
+    OUT PUINT ErrorLine)
+{
+#ifdef __REACTOS__
+    HINF hInf = NULL;
+    ULONG ErrorLineUL;
+    NTSTATUS Status;
+
+    Status = InfOpenBufferedFile(&hInf,
+                                 FileBuffer,
+                                 FileSize,
+                                 LANGIDFROMLCID(LocaleId),
+                                 &ErrorLineUL);
+    *ErrorLine = (UINT)ErrorLineUL;
+    if (!NT_SUCCESS(Status))
+        return INVALID_HANDLE_VALUE;
+
+    return hInf;
+#else
+    return INVALID_HANDLE_VALUE;
+#endif /* !__REACTOS__ */
+}
+
+#endif
+
+/* EOF */
index c7fcbee..13cdd88 100644 (file)
 #include "reactos.h"
 #include "resource.h"
 
+#define NDEBUG
+#include <debug.h>
+
 /* GLOBALS ******************************************************************/
 
+HANDLE ProcessHeap;
+BOOLEAN IsUnattendedSetup = FALSE;
+SETUPDATA SetupData;
 
-LONG LoadGenentry(HINF hinf,PCTSTR name,PGENENTRY *gen,PINFCONTEXT context);
 
 /* FUNCTIONS ****************************************************************/
 
+LONG LoadGenentry(HINF hinf,PCTSTR name,PGENENTRY *gen,PINFCONTEXT context);
+
 static VOID
 CenterWindow(HWND hWnd)
 {
@@ -82,6 +89,19 @@ CreateTitleFont(VOID)
     return hFont;
 }
 
+INT DisplayError(
+    IN HWND hParentWnd OPTIONAL,
+    IN UINT uIDTitle,
+    IN UINT uIDMessage)
+{
+    WCHAR message[512], caption[64];
+
+    LoadStringW(SetupData.hInstance, uIDMessage, message, ARRAYSIZE(message));
+    LoadStringW(SetupData.hInstance, uIDTitle, caption, ARRAYSIZE(caption));
+
+    return MessageBoxW(hParentWnd, message, caption, MB_OK | MB_ICONERROR);
+}
+
 static INT_PTR CALLBACK
 StartDlgProc(HWND hwndDlg,
              UINT uMsg,
@@ -276,9 +296,9 @@ DeviceDlgProc(HWND hwndDlg,
                     if (tindex != CB_ERR)
                     {
                         pSetupData->SelectedComputer = SendMessage(hList,
-                                                                 CB_GETITEMDATA,
-                                                                 (WPARAM) tindex,
-                                                                 (LPARAM) 0);
+                                                                   CB_GETITEMDATA,
+                                                                   (WPARAM) tindex,
+                                                                   (LPARAM) 0);
                     }
 
                     hList = GetDlgItem(hwndDlg, IDC_DISPLAY);
@@ -287,9 +307,9 @@ DeviceDlgProc(HWND hwndDlg,
                     if (tindex != CB_ERR)
                     {
                         pSetupData->SelectedDisplay = SendMessage(hList,
-                                                                CB_GETITEMDATA,
-                                                                (WPARAM) tindex,
-                                                                (LPARAM) 0);
+                                                                  CB_GETITEMDATA,
+                                                                  (WPARAM) tindex,
+                                                                  (LPARAM) 0);
                     }
 
                     hList =GetDlgItem(hwndDlg, IDC_KEYBOARD);
@@ -298,9 +318,9 @@ DeviceDlgProc(HWND hwndDlg,
                     if (tindex != CB_ERR)
                     {
                         pSetupData->SelectedKeyboard = SendMessage(hList,
-                                                                 CB_GETITEMDATA,
-                                                                 (WPARAM) tindex,
-                                                                 (LPARAM) 0);
+                                                                   CB_GETITEMDATA,
+                                                                   (WPARAM) tindex,
+                                                                   (LPARAM) 0);
                     }
                     return TRUE;
                 }
@@ -498,37 +518,15 @@ RestartDlgProc(HWND hwndDlg,
 BOOL LoadSetupData(
     PSETUPDATA pSetupData)
 {
-    WCHAR szPath[MAX_PATH];
-    TCHAR tmp[10];
-    WCHAR *ch;
-    HINF hTxtsetupSif = INVALID_HANDLE_VALUE;
+    BOOL ret = TRUE;
     INFCONTEXT InfContext;
+    TCHAR tmp[10];
     //TCHAR szValue[MAX_PATH];
     DWORD LineLength;
     LONG Count;
-    BOOL ret = TRUE;
-
-    GetModuleFileNameW(NULL,szPath,MAX_PATH);
-    ch = strrchrW(szPath,L'\\');
-    if (ch != NULL)
-        *ch = L'\0';
-
-    wcscat(szPath, L"\\txtsetup.sif");
-    hTxtsetupSif = SetupOpenInfFileW(szPath, NULL, INF_STYLE_OLDNT, NULL);
-    if (hTxtsetupSif == INVALID_HANDLE_VALUE)
-    {
-        TCHAR message[512], caption[64];
-
-        // txtsetup.sif cannot be found
-        LoadString(pSetupData->hInstance, IDS_NO_TXTSETUP_SIF, message, sizeof(message)/sizeof(TCHAR));
-        LoadString(pSetupData->hInstance, IDS_CAPTION, caption, sizeof(caption)/sizeof(TCHAR));
-
-        MessageBox(NULL, message, caption, MB_OK | MB_ICONERROR);
-        return FALSE;
-    }
 
     // get language list
-    pSetupData->LangCount = SetupGetLineCount(hTxtsetupSif, _T("Language"));
+    pSetupData->LangCount = SetupGetLineCount(pSetupData->SetupInf, _T("Language"));
     if (pSetupData->LangCount > 0)
     {
         pSetupData->pLanguages = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(LANG) * pSetupData->LangCount);
@@ -539,7 +537,7 @@ BOOL LoadSetupData(
         }
 
         Count = 0;
-        if (SetupFindFirstLine(hTxtsetupSif, _T("Language"), NULL, &InfContext))
+        if (SetupFindFirstLine(pSetupData->SetupInf, _T("Language"), NULL, &InfContext))
         {
             do
             {
@@ -561,7 +559,7 @@ BOOL LoadSetupData(
     }
 
     // get keyboard layout list
-    pSetupData->KbLayoutCount = SetupGetLineCount(hTxtsetupSif, _T("KeyboardLayout"));
+    pSetupData->KbLayoutCount = SetupGetLineCount(pSetupData->SetupInf, _T("KeyboardLayout"));
     if (pSetupData->KbLayoutCount > 0)
     {
         pSetupData->pKbLayouts = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(KBLAYOUT) * pSetupData->KbLayoutCount);
@@ -572,7 +570,7 @@ BOOL LoadSetupData(
         }
 
         Count = 0;
-        if (SetupFindFirstLine(hTxtsetupSif, _T("KeyboardLayout"), NULL, &InfContext))
+        if (SetupFindFirstLine(pSetupData->SetupInf, _T("KeyboardLayout"), NULL, &InfContext))
         {
             do
             {
@@ -598,7 +596,7 @@ BOOL LoadSetupData(
     pSetupData->DefaultLang = -1;
 
     // TODO: get defaults from underlaying running system
-    if (SetupFindFirstLine(hTxtsetupSif, _T("NLS"), _T("DefaultLayout"), &InfContext))
+    if (SetupFindFirstLine(pSetupData->SetupInf, _T("NLS"), _T("DefaultLayout"), &InfContext))
     {
         SetupGetStringField(&InfContext, 1, tmp, sizeof(tmp) / sizeof(TCHAR), &LineLength);
         for (Count = 0; Count < pSetupData->KbLayoutCount; Count++)
@@ -611,7 +609,7 @@ BOOL LoadSetupData(
         }
     }
 
-    if (SetupFindFirstLine(hTxtsetupSif, _T("NLS"), _T("DefaultLanguage"), &InfContext))
+    if (SetupFindFirstLine(pSetupData->SetupInf, _T("NLS"), _T("DefaultLanguage"), &InfContext))
     {
         SetupGetStringField(&InfContext, 1, tmp, sizeof(tmp) / sizeof(TCHAR), &LineLength);
         for (Count = 0; Count < pSetupData->LangCount; Count++)
@@ -625,21 +623,21 @@ BOOL LoadSetupData(
     }
 
     // get computers list
-    pSetupData->CompCount = LoadGenentry(hTxtsetupSif,_T("Computer"),&pSetupData->pComputers,&InfContext);
+    pSetupData->CompCount = LoadGenentry(pSetupData->SetupInf,_T("Computer"),&pSetupData->pComputers,&InfContext);
 
     // get display list
-    pSetupData->DispCount = LoadGenentry(hTxtsetupSif,_T("Display"),&pSetupData->pDisplays,&InfContext);
+    pSetupData->DispCount = LoadGenentry(pSetupData->SetupInf,_T("Display"),&pSetupData->pDisplays,&InfContext);
 
     // get keyboard list
-    pSetupData->KeybCount = LoadGenentry(hTxtsetupSif, _T("Keyboard"),&pSetupData->pKeyboards,&InfContext);
+    pSetupData->KeybCount = LoadGenentry(pSetupData->SetupInf, _T("Keyboard"),&pSetupData->pKeyboards,&InfContext);
 
     // get install directory
-    if (SetupFindFirstLine(hTxtsetupSif, _T("SetupData"), _T("DefaultPath"), &InfContext))
+    if (SetupFindFirstLine(pSetupData->SetupInf, _T("SetupData"), _T("DefaultPath"), &InfContext))
     {
         SetupGetStringField(&InfContext,
                             1,
-                            pSetupData->InstallDir,
-                            sizeof(pSetupData->InstallDir) / sizeof(TCHAR),
+                            pSetupData->USetupData.InstallationDirectory,
+                            sizeof(pSetupData->USetupData.InstallationDirectory) / sizeof(TCHAR),
                             &LineLength);
     }
 
@@ -659,9 +657,6 @@ done:
         }
     }
 
-    if (hTxtsetupSif != INVALID_HANDLE_VALUE)
-        SetupCloseInfFile(hTxtsetupSif);
-
     return ret;
 }
 
@@ -702,89 +697,83 @@ LONG LoadGenentry(HINF hinf,PCTSTR name,PGENENTRY *gen,PINFCONTEXT context)
     return TotalCount;
 }
 
-BOOL isUnattendSetup(VOID)
+/*
+ * Attempts to convert a pure NT file path into a corresponding Win32 path.
+ * Adapted from GetInstallSourceWin32() in dll/win32/syssetup/wizard.c
+ */
+BOOL
+ConvertNtPathToWin32Path(
+    OUT PWSTR pwszPath,
+    IN DWORD cchPathMax,
+    IN PCWSTR pwszNTPath)
 {
-    WCHAR szPath[MAX_PATH];
-    WCHAR *ch;
-    HINF hUnattendedInf;
-    INFCONTEXT InfContext;
-    TCHAR szValue[MAX_PATH];
-    DWORD LineLength;
-    //HKEY hKey;
-    BOOL result = 0;
+    WCHAR wszDrives[512];
+    WCHAR wszNTPath[512]; // MAX_PATH ?
+    DWORD cchDrives;
+    PWCHAR pwszDrive;
 
-    GetModuleFileNameW(NULL, szPath, MAX_PATH);
-    ch = strrchrW(szPath, L'\\');
-    if (ch != NULL)
-        *ch = L'\0';
+    *pwszPath = UNICODE_NULL;
 
-    wcscat(szPath, L"\\unattend.inf");
-    hUnattendedInf = SetupOpenInfFileW(szPath, NULL, INF_STYLE_OLDNT, NULL);
+    cchDrives = GetLogicalDriveStringsW(_countof(wszDrives) - 1, wszDrives);
+    if (cchDrives == 0 || cchDrives >= _countof(wszDrives))
+    {
+        /* Buffer too small or failure */
+        DPRINT1("GetLogicalDriveStringsW failed\n");
+        return FALSE;
+    }
 
-    if (hUnattendedInf != INVALID_HANDLE_VALUE)
+    for (pwszDrive = wszDrives; *pwszDrive; pwszDrive += wcslen(pwszDrive) + 1)
     {
-        if (SetupFindFirstLine(hUnattendedInf, _T("Unattend"), _T("UnattendSetupEnabled"),&InfContext))
+        /* Retrieve the NT path corresponding to the current Win32 DOS path */
+        pwszDrive[2] = UNICODE_NULL; // Temporarily remove the backslash
+        QueryDosDeviceW(pwszDrive, wszNTPath, _countof(wszNTPath));
+        pwszDrive[2] = L'\\';        // Restore the backslash
+
+        wcscat(wszNTPath, L"\\");    // Concat a backslash
+
+        DPRINT1("Testing '%S' --> '%S'\n", pwszDrive, wszNTPath);
+
+        /* Check whether the NT path corresponds to the NT installation source path */
+        if (!_wcsnicmp(wszNTPath, pwszNTPath, wcslen(wszNTPath)))
         {
-            if (SetupGetStringField(&InfContext,
-                                    1,
-                                    szValue,
-                                    sizeof(szValue) / sizeof(TCHAR),
-                                    &LineLength) && (_tcsicmp(szValue, _T("yes")) == 0))
-            {
-                result = 1; // unattendSetup enabled
-                // read values and store in SetupData
-            }
+            /* Found it! */
+            wsprintf(pwszPath, L"%s%s", // cchPathMax
+                     pwszDrive, pwszNTPath + wcslen(wszNTPath));
+            DPRINT1("ConvertNtPathToWin32Path: %S\n", pwszPath);
+            return TRUE;
         }
-            SetupCloseInfFile(hUnattendedInf);
     }
 
-    return result;
+    return FALSE;
 }
 
-#if 0
-static
-VOID
-EnableShutdownPrivilege(VOID)
+/* Used to enable and disable the shutdown privilege */
+/* static */ BOOL
+EnablePrivilege(LPCWSTR lpszPrivilegeName, BOOL bEnablePrivilege)
 {
-    HANDLE hToken = NULL;
-    TOKEN_PRIVILEGES Privileges;
-
-    /* Get shutdown privilege */
-    if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &hToken))
-    {
-//        FatalError("OpenProcessToken() failed!");
-        return;
-    }
+    BOOL   Success;
+    HANDLE hToken;
+    TOKEN_PRIVILEGES tp;
 
-    if (!LookupPrivilegeValue(NULL,
-                              SE_SHUTDOWN_NAME,
-                              &Privileges.Privileges[0].Luid))
-    {
-//        FatalError("LookupPrivilegeValue() failed!");
-       goto done;
-    }
+    Success = OpenProcessToken(GetCurrentProcess(),
+                               TOKEN_ADJUST_PRIVILEGES,
+                               &hToken);
+    if (!Success) return Success;
 
-    Privileges.PrivilegeCount = 1;
-    Privileges.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
+    Success = LookupPrivilegeValueW(NULL,
+                                    lpszPrivilegeName,
+                                    &tp.Privileges[0].Luid);
+    if (!Success) goto Quit;
 
-    if (AdjustTokenPrivileges(hToken,
-                              FALSE,
-                              &Privileges,
-                              0,
-                              (PTOKEN_PRIVILEGES)NULL,
-                              NULL) == 0)
-    {
-//        FatalError("AdjustTokenPrivileges() failed!");
-       goto done;
-    }
+    tp.PrivilegeCount = 1;
+    tp.Privileges[0].Attributes = (bEnablePrivilege ? SE_PRIVILEGE_ENABLED : 0);
 
-done:
-    if (hToken != NULL)
-        CloseHandle(hToken);
+    Success = AdjustTokenPrivileges(hToken, FALSE, &tp, 0, NULL, NULL);
 
-    return;
+Quit:
+    CloseHandle(hToken);
+    return Success;
 }
-#endif
 
 int WINAPI
 _tWinMain(HINSTANCE hInst,
@@ -792,40 +781,75 @@ _tWinMain(HINSTANCE hInst,
           LPTSTR lpszCmdLine,
           int nCmdShow)
 {
-    PSETUPDATA pSetupData = NULL;
+    NTSTATUS Status;
+    ULONG Error;
     PROPSHEETHEADER psh;
     HPROPSHEETPAGE ahpsp[8];
     PROPSHEETPAGE psp = {0};
     UINT nPages = 0;
 
-    pSetupData = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(SETUPDATA));
-    if (pSetupData == NULL)
+    ProcessHeap = GetProcessHeap();
+
+    /* Initialize global unicode strings */
+    RtlInitUnicodeString(&SetupData.USetupData.SourcePath, NULL);
+    RtlInitUnicodeString(&SetupData.USetupData.SourceRootPath, NULL);
+    RtlInitUnicodeString(&SetupData.USetupData.SourceRootDir, NULL);
+    // RtlInitUnicodeString(&InstallPath, NULL);
+    RtlInitUnicodeString(&SetupData.USetupData.DestinationPath, NULL);
+    RtlInitUnicodeString(&SetupData.USetupData.DestinationArcPath, NULL);
+    RtlInitUnicodeString(&SetupData.USetupData.DestinationRootPath, NULL);
+    RtlInitUnicodeString(&SetupData.USetupData.SystemRootPath, NULL);
+
+    /* Get the source path and source root path */
+    //
+    // NOTE: Sometimes the source path may not be in SystemRoot !!
+    // (and this is the case when using the 1st-stage GUI setup!)
+    //
+    Status = GetSourcePaths(&SetupData.USetupData.SourcePath,
+                            &SetupData.USetupData.SourceRootPath,
+                            &SetupData.USetupData.SourceRootDir);
+    if (!NT_SUCCESS(Status))
     {
-        return 1;
+        DPRINT1("GetSourcePaths() failed (Status 0x%08lx)", Status);
+        // MUIDisplayError(ERROR_NO_SOURCE_DRIVE, Ir, POPUP_WAIT_ENTER);
+        MessageBoxW(NULL, L"GetSourcePaths failed!", L"Error", MB_ICONERROR);
+        goto Quit;
     }
+    DPRINT1("SourcePath: '%wZ'\n", &SetupData.USetupData.SourcePath);
+    DPRINT1("SourceRootPath: '%wZ'\n", &SetupData.USetupData.SourceRootPath);
+    DPRINT1("SourceRootDir: '%wZ'\n", &SetupData.USetupData.SourceRootDir);
 
-    pSetupData->hInstance = hInst;
-    pSetupData->bUnattend = isUnattendSetup();
+    /* Load 'txtsetup.sif' from the installation media */
+    Error = LoadSetupInf(&SetupData.SetupInf, &SetupData.USetupData);
+    if (Error != ERROR_SUCCESS)
+    {
+        // MUIDisplayError(Error, Ir, POPUP_WAIT_ENTER);
+        DisplayError(NULL, IDS_CAPTION, IDS_NO_TXTSETUP_SIF);
+        goto Quit;
+    }
+    /* Load extra setup data (HW lists etc...) */
+    if (!LoadSetupData(&SetupData))
+        goto Quit;
 
-    LoadString(hInst,IDS_ABORTSETUP, pSetupData->szAbortMessage, sizeof(pSetupData->szAbortMessage)/sizeof(TCHAR));
-    LoadString(hInst,IDS_ABORTSETUP2, pSetupData->szAbortTitle, sizeof(pSetupData->szAbortTitle)/sizeof(TCHAR));
+    SetupData.hInstance = hInst;
+
+    CheckUnattendedSetup(&SetupData.USetupData);
+    SetupData.bUnattend = IsUnattendedSetup;
+
+    LoadStringW(hInst, IDS_ABORTSETUP, SetupData.szAbortMessage, ARRAYSIZE(SetupData.szAbortMessage));
+    LoadStringW(hInst, IDS_ABORTSETUP2, SetupData.szAbortTitle, ARRAYSIZE(SetupData.szAbortTitle));
 
     /* Create title font */
-    pSetupData->hTitleFont = CreateTitleFont();
+    SetupData.hTitleFont = CreateTitleFont();
 
-    if (!pSetupData->bUnattend)
+    if (!SetupData.bUnattend)
     {
-        if (!LoadSetupData(pSetupData))
-        {
-            HeapFree(GetProcessHeap(), 0, pSetupData);
-            return 0;
-        }
-
         /* Create the Start page, until setup is working */
+        // NOTE: What does "until setup is working" mean??
         psp.dwSize = sizeof(PROPSHEETPAGE);
         psp.dwFlags = PSP_DEFAULT | PSP_HIDEHEADER;
         psp.hInstance = hInst;
-        psp.lParam = (LPARAM)pSetupData;
+        psp.lParam = (LPARAM)&SetupData;
         psp.pfnDlgProc = StartDlgProc;
         psp.pszTemplate = MAKEINTRESOURCE(IDD_STARTPAGE);
         ahpsp[nPages++] = CreatePropertySheetPage(&psp);
@@ -836,7 +860,7 @@ _tWinMain(HINSTANCE hInst,
         psp.pszHeaderTitle = MAKEINTRESOURCE(IDS_TYPETITLE);
         psp.pszHeaderSubTitle = MAKEINTRESOURCE(IDS_TYPESUBTITLE);
         psp.hInstance = hInst;
-        psp.lParam = (LPARAM)pSetupData;
+        psp.lParam = (LPARAM)&SetupData;
         psp.pfnDlgProc = TypeDlgProc;
         psp.pszTemplate = MAKEINTRESOURCE(IDD_TYPEPAGE);
         ahpsp[nPages++] = CreatePropertySheetPage(&psp);
@@ -847,7 +871,7 @@ _tWinMain(HINSTANCE hInst,
         psp.pszHeaderTitle = MAKEINTRESOURCE(IDS_DEVICETITLE);
         psp.pszHeaderSubTitle = MAKEINTRESOURCE(IDS_DEVICESUBTITLE);
         psp.hInstance = hInst;
-        psp.lParam = (LPARAM)pSetupData;
+        psp.lParam = (LPARAM)&SetupData;
         psp.pfnDlgProc = DeviceDlgProc;
         psp.pszTemplate = MAKEINTRESOURCE(IDD_DEVICEPAGE);
         ahpsp[nPages++] = CreatePropertySheetPage(&psp);
@@ -858,7 +882,7 @@ _tWinMain(HINSTANCE hInst,
         psp.pszHeaderTitle = MAKEINTRESOURCE(IDS_DRIVETITLE);
         psp.pszHeaderSubTitle = MAKEINTRESOURCE(IDS_DRIVESUBTITLE);
         psp.hInstance = hInst;
-        psp.lParam = (LPARAM)pSetupData;
+        psp.lParam = (LPARAM)&SetupData;
         psp.pfnDlgProc = DriveDlgProc;
         psp.pszTemplate = MAKEINTRESOURCE(IDD_DRIVEPAGE);
         ahpsp[nPages++] = CreatePropertySheetPage(&psp);
@@ -869,7 +893,7 @@ _tWinMain(HINSTANCE hInst,
         psp.pszHeaderTitle = MAKEINTRESOURCE(IDS_SUMMARYTITLE);
         psp.pszHeaderSubTitle = MAKEINTRESOURCE(IDS_SUMMARYSUBTITLE);
         psp.hInstance = hInst;
-        psp.lParam = (LPARAM)pSetupData;
+        psp.lParam = (LPARAM)&SetupData;
         psp.pfnDlgProc = SummaryDlgProc;
         psp.pszTemplate = MAKEINTRESOURCE(IDD_SUMMARYPAGE);
         ahpsp[nPages++] = CreatePropertySheetPage(&psp);
@@ -881,7 +905,7 @@ _tWinMain(HINSTANCE hInst,
     psp.pszHeaderTitle = MAKEINTRESOURCE(IDS_PROCESSTITLE);
     psp.pszHeaderSubTitle = MAKEINTRESOURCE(IDS_PROCESSSUBTITLE);
     psp.hInstance = hInst;
-    psp.lParam = (LPARAM)pSetupData;
+    psp.lParam = (LPARAM)&SetupData;
     psp.pfnDlgProc = ProcessDlgProc;
     psp.pszTemplate = MAKEINTRESOURCE(IDD_PROCESSPAGE);
     ahpsp[nPages++] = CreatePropertySheetPage(&psp);
@@ -890,7 +914,7 @@ _tWinMain(HINSTANCE hInst,
     psp.dwSize = sizeof(PROPSHEETPAGE);
     psp.dwFlags = PSP_DEFAULT | PSP_HIDEHEADER;
     psp.hInstance = hInst;
-    psp.lParam = (LPARAM)pSetupData;
+    psp.lParam = (LPARAM)&SetupData;
     psp.pfnDlgProc = RestartDlgProc;
     psp.pszTemplate = MAKEINTRESOURCE(IDD_RESTARTPAGE);
     ahpsp[nPages++] = CreatePropertySheetPage(&psp);
@@ -909,14 +933,17 @@ _tWinMain(HINSTANCE hInst,
     /* Display the wizard */
     PropertySheet(&psh);
 
-    if (pSetupData->hTitleFont)
-        DeleteObject(pSetupData->hTitleFont);
+    if (SetupData.hTitleFont)
+        DeleteObject(SetupData.hTitleFont);
+
+    SetupCloseInfFile(SetupData.SetupInf);
 
-    HeapFree(GetProcessHeap(), 0, pSetupData);
+Quit:
 
-#if 0
-    EnableShutdownPrivilege();
+#if 0 // NOTE: Disabled for testing purposes only!
+    EnablePrivilege(SE_SHUTDOWN_NAME, TRUE);
     ExitWindowsEx(EWX_REBOOT, 0);
+    EnablePrivilege(SE_SHUTDOWN_NAME, FALSE);
 #endif
 
     return 0;
index c7bcfdc..15323db 100644 (file)
 #ifndef _REACTOS_PCH_
 #define _REACTOS_PCH_
 
+/* C Headers */
+#include <stdlib.h>
 #include <stdarg.h>
+#include <tchar.h>
+
+/* PSDK/NDK */
+#define WIN32_NO_STATUS
 #include <windef.h>
 #include <winbase.h>
 #include <winreg.h>
 #include <wingdi.h>
 #include <winuser.h>
-#include <tchar.h>
-#include <setupapi.h>
+
+#include <commctrl.h>
+/**/#include <setupapi.h>/**/
 #include <devguid.h>
-#include <wine/unicode.h>
+// #include <wine/unicode.h>
+
+#define NTOS_MODE_USER
+#include <ndk/cmtypes.h> // For CM_DISK stuff
+#include <ndk/iofuncs.h> // For NtCreate/OpenFile
+#include <ndk/rtlfuncs.h>
+
+
+/* Setup library headers */
+// #include <reactos/rosioctl.h>
+#include <../lib/setuplib.h>
+// #include "errorcode.h"
 
 
 typedef struct _LANG
@@ -71,20 +89,22 @@ typedef struct _SETUPDATA
     TCHAR szAbortMessage[512];
     TCHAR szAbortTitle[64];
 
+    USETUP_DATA USetupData;
+    HINF SetupInf;
+
     // Settings
-    LONG DestDiskNumber; // physical disk
-    LONG DestPartNumber; // partition on disk
     LONG DestPartSize; // if partition doesn't exist, size of partition
     LONG FSType; // file system type on partition 
-    LONG MBRInstallType; // install bootloader
     LONG FormatPart; // type of format the partition
+
     LONG SelectedLangId; // selected language (table index)
     LONG SelectedKBLayout; // selected keyboard layout (table index)
-    TCHAR InstallDir[MAX_PATH]; // installation directory on hdd
     LONG SelectedComputer; // selected computer type (table index)
     LONG SelectedDisplay; // selected display type (table index)
     LONG SelectedKeyboard; // selected keyboard type (table index)
     BOOLEAN RepairUpdateFlag; // flag for update/repair an installed reactos
+
+
     // txtsetup.sif data
     LONG DefaultLang; // default language (table index)
     PLANG pLanguages;
@@ -100,6 +120,9 @@ typedef struct _SETUPDATA
     LONG KeybCount;
 } SETUPDATA, *PSETUPDATA;
 
+extern HANDLE ProcessHeap;
+extern BOOLEAN IsUnattendedSetup;
+
 typedef struct _IMGINFO
 {
     HBITMAP hBitmap;
@@ -109,6 +132,17 @@ typedef struct _IMGINFO
 
 
 
+/*
+ * Attempts to convert a pure NT file path into a corresponding Win32 path.
+ * Adapted from GetInstallSourceWin32() in dll/win32/syssetup/wizard.c
+ */
+BOOL
+ConvertNtPathToWin32Path(
+    OUT PWSTR pwszPath,
+    IN DWORD cchPathMax,
+    IN PCWSTR pwszNTPath);
+
+
 /* drivepage.c */
 INT_PTR
 CALLBACK