From 150be524791dcb9fd70b53be1528b62d9ab02786 Mon Sep 17 00:00:00 2001 From: Pete Batard Date: Sat, 24 Jun 2017 17:23:06 +0100 Subject: [PATCH] [iso] notify if the file size on disk is smaller than expected ISO size * Closes #963 * Also fix a potential issue with Notification() --- res/localization/rufus.loc | 4 ++++ src/iso.c | 7 +++++++ src/msapi_utf8.h | 13 ++++++++++++- src/net.c | 3 +++ src/rufus.c | 11 +++++++++++ src/rufus.h | 1 + src/rufus.rc | 10 +++++----- src/stdlg.c | 4 +++- 8 files changed, 46 insertions(+), 7 deletions(-) diff --git a/res/localization/rufus.loc b/res/localization/rufus.loc index 3eecd28a..20e3e3b3 100644 --- a/res/localization/rufus.loc +++ b/res/localization/rufus.loc @@ -559,6 +559,10 @@ t MSG_293 "Unsupported Windows version" t MSG_294 "This version of Windows is no longer supported by Rufus." t MSG_295 "Warning: Unofficial version" t MSG_296 "This version of Rufus was NOT produced by its official developer(s).\n\nAre you sure you want to run it?" +t MSG_297 "Truncated ISO detected" +t MSG_298 "The ISO file you have selected does not match its declared size: %s of data is missing!\n\nIf you obtained " + "this file from the Internet, you should try to download a new copy and verify that the MD5 or SHA checksums match " + "the official ones.\n\nNote that you can compute the MD5 or SHA in Rufus by clicking the '#' button." ################################################################################ ############################# TRANSLATOR END COPY ############################## diff --git a/src/iso.c b/src/iso.c index d494fa79..f436cb57 100644 --- a/src/iso.c +++ b/src/iso.c @@ -651,6 +651,7 @@ BOOL ExtractISO(const char* src_iso, const char* dest_dir, BOOL scan) FILE* fd; int r = 1; iso9660_t* p_iso = NULL; + iso9660_pvd_t pvd; udf_t* p_udf = NULL; udf_dirent_t* p_udf_root; char *tmp, *buf, *ext; @@ -705,6 +706,8 @@ BOOL ExtractISO(const char* src_iso, const char* dest_dir, BOOL scan) if (scan_only) { if (udf_get_logical_volume_id(p_udf, img_report.label, sizeof(img_report.label)) <= 0) img_report.label[0] = 0; + // Open the UDF as ISO so that we can perform size checks + p_iso = iso9660_open(src_iso); } r = udf_extract_files(p_udf, p_udf_root, ""); goto out; @@ -746,6 +749,10 @@ try_iso: out: iso_blocking_status = -1; if (scan_only) { + struct __stat64 stat; + // Find if there is a mismatch between the ISO size, as reported by the PVD, and the actual file size + if ((iso9660_ifs_read_pvd(p_iso, &pvd)) && (_stat64U(src_iso, &stat) == 0)) + img_report.mismatch_size = (int64_t)(iso9660_get_pvd_space_size(&pvd)) * ISO_BLOCKSIZE - stat.st_size; // Remove trailing spaces from the label for (j=safe_strlen(img_report.label)-1; ((j>0)&&(isspaceU(img_report.label[j]))); j--) img_report.label[j] = 0; diff --git a/src/msapi_utf8.h b/src/msapi_utf8.h index 9f71a5ff..b9bd8178 100644 --- a/src/msapi_utf8.h +++ b/src/msapi_utf8.h @@ -3,7 +3,7 @@ * Compensating for what Microsoft should have done a long long time ago. * Also see http://utf8everywhere.org/ * - * Copyright © 2010-2015 Pete Batard + * Copyright © 2010-2017 Pete Batard * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -31,6 +31,8 @@ #include #include #include +#include +#include #if !defined(DDKBUILD) #include #endif @@ -924,6 +926,15 @@ static __inline int _openU(const char *filename, int oflag , int pmode) } #endif +static __inline int _stat64U(const char *path, struct __stat64 *buffer) +{ + int ret; + wconvert(path); + ret = _wstat64(wpath, buffer); + wfree(path); + return ret; +} + // returned UTF-8 string must be freed static __inline char* getenvU(const char* varname) { diff --git a/src/net.c b/src/net.c index 5de58b42..57a13ff5 100644 --- a/src/net.c +++ b/src/net.c @@ -533,6 +533,9 @@ static DWORD WINAPI CheckForUpdatesThread(LPVOID param) } vuprintf("Found match for %s on server %s", urlpath, server_url); + // IMPORTANT: You might need to edit your server's MIME conf so that it returns + // 'text/plain' for .ver files. Use 'curl -I' to check that you get something + // like 'Content-Type: text/plain; charset=UTF-8' when fetching your .ver files. dwSize = sizeof(mime); HttpQueryInfoA(hRequest, HTTP_QUERY_CONTENT_TYPE, (LPVOID)&mime, &dwSize, NULL); if (strncmp(mime, "text/plain", sizeof("text/plain")-1) != 0) diff --git a/src/rufus.c b/src/rufus.c index 1a95fcca..32c8116a 100644 --- a/src/rufus.c +++ b/src/rufus.c @@ -973,6 +973,17 @@ static void DisplayISOProps(void) uprintf("ISO label: '%s'", img_report.label); uprintf(" Size: %s (Projected)", SizeToHumanReadable(img_report.projected_size, FALSE, FALSE)); + if (img_report.mismatch_size > 0) { + uprintf(" ERROR: Detected that file on disk has been truncated by %s!", + SizeToHumanReadable(img_report.mismatch_size, FALSE, FALSE)); + MessageBoxU(hMainDialog, lmprintf(MSG_298, SizeToHumanReadable(img_report.mismatch_size, FALSE, FALSE)), + lmprintf(MSG_297), MB_ICONWARNING); + } else if (img_report.mismatch_size < 0) { + // Not an error (ISOHybrid?), but we report it just in case + uprintf(" Note: File on disk is larger than reported ISO size by %s...", + SizeToHumanReadable(-img_report.mismatch_size, FALSE, FALSE)); + } + PRINT_ISO_PROP(img_report.has_4GB_file, " Has a >4GB file"); PRINT_ISO_PROP(img_report.has_long_filename, " Has a >64 chars filename"); PRINT_ISO_PROP(HAS_SYSLINUX(img_report), " Uses: Syslinux/Isolinux v%s", img_report.sl_version_str); diff --git a/src/rufus.h b/src/rufus.h index d2a2b981..652231dc 100644 --- a/src/rufus.h +++ b/src/rufus.h @@ -279,6 +279,7 @@ typedef struct { char install_wim_path[64]; /* path to install.wim or install.swm */ uint64_t image_size; uint64_t projected_size; + int64_t mismatch_size; uint32_t install_wim_version; BOOLEAN is_iso; BOOLEAN is_bootable_img; diff --git a/src/rufus.rc b/src/rufus.rc index 57865bd8..a4a467a0 100644 --- a/src/rufus.rc +++ b/src/rufus.rc @@ -33,7 +33,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 EXSTYLE WS_EX_ACCEPTFILES -CAPTION "Rufus 2.15.1119" +CAPTION "Rufus 2.15.1120" FONT 8, "Segoe UI Symbol", 400, 0, 0x0 BEGIN LTEXT "Device",IDS_DEVICE_TXT,9,6,200,8 @@ -334,8 +334,8 @@ END // VS_VERSION_INFO VERSIONINFO - FILEVERSION 2,15,1119,0 - PRODUCTVERSION 2,15,1119,0 + FILEVERSION 2,15,1120,0 + PRODUCTVERSION 2,15,1120,0 FILEFLAGSMASK 0x3fL #ifdef _DEBUG FILEFLAGS 0x1L @@ -352,13 +352,13 @@ BEGIN BEGIN VALUE "CompanyName", "Akeo Consulting (http://akeo.ie)" VALUE "FileDescription", "Rufus" - VALUE "FileVersion", "2.15.1119" + VALUE "FileVersion", "2.15.1120" VALUE "InternalName", "Rufus" VALUE "LegalCopyright", "© 2011-2017 Pete Batard (GPL v3)" VALUE "LegalTrademarks", "http://www.gnu.org/copyleft/gpl.html" VALUE "OriginalFilename", "rufus.exe" VALUE "ProductName", "Rufus" - VALUE "ProductVersion", "2.15.1119" + VALUE "ProductVersion", "2.15.1120" END END BLOCK "VarFileInfo" diff --git a/src/stdlg.c b/src/stdlg.c index 2c830cc0..b511420f 100644 --- a/src/stdlg.c +++ b/src/stdlg.c @@ -813,7 +813,8 @@ BOOL Notification(int type, const notification_info* more_info, char* title, cha dialog_showing++; szMessageText = (char*)malloc(MAX_PATH); if (szMessageText == NULL) return FALSE; - szMessageTitle = title; + szMessageTitle = safe_strdup(title); + if (szMessageTitle == NULL) return FALSE; va_start(args, format); safe_vsnprintf(szMessageText, MAX_PATH-1, format, args); va_end(args); @@ -839,6 +840,7 @@ BOOL Notification(int type, const notification_info* more_info, char* title, cha } ret = (MyDialogBox(hMainInstance, IDD_NOTIFICATION, hMainDialog, NotificationCallback) == IDYES); safe_free(szMessageText); + safe_free(szMessageTitle); dialog_showing--; return ret; }