Skip to content

Commit

Permalink
[togo] enable selection of Windows version
Browse files Browse the repository at this point in the history
* Closes #847
* Also set rufus-next to 2.12
  • Loading branch information
pbatard committed Dec 13, 2016
1 parent 5113be0 commit 7d302d3
Show file tree
Hide file tree
Showing 15 changed files with 349 additions and 78 deletions.
20 changes: 10 additions & 10 deletions configure
@@ -1,6 +1,6 @@
#! /bin/sh
# Guess values for system-dependent variables and create Makefiles.
# Generated by GNU Autoconf 2.69 for rufus 2.11.
# Generated by GNU Autoconf 2.69 for rufus 2.12.
#
# Report bugs to <https://github.com/pbatard/rufus/issues>.
#
Expand Down Expand Up @@ -580,8 +580,8 @@ MAKEFLAGS=
# Identity of this package.
PACKAGE_NAME='rufus'
PACKAGE_TARNAME='rufus'
PACKAGE_VERSION='2.11'
PACKAGE_STRING='rufus 2.11'
PACKAGE_VERSION='2.12'
PACKAGE_STRING='rufus 2.12'
PACKAGE_BUGREPORT='https://github.com/pbatard/rufus/issues'
PACKAGE_URL='http://rufus.akeo.ie'

