[syslinux] update Syslinux to v6.03

* Also add experimental support for Syslinux/NTFS
* Closes #391
This commit is contained in:
Pete Batard 2014-11-11 19:53:39 +00:00
parent 37ffbabaaf
commit 6ca024ae3b
23 changed files with 747 additions and 140 deletions

View file

@ -1554,7 +1554,7 @@ DWORD WINAPI FormatThread(void* param)
// We must close and unlock the volume to write files to it
safe_unlockclose(hLogicalVolume);
} else if ( (dt == DT_SYSLINUX_V4) || (dt == DT_SYSLINUX_V5) || ((dt == DT_ISO) && ((fs == FS_FAT16) || (fs == FS_FAT32))) ) {
if (!InstallSyslinux(DriveIndex, drive_name[0])) {
if (!InstallSyslinux(DriveIndex, drive_name[0], fs)) {
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|ERROR_INSTALL_FAILURE;
}
}

View file

@ -50,8 +50,8 @@
#define IDR_FD_EGA18_CPX 326
#define IDR_SL_LDLINUX_V4_BSS 400
#define IDR_SL_LDLINUX_V4_SYS 401
#define IDR_SL_LDLINUX_V5_BSS 402
#define IDR_SL_LDLINUX_V5_SYS 403
#define IDR_SL_LDLINUX_V6_BSS 402
#define IDR_SL_LDLINUX_V6_SYS 403
#define IDR_SL_MBOOT_C32 404
#define IDR_LC_RUFUS_LOC 500
#define IDR_XT_HOGGER 501

View file

@ -1178,7 +1178,8 @@ static BOOL BootCheck(void)
}
}
}
} else if (iso_report.sl_version != embedded_sl_version[1]) {
} else if ((iso_report.sl_version != embedded_sl_version[1]) ||
(safe_strcmp(iso_report.sl_version_ext, embedded_sl_version_ext[1]) != 0)) {
// Unlike what was the case for v4 and earlier, Syslinux v5+ versions are INCOMPATIBLE with one another!
IGNORE_RETVAL(_chdirU(app_dir));
IGNORE_RETVAL(_mkdir(FILES_DIR));
@ -1200,7 +1201,7 @@ static BOOL BootCheck(void)
iso_report.sl_version_str, iso_report.sl_version_ext);
} else {
r = MessageBoxU(hMainDialog, lmprintf(MSG_114, iso_report.sl_version_str, iso_report.sl_version_ext,
embedded_sl_version_str[1]),
embedded_sl_version_str[1], embedded_sl_version_ext[1]),
lmprintf(MSG_115), MB_YESNO|MB_ICONWARNING|MB_IS_RTL);
if (r != IDYES)
return FALSE;
@ -1287,7 +1288,7 @@ void InitDialog(HWND hDlg)
HDC hDC;
int i, i16, s16;
char tmp[128], *token, *buf, *ext;
static char* resource[2] = { MAKEINTRESOURCEA(IDR_SL_LDLINUX_V4_SYS), MAKEINTRESOURCEA(IDR_SL_LDLINUX_V5_SYS) };
static char* resource[2] = { MAKEINTRESOURCEA(IDR_SL_LDLINUX_V4_SYS), MAKEINTRESOURCEA(IDR_SL_LDLINUX_V6_SYS) };
#ifdef RUFUS_TEST
ShowWindow(GetDlgItem(hDlg, IDC_TEST), SW_SHOW);
@ -1505,9 +1506,9 @@ void SetBoot(int fs, int bt)
IGNORE_RETVAL(ComboBox_SetItemData(hBootType, ComboBox_AddStringU(hBootType, lmprintf(MSG_036)), DT_ISO));
IGNORE_RETVAL(ComboBox_SetItemData(hBootType, ComboBox_AddStringU(hBootType, lmprintf(MSG_095)), DT_IMG));
// If needed (advanced mode) also append a Syslinux option
if ( (bt == BT_BIOS) && (((fs == FS_FAT16) || (fs == FS_FAT32)) && (advanced_mode)) ) {
if ( (bt == BT_BIOS) && (((fs == FS_FAT16) || (fs == FS_FAT32) || (fs == FS_NTFS)) && (advanced_mode)) ) {
IGNORE_RETVAL(ComboBox_SetItemData(hBootType, ComboBox_AddStringU(hBootType, "Syslinux 4"), DT_SYSLINUX_V4));
IGNORE_RETVAL(ComboBox_SetItemData(hBootType, ComboBox_AddStringU(hBootType, "Syslinux 5"), DT_SYSLINUX_V5));
IGNORE_RETVAL(ComboBox_SetItemData(hBootType, ComboBox_AddStringU(hBootType, "Syslinux 6"), DT_SYSLINUX_V5));
IGNORE_RETVAL(ComboBox_SetItemData(hBootType, ComboBox_AddStringU(hBootType, "ReactOS"), DT_REACTOS));
}
if ((!advanced_mode) && (selection_default >= DT_SYSLINUX_V4)) {

View file

@ -369,7 +369,7 @@ extern BOOL Question(char* title, char* format, ...);
extern BOOL ExtractDOS(const char* path);
extern BOOL ExtractISO(const char* src_iso, const char* dest_dir, BOOL scan);
extern int64_t ExtractISOFile(const char* iso, const char* iso_file, const char* dest_file, DWORD attributes);
extern BOOL InstallSyslinux(DWORD drive_index, char drive_letter);
extern BOOL InstallSyslinux(DWORD drive_index, char drive_letter, int fs);
extern uint16_t GetSyslinuxVersion(char* buf, size_t buf_size, char** ext);
extern BOOL CreateProgress(void);
extern BOOL SetAutorun(const char* path);

View file

@ -32,7 +32,7 @@ LANGUAGE LANG_NEUTRAL, SUBLANG_NEUTRAL
IDD_DIALOG DIALOGEX 12, 12, 206, 329
STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "Rufus 1.5.0.537"
CAPTION "Rufus 1.5.0.538"
FONT 8, "MS Shell Dlg", 400, 0, 0x1
BEGIN
DEFPUSHBUTTON "Start",IDC_START,94,291,50,14
@ -165,7 +165,7 @@ END
RTL_IDD_DIALOG DIALOGEX 12, 12, 206, 329
STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU
EXSTYLE WS_EX_RTLREADING | WS_EX_APPWINDOW | WS_EX_LAYOUTRTL
CAPTION "Rufus 1.5.0.537"
CAPTION "Rufus 1.5.0.538"
FONT 8, "MS Shell Dlg", 400, 0, 0x1
BEGIN
DEFPUSHBUTTON "Start",IDC_START,94,291,50,14
@ -336,8 +336,8 @@ BEGIN
"#endif\r\n"
"IDR_SL_LDLINUX_V4_BSS RCDATA ""../res/syslinux/ldlinux_v4.bss""\r\n"
"IDR_SL_LDLINUX_V4_SYS RCDATA ""../res/syslinux/ldlinux_v4.sys""\r\n"
"IDR_SL_LDLINUX_V5_BSS RCDATA ""../res/syslinux/ldlinux_v5.bss""\r\n"
"IDR_SL_LDLINUX_V5_SYS RCDATA ""../res/syslinux/ldlinux_v5.sys""\r\n"
"IDR_SL_LDLINUX_V6_BSS RCDATA ""../res/syslinux/ldlinux_v6.bss""\r\n"
"IDR_SL_LDLINUX_V6_SYS RCDATA ""../res/syslinux/ldlinux_v6.sys""\r\n"
"IDR_SL_MBOOT_C32 RCDATA ""../res/syslinux/mboot.c32""\r\n"
"IDR_FD_COMMAND_COM RCDATA ""../res/freedos/COMMAND.COM""\r\n"
"IDR_FD_KERNEL_SYS RCDATA ""../res/freedos/KERNEL.SYS""\r\n"
@ -428,8 +428,8 @@ END
//
VS_VERSION_INFO VERSIONINFO
FILEVERSION 1,5,0,537
PRODUCTVERSION 1,5,0,537
FILEVERSION 1,5,0,538
PRODUCTVERSION 1,5,0,538
FILEFLAGSMASK 0x3fL
#ifdef _DEBUG
FILEFLAGS 0x1L
@ -446,13 +446,13 @@ BEGIN
BEGIN
VALUE "CompanyName", "Akeo Consulting (http://akeo.ie)"
VALUE "FileDescription", "Rufus"
VALUE "FileVersion", "1.5.0.537"
VALUE "FileVersion", "1.5.0.538"
VALUE "InternalName", "Rufus"
VALUE "LegalCopyright", "© 2011-2014 Pete Batard (GPL v3)"
VALUE "LegalTrademarks", "http://www.gnu.org/copyleft/gpl.html"
VALUE "OriginalFilename", "rufus.exe"
VALUE "ProductName", "Rufus"
VALUE "ProductVersion", "1.5.0.537"
VALUE "ProductVersion", "1.5.0.538"
END
END
BLOCK "VarFileInfo"
@ -490,8 +490,8 @@ IDR_LC_RUFUS_LOC RCDATA "../res/localization/embedded.lo
#endif
IDR_SL_LDLINUX_V4_BSS RCDATA "../res/syslinux/ldlinux_v4.bss"
IDR_SL_LDLINUX_V4_SYS RCDATA "../res/syslinux/ldlinux_v4.sys"
IDR_SL_LDLINUX_V5_BSS RCDATA "../res/syslinux/ldlinux_v5.bss"
IDR_SL_LDLINUX_V5_SYS RCDATA "../res/syslinux/ldlinux_v5.sys"
IDR_SL_LDLINUX_V6_BSS RCDATA "../res/syslinux/ldlinux_v6.bss"
IDR_SL_LDLINUX_V6_SYS RCDATA "../res/syslinux/ldlinux_v6.sys"
IDR_SL_MBOOT_C32 RCDATA "../res/syslinux/mboot.c32"
IDR_FD_COMMAND_COM RCDATA "../res/freedos/COMMAND.COM"
IDR_FD_KERNEL_SYS RCDATA "../res/freedos/KERNEL.SYS"

View file

@ -36,6 +36,7 @@
#include "syslxfs.h"
#include "libfat.h"
#include "setadv.h"
#include "ntfssect.h"
unsigned char* syslinux_ldlinux[2] = { NULL, NULL };
DWORD syslinux_ldlinux_len[2];
@ -69,7 +70,7 @@ int libfat_readfile(intptr_t pp, void *buf, size_t secsize,
* Extract the ldlinux.sys and ldlinux.bss from resources,
* then patch and install them
*/
BOOL InstallSyslinux(DWORD drive_index, char drive_letter)
BOOL InstallSyslinux(DWORD drive_index, char drive_letter, int fs_type)
{
HANDLE f_handle = INVALID_HANDLE_VALUE;
HANDLE d_handle = INVALID_HANDLE_VALUE;
@ -77,12 +78,12 @@ BOOL InstallSyslinux(DWORD drive_index, char drive_letter)
DWORD bytes_written;
BOOL r = FALSE;
FILE* fd;
size_t len;
size_t length;
static unsigned char sectbuf[SECTOR_SIZE];
static char* resource[2][2] = {
{ MAKEINTRESOURCEA(IDR_SL_LDLINUX_V4_SYS), MAKEINTRESOURCEA(IDR_SL_LDLINUX_V4_BSS) },
{ MAKEINTRESOURCEA(IDR_SL_LDLINUX_V5_SYS), MAKEINTRESOURCEA(IDR_SL_LDLINUX_V5_BSS) } };
{ MAKEINTRESOURCEA(IDR_SL_LDLINUX_V6_SYS), MAKEINTRESOURCEA(IDR_SL_LDLINUX_V6_BSS) } };
const char* ldlinux = "ldlinux";
const char* syslinux = "syslinux";
const char* ldlinux_ext[3] = { "sys", "bss", "c32" };
@ -116,9 +117,9 @@ BOOL InstallSyslinux(DWORD drive_index, char drive_letter)
uprintf("Could not open %s\n", path);
goto out;
}
len = fread(syslinux_ldlinux[i], 1, (size_t)syslinux_ldlinux_len[i], fd);
length = fread(syslinux_ldlinux[i], 1, (size_t)syslinux_ldlinux_len[i], fd);
fclose(fd);
if (len != (size_t)syslinux_ldlinux_len[i]) {
if (length != (size_t)syslinux_ldlinux_len[i]) {
uprintf("Could not read %s\n", path);
goto out;
}
@ -148,8 +149,8 @@ BOOL InstallSyslinux(DWORD drive_index, char drive_letter)
}
/* Write ldlinux.sys file */
if (!WriteFile(f_handle, syslinux_ldlinux[0], syslinux_ldlinux_len[0],
&bytes_written, NULL) ||
if (!WriteFile(f_handle, (const char _force *)syslinux_ldlinux[0],
syslinux_ldlinux_len[0], &bytes_written, NULL) ||
bytes_written != syslinux_ldlinux_len[0]) {
uprintf("Could not write '%s'\n", &path[3]);
goto out;
@ -183,6 +184,39 @@ BOOL InstallSyslinux(DWORD drive_index, char drive_letter)
sectors = (libfat_sector_t*) calloc(ldlinux_sectors, sizeof *sectors);
if (sectors == NULL)
goto out;
if (fs_type == FS_NTFS) {
DWORD err;
S_NTFSSECT_VOLINFO vol_info;
LARGE_INTEGER vcn, lba, len;
S_NTFSSECT_EXTENT extent;
static_sprintf(tmp, "%C:\\", drive_letter);
err = NtfsSectGetVolumeInfo(tmp, &vol_info);
if (err != ERROR_SUCCESS) {
uprintf("Could not fetch NTFS volume info");
goto out;
}
secp = sectors;
nsectors = 0;
for (vcn.QuadPart = 0;
NtfsSectGetFileVcnExtent(f_handle, &vcn, &extent) == ERROR_SUCCESS;
vcn = extent.NextVcn) {
err = NtfsSectLcnToLba(&vol_info, &extent.FirstLcn, &lba);
if (err != ERROR_SUCCESS) {
uprintf("Could not translate LDLINUX.SYS LCN to disk LBA");
goto out;
}
lba.QuadPart -= vol_info.PartitionLba.QuadPart;
len.QuadPart = ((extent.NextVcn.QuadPart -
extent.FirstVcn.QuadPart) *
vol_info.SectorsPerCluster);
while (len.QuadPart-- && nsectors < ldlinux_sectors) {
*secp++ = lba.QuadPart++;
nsectors++;
}
}
goto map_done;
}
fs = libfat_open(libfat_readfile, (intptr_t) d_handle);
if (fs == NULL) {
uprintf("Syslinux FAT access error\n");
@ -198,6 +232,7 @@ BOOL InstallSyslinux(DWORD drive_index, char drive_letter)
s = libfat_nextsector(fs, s);
}
libfat_close(fs);
map_done:
/* Patch ldlinux.sys and the boot sector */
syslinux_patch(sectors, nsectors, 0, 0, NULL, NULL);
@ -224,7 +259,7 @@ BOOL InstallSyslinux(DWORD drive_index, char drive_letter)
}
/* Make the syslinux boot sector */
syslinux_make_bootsect(sectbuf, VFAT);
syslinux_make_bootsect(sectbuf, (fs_type == FS_NTFS)?NTFS:VFAT);
/* Write boot sector back */
if (SetFilePointer(d_handle, 0, NULL, FILE_BEGIN) != 0 ||

View file

@ -20,6 +20,7 @@
</ItemGroup>
<ItemGroup>
<ClInclude Include="..\advconst.h" />
<ClInclude Include="..\ntfssect.h" />
<ClInclude Include="..\syslinux.h" />
<ClInclude Include="..\syslxcom.h" />
<ClInclude Include="..\syslxfs.h" />
@ -27,6 +28,7 @@
</ItemGroup>
<ItemGroup>
<ClCompile Include="..\fs.c" />
<ClCompile Include="..\ntfssect.c" />
<ClCompile Include="..\setadv.c" />
<ClCompile Include="..\syslxmod.c" />
</ItemGroup>

View file

@ -26,6 +26,9 @@
<ClInclude Include="..\syslxcom.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="..\ntfssect.h">
<Filter>Header Files</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="..\fs.c">
@ -37,5 +40,8 @@
<ClCompile Include="..\syslxmod.c">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="..\ntfssect.c">
<Filter>Source Files</Filter>
</ClCompile>
</ItemGroup>
</Project>

View file

@ -13,5 +13,6 @@ TARGETLIBS=$(SDK_LIB_PATH)\kernel32.lib \
$(SDK_LIB_PATH)\user32.lib
SOURCES=fs.c \
ntfssect.c \
setadv.c \
syslxmod.c

View file

@ -1,4 +1,4 @@
noinst_LIBRARIES = libinstaller.a
libinstaller_a_SOURCES = fs.c setadv.c syslxmod.c
libinstaller_a_SOURCES = fs.c ntfssect.c setadv.c syslxmod.c
libinstaller_a_CFLAGS = $(AM_CFLAGS)

View file

@ -53,6 +53,7 @@ am__v_at_0 = @
libinstaller_a_AR = $(AR) $(ARFLAGS)
libinstaller_a_LIBADD =
am_libinstaller_a_OBJECTS = libinstaller_a-fs.$(OBJEXT) \
libinstaller_a-ntfssect.$(OBJEXT) \
libinstaller_a-setadv.$(OBJEXT) \
libinstaller_a-syslxmod.$(OBJEXT)
libinstaller_a_OBJECTS = $(am_libinstaller_a_OBJECTS)
@ -166,7 +167,7 @@ top_build_prefix = @top_build_prefix@
top_builddir = @top_builddir@
top_srcdir = @top_srcdir@
noinst_LIBRARIES = libinstaller.a
libinstaller_a_SOURCES = fs.c setadv.c syslxmod.c
libinstaller_a_SOURCES = fs.c ntfssect.c setadv.c syslxmod.c
libinstaller_a_CFLAGS = $(AM_CFLAGS)
all: all-am
@ -232,6 +233,14 @@ libinstaller_a-fs.obj: fs.c
$(AM_V_CC) @AM_BACKSLASH@
$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libinstaller_a_CFLAGS) $(CFLAGS) -c -o libinstaller_a-fs.obj `if test -f 'fs.c'; then $(CYGPATH_W) 'fs.c'; else $(CYGPATH_W) '$(srcdir)/fs.c'; fi`
libinstaller_a-ntfssect.o: ntfssect.c
$(AM_V_CC) @AM_BACKSLASH@
$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libinstaller_a_CFLAGS) $(CFLAGS) -c -o libinstaller_a-ntfssect.o `test -f 'ntfssect.c' || echo '$(srcdir)/'`ntfssect.c
libinstaller_a-ntfssect.obj: ntfssect.c
$(AM_V_CC) @AM_BACKSLASH@
$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libinstaller_a_CFLAGS) $(CFLAGS) -c -o libinstaller_a-ntfssect.obj `if test -f 'ntfssect.c'; then $(CYGPATH_W) 'ntfssect.c'; else $(CYGPATH_W) '$(srcdir)/ntfssect.c'; fi`
libinstaller_a-setadv.o: setadv.c
$(AM_V_CC) @AM_BACKSLASH@
$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libinstaller_a_CFLAGS) $(CFLAGS) -c -o libinstaller_a-setadv.o `test -f 'setadv.c' || echo '$(srcdir)/'`setadv.c

