[togo] Add Windows To Go support - part 2

* Closes #126
* Only supported on Windows 8 or later for now
* Also fix MinGW and WDK compilation issues
This commit is contained in:
Pete Batard 2015-01-16 01:51:24 +00:00
parent 295650a8b4
commit 032d4413c8
17 changed files with 251 additions and 70 deletions

View File

@ -259,9 +259,16 @@ t MSG_093 "IMPORTANT: THIS DRIVE CONTAINS MULTIPLE PARTITIONS!!\n\n"
"Should you wish to proceed, you are responsible for any data loss on these partitions."
t MSG_094 "Multiple partitions detected"
t MSG_095 "DD Image"
t MSG_096 "Only FAT/FAT32 is supported for this type of ISO. Please select FAT/FAT32 as the File system."
t MSG_097 "Only 'bootmgr' or 'WinPE' based ISO images can currently be used with NTFS."
t MSG_098 "FAT/FAT32 can only be used for isolinux based ISO images or when the Target Type is UEFI."
t MSG_096 "The file system currently selected can not be used with this type of ISO. "
"Please select a different file system or use a different ISO."
t MSG_097 "'Windows To Go' can only be applied if the file system is NTFS."
t MSG_098 "IMPORTANT: You are trying to install 'Windows To Go', but your USB drive doesn't "
"have the 'FIXED' attribute. Because of this Windows will most likely freeze during boot, "
"as Microsoft hasn't designed it to work with drives that are 'REMOVABLE'.\n\n"
"Do you still want to proceed?\n\n"
"Note: the 'FIXED/REMOVABLE' attribute is a hardware property that can only be changed "
"using custom tools from the drive manufacturer. However those tools are ALMOST NEVER "
"provided to the public..."
t MSG_099 "Filesystem limitation"
t MSG_100 "This ISO image contains a file larger than 4GB, which is more than the "
"maximum size allowed for a FAT or FAT32 file system."
@ -364,6 +371,7 @@ t MSG_186 "Rufus does not install or run background services, therefore update c
t MSG_187 "Invalid image for selected boot option"
t MSG_188 "The current image doesn't match the boot option selected. Please use a different image or choose a different boot option."
t MSG_189 "This ISO image is not compatible with the selected filesystem"
t MSG_190 "Incompatible drive detected"
t MSG_191 "Write pass"
t MSG_192 "Read pass"
t MSG_193 "Downloaded %s"

11
res/togo/san_policy.xml Normal file
View File

@ -0,0 +1,11 @@
<?xml version='1.0' encoding='utf-8' standalone='yes'?>
<unattend xmlns="urn:schemas-microsoft-com:unattend">
<settings pass="offlineServicing">
<component name="Microsoft-Windows-PartitionManager" processorArchitecture="x86" publicKeyToken="31bf3856ad364e35" language="neutral" versionScope="nonSxS" xmlns:wcm="http://schemas.microsoft.com/WMIConfig/2002/State" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<SanPolicy>4</SanPolicy>
</component>
<component name="Microsoft-Windows-PartitionManager" processorArchitecture="amd64" publicKeyToken="31bf3856ad364e35" language="neutral" versionScope="nonSxS" xmlns:wcm="http://schemas.microsoft.com/WMIConfig/2002/State" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<SanPolicy>4</SanPolicy>
</component>
</settings>
</unattend>

11
res/togo/unattend.xml Normal file
View File

@ -0,0 +1,11 @@
<?xml version="1.0" encoding="utf-8"?>
<unattend xmlns="urn:schemas-microsoft-com:unattend">
<settings pass="oobeSystem">
<component name="Microsoft-Windows-WinRE-RecoveryAgent" processorArchitecture="x86" publicKeyToken="31bf3856ad364e35" language="neutral" versionScope="nonSxS" xmlns:wcm="http://schemas.microsoft.com/WMIConfig/2002/State" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<UninstallWindowsRE>true</UninstallWindowsRE>
</component>
<component name="Microsoft-Windows-WinRE-RecoveryAgent" processorArchitecture="amd64" publicKeyToken="31bf3856ad364e35" language="neutral" versionScope="nonSxS" xmlns:wcm="http://schemas.microsoft.com/WMIConfig/2002/State" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<UninstallWindowsRE>true</UninstallWindowsRE>
</component>
</settings>
</unattend>