Expand Down Expand Up @@ -1228,7 +1228,7 @@ if test "$ac_init_help" = "long"; then
# Omit some internal or obsolete options to make the list less imposing.
# This message is too long to be a string in the A/UX 3.1 sh.
cat <<_ACEOF
\`configure' configures rufus 2.11 to adapt to many kinds of systems.
\`configure' configures rufus 2.12 to adapt to many kinds of systems.
Usage: $0 [OPTION]... [VAR=VALUE]...
Expand Down Expand Up @@ -1294,7 +1294,7 @@ fi

if test -n "$ac_init_help"; then
case $ac_init_help in
short | recursive ) echo "Configuration of rufus 2.11:";;
short | recursive ) echo "Configuration of rufus 2.12:";;
esac
cat <<\_ACEOF
Expand Down Expand Up @@ -1385,7 +1385,7 @@ fi
test -n "$ac_init_help" && exit $ac_status
if $ac_init_version; then
cat <<\_ACEOF
rufus configure 2.11
rufus configure 2.12
generated by GNU Autoconf 2.69
Copyright (C) 2012 Free Software Foundation, Inc.
Expand Down Expand Up @@ -1440,7 +1440,7 @@ cat >config.log <<_ACEOF
This file contains any messages produced by compilers while
running configure, to aid debugging if configure makes a mistake.
It was created by rufus $as_me 2.11, which was
It was created by rufus $as_me 2.12, which was
generated by GNU Autoconf 2.69. Invocation command line was
$ $0 $@
Expand Down Expand Up @@ -2303,7 +2303,7 @@ fi
# Define the identity of the package.
PACKAGE='rufus'
VERSION='2.11'
VERSION='2.12'
cat >>confdefs.h <<_ACEOF
Expand Down Expand Up @@ -4482,7 +4482,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
# report actual input values of CONFIG_FILES etc. instead of their
# values after options handling.
ac_log="
This file was extended by rufus $as_me 2.11, which was
This file was extended by rufus $as_me 2.12, which was
generated by GNU Autoconf 2.69. Invocation command line was
CONFIG_FILES = $CONFIG_FILES
Expand Down Expand Up @@ -4536,7 +4536,7 @@ _ACEOF
cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
ac_cs_version="\\
rufus config.status 2.11
rufus config.status 2.12
configured by $0, generated by GNU Autoconf 2.69,
with options \\"\$ac_cs_config\\"
Expand Down
2 changes: 1 addition & 1 deletion configure.ac
@@ -1,4 +1,4 @@
AC_INIT([rufus], [2.11], [https://github.com/pbatard/rufus/issues], [rufus], [http://rufus.akeo.ie])
AC_INIT([rufus], [2.12], [https://github.com/pbatard/rufus/issues], [rufus], [http://rufus.akeo.ie])
AM_INIT_AUTOMAKE([-Wno-portability foreign no-dist no-dependencies])
AC_CONFIG_SRCDIR([src/rufus.c])
AC_CONFIG_MACRO_DIR([m4])
Expand Down
2 changes: 2 additions & 0 deletions res/localization/rufus.loc
Expand Up @@ -553,6 +553,8 @@ t MSG_287 "Detection of non-USB removable drives"
t MSG_288 "Missing elevated privileges"
t MSG_289 "This application can only run with elevated privileges"
t MSG_290 "File Indexing"
t MSG_291 "Version selection"
t MSG_292 "Please select the version of Windows you want to install:"

################################################################################
############################# TRANSLATOR END COPY ##############################
Expand Down
8 changes: 4 additions & 4 deletions src/dev.c
Expand Up @@ -313,7 +313,7 @@ BOOL GetDevices(DWORD devnum)
StrArrayClear(&DriveLabel);
StrArrayCreate(&dev_if_path, 128);
// Add a dummy for string index zero, as this is what non matching hashes will point to
StrArrayAdd(&dev_if_path, "");
StrArrayAdd(&dev_if_path, "", TRUE);

device_id = (char*)malloc(MAX_PATH);
if (device_id == NULL)
Expand All @@ -340,7 +340,7 @@ BOOL GetDevices(DWORD devnum)
// Find the Device IDs for all the children of this hub
if (CM_Get_Child(&device_inst, dev_info_data.DevInst, 0) == CR_SUCCESS) {
device_id[0] = 0;
s = StrArrayAdd(&dev_if_path, devint_detail_data->DevicePath);
s = StrArrayAdd(&dev_if_path, devint_detail_data->DevicePath, TRUE);
uuprintf(" Hub[%d] = '%s'", s, devint_detail_data->DevicePath);
if ((s>= 0) && (CM_Get_Device_IDA(device_inst, device_id, MAX_PATH, 0) == CR_SUCCESS)) {
if ((k = htab_hash(device_id, &htab_devid)) != 0) {
Expand Down Expand Up @@ -741,8 +741,8 @@ BOOL GetDevices(DWORD devnum)
}

// Must ensure that the combo box is UNSORTED for indexes to be the same
StrArrayAdd(&DriveID, buffer);
StrArrayAdd(&DriveLabel, label);
StrArrayAdd(&DriveID, buffer, TRUE);
StrArrayAdd(&DriveLabel, label, TRUE);

IGNORE_RETVAL(ComboBox_SetItemData(hDeviceList, ComboBox_AddStringU(hDeviceList, entry), drive_index));
maxwidth = max(maxwidth, GetEntryWidth(hDeviceList, entry));
Expand Down
46 changes: 44 additions & 2 deletions src/format.c
Expand Up @@ -1277,8 +1277,11 @@ static BOOL SetupWinToGo(const char* drive_name, BOOL use_ms_efi)
static char san_policy_path[] = "?:\\san_policy.xml";
#endif
static char unattend_path[] = "?:\\Windows\\System32\\sysprep\\unattend.xml";
StrArray version_name, version_index;
char *mounted_iso, *ms_efi = NULL, image[128], cmd[MAX_PATH];
char tmp_path[MAX_PATH] = "", xml_file[MAX_PATH] = "";
unsigned char *buffer;
int i, index;
wchar_t wVolumeName[] = L"?:";
DWORD bufsize;
ULONG cluster_size;
Expand All @@ -1305,11 +1308,50 @@ static BOOL SetupWinToGo(const char* drive_name, BOOL use_ms_efi)
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_ISO_EXTRACT);
return FALSE;
}
static_sprintf(image, "%s%s", mounted_iso, &img_report.install_wim_path[2]);
uprintf("Mounted ISO as '%s'", mounted_iso);

// Then we need to take a look at the XML file in install.wim to allow users
// to select the version they want to extract
if ((GetTempPathU(sizeof(tmp_path), tmp_path) == 0)
|| (GetTempFileNameU(tmp_path, APPLICATION_NAME, 0, xml_file) == 0)
|| (xml_file[0] == 0)) {
// Last ditch effort to get a loc file - just extract it to the current directory
safe_strcpy(xml_file, sizeof(xml_file), ".\\RufVXml.tmp");
}
// GetTempFileName() may leave a file behind
DeleteFileU(xml_file);

// Must use the Windows WIM API as 7z messes up the XML
if (!WimExtractFile_API(image, 0, "[1].xml", xml_file)) {
uprintf("Failed to acquire WIM index");
}
StrArrayCreate(&version_name, 16);
StrArrayCreate(&version_index, 16);
for (i = 0; (StrArrayAdd(&version_name, get_token_data_file_indexed("DISPLAYNAME", xml_file, i+1), FALSE) >= 0) &&
(StrArrayAdd(&version_index, get_token_data_file_indexed("IMAGE INDEX", xml_file, i+1), FALSE) >= 0); i++);
DeleteFileU(xml_file);

if (i > 1)
i = Selection(lmprintf(MSG_291), lmprintf(MSG_292), version_name.String, i);
if (i <= 0) {
uprintf("Cancelled by user");
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|ERROR_CANCELLED;
UnMountISO();
StrArrayDestroy(&version_name);
StrArrayDestroy(&version_index);
return FALSE;
} else if (i == 0) {
index = 1;
} else {
index = atoi(version_index.String[i - 1]);
}
uprintf("Selected: '%s' (index %s)", version_name.String[i - 1], version_index.String[i - 1]);
StrArrayDestroy(&version_name);
StrArrayDestroy(&version_index);

// Now we use the WIM API to apply that image
static_sprintf(image, "%s%s", mounted_iso, &img_report.install_wim_path[2]);
if (!WimApplyImage(image, 1, drive_name)) {
if (!WimApplyImage(image, index, 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);
Expand Down
4 changes: 2 additions & 2 deletions src/iso.c
Expand Up @@ -226,12 +226,12 @@ static BOOL check_iso_props(const char* psz_dirname, int64_t i_file_length, cons

if (props->is_syslinux_cfg) {
// Maintain a list of all the isolinux/syslinux configs identified so far
StrArrayAdd(&config_path, psz_fullpath);
StrArrayAdd(&config_path, psz_fullpath, TRUE);
}
for (i=0; i<ARRAYSIZE(isolinux_bin); i++) {
if (safe_stricmp(psz_basename, isolinux_bin[i]) == 0) {
// Maintain a list of all the isolinux.bin files found
StrArrayAdd(&isolinux_path, psz_fullpath);
StrArrayAdd(&isolinux_path, psz_fullpath, TRUE);
}
}

Expand Down
14 changes: 14 additions & 0 deletions src/localization_data.h
Expand Up @@ -96,6 +96,20 @@ const loc_control_id control_id[] = {
LOC_CTRL(IDC_SELECTION_LINE),
LOC_CTRL(IDC_SELECTION_CHOICE1),
LOC_CTRL(IDC_SELECTION_CHOICE2),
LOC_CTRL(IDC_SELECTION_CHOICE3),
LOC_CTRL(IDC_SELECTION_CHOICE4),
LOC_CTRL(IDC_SELECTION_CHOICE5),
LOC_CTRL(IDC_SELECTION_CHOICE6),
LOC_CTRL(IDC_SELECTION_CHOICE7),
LOC_CTRL(IDC_SELECTION_CHOICE8),
LOC_CTRL(IDC_SELECTION_CHOICE9),
LOC_CTRL(IDC_SELECTION_CHOICE10),
LOC_CTRL(IDC_SELECTION_CHOICE11),
LOC_CTRL(IDC_SELECTION_CHOICE12),
LOC_CTRL(IDC_SELECTION_CHOICE13),
LOC_CTRL(IDC_SELECTION_CHOICE14),
LOC_CTRL(IDC_SELECTION_CHOICE15),
LOC_CTRL(IDC_SELECTION_CHOICEMAX),
LOC_CTRL(IDS_DEVICE_TXT),
LOC_CTRL(IDS_PARTITION_TYPE_TXT),
LOC_CTRL(IDS_FILESYSTEM_TXT),
Expand Down
25 changes: 16 additions & 9 deletions src/parser.c
Expand Up @@ -571,20 +571,24 @@ BOOL get_loc_data_file(const char* filename, loc_cmd* lcmd)

/*
* Parse a line of UTF-16 text and return the data if it matches the 'token'
* The parsed line is of the form: [ ]token[ ]=[ ]["]data["][ ] and is
* The parsed line is of the form: [ ][<][ ]token[ ][=|>][ ]["]data["][ ][<] and is
* modified by the parser
*/
static wchar_t* get_token_data_line(const wchar_t* wtoken, wchar_t* wline)
{
size_t i, r;
BOOLEAN quoteth = FALSE;
BOOLEAN xml = FALSE;

if ((wtoken == NULL) || (wline == NULL) || (wline[0] == 0))
return NULL;

i = 0;

// Skip leading spaces
// Skip leading spaces and opening '<'
i += wcsspn(&wline[i], wspace);
if (wline[i] == L'<')
i++;
i += wcsspn(&wline[i], wspace);

// Our token should begin a line
Expand All @@ -597,12 +601,14 @@ static wchar_t* get_token_data_line(const wchar_t* wtoken, wchar_t* wline)
// Skip spaces
i += wcsspn(&wline[i], wspace);

// Check for an equal sign
if (wline[i] != L'=')
// Check for '=' or '>' sign
if (wline[i] == L'>')
xml = TRUE;
else if (wline[i] != L'=')
return NULL;
i++;

// Skip spaces after equal sign
// Skip spaces
i += wcsspn(&wline[i], wspace);

// eliminate leading quote, if it exists
Expand All @@ -615,7 +621,7 @@ static wchar_t* get_token_data_line(const wchar_t* wtoken, wchar_t* wline)
r = i;

// locate end of string or quote
while ( (wline[i] != 0) && ((wline[i] != L'"') || ((wline[i] == L'"') && (!quoteth))) )
while ( (wline[i] != 0) && (((wline[i] != L'"') && (wline[i] != L'<')) || ((wline[i] == L'"') && (!quoteth)) || ((wline[i] == L'<') && (!xml))) )
i++;
wline[i--] = 0;

Expand All @@ -627,11 +633,12 @@ static wchar_t* get_token_data_line(const wchar_t* wtoken, wchar_t* wline)
}

/*
* Parse a file (ANSI or UTF-8 or UTF-16) and return the data for the first occurrence of 'token'
* Parse a file (ANSI or UTF-8 or UTF-16) and return the data for the 'index'th occurrence of 'token'
* The returned string is UTF-8 and MUST be freed by the caller
*/
char* get_token_data_file(const char* token, const char* filename)
char* get_token_data_file_indexed(const char* token, const char* filename, int index)
{
int i = 0;
wchar_t *wtoken = NULL, *wdata= NULL, *wfilename = NULL;
wchar_t buf[1024];
FILE* fd = NULL;
Expand Down Expand Up @@ -659,7 +666,7 @@ char* get_token_data_file(const char* token, const char* filename)
// Ideally, we'd check that our buffer fits the line
while (fgetws(buf, ARRAYSIZE(buf), fd) != NULL) {
wdata = get_token_data_line(wtoken, buf);
if (wdata != NULL) {
if ((wdata != NULL) && (++i == index)) {
ret = wchar_to_utf8(wdata);
break;
}
Expand Down
14 changes: 14 additions & 0 deletions src/resource.h
Expand Up @@ -134,6 +134,20 @@
#define IDC_SELECTION_LINE 1076
#define IDC_SELECTION_CHOICE1 1077
#define IDC_SELECTION_CHOICE2 1078
#define IDC_SELECTION_CHOICE3 1079
#define IDC_SELECTION_CHOICE4 1080
#define IDC_SELECTION_CHOICE5 1081
#define IDC_SELECTION_CHOICE6 1082
#define IDC_SELECTION_CHOICE7 1083
#define IDC_SELECTION_CHOICE8 1084
#define IDC_SELECTION_CHOICE9 1085
#define IDC_SELECTION_CHOICE10 1086
#define IDC_SELECTION_CHOICE11 1087
#define IDC_SELECTION_CHOICE12 1088
#define IDC_SELECTION_CHOICE13 1089
#define IDC_SELECTION_CHOICE14 1090
#define IDC_SELECTION_CHOICE15 1091
#define IDC_SELECTION_CHOICEMAX 1092
#define IDS_DEVICE_TXT 2000
#define IDS_PARTITION_TYPE_TXT 2001
#define IDS_FILESYSTEM_TXT 2002
Expand Down
9 changes: 8 additions & 1 deletion src/rufus.c
Expand Up @@ -2108,6 +2108,10 @@ void SaveISO(void)
}
}

#ifdef RUFUS_TEST
extern int SelectionDyn(char* title, char* message, char** szChoice, int nChoices);
#endif

/*
* Main dialog callback
*/
Expand Down Expand Up @@ -2140,6 +2144,8 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA
case WM_COMMAND:
#ifdef RUFUS_TEST
if (LOWORD(wParam) == IDC_TEST) {
char* choices[] = { "Choice 1", "Choice 2", "Choice 3" };
SelectionDyn("Test Choice", "Unused", choices, ARRAYSIZE(choices));
break;
}
#endif
Expand Down Expand Up @@ -2438,8 +2444,9 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA
(ComboBox_GetItemData(hBootType, ComboBox_GetCurSel(hBootType)) == BT_ISO)) {
char* iso_image = lmprintf(MSG_036);
char* dd_image = lmprintf(MSG_095);
char* choices[2] = { lmprintf(MSG_276, iso_image), lmprintf(MSG_277, dd_image) };
i = Selection(lmprintf(MSG_274), lmprintf(MSG_275, iso_image, dd_image, iso_image, dd_image),
lmprintf(MSG_276, iso_image), lmprintf(MSG_277, dd_image));
choices, 2);
if (i < 0) { // Cancel
format_op_in_progress = FALSE;
PROCESS_QUEUED_EVENTS;
Expand Down
9 changes: 6 additions & 3 deletions src/rufus.h
Expand Up @@ -422,7 +422,7 @@ extern BOOL CreateTooltip(HWND hControl, const char* message, int duration);
extern void DestroyTooltip(HWND hWnd);
extern void DestroyAllTooltips(void);
extern BOOL Notification(int type, const notification_info* more_info, char* title, char* format, ...);
extern int Selection(char* title, char* message, char* selection1, char* selection2);
extern int Selection(char* title, char* message, char** choices, int size);
extern SIZE GetTextSize(HWND hCtrl);
extern BOOL ExtractDOS(const char* path);
extern BOOL ExtractISO(const char* src_iso, const char* dest_dir, BOOL scan);
Expand Down Expand Up @@ -450,7 +450,8 @@ extern BOOL SetUpdateCheck(void);
extern BOOL CheckForUpdates(BOOL force);
extern void DownloadNewVersion(void);
extern BOOL IsShown(HWND hDlg);
extern char* get_token_data_file(const char* token, const char* filename);
extern char* get_token_data_file_indexed(const char* token, const char* filename, int index);
#define get_token_data_file(token, filename) get_token_data_file_indexed(token, filename, 1)
extern char* set_token_data_file(const char* token, const char* data, const char* filename);
extern char* get_token_data_buffer(const char* token, unsigned int n, const char* buffer, size_t buffer_size);
extern char* insert_section_data(const char* filename, const char* section, const char* data, BOOL dos2unix);
Expand All @@ -459,6 +460,8 @@ extern char* replace_char(const char* src, const char c, const char* rep);
extern void parse_update(char* buf, size_t len);
extern uint8_t WimExtractCheck(void);
extern BOOL WimExtractFile(const char* wim_image, int index, const char* src, const char* dst);
extern BOOL WimExtractFile_API(const char* image, int index, const char* src, const char* dst);
extern BOOL WimExtractFile_7z(const char* image, int index, const char* src, const char* dst);
extern BOOL WimApplyImage(const char* image, int index, const char* dst);
extern BOOL IsBootableImage(const char* path);
extern BOOL AppendVHDFooter(const char* vhd_path);
Expand Down Expand Up @@ -507,7 +510,7 @@ typedef struct {
uint32_t Max; // Maximum array size
} StrArray;
extern void StrArrayCreate(StrArray* arr, uint32_t initial_size);
extern int32_t StrArrayAdd(StrArray* arr, const char* str);
extern int32_t StrArrayAdd(StrArray* arr, const char* str, BOOL );
extern void StrArrayClear(StrArray* arr);
extern void StrArrayDestroy(StrArray* arr);
#define IsStrArrayEmpty(arr) (arr.Index == 0)
Expand Down

0 comments on commit 7d302d3

Please sign in to comment.