View file

@ -18,6 +18,8 @@
#define _XOPEN_SOURCE 500 /* Required on glibc 2.x */
#define _BSD_SOURCE
/* glibc 2.20 deprecates _BSD_SOURCE in favour of _DEFAULT_SOURCE */
#define _DEFAULT_SOURCE 1
#include <stdio.h>
#include <inttypes.h>
#include <string.h>

View file

@ -0,0 +1,359 @@
/* -------------------------------------------------------------------------- *
*
* Copyright 2011 Shao Miller - All Rights Reserved
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, Inc., 53 Temple Place Ste 330,
* Boston MA 02111-1307, USA; either version 2 of the License, or
* (at your option) any later version; incorporated herein by reference.
*
* ------------------------------------------------------------------------- */
/****
* ntfssect.c
*
* Fetch NTFS file cluster & sector information via Windows
*
* With special thanks to Mark Roddy for his article:
* http://www.wd-3.com/archive/luserland.htm
*/
#if defined(_MSC_VER)
#pragma warning(disable:4996)
#endif
#include <windows.h>
#include <winioctl.h>
#include <stddef.h>
#include <string.h>
#include "ntfssect.h"
/*** Macros */
#define M_ERR(msg) (NtfsSectLastErrorMessage = (msg))
/*** Function declarations */
static DWORD NtfsSectGetVolumeHandle(
CHAR * VolumeName,
S_NTFSSECT_VOLINFO * VolumeInfo
);
static DWORD NtfsSectGetVolumePartitionLba(S_NTFSSECT_VOLINFO * VolumeInfo);
/*** Objects */
CHAR * NtfsSectLastErrorMessage;
/*** Function definitions */
DWORD M_NTFSSECT_API NtfsSectGetFileVcnExtent(
HANDLE File,
LARGE_INTEGER * Vcn,
S_NTFSSECT_EXTENT * Extent
) {
BOOL bad, ok;
DWORD output_size, rc;
STARTING_VCN_INPUT_BUFFER input;
RETRIEVAL_POINTERS_BUFFER output;
bad = (
File == INVALID_HANDLE_VALUE ||
!Vcn ||
Vcn->QuadPart < 0 ||
!Extent
);
if (bad)
return ERROR_INVALID_PARAMETER;
input.StartingVcn = *Vcn;
ok = DeviceIoControl(
File,
FSCTL_GET_RETRIEVAL_POINTERS,
&input,
sizeof input,
&output,
sizeof output,
&output_size,
NULL
);
ok = ok;
rc = GetLastError();
switch (rc) {
case NO_ERROR:
case ERROR_MORE_DATA:
Extent->FirstVcn = output.StartingVcn;
Extent->NextVcn = output.Extents[0].NextVcn;
Extent->FirstLcn = output.Extents[0].Lcn;
return ERROR_SUCCESS;
case ERROR_HANDLE_EOF:
break;
default:
M_ERR("NtfsSectGetFileVcnExtent(): Unknown status!");
}
return rc;
}
/* Internal use only */
static DWORD NtfsSectGetVolumeHandle(
CHAR * VolumeName,
S_NTFSSECT_VOLINFO * VolumeInfo
) {
#define M_VOL_PREFIX "\\\\.\\"
CHAR volname[sizeof M_VOL_PREFIX - 1 + MAX_PATH + 1] = M_VOL_PREFIX;
CHAR * const volname_short = volname + sizeof M_VOL_PREFIX - 1;
CHAR * c;
DWORD rc;
/* Prefix "\\.\" onto the passed volume name */
strcpy(volname + sizeof M_VOL_PREFIX - 1, VolumeName);
/* Find the last non-null character */
for (c = volname_short; *c; ++c)
;
/* Remove trailing back-slash */
if (c[-1] == '\\')
c[-1] = 0;
/* Open the volume */
VolumeInfo->Handle = CreateFileA(
volname,
GENERIC_READ,
FILE_SHARE_READ | FILE_SHARE_WRITE,
NULL,
OPEN_EXISTING,
0,
NULL
);
rc = GetLastError();
if (VolumeInfo->Handle == INVALID_HANDLE_VALUE) {
M_ERR("Unable to open volume handle!");
goto err_handle;
}
return ERROR_SUCCESS;
CloseHandle(VolumeInfo->Handle);
err_handle:
return rc;
}
DWORD M_NTFSSECT_API NtfsSectGetVolumeInfo(
CHAR * VolumeName,
S_NTFSSECT_VOLINFO * VolumeInfo
) {
S_NTFSSECT_XPFUNCS xp_funcs;
DWORD rc, free_clusts, total_clusts;
BOOL ok;
if (!VolumeName || !VolumeInfo)
return ERROR_INVALID_PARAMETER;
rc = NtfsSectGetVolumeHandle(VolumeName, VolumeInfo);
if (rc != ERROR_SUCCESS)
goto err_handle;
rc = NtfsSectLoadXpFuncs(&xp_funcs);
if (rc != ERROR_SUCCESS)
goto err_xp_funcs;
ok = xp_funcs.GetDiskFreeSpace(
VolumeName,
&VolumeInfo->SectorsPerCluster,
&VolumeInfo->BytesPerSector,
&free_clusts,
&total_clusts
);
rc = GetLastError();
if (!ok) {
M_ERR("GetDiskFreeSpace() failed!");
goto err_freespace;
}
rc = NtfsSectGetVolumePartitionLba(VolumeInfo);
if (rc != ERROR_SUCCESS)
goto err_lba;
VolumeInfo->Size = sizeof *VolumeInfo;
rc = ERROR_SUCCESS;
err_lba:
err_freespace:
NtfsSectUnloadXpFuncs(&xp_funcs);
err_xp_funcs:
if (rc != ERROR_SUCCESS) {
CloseHandle(VolumeInfo->Handle);
VolumeInfo->Handle = INVALID_HANDLE_VALUE;
}
err_handle:
return rc;
}
DWORD M_NTFSSECT_API NtfsSectGetVolumeInfoFromFileName(
CHAR * FileName,
S_NTFSSECT_VOLINFO * VolumeInfo
) {
S_NTFSSECT_XPFUNCS xp_funcs;
DWORD rc;
CHAR volname[MAX_PATH + 1];
BOOL ok;
if (!FileName || !VolumeInfo)
return ERROR_INVALID_PARAMETER;
rc = NtfsSectLoadXpFuncs(&xp_funcs);
if (rc != ERROR_SUCCESS) {
goto err_xp_funcs;
}
ok = xp_funcs.GetVolumePathName(
FileName,
volname,
sizeof volname
);
rc = GetLastError();
if (!ok) {
M_ERR("GetVolumePathName() failed!");
goto err_volname;
}
rc = NtfsSectGetVolumeInfo(volname, VolumeInfo);
err_volname:
NtfsSectUnloadXpFuncs(&xp_funcs);
err_xp_funcs:
return rc;
}
/* Internal use only */
static DWORD NtfsSectGetVolumePartitionLba(S_NTFSSECT_VOLINFO * VolumeInfo) {
BOOL ok;
VOLUME_DISK_EXTENTS vol_disk_extents;
DWORD output_size, rc;
ok = DeviceIoControl(
VolumeInfo->Handle,
IOCTL_VOLUME_GET_VOLUME_DISK_EXTENTS,
NULL,
0,
&vol_disk_extents,
sizeof vol_disk_extents,
&output_size,
NULL
);
rc = GetLastError();
if (!ok) {
M_ERR("Couldn't fetch volume disk extent(s)!");
goto err_vol_disk_extents;
}
if (vol_disk_extents.NumberOfDiskExtents != 1) {
M_ERR("Unsupported number of volume disk extents!");
goto err_num_of_extents;
}
VolumeInfo->PartitionLba.QuadPart = (
vol_disk_extents.Extents[0].StartingOffset.QuadPart /
VolumeInfo->BytesPerSector
);
return ERROR_SUCCESS;
err_num_of_extents:
err_vol_disk_extents:
return rc;
}
DWORD M_NTFSSECT_API NtfsSectLcnToLba(
const S_NTFSSECT_VOLINFO * VolumeInfo,
const LARGE_INTEGER * Lcn,
LARGE_INTEGER * Lba
) {
BOOL bad;
bad = (
!VolumeInfo ||
!VolumeInfo->BytesPerSector ||
!VolumeInfo->SectorsPerCluster ||
!Lcn ||
Lcn->QuadPart < 0 ||
!Lba
);
if (bad)
return ERROR_INVALID_PARAMETER;
Lba->QuadPart = (
VolumeInfo->PartitionLba.QuadPart +
Lcn->QuadPart *
VolumeInfo->SectorsPerCluster
);
return ERROR_SUCCESS;
}
DWORD M_NTFSSECT_API NtfsSectLoadXpFuncs(S_NTFSSECT_XPFUNCS * XpFuncs) {
DWORD rc;
if (!XpFuncs)
return ERROR_INVALID_PARAMETER;
XpFuncs->Size = sizeof *XpFuncs;
XpFuncs->Kernel32 = LoadLibraryA("kernel32.dll");
rc = GetLastError();
if (!XpFuncs->Kernel32) {
M_ERR("KERNEL32.DLL not found!");
goto err;
}
XpFuncs->GetVolumePathName = (F_KERNEL32_GETVOLUMEPATHNAME *) (
GetProcAddress(
XpFuncs->Kernel32,
"GetVolumePathNameA"
)
);
rc = GetLastError();
if (!XpFuncs->GetVolumePathName) {
M_ERR("GetVolumePathName() not found in KERNEL32.DLL!");
goto err;
}
XpFuncs->GetDiskFreeSpace = (F_KERNEL32_GETDISKFREESPACE *) (
GetProcAddress(
XpFuncs->Kernel32,
"GetDiskFreeSpaceA"
)
);
rc = GetLastError();
if (!XpFuncs->GetDiskFreeSpace) {
M_ERR("GetDiskFreeSpace() not found in KERNEL32.DLL!");
goto err;
}
return ERROR_SUCCESS;
err:
NtfsSectUnloadXpFuncs(XpFuncs);
return rc;
}
VOID M_NTFSSECT_API NtfsSectUnloadXpFuncs(S_NTFSSECT_XPFUNCS * XpFuncs) {
if (!XpFuncs)
return;
XpFuncs->GetDiskFreeSpace = NULL;
XpFuncs->GetVolumePathName = NULL;
if (XpFuncs->Kernel32)
FreeLibrary(XpFuncs->Kernel32);
XpFuncs->Kernel32 = NULL;
XpFuncs->Size = 0;
return;
}