View File

@ -223,7 +223,6 @@
</ItemGroup>
<ItemGroup>
<None Include="..\..\res\down.ico" />
<None Include="..\..\res\localization\rufus.loc" />
<None Include="..\..\res\rufus.ico" />
<None Include="..\..\res\up.ico" />
</ItemGroup>

View File

@ -139,9 +139,6 @@
<None Include="..\..\res\down.ico">
<Filter>Resource Files</Filter>
</None>
<None Include="..\..\res\localization\rufus.loc">
<Filter>Resource Files</Filter>
</None>
</ItemGroup>
<ItemGroup>
<Manifest Include="..\common_controls_and_elevation.manifest">

View File

@ -187,6 +187,11 @@ static inline ssize_t full_read(int fd, void *buf, size_t count) {
return rb;
}
static inline struct tm *localtime_r(const time_t *timep, struct tm *result) {
result = localtime(timep);
return result;
}
#define full_write _write
#define safe_read full_read
#define lstat stat
@ -197,11 +202,6 @@ static inline ssize_t full_read(int fd, void *buf, size_t count) {
#define mkdir(x, y) _mkdirU(x)
#if defined(_MSC_VER)
static inline struct tm *localtime_r(const time_t *timep, struct tm *result) {
result = localtime(timep);
return result;
}
#define _S_IFBLK 0x3000
#define S_IFMT _S_IFMT

View File

@ -751,7 +751,7 @@ BOOL GetDrivePartitionData(DWORD DriveIndex, char* FileSystemName, DWORD FileSys
SelectedDrive.nPartitions++;
tmp[0] = 0;
wchar_to_utf8_no_alloc(DriveLayout->PartitionEntry[i].Gpt.Name, tmp, sizeof(tmp));
suprintf("Partition %d:\r\n Type: %s\r\n Name: '%s'\n", DriveLayout->PartitionEntry[i].PartitionNumber,
suprintf("Partition %d:\r\n Type: %s\r\n Name: '%s'\n", i+1,
GuidToString(&DriveLayout->PartitionEntry[i].Gpt.PartitionType), tmp);
suprintf(" ID: %s\r\n Size: %s (%lld bytes)\r\n Start Sector: %lld, Attributes: 0x%016llX\n",
GuidToString(&DriveLayout->PartitionEntry[i].Gpt.PartitionId), SizeToHumanReadable(DriveLayout->PartitionEntry[i].PartitionLength.QuadPart, TRUE, FALSE),

View File

@ -1225,6 +1225,79 @@ out:
return r;
}
// http://technet.microsoft.com/en-ie/library/jj721578.aspx
static BOOL SetupWinToGo(const char* drive_name)
{
char san_policy_path[] = "?:\\san_policy.xml", unattend_path[] = "?:\\Windows\\System32\\sysprep\\unattend.xml";
char *mounted_iso, image[128], cmd[128];
unsigned char *buffer;
DWORD bufsize;
FILE* fd;
uprintf("Windows To Go mode selected");
// First, we need to access the install.wim image, that resides on the ISO
mounted_iso = MountISO(image_path);
if (mounted_iso == NULL) {
uprintf("Could not mount ISO for Windows To Go installation");
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_ISO_EXTRACT);
return FALSE;
}
uprintf("Mounted ISO as '%s'", mounted_iso);
// Now we use the WIM API to apply that image
static_sprintf(image, "%s\\sources\\install.wim", mounted_iso);
if (!WimApplyImage(image, 1, drive_name)) {
uprintf("Failed to apply Windows To Go image");
if (!IS_ERROR(FormatStatus))
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_ISO_EXTRACT);
UnMountISO();
return FALSE;
}
UnMountISO();
uprintf("Setting up boot for Windows To Go...");
static_sprintf(cmd, "%C:\\Windows\\System32\\bcdboot.exe %C:\\Windows /f ALL /s %C:",
drive_name[0], drive_name[0], drive_name[0]);
if (RunCommand(cmd, NULL, TRUE) != 0) {
// Fatal, as the UFD is unlikely to boot then
uprintf("Command '%s' failed to run", cmd);
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_ISO_EXTRACT);
return FALSE;
}
UpdateProgress(OP_DOS, 99.0f);
// The following are non fatal if they fail
buffer = GetResource(hMainInstance, MAKEINTRESOURCEA(IDR_TOGO_SAN_POLICY_XML),
_RT_RCDATA, "san_policy.xml", &bufsize, FALSE);
san_policy_path[0] = drive_name[0];
uprintf("Applying san_policy.xml...");
fd = fopenU(san_policy_path, "wb");
if ((fd == NULL) || (fwrite(buffer, 1, bufsize, fd) != bufsize)) {
uprintf("Could not write '%s'\n", san_policy_path);
if (fd)
fclose(fd);
} else {
fclose(fd);
static_sprintf(cmd, "dism /Image:%C:\\ /Apply-Unattend:%s", drive_name[0], san_policy_path);
if (RunCommand(cmd, NULL, TRUE) != 0)
uprintf("Command '%s' failed to run");
}
uprintf("Copying 'unattend.xml'");
buffer = GetResource(hMainInstance, MAKEINTRESOURCEA(IDR_TOGO_UNATTEND_XML),
_RT_RCDATA, "unattend.xml", &bufsize, FALSE);
unattend_path[0] = drive_name[0];
fd = fopenU(unattend_path, "wb");
if ((fd == NULL) || (fwrite(buffer, 1, bufsize, fd) != bufsize)) {
uprintf("Could not write '%s'\n", unattend_path);
}
fclose(fd);
UpdateProgress(OP_DOS, 100.0f);
return TRUE;
}
/*
* Detect if a Windows Format prompt is active, by enumerating the
* whole Windows tree and looking for the relevant popup
@ -1305,10 +1378,10 @@ DWORD WINAPI FormatThread(void* param)
LARGE_INTEGER li;
uint64_t wb;
uint8_t *buffer = NULL, *aligned_buffer;
char *bb_msg, *guid_volume = NULL, *mounted_iso;
char *bb_msg, *guid_volume = NULL;
char drive_name[] = "?:\\";
char drive_letters[27];
char logfile[MAX_PATH], image[128], *userdir;
char logfile[MAX_PATH], *userdir;
char wim_image[] = "?:\\sources\\install.wim";
char efi_dst[] = "?:\\efi\\boot\\bootx64.efi";
char kolibri_dst[] = "?:\\MTLD_F32";
@ -1693,28 +1766,24 @@ DWORD WINAPI FormatThread(void* param)
UpdateProgress(OP_DOS, 0.0f);
PrintInfoDebug(0, MSG_231);
drive_name[2] = 0;
// TODO: Check that we have apply-wim support
if (HAS_TOGO(iso_report) && (Button_GetCheck(GetDlgItem(hMainDialog, IDC_WINDOWS_TO_GO)) == BST_CHECKED)) {
uprintf("Windows To Go mode selected");
mounted_iso = MountISO(image_path);
if (mounted_iso == NULL) {
uprintf("Could not mount ISO for Windows To Go installation");
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_ISO_EXTRACT);
} else {
uprintf("Mounted ISO as '%s'", mounted_iso);
static_sprintf(image, "%s\\sources\\install.wim", mounted_iso);
if (!WimApplyImage(image, 1, drive_name)) {
uprintf("Failed to setup Windows To Go");
if (!IS_ERROR(FormatStatus))
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_ISO_EXTRACT);
}
UnMountISO();
}
if (IS_ERROR(FormatStatus))
// Sanity checks
if (fs != FS_NTFS) {
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_INCOMPATIBLE_FS);
goto out;
}
if ((nWindowsVersion < WINDOWS_8) || ((WimExtractCheck() & 4) == 0)) {
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|ERROR_NOT_SUPPORTED;
goto out;
}
if (!SetupWinToGo(drive_name)) {
if (!IS_ERROR(FormatStatus))
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|ERROR_ISO_EXTRACT;
goto out;
}
} else if (!ExtractISO(image_path, drive_name, FALSE)) {
if (!IS_ERROR(FormatStatus))
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|ERROR_CANNOT_COPY;
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|ERROR_ISO_EXTRACT;
goto out;
}
if (iso_report.has_kolibrios) {

View File

@ -925,8 +925,8 @@ out:
/*
* The following is used for native ISO mounting in Windows 8 or later
*/
const GUID VIRTUAL_STORAGE_TYPE_VENDOR_MICROSOFT =
{ 0xEC984AECL, 0xA0F9, 0x47e9, { 0x90, 0x1F, 0x71, 0x41, 0x5A, 0x66, 0x34, 0x5B } };
#define VIRTUAL_STORAGE_TYPE_VENDOR_MICROSOFT \
{ 0xEC984AECL, 0xA0F9, 0x47e9, { 0x90, 0x1F, 0x71, 0x41, 0x5A, 0x66, 0x34, 0x5B } }
typedef enum _VIRTUAL_DISK_ACCESS_MASK {
VIRTUAL_DISK_ACCESS_NONE = 0x00000000,
@ -1015,7 +1015,7 @@ static HANDLE mounted_handle = INVALID_HANDLE_VALUE;
char* MountISO(const char* path)
{
VIRTUAL_STORAGE_TYPE vtype = { 1, VIRTUAL_STORAGE_TYPE_VENDOR_MICROSOFT };
ATTACH_VIRTUAL_DISK_PARAMETERS vparams = { ATTACH_VIRTUAL_DISK_VERSION_1, 0 };
ATTACH_VIRTUAL_DISK_PARAMETERS vparams = {0};
DWORD r;
wchar_t wtmp[128];
ULONG size = ARRAYSIZE(wtmp);
@ -1037,6 +1037,7 @@ char* MountISO(const char* path)
goto out;
}
vparams.Version = ATTACH_VIRTUAL_DISK_VERSION_1;
r = pfAttachVirtualDisk(mounted_handle, NULL, ATTACH_VIRTUAL_DISK_FLAG_READ_ONLY |
ATTACH_VIRTUAL_DISK_FLAG_NO_DRIVE_LETTER, 0, &vparams, NULL);
if (r != ERROR_SUCCESS) {

View File

@ -407,11 +407,11 @@ char* lmprintf(int msg_id, ...)
#define MSG_INFO 1
#define MSG_LOW_PRI 0
#define MSG_HIGH_PRI 1
char szMessage[2][2][MSG_LEN] = { 0 };
char szMessage[2][2][MSG_LEN] = { {"", ""}, {"", ""} };
char* szStatusMessage = szMessage[MSG_STATUS][MSG_HIGH_PRI];
static BOOL bStatusTimerArmed = FALSE;
static __inline OutputMessage(BOOL info, char* msg)
static void __inline OutputMessage(BOOL info, char* msg)
{
if (info)
SetWindowTextU(hInfo, msg);

View File

@ -506,9 +506,9 @@ static __inline int SHDeleteDirectoryExU(HWND hwnd, const char* pszPath, FILEOP_
// which is always expected to be larger than our UTF-16 one, and add 2 chars for good measure.
size_t wpszPath_len = strlen(pszPath) + 2;
wchar_t* wpszPath = (wchar_t*)calloc(wpszPath_len, sizeof(wchar_t));
SHFILEOPSTRUCTW shfo = { hwnd, FO_DELETE, wpszPath, NULL, fFlags, FALSE, NULL, NULL };
utf8_to_wchar_no_alloc(pszPath, wpszPath, wpszPath_len);
// FOF_SILENT | FOF_NOERRORUI | FOF_NOCONFIRMATION,
SHFILEOPSTRUCTW shfo = { hwnd, FO_DELETE, wpszPath, NULL, fFlags, FALSE, NULL, NULL };
ret = SHFileOperationW(&shfo);
wfree(pszPath);
return ret;

View File

@ -70,6 +70,8 @@
#define IDR_LC_RUFUS_LOC 500
#define IDR_XT_HOGGER 501
#define IDR_UEFI_TOGO 502
#define IDR_TOGO_SAN_POLICY_XML 503
#define IDR_TOGO_UNATTEND_XML 504
#define IDC_DEVICE 1001
#define IDC_FILESYSTEM 1002
#define IDC_START 1003
@ -411,7 +413,7 @@
#ifdef APSTUDIO_INVOKED
#ifndef APSTUDIO_READONLY_SYMBOLS
#define _APS_NO_MFC 1
#define _APS_NEXT_RESOURCE_VALUE 502
#define _APS_NEXT_RESOURCE_VALUE 505
#define _APS_NEXT_COMMAND_VALUE 40001
#define _APS_NEXT_CONTROL_VALUE 1071
#define _APS_NEXT_SYMED_VALUE 4000

View File

@ -933,8 +933,11 @@ static void DisplayISOProps(void)
uprintf(" Uses ReactOS: %s", YesNo(IS_REACTOS(iso_report)));
uprintf(" Uses WinPE: %s%s", YesNo(IS_WINPE(iso_report.winpe)), (iso_report.uses_minint) ? " (with /minint)" : "");
if ( ((!togo_mode) && (HAS_TOGO(iso_report))) || ((togo_mode) && (!HAS_TOGO(iso_report))) )
ToggleToGo();
// We don't support ToGo on Windows 7 or earlier, for lack of ISO mount capabilities
// TODO: add install.wim extraction workaround for Windows 7
if (nWindowsVersion >= WINDOWS_8)
if ( ((!togo_mode) && (HAS_TOGO(iso_report))) || ((togo_mode) && (!HAS_TOGO(iso_report))) )
ToggleToGo();
}
// The scanning process can be blocking for message processing => use a thread
@ -1186,7 +1189,18 @@ static BOOL BootCheck(void)
}
fs = (int)ComboBox_GetItemData(hFileSystem, ComboBox_GetCurSel(hFileSystem));
bt = GETBIOSTYPE((int)ComboBox_GetItemData(hPartitionScheme, ComboBox_GetCurSel(hPartitionScheme)));
if (bt == BT_UEFI) {
if ((togo_mode) && (Button_GetCheck(GetDlgItem(hMainDialog, IDC_WINDOWS_TO_GO)) == BST_CHECKED)) {
if (fs != FS_NTFS) {
// Windows To Go only works for NTFS
MessageBoxU(hMainDialog, lmprintf(MSG_097), lmprintf(MSG_092), MB_OK|MB_ICONERROR|MB_IS_RTL);
return FALSE;
} else if (SelectedDrive.Geometry.MediaType != FixedMedia) {
// I never had any success with drives that have the REMOVABLE attribute set, no matter the
// method or tool I tried. If you manage to get this working, I'd like to hear from you!
if (MessageBoxU(hMainDialog, lmprintf(MSG_098), lmprintf(MSG_190), MB_YESNO|MB_ICONWARNING|MB_IS_RTL) != IDYES)
return FALSE;
}
} else if (bt == BT_UEFI) {
if (!iso_report.has_efi) {
// Unsupported ISO
MessageBoxU(hMainDialog, lmprintf(MSG_091), lmprintf(MSG_090), MB_OK|MB_ICONERROR|MB_IS_RTL);
@ -1198,24 +1212,16 @@ static BOOL BootCheck(void)
ShellExecuteA(hMainDialog, "open", SEVENZIP_URL, NULL, NULL, SW_SHOWNORMAL);
return FALSE;
}
} else if ((fs == FS_NTFS) && (!iso_report.has_bootmgr) && (!IS_WINPE(iso_report.winpe)) && (!IS_GRUB(iso_report))) {
if (HAS_SYSLINUX(iso_report)) {
// Only FAT/FAT32 is supported for this type of ISO
MessageBoxU(hMainDialog, lmprintf(MSG_096), lmprintf(MSG_092), MB_OK|MB_ICONERROR|MB_IS_RTL);
} else {
// Only 'bootmgr' or 'WinPE' based ISO images can currently be used with NTFS
MessageBoxU(hMainDialog, lmprintf(MSG_097), lmprintf(MSG_090), MB_OK|MB_ICONERROR|MB_IS_RTL);
}
} else if ( ((fs == FS_NTFS) && (!iso_report.has_bootmgr) && (!IS_WINPE(iso_report.winpe)) && (!IS_GRUB(iso_report)))
|| (((fs == FS_FAT16)||(fs == FS_FAT32)) && (!HAS_SYSLINUX(iso_report)) && (!allow_dual_uefi_bios) &&
(!IS_REACTOS(iso_report)) && (!iso_report.has_kolibrios) && (!IS_GRUB(iso_report))) ) {
// Incompatible FS and ISO
MessageBoxU(hMainDialog, lmprintf(MSG_096), lmprintf(MSG_092), MB_OK|MB_ICONERROR|MB_IS_RTL);
return FALSE;
} else if ((fs == FS_FAT16) && (iso_report.has_kolibrios)) {
// KolibriOS doesn't support FAT16
MessageBoxU(hMainDialog, lmprintf(MSG_189), lmprintf(MSG_099), MB_OK|MB_ICONERROR|MB_IS_RTL);
return FALSE;
} else if (((fs == FS_FAT16)||(fs == FS_FAT32)) && (!HAS_SYSLINUX(iso_report)) && (!allow_dual_uefi_bios) &&
(!IS_REACTOS(iso_report)) && (!iso_report.has_kolibrios) && (!IS_GRUB(iso_report))) {
// FAT/FAT32 can only be used for isolinux based ISO images or when the Target Type is UEFI
MessageBoxU(hMainDialog, lmprintf(MSG_098), lmprintf(MSG_090), MB_OK|MB_ICONERROR|MB_IS_RTL);
return FALSE;
}
if (((fs == FS_FAT16)||(fs == FS_FAT32)) && (iso_report.has_4GB_file)) {
// This ISO image contains a file larger than 4GB file (FAT32)
@ -2153,6 +2159,16 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_CANT_START_THREAD);
}
break;
case IDC_WINDOWS_TO_GO:
if (Button_GetCheck(GetDlgItem(hMainDialog, IDC_WINDOWS_TO_GO)) == BST_CHECKED) {
for (i=0; i<ComboBox_GetCount(hFileSystem); i++) {
if (ComboBox_GetItemData(hFileSystem, i) == FS_NTFS) {
IGNORE_RETVAL(ComboBox_SetCurSel(hFileSystem, i));
break;
}
}
}
break;
case IDC_RUFUS_MBR:
if ((HIWORD(wParam)) == BN_CLICKED)
mbr_selected_by_user = IsChecked(IDC_RUFUS_MBR);

View File

@ -395,6 +395,7 @@ extern char* FileDialog(BOOL save, char* path, const ext_t* ext, DWORD options);
extern BOOL FileIO(BOOL save, char* path, char** buffer, DWORD* size);
extern unsigned char* GetResource(HMODULE module, char* name, char* type, const char* desc, DWORD* len, BOOL duplicate);
extern DWORD GetResourceSize(HMODULE module, char* name, char* type, const char* desc);
extern DWORD RunCommand(const char* cmdline, const char* dir, BOOL log);
extern BOOL GetUSBDevices(DWORD devnum);
extern BOOL SetLGP(BOOL bRestore, BOOL* bExistingKey, const char* szPath, const char* szPolicy, DWORD dwValue);
extern LONG GetEntryWidth(HWND hDropDown, const char* entry);

View File

@ -32,7 +32,7 @@ LANGUAGE LANG_NEUTRAL, SUBLANG_NEUTRAL
IDD_DIALOG DIALOGEX 12, 12, 242, 376
STYLE DS_SETFONT | DS_MODALFRAME | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "Rufus 2.0.0.574"
CAPTION "Rufus 2.0.0.575"
FONT 8, "Segoe UI", 400, 0, 0x1
BEGIN
DEFPUSHBUTTON "Start",IDC_START,127,339,50,14
@ -157,7 +157,7 @@ END
IDD_DIALOG_XP DIALOGEX 12, 12, 242, 376
STYLE DS_SETFONT | DS_MODALFRAME | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "Rufus 2.0.0.574"
CAPTION "Rufus 2.0.0.575"
FONT 8, "MS Shell Dlg", 400, 0, 0x1
BEGIN
DEFPUSHBUTTON "Start",IDC_START,127,339,50,14
@ -283,7 +283,7 @@ END
IDD_DIALOG_RTL DIALOGEX 12, 12, 242, 376
STYLE DS_SETFONT | DS_MODALFRAME | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU
EXSTYLE WS_EX_RTLREADING | WS_EX_APPWINDOW | WS_EX_LAYOUTRTL
CAPTION "Rufus 2.0.0.574"
CAPTION "Rufus 2.0.0.575"
FONT 8, "Segoe UI", 400, 0, 0x1
BEGIN
DEFPUSHBUTTON "Start",IDC_START,127,339,50,14
@ -415,7 +415,7 @@ END
IDD_DIALOG_RTL_XP DIALOGEX 12, 12, 242, 376
STYLE DS_SETFONT | DS_MODALFRAME | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU
EXSTYLE WS_EX_RTLREADING | WS_EX_APPWINDOW | WS_EX_LAYOUTRTL
CAPTION "Rufus 2.0.0.574"
CAPTION "Rufus 2.0.0.575"
FONT 8, "MS Shell Dlg", 400, 0, 0x1
BEGIN
DEFPUSHBUTTON "Start",IDC_START,127,339,50,14
@ -612,6 +612,8 @@ BEGIN
"IDR_FD_EGA18_CPX RCDATA ""../res/freedos/ega18.cpx""\r\n"
"IDR_XT_HOGGER RCDATA ""../res/hogger/hogger.exe""\r\n"
"IDR_UEFI_TOGO RCDATA ""../res/uefi/uefi-togo.img""\r\n"
"IDR_TOGO_SAN_POLICY_XML RCDATA ""../res/togo/san_policy.xml""\r\n"
"IDR_TOGO_UNATTEND_XML RCDATA ""../res/togo/unattend.xml""\r\n"
"\r\n"
"// Must reference a manifest for visual styles and elevation\r\n"
"// Oh, and it must happen at the end, or MinGW will ignore it!\r\n"
@ -669,8 +671,8 @@ END
//
VS_VERSION_INFO VERSIONINFO
FILEVERSION 2,0,0,574
PRODUCTVERSION 2,0,0,574
FILEVERSION 2,0,0,575
PRODUCTVERSION 2,0,0,575
FILEFLAGSMASK 0x3fL
#ifdef _DEBUG
FILEFLAGS 0x1L
@ -687,13 +689,13 @@ BEGIN
BEGIN
VALUE "CompanyName", "Akeo Consulting (http://akeo.ie)"
VALUE "FileDescription", "Rufus"
VALUE "FileVersion", "2.0.0.574"
VALUE "FileVersion", "2.0.0.575"
VALUE "InternalName", "Rufus"
VALUE "LegalCopyright", "© 2011-2015 Pete Batard (GPL v3)"
VALUE "LegalTrademarks", "http://www.gnu.org/copyleft/gpl.html"
VALUE "OriginalFilename", "rufus.exe"
VALUE "ProductName", "Rufus"
VALUE "ProductVersion", "2.0.0.574"
VALUE "ProductVersion", "2.0.0.575"
END
END
BLOCK "VarFileInfo"
@ -765,6 +767,8 @@ IDR_FD_EGA17_CPX RCDATA "../res/freedos/ega17.cpx"
IDR_FD_EGA18_CPX RCDATA "../res/freedos/ega18.cpx"
IDR_XT_HOGGER RCDATA "../res/hogger/hogger.exe"
IDR_UEFI_TOGO RCDATA "../res/uefi/uefi-togo.img"
IDR_TOGO_SAN_POLICY_XML RCDATA "../res/togo/san_policy.xml"
IDR_TOGO_UNATTEND_XML RCDATA "../res/togo/unattend.xml"
// Must reference a manifest for visual styles and elevation
// Oh, and it must happen at the end, or MinGW will ignore it!

View File

@ -528,6 +528,68 @@ DWORD GetResourceSize(HMODULE module, char* name, char* type, const char* desc)
return (GetResource(module, name, type, desc, &len, FALSE) == NULL)?0:len;
}
// Run a console command, with optional redirection of stdout and stderr to our log
DWORD RunCommand(const char* cmd, const char* dir, BOOL log)
{
DWORD ret, dwRead, dwAvail, dwMsg;
STARTUPINFOA si = {0};
PROCESS_INFORMATION pi = {0};
HANDLE hOutputRead = INVALID_HANDLE_VALUE, hOutputWrite = INVALID_HANDLE_VALUE;
HANDLE hDupOutputWrite = INVALID_HANDLE_VALUE;
char output[1024];
si.cb = sizeof(si);
if (log) {
if (!CreatePipe(&hOutputRead, &hOutputWrite, NULL, sizeof(output)-1)) {
ret = GetLastError();
uprintf("Could not set commandline pipe: %s", WindowsErrorString());
goto out;
}
// We need an inheritable pipe endpoint handle
DuplicateHandle(GetCurrentProcess(), hOutputWrite, GetCurrentProcess(), &hDupOutputWrite,
0L, TRUE, DUPLICATE_CLOSE_SOURCE | DUPLICATE_SAME_ACCESS);
si.dwFlags = STARTF_USESHOWWINDOW | STARTF_USESTDHANDLES;
si.wShowWindow = SW_HIDE;
si.hStdOutput = hDupOutputWrite;
si.hStdError = hDupOutputWrite;
}
if (!CreateProcessU(NULL, cmd, NULL, NULL, TRUE,
NORMAL_PRIORITY_CLASS | CREATE_NO_WINDOW, NULL, dir, &si, &pi)) {
ret = GetLastError();
uprintf("Unable to launch command '%s': %s", WindowsErrorString());
goto out;
}
if (log) {
while (1) {
if (PeekNamedPipe(hOutputRead, output, sizeof(output)-1, &dwRead, &dwAvail, &dwMsg)) {
// Don't care about possible multiple reads being needed
if ((dwAvail != 0) && (ReadFile(hOutputRead, output, dwAvail, &dwRead, NULL)) && (dwRead != 0)) {
// This seems to be needed. Won't overflow since we set our max sizes to sizeof(output)-1
output[dwAvail] = 0;
uprintf(output);
}
}
if (WaitForSingleObject(pi.hProcess, 0) == WAIT_OBJECT_0)
break;
Sleep(100);
};
} else {
WaitForSingleObject(pi.hProcess, INFINITE);
}
if (!GetExitCodeProcess(pi.hProcess, &ret))
ret = GetLastError();
CloseHandle(pi.hProcess);
CloseHandle(pi.hThread);
out:
safe_closehandle(hDupOutputWrite);
safe_closehandle(hOutputRead);
return ret;
}
/*
* Set or restore a Local Group Policy DWORD key indexed by szPath/SzPolicy
*/

View File

@ -430,6 +430,7 @@ static BOOL WimExtractFile_7z(const char* image, int index, const char* src, con
}
tmpdst[i] = 0;
// TODO: use RunCommand
si.cb = sizeof(si);
safe_sprintf(cmdline, sizeof(cmdline), "7z -y e \"%s\" %d\\%s", image, index, src);
uprintf("Extracting: %s (From %s)", dst, src);
@ -509,12 +510,11 @@ DWORD WINAPI WimProgressCallback(DWORD dwMsgId, WPARAM wParam, LPARAM lParam, PV
switch (dwMsgId) {
case WIM_MSG_PROGRESS:
uprintf(" %d%% completed", (DWORD)wParam);
UpdateProgress(OP_DOS, 1.0f*(DWORD)wParam);
UpdateProgress(OP_DOS, 0.98f*(DWORD)wParam);
break;
case WIM_MSG_PROCESS:
// The amount of files processed is a bit overwhelming, and displaying it all slows us down
//#define WIM_DISPLAY_INDIVIDUAL_FILES
#if WIM_DISPLAY_INDIVIDUAL_FILES
#if 0
str = wchar_to_utf8((PWSTR)wParam);
uprintf("Applying: '%s'", str);
PrintStatus(0, MSG_000, str); // MSG_000 is "%s"
@ -595,7 +595,7 @@ static DWORD WINAPI WimApplyImageThread(LPVOID param)
goto out;
}
uprintf("Applying image...");
uprintf("Applying Windows image...");
if (!pfWIMApplyImage(hImage, wdst, 0)) {
uprintf(" Could not apply image: %s", WindowsErrorString());
goto out;
@ -618,11 +618,11 @@ out:
BOOL WimApplyImage(const char* image, int index, const char* dst)
{
HANDLE handle;
DWORD dw = 0;
_image = image;
_index = index;
_dst = dst;
HANDLE handle;
DWORD dw = 0;
handle = CreateThread(NULL, 0, WimApplyImageThread, NULL, 0, NULL);
if (handle == NULL) {