summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlek Du <alek.du@intel.com>2010-06-08 22:28:33 -0700
committerH. Peter Anvin <hpa@linux.intel.com>2010-06-09 10:57:27 -0700
commit146c34a2632a4295b1aef44ef79e84b4d4b9cf7e (patch)
treeeb744f032eaee413fcff54c3c67ad2f8daab5207
parent0153498e9ce97fbf7329b590ddb7a373e33b12e6 (diff)
downloadsyslinux-146c34a2632a4295b1aef44ef79e84b4d4b9cf7e.tar.gz
Make syslinux installer real "pathbased"
The previous merging extlinux/syslinux patch is not sufficient, the syslinux is not real "patchbased", hence: * fill currentdir in patcharea * search "extlinux.conf" and "syslinux.cfg" for generic_load_config * define boot_image and boot_sector macro for ldsyslinux this could make further merging extlinux and syslinux possible Signed-off-by: Alek Du <alek.du@intel.com> Signed-off-by: H. Peter Anvin <hpa@linux.intel.com>
-rw-r--r--core/fs/fat/fat.c2
-rw-r--r--core/fs/lib/loadconfig.c16
-rw-r--r--dos/syslinux.c2
-rw-r--r--libinstaller/syslinux.h7
-rw-r--r--libinstaller/syslxmod.c32
-rw-r--r--linux/syslinux.c2
-rw-r--r--mtools/syslinux.c2
-rw-r--r--win32/syslinux.c2
8 files changed, 43 insertions, 22 deletions
diff --git a/core/fs/fat/fat.c b/core/fs/fat/fat.c
index a21f4312..9877a4d5 100644
--- a/core/fs/fat/fat.c
+++ b/core/fs/fat/fat.c
@@ -708,7 +708,7 @@ static int vfat_load_config(void)
com32sys_t regs;
int i;
- /* If installed by extlinux, try the extlinux filename */
+ /* If path filled by installer, then use that to load config*/
if (*CurrentDirName && !generic_load_config())
return 0;
diff --git a/core/fs/lib/loadconfig.c b/core/fs/lib/loadconfig.c
index 9318c1c3..d84bdef9 100644
--- a/core/fs/lib/loadconfig.c
+++ b/core/fs/lib/loadconfig.c
@@ -5,20 +5,26 @@
#include <fs.h>
/*
- * Standard version of load_config for extlinux-installed filesystems
+ * Standard version of load_config for extlinux/syslinux filesystems
*/
int generic_load_config(void)
{
com32sys_t regs;
chdir(CurrentDirName);
+ /* try extlinux.conf first */
realpath(ConfigName, "extlinux.conf", FILENAME_MAX);
-
- dprintf("Config = %s\n", ConfigName);
-
+ dprintf("Try config = %s\n", ConfigName);
memset(&regs, 0, sizeof regs);
regs.edi.w[0] = OFFS_WRT(ConfigName, 0);
call16(core_open, &regs, &regs);
-
+ /* give syslinux.cfg a chance ? */
+ if (regs.eflags.l & EFLAGS_ZF) {
+ realpath(ConfigName, "syslinux.cfg", FILENAME_MAX);
+ dprintf("Then try config = %s\n", ConfigName);
+ memset(&regs, 0, sizeof regs);
+ regs.edi.w[0] = OFFS_WRT(ConfigName, 0);
+ call16(core_open, &regs, &regs);
+ }
return (regs.eflags.l & EFLAGS_ZF) ? -1 : 0;
}
diff --git a/dos/syslinux.c b/dos/syslinux.c
index 61020a1f..94517e8f 100644
--- a/dos/syslinux.c
+++ b/dos/syslinux.c
@@ -755,7 +755,7 @@ int main(int argc, char *argv[])
/*
* Patch ldlinux.sys and the boot sector
*/
- i = syslinux_patch(sectors, nsectors, stupid, raid_mode);
+ i = syslinux_patch(sectors, nsectors, stupid, raid_mode, subdir);
patch_sectors = (i + SECTOR_SIZE - 1) >> SECTOR_SHIFT;
/*
diff --git a/libinstaller/syslinux.h b/libinstaller/syslinux.h
index 8d0212c8..311b9f2e 100644
--- a/libinstaller/syslinux.h
+++ b/libinstaller/syslinux.h
@@ -26,6 +26,11 @@ extern unsigned char syslinux_ldlinux[];
extern const unsigned int syslinux_ldlinux_len;
extern const int syslinux_ldlinux_mtime;
+#define boot_sector syslinux_bootsect
+#define boot_sector_len syslinux_bootsect_len
+#define boot_image syslinux_ldlinux
+#define boot_image_len syslinux_ldlinux_len
+
extern unsigned char syslinux_mbr[];
extern const unsigned int syslinux_mbr_len;
extern const int syslinux_mbr_mtime;
@@ -42,6 +47,6 @@ const char *syslinux_check_bootsect(const void *bs);
/* This patches the boot sector and ldlinux.sys based on a sector map */
int syslinux_patch(const uint32_t * sectors, int nsectors,
- int stupid, int raid_mode);
+ int stupid, int raid_mode, const char *subdir);
#endif
diff --git a/libinstaller/syslxmod.c b/libinstaller/syslxmod.c
index 9ab139c6..b28a443b 100644
--- a/libinstaller/syslxmod.c
+++ b/libinstaller/syslxmod.c
@@ -29,7 +29,7 @@ void syslinux_make_bootsect(void *bs)
{
struct boot_sector *bootsect = bs;
const struct boot_sector *sbs =
- (const struct boot_sector *)syslinux_bootsect;
+ (const struct boot_sector *)boot_sector;
memcpy(&bootsect->bsHead, &sbs->bsHead, bsHeadLen);
memcpy(&bootsect->bsCode, &sbs->bsCode, bsCodeLen);
@@ -227,14 +227,15 @@ static __noinline void set_32_sl(uint32_t * p, uint32_t v)
* otherwise -1.
*/
int syslinux_patch(const uint32_t * sectors, int nsectors,
- int stupid, int raid_mode)
+ int stupid, int raid_mode, const char *subdir)
{
struct patch_area *patcharea;
uint32_t *wp;
- int nsect = (syslinux_ldlinux_len + 511) >> 9;
+ int nsect = (boot_image_len + 511) >> 9;
uint32_t csum;
int i, dw, nptrs, rv;
- struct boot_sector *sbs = (struct boot_sector *)syslinux_bootsect;
+ struct boot_sector *sbs = (struct boot_sector *)boot_sector;
+ int diroffset, dirlen;
if (nsectors < nsect)
return -1;
@@ -254,18 +255,29 @@ int syslinux_patch(const uint32_t * sectors, int nsectors,
set_32(&sbs->NextSector, *sectors++);
/* Search for LDLINUX_MAGIC to find the patch area */
- for (wp = (uint32_t *) syslinux_ldlinux; get_32_sl(wp) != LDLINUX_MAGIC;
+ for (wp = (uint32_t *)boot_image; get_32_sl(wp) != LDLINUX_MAGIC;
wp++) ;
patcharea = (struct patch_area *)wp;
/* Set up the totals */
- dw = syslinux_ldlinux_len >> 2; /* COMPLETE dwords, excluding ADV */
+ dw = boot_image_len >> 2; /* COMPLETE dwords, excluding ADV */
set_16_sl(&patcharea->data_sectors, nsect); /* Not including ADVs */
set_16_sl(&patcharea->adv_sectors, 2); /* ADVs need 2 sectors */
set_32_sl(&patcharea->dwords, dw);
+ /* Poke in the base directory path */
+ if (subdir) {
+ diroffset = get_16(&patcharea->diroffset);
+ dirlen = get_16(&patcharea->dirlen);
+ if (dirlen <= strlen(subdir)) {
+ fprintf(stderr, "Subdirectory path too long... aborting install!\n");
+ exit(1);
+ }
+ memcpy((char *)boot_image + diroffset, subdir, strlen(subdir) + 1);
+ }
+
/* Set the sector pointers */
- wp = (uint32_t *) ((char *)syslinux_ldlinux +
+ wp = (uint32_t *) ((char *)boot_image +
get_16_sl(&patcharea->secptroffset));
nptrs = get_16_sl(&patcharea->secptrcnt);
@@ -277,16 +289,14 @@ int syslinux_patch(const uint32_t * sectors, int nsectors,
while (nptrs--)
set_32_sl(wp++, 0);
- rv = (char *)wp - (char *)syslinux_ldlinux;
-
/* Now produce a checksum */
set_32_sl(&patcharea->checksum, 0);
csum = LDLINUX_MAGIC;
- for (i = 0, wp = (uint32_t *) syslinux_ldlinux; i < dw; i++, wp++)
+ for (i = 0, wp = (uint32_t *)boot_image; i < dw; i++, wp++)
csum -= get_32_sl(wp); /* Negative checksum */
set_32_sl(&patcharea->checksum, csum);
- return rv;
+ return dw << 2;
}
diff --git a/linux/syslinux.c b/linux/syslinux.c
index 3032edce..1194fbb3 100644
--- a/linux/syslinux.c
+++ b/linux/syslinux.c
@@ -465,7 +465,7 @@ umount:
/*
* Patch ldlinux.sys and the boot sector
*/
- i = syslinux_patch(sectors, ldlinux_sectors, opt.stupid_mode, opt.raid_mode);
+ i = syslinux_patch(sectors, ldlinux_sectors, opt.stupid_mode, opt.raid_mode, subdir);
patch_sectors = (i + SECTOR_SIZE - 1) >> SECTOR_SHIFT;
/*
diff --git a/mtools/syslinux.c b/mtools/syslinux.c
index 2c5387ed..2b82b33e 100644
--- a/mtools/syslinux.c
+++ b/mtools/syslinux.c
@@ -267,7 +267,7 @@ int main(int argc, char *argv[])
libfat_close(fs);
/* Patch ldlinux.sys and the boot sector */
- i = syslinux_patch(sectors, nsectors, stupid, raid_mode);
+ i = syslinux_patch(sectors, nsectors, stupid, raid_mode, subdir);
patch_sectors = (i + SECTOR_SIZE - 1) >> SECTOR_SHIFT;
/* Write the now-patched first sectors of ldlinux.sys */
diff --git a/win32/syslinux.c b/win32/syslinux.c
index d8c6c82b..bd042739 100644
--- a/win32/syslinux.c
+++ b/win32/syslinux.c
@@ -433,7 +433,7 @@ int main(int argc, char *argv[])
/*
* Patch ldlinux.sys and the boot sector
*/
- syslinux_patch(sectors, nsectors, stupid, raid_mode);
+ syslinux_patch(sectors, nsectors, stupid, raid_mode, subdir);
/*
* Rewrite the file