View file

@ -0,0 +1,152 @@
/* -------------------------------------------------------------------------- *
*
* Copyright 2011 Shao Miller - All Rights Reserved
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, Inc., 53 Temple Place Ste 330,
* Boston MA 02111-1307, USA; either version 2 of the License, or
* (at your option) any later version; incorporated herein by reference.
*
* ------------------------------------------------------------------------- */
#ifndef M_NTFSSECT_H_
/****
* ntfssect.h
*
* Fetch NTFS file cluster & sector information via Windows
*
* With special thanks to Mark Roddy for his article:
* http://www.wd-3.com/archive/luserland.htm
*/
/*** Macros */
#define M_NTFSSECT_H_
#define M_NTFSSECT_API
/*** Object types */
/* An "extent;" a contiguous range of file data */
typedef struct S_NTFSSECT_EXTENT_ S_NTFSSECT_EXTENT;
/* Volume info relevant to file cluster & sector info */
typedef struct S_NTFSSECT_VOLINFO_ S_NTFSSECT_VOLINFO;
/* Stores function pointers to some Windows functions */
typedef struct S_NTFSSECT_XPFUNCS_ S_NTFSSECT_XPFUNCS;
/*** Function types */
/* The function type for Kernel32.dll's GetDiskFreeSpace() */
typedef BOOL WINAPI F_KERNEL32_GETDISKFREESPACE(
LPCSTR,
LPDWORD,
LPDWORD,
LPDWORD,
LPDWORD
);
/* The function type for Kernel32.dll's GetVolumePathName() */
typedef BOOL WINAPI F_KERNEL32_GETVOLUMEPATHNAME(LPCSTR, LPCSTR, DWORD);
/*** Function declarations */
/**
* Fetch the extent containing a particular VCN
*
* @v File
* @v Vcn
* @v Extent
* @ret DWORD
*/
DWORD M_NTFSSECT_API NtfsSectGetFileVcnExtent(
HANDLE File,
LARGE_INTEGER * Vcn,
S_NTFSSECT_EXTENT * Extent
);
/**
* Populate a volume info object
*
* @v VolumeName
* @v VolumeInfo
* @ret DWORD
*/
DWORD M_NTFSSECT_API NtfsSectGetVolumeInfo(
CHAR * VolumeName,
S_NTFSSECT_VOLINFO * VolumeInfo
);
/**
* Populate a volume info object
*
* @v FileName
* @v VolumeInfo
* @ret DWORD
*/
DWORD M_NTFSSECT_API NtfsSectGetVolumeInfoFromFileName(
CHAR * FileName,
S_NTFSSECT_VOLINFO * VolumeInfo
);
/**
* Convert a volume LCN to an absolute disk LBA
*
* @v VolumeInfo
* @v Lcn
* @v Lba
* @ret DWORD
*/
DWORD M_NTFSSECT_API NtfsSectLcnToLba(
const S_NTFSSECT_VOLINFO * VolumeInfo,
const LARGE_INTEGER * Lcn,
LARGE_INTEGER * Lba
);
/**
* Load some helper XP functions
*
* @v XpFuncs
* @ret DWORD
*/
DWORD M_NTFSSECT_API NtfsSectLoadXpFuncs(S_NTFSSECT_XPFUNCS * XpFuncs);
/**
* Unload some helper XP functions
*
* @v XpFuncs
* @ret DWORD
*/
VOID M_NTFSSECT_API NtfsSectUnloadXpFuncs(S_NTFSSECT_XPFUNCS * XpFuncs);
/*** Object declarations */
/**
* The last error message set by one of our functions.
* Obviously not per-thread
*/
extern CHAR * NtfsSectLastErrorMessage;
/*** Struct/union definitions */
struct S_NTFSSECT_EXTENT_ {
LARGE_INTEGER FirstVcn;
LARGE_INTEGER NextVcn;
LARGE_INTEGER FirstLcn;
};
struct S_NTFSSECT_VOLINFO_ {
DWORD Size;
HANDLE Handle;
DWORD BytesPerSector;
DWORD SectorsPerCluster;
LARGE_INTEGER PartitionLba;
};
struct S_NTFSSECT_XPFUNCS_ {
DWORD Size;
HMODULE Kernel32;
F_KERNEL32_GETVOLUMEPATHNAME * GetVolumePathName;
F_KERNEL32_GETDISKFREESPACE * GetDiskFreeSpace;
};
#endif /* M_NTFSSECT_H_ */

View file

@ -18,6 +18,14 @@
#include "advconst.h"
#include "setadv.h"
#ifdef __CHECKER__
# define _slimg __attribute__((noderef,address_space(1)))
# define _force __attribute__((force))
#else
# define _slimg
# define _force
#endif
/* The standard boot sector and ldlinux image */
extern unsigned char* syslinux_ldlinux[2];
extern DWORD syslinux_ldlinux_len[2];

View file

@ -1,5 +1,5 @@
/*
* Copyright 2011 Paulo Alcantara <pcacjr@gmail.com>
* Copyright 2011-2012 Paulo Alcantara <pcacjr@zytor.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@ -12,13 +12,16 @@
#ifndef _SYSLXFS_H_
#define _SYSLXFS_H_
/* Global fs_type for handling fat, ntfs, ext2/3/4 and btrfs */
/* Global fs_type for handling fat, ntfs, ext2/3/4, btrfs, xfs and ufs1/2 */
enum filesystem {
NONE,
EXT2,
BTRFS,
VFAT,
NTFS,
XFS,
UFS1,
UFS2,
};
//extern int fs_type;

View file

@ -1,7 +1,7 @@
/* ----------------------------------------------------------------------- *
*
* Copyright 2007-2008 H. Peter Anvin - All Rights Reserved
* Copyright 2009-2011 Intel Corporation; author: H. Peter Anvin
* Copyright 2009-2014 Intel Corporation; author: H. Peter Anvin
* Copyright 2011 Paulo Alcantara <pcacjr@gmail.com>
*
* This program is free software; you can redistribute it and/or modify
@ -26,16 +26,15 @@
#ifdef __GNUC__
# ifdef __MINGW32__
/* gcc 4.7 miscompiles packed structures in MS-bitfield mode */
# define GNUC_PACKED __attribute__((packed,gcc_struct))
# define PACKME
# define PACKED __attribute__((packed,gcc_struct))
# else
# define GNUC_PACKED __attribute__((packed))
# define PACKME
# define PACKED __attribute__((packed))
# endif
# define PRAGMA_BEGIN_PACKED
# define PRAGMA_END_PACKED
#elif defined(_MSC_VER)
# define GNUC_PACKED
# define PRAGMA_BEGIN_PACKED __pragma(pack(push, 1))
# define PRAGMA_END_PACKED __pragma(pack(pop))
# define PACKME __pragma(pack(push, 1))
# define PACKED __pragma(pack(pop))
#else
# error "Need to define PACKED for this compiler"
#endif
@ -66,7 +65,7 @@ static inline uint32_t get_32(const uint32_t * p)
return *p;
#else
const uint16_t *pp = (const uint16_t *)p;
return get_16(pp[0]) + (uint32_t)get_16(pp[1]);
return get_16(&pp[0]) + ((uint32_t)get_16(&pp[1]) << 16);
#endif
}
@ -77,7 +76,7 @@ static inline uint64_t get_64(const uint64_t * p)
return *p;
#else
const uint32_t *pp = (const uint32_t *)p;
return get_32(pp[0]) + (uint64_t)get_32(pp[1]);
return get_32(&pp[0]) + ((uint64_t)get_32(&pp[1]) << 32);
#endif
}
@ -104,11 +103,9 @@ static inline void set_32(uint32_t *p, uint32_t v)
/* Littleendian and unaligned-capable */
*p = v;
#else
uint8_t *pp = (uint8_t *) p;
pp[0] = (v & 0xff);
pp[1] = ((v >> 8) & 0xff);
pp[2] = ((v >> 16) & 0xff);
pp[3] = ((v >> 24) & 0xff);
uint16_t *pp = (uint16_t *) p;
set_16(&pp[0], v);
set_16(&pp[1], v >> 16);
#endif
}
@ -119,8 +116,8 @@ static inline void set_64(uint64_t *p, uint64_t v)
*p = v;
#else
uint32_t *pp = (uint32_t *) p;
set_32(pp[0], v);
set_32(pp[1], v >> 32);
set_32(&pp[0], v);
set_32(&pp[1], v >> 32);
#endif
}
@ -130,47 +127,65 @@ static inline void set_64(uint64_t *p, uint64_t v)
*/
#ifdef __MSDOS__
static inline __attribute__ ((const))
uint16_t ds(void)
{
uint16_t v;
asm("movw %%ds,%0":"=rm"(v));
return v;
}
static inline void *set_fs(const void *p)
{
uint16_t seg;
seg = ds() + ((size_t) p >> 4);
asm volatile ("movw %0,%%fs"::"rm" (seg));
return (void *)((size_t) p & 0xf);
}
uint8_t get_8_sl(const uint8_t * p);
uint16_t get_16_sl(const uint16_t * p);
uint32_t get_32_sl(const uint32_t * p);
uint64_t get_64_sl(const uint64_t * p);
void set_8_sl(uint8_t * p, uint8_t v);
void set_16_sl(uint16_t * p, uint16_t v);
void set_32_sl(uint32_t * p, uint32_t v);
void set_64_sl(uint64_t * p, uint64_t v);
void memcpy_to_sl(void *dst, const void *src, size_t len);
void memcpy_from_sl(void *dst, const void *src, size_t len);
uint8_t get_8_sl(const uint8_t _slimg * p);
uint16_t get_16_sl(const uint16_t _slimg * p);
uint32_t get_32_sl(const uint32_t _slimg * p);
uint64_t get_64_sl(const uint64_t _slimg * p);
void set_8_sl(uint8_t _slimg * p, uint8_t v);
void set_16_sl(uint16_t _slimg * p, uint16_t v);
void set_32_sl(uint32_t _slimg * p, uint32_t v);
void set_64_sl(uint64_t _slimg * p, uint64_t v);
void memcpy_to_sl(void _slimg *dst, const void *src, size_t len);
void memcpy_from_sl(void *dst, const void _slimg *src, size_t len);
void memset_sl(void _slimg *dst, int c, size_t len);
#else
/* Sane system ... */
#define get_8_sl(x) get_8(x)
#define get_16_sl(x) get_16(x)
#define get_32_sl(x) get_32(x)
#define get_64_sl(x) get_64(x)
#define set_8_sl(x,y) set_8(x,y)
#define set_16_sl(x,y) set_16(x,y)
#define set_32_sl(x,y) set_32(x,y)
#define set_64_sl(x,y) set_64(x,y)
#define memcpy_to_sl(d,s,l) memcpy(d,s,l)
#define memcpy_from_sl(d,s,l) memcpy(d,s,l)
static inline uint8_t get_8_sl(const uint8_t _slimg * p)
{
return get_8((const uint8_t _force *)p);
}
static inline uint16_t get_16_sl(const uint16_t _slimg * p)
{
return get_16((const uint16_t _force *)p);
}
static inline uint32_t get_32_sl(const uint32_t _slimg * p)
{
return get_32((const uint32_t _force *)p);
}
static inline uint64_t get_64_sl(const uint64_t _slimg * p)
{
return get_64((const uint64_t _force *)p);
}
static inline void set_8_sl(uint8_t _slimg * p, uint8_t v)
{
set_8((uint8_t _force *)p, v);
}
static inline void set_16_sl(uint16_t _slimg * p, uint16_t v)
{
set_16((uint16_t _force *)p, v);
}
static inline void set_32_sl(uint32_t _slimg * p, uint32_t v)
{
set_32((uint32_t _force *)p, v);
}
static inline void set_64_sl(uint64_t _slimg * p, uint64_t v)
{
set_64((uint64_t _force *)p, v);
}
static inline void memcpy_to_sl(void _slimg *dst, const void *src, size_t len)
{
memcpy((void _force *)dst, src, len);
}
static inline void memcpy_from_sl(void *dst, const void _slimg *src, size_t len)
{
memcpy(dst, (const void _force *)src, len);
}
static inline void memset_sl(void _slimg *dst, int c, size_t len)
{
memset((void _force *)dst, c, len);
}
#endif
@ -204,13 +219,14 @@ struct ext_patch_area {
};
/* Sector extent */
PRAGMA_BEGIN_PACKED
PACKME
struct syslinux_extent {
uint64_t lba;
uint16_t len;
} GNUC_PACKED;
} PACKED;
/* FAT bootsector format, also used by other disk-based derivatives */
PACKME
struct fat_boot_sector {
uint8_t bsJump[3];
char bsOemName[8];
@ -227,7 +243,9 @@ struct fat_boot_sector {
uint32_t bsHiddenSecs;
uint32_t bsHugeSectors;
PACKME
union {
PACKME
struct {
uint8_t DriveNumber;
uint8_t Reserved1;
@ -236,7 +254,8 @@ struct fat_boot_sector {
char VolumeLabel[11];
char FileSysType[8];
uint8_t Code[442];
} GNUC_PACKED bs16;
} PACKED bs16;
PACKME
struct {
uint32_t FATSz32;
uint16_t ExtFlags;
@ -252,15 +271,16 @@ struct fat_boot_sector {
char VolumeLabel[11];
char FileSysType[8];
uint8_t Code[414];
} GNUC_PACKED bs32;
} GNUC_PACKED;
} PACKED bs32;
} PACKED;
uint32_t bsMagic;
uint16_t bsForwardPtr;
uint16_t bsSignature;
} GNUC_PACKED;
} PACKED;
/* NTFS bootsector format */
PACKME
struct ntfs_boot_sector {
uint8_t bsJump[3];
char bsOemName[8];
@ -291,8 +311,7 @@ struct ntfs_boot_sector {
uint32_t bsMagic;
uint16_t bsForwardPtr;
uint16_t bsSignature;
} GNUC_PACKED;
PRAGMA_END_PACKED
} PACKED;
#define FAT_bsHead bsJump
#define FAT_bsHeadLen offsetof(struct fat_boot_sector, bsBytesPerSec)

View file

@ -1,7 +1,7 @@
/* ----------------------------------------------------------------------- *
*
* Copyright 1998-2008 H. Peter Anvin - All Rights Reserved
* Copyright 2009-2010 Intel Corporation; author H. Peter Anvin
* Copyright 2009-2014 Intel Corporation; author H. Peter Anvin
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@ -17,6 +17,8 @@
#define _XOPEN_SOURCE 500 /* Required on glibc 2.x */
#define _BSD_SOURCE
/* glibc 2.20 deprecates _BSD_SOURCE in favour of _DEFAULT_SOURCE */
#define _DEFAULT_SOURCE 1
#include <stdio.h>
#include <inttypes.h>
#include <string.h>
@ -30,7 +32,7 @@
/*
* Generate sector extents
*/
static void generate_extents(struct syslinux_extent *ex, int nptrs,
static void generate_extents(struct syslinux_extent _slimg *ex, int nptrs,
const sector_t *sectp, int nsect)
{
uint32_t addr = 0x8000; /* ldlinux.sys starts loading here */
@ -42,7 +44,7 @@ static void generate_extents(struct syslinux_extent *ex, int nptrs,
len = 0;
lba = 0;
memset(ex, 0, nptrs * sizeof *ex);
memset_sl(ex, 0, nptrs * sizeof *ex);
while (nsect) {
sect = *sectp++;
@ -81,10 +83,15 @@ static void generate_extents(struct syslinux_extent *ex, int nptrs,
/*
* Form a pointer based on a 16-bit patcharea/epa field
*/
static inline void *ptr(void *img, uint16_t *offset_p)
static inline void *ptr(void *img, const uint16_t _slimg *offset_p)
{
return (char *)img + get_16_sl(offset_p);
}
static inline void _slimg *slptr(void _slimg *img,
const uint16_t _slimg *offset_p)
{
return (char _slimg *)img + get_16_sl(offset_p);
}
/*
* This patches the boot sector and the beginning of ldlinux.sys
@ -101,25 +108,26 @@ int syslinux_patch(const sector_t *sectp, int nsectors,
int stupid, int raid_mode,
const char *subdir, const char *subvol)
{
struct patch_area *patcharea;
struct ext_patch_area *epa;
struct syslinux_extent *ex;
uint32_t *wp;
struct patch_area _slimg *patcharea;
struct ext_patch_area _slimg *epa;
struct syslinux_extent _slimg *ex;
const uint32_t _slimg *wp;
int nsect = ((boot_image_len + SECTOR_SIZE - 1) >> SECTOR_SHIFT) + 2;
uint32_t csum;
int i, dw, nptrs;
struct fat_boot_sector *sbs = (struct fat_boot_sector *)boot_sector;
uint64_t *advptrs;
uint64_t _slimg *advptrs;
if (nsectors < nsect)
return -1; /* The actual file is too small for content */
/* Search for LDLINUX_MAGIC to find the patch area */
for (wp = (uint32_t *)boot_image; get_32_sl(wp) != LDLINUX_MAGIC;
for (wp = (const uint32_t _slimg *)boot_image;
get_32_sl(wp) != LDLINUX_MAGIC;
wp++)
;
patcharea = (struct patch_area *)wp;
epa = ptr(boot_image, &patcharea->epaoffset);
patcharea = (struct patch_area _slimg *)wp;
epa = slptr(boot_image, &patcharea->epaoffset);
/* First sector need pointer in boot sector */
set_32(ptr(sbs, &epa->sect1ptr0), (uint32_t) sectp[0]);
@ -145,20 +153,22 @@ int syslinux_patch(const sector_t *sectp, int nsectors,
}
/* Set the sector extents */
ex = ptr(boot_image, &epa->secptroffset);
ex = slptr(boot_image, &epa->secptroffset);
nptrs = get_16_sl(&epa->secptrcnt);
#if 0
if (nsect > nptrs) {
/* Not necessarily an error in this case, but a general problem */
fprintf(stderr, "Insufficient extent space, build error!\n");
exit(1);
}
#endif
/* -1 for the pointer in the boot sector, -2 for the two ADVs */
generate_extents(ex, nptrs, sectp, nsect-1-2);
/* ADV pointers */
advptrs = ptr(boot_image, &epa->advptroffset);
advptrs = slptr(boot_image, &epa->advptroffset);
set_64_sl(&advptrs[0], sectp[nsect-1-2]);
set_64_sl(&advptrs[1], sectp[nsect-1-1]);
@ -169,7 +179,7 @@ int syslinux_patch(const sector_t *sectp, int nsectors,
fprintf(stderr, "Subdirectory path too long... aborting install!\n");
exit(1);
}
memcpy_to_sl(ptr(boot_image, &epa->diroffset), subdir, sublen);
memcpy_to_sl(slptr(boot_image, &epa->diroffset), subdir, sublen);
}
/* Poke in the subvolume information */
@ -179,14 +189,14 @@ int syslinux_patch(const sector_t *sectp, int nsectors,
fprintf(stderr, "Subvol name too long... aborting install!\n");
exit(1);
}
memcpy_to_sl(ptr(boot_image, &epa->subvoloffset), subvol, sublen);
memcpy_to_sl(slptr(boot_image, &epa->subvoloffset), subvol, sublen);
}
/* Now produce a checksum */
set_32_sl(&patcharea->checksum, 0);
csum = LDLINUX_MAGIC;
for (i = 0, wp = (uint32_t *)boot_image; i < dw; i++, wp++)
for (i = 0, wp = (const uint32_t _slimg *)boot_image; i < dw; i++, wp++)
csum -= get_32_sl(wp); /* Negative checksum */
set_32_sl(&patcharea->checksum, csum);