wok-next diff syslinux/stuff/iso2exe/bootlinux.c @ rev 17454

syslinux/iso2exe: create a vfat partition in usb bootkey (DOS case only)
author Pascal Bellard <pascal.bellard@slitaz.org>
date Thu Dec 18 11:42:27 2014 +0100 (2014-12-18)
parents c15bb3c9e12d
children 188b82599301
line diff
     1.1 --- a/syslinux/stuff/iso2exe/bootlinux.c	Wed Sep 17 15:21:35 2014 +0200
     1.2 +++ b/syslinux/stuff/iso2exe/bootlinux.c	Thu Dec 18 11:42:27 2014 +0100
     1.3 @@ -2,7 +2,6 @@
     1.4  #include "libdos.h"
     1.5  #include "iso9660.h"
     1.6  
     1.7 -static unsigned setup_version;
     1.8  #define ELKSSIG		0x1E6
     1.9  #define SETUPSECTORS	0x1F1
    1.10  #define ROFLAG		0x1F2
    1.11 @@ -45,9 +44,9 @@
    1.12  static int vm86(void)
    1.13  {
    1.14  #asm
    1.15 -		xor	ax, ax
    1.16 -		cmp	ax, _iselks
    1.17 -		jne	fakerealmode	// elks may run on a 8086
    1.18 +		mov	ax, _iselks
    1.19 +		dec	ax
    1.20 +		je	fakerealmode	// elks may run on a 8086
    1.21  		smsw	ax		// 286+
    1.22  		and	ax, #1		// 0:realmode	1:vm86
    1.23  fakerealmode:
    1.24 @@ -59,37 +58,51 @@
    1.25  	int align;
    1.26  } mem = { 0x100000, 0 };
    1.27  
    1.28 +#ifdef __MSDOS__ 
    1.29 +#define A20HOLDBUFFER	0x80000
    1.30 +static int a20buffer = 0;
    1.31 +#endif
    1.32 +
    1.33  static void movehi(void)
    1.34  {
    1.35  #asm
    1.36  		push	si
    1.37  		push	di
    1.38  
    1.39 +		xor	ax, ax
    1.40  		mov	si, #_mem
    1.41  		cmp	word ptr [si+2], #0x10
    1.42 +#ifdef __MSDOS__ 
    1.43 +		jne	nota20
    1.44 +		mov	ax, #A20HOLDBUFFER/16
    1.45 +		mov	_a20buffer, ax
    1.46 +		mov	di, [si]	// mem.base & 0xFFFF
    1.47 +		jmp	mvbuffer
    1.48 +nota20:
    1.49 +#endif
    1.50  		jnc	movehiz
    1.51 -		mov	ax, [si+1]
    1.52 +		lodsb
    1.53 +		xchg	ax, di
    1.54 +		lodsw
    1.55  		mov	cl, #4
    1.56  		shl	ax, cl		// 8086 support for elks
    1.57 +mvbuffer:
    1.58  		mov	es, ax
    1.59 -		mov	di, #0x00FF
    1.60 -		and	di, [si]
    1.61  		mov	si, #_buffer
    1.62 +		cld
    1.63  		mov	cx, #BUFFERSZ/2
    1.64 -		cld
    1.65  		rep
    1.66  		  movw
    1.67  		jmp	movedone
    1.68 -movehiz:
    1.69 -		xor	di, di		// 30
    1.70 +movehiz:				// 30
    1.71  		mov	cx, #9		// 2E..1E
    1.72  zero1:
    1.73 -		push	di
    1.74 +		push	ax
    1.75  		loop	zero1
    1.76  		push	dword [si]	// 1A mem.base
    1.77  		push	#-1		// 18
    1.78 -		push	di		// 16
    1.79 -		xor	eax, eax
    1.80 +		push	ax		// 16
    1.81 +		cwde
    1.82  		cdq
    1.83  		mov	dx, ds
    1.84  		shl	edx, #4
    1.85 @@ -99,7 +112,7 @@
    1.86  		push	#-1		// 10
    1.87  		mov	cl, #8		// 0E..00
    1.88  zero2:
    1.89 -		push	di
    1.90 +		push	#0
    1.91  		loop	zero2
    1.92  		mov	ch, #BUFFERSZ/512
    1.93  		push	ss
    1.94 @@ -117,10 +130,6 @@
    1.95  #endasm
    1.96  }
    1.97  
    1.98 -#define ZIMAGE_SUPPORT
    1.99 -#define FULL_ZIMAGE
   1.100 -
   1.101 -#ifdef ZIMAGE_SUPPORT
   1.102  static unsigned zimage = 0;
   1.103  static unsigned getss(void)
   1.104  {
   1.105 @@ -128,7 +137,6 @@
   1.106  	mov	ax, ss
   1.107  #endasm
   1.108  }
   1.109 -#endif
   1.110  
   1.111  static unsigned extendedramsizeinkb(void)
   1.112  {
   1.113 @@ -190,12 +198,13 @@
   1.114  #asm
   1.115  		push	si
   1.116  		mov	es, _setupseg
   1.117 +		xchg	di, _setupofs
   1.118  		mov	si, #_buffer
   1.119 -		xchg	di, _setupofs
   1.120 +		cld
   1.121  		mov	cx, #BUFFERSZ/2
   1.122  		rep
   1.123  		  movsw
   1.124 -		xchg	_setupofs, di
   1.125 +		xchg	di, _setupofs
   1.126  		pop	si
   1.127  #endasm
   1.128  }
   1.129 @@ -207,16 +216,25 @@
   1.130  #endasm
   1.131  }
   1.132  
   1.133 +#define WORD(x)	* (unsigned short *) (x)
   1.134 +#define LONG(x)	* (unsigned long *) (x)
   1.135 +static unsigned setup_version = 0;
   1.136  static unsigned long kernel_version = 0;
   1.137  unsigned long loadkernel(void)
   1.138  {
   1.139 -	unsigned setup, n = BUFFERSZ;
   1.140 +	unsigned setup;
   1.141 +#define LINUX001_SUPPORT
   1.142 +#ifdef LINUX001_SUPPORT
   1.143 +	unsigned n = 512;
   1.144 +#else
   1.145 +	unsigned n = BUFFERSZ;
   1.146 +#endif
   1.147  	unsigned long syssize = 0;
   1.148  
   1.149  	do {
   1.150  		isoread(buffer, n);
   1.151  		if (setupofs == 0) {
   1.152 -			if (* (unsigned short *) (buffer + BOOTFLAG) != 0xAA55)
   1.153 +			if (WORD(buffer + BOOTFLAG) != 0xAA55)
   1.154  				die("The kernel is not bootable");
   1.155  #asm
   1.156  			int	0x12
   1.157 @@ -230,16 +248,25 @@
   1.158  			mov	_setupseg, ax
   1.159  has640k:
   1.160  #endasm
   1.161 +			syssize = LONG(buffer + SYSSIZE) << 4;
   1.162 +			if (!syssize) syssize = 0x7F000;
   1.163  			setup = (1 + buffer[SETUPSECTORS]) << 9;
   1.164 -			if (setup == 512) setup = 5 << 9;
   1.165 -			syssize = * (unsigned long  *) (buffer + SYSSIZE) << 4;
   1.166 -			if (!syssize) syssize = 0x7F000;
   1.167 -			setup_version = * (unsigned short *) (buffer + VERSION);
   1.168 +			if (setup == 512) {
   1.169 +#ifdef LINUX001_SUPPORT
   1.170 +				if (WORD(buffer + 0x3F) == 0x3AE8) /* linux 0.01 */
   1.171 +					goto linux001;
   1.172 +#endif
   1.173 +				setup = 5 << 9;
   1.174 +			}
   1.175 +#ifdef LINUX001_SUPPORT
   1.176 +			n = BUFFERSZ;
   1.177 +			isoread(buffer+512, BUFFERSZ-512);
   1.178 +#endif
   1.179  #define HDRS	0x53726448
   1.180 -			if (* (unsigned long *) (buffer + HEADER) != HDRS)
   1.181 -				setup_version = 0;
   1.182 +			if (LONG(buffer + HEADER) == HDRS)
   1.183 +				setup_version = WORD(buffer + VERSION);
   1.184  #define ELKS	0x534B4C45
   1.185 -			if (* (unsigned long *) (buffer + ELKSSIG) == ELKS)
   1.186 +			if (LONG(buffer + ELKSSIG) == ELKS)
   1.187  				iselks = 1;
   1.188  			if (setup_version < 0x204)
   1.189  				syssize &= 0x000FFFFFUL;
   1.190 @@ -256,34 +283,24 @@
   1.191  				retf
   1.192  end_realmode_switch:
   1.193  #endasm
   1.194 -				* (unsigned short *) (buffer + RMSWOFS) = 
   1.195 -					far_realmode_switch;
   1.196 -				* (unsigned short *) (buffer + RMSWSEG) = 
   1.197 -					getcs();
   1.198 +				WORD(buffer + RMSWOFS) =  far_realmode_switch;
   1.199 +				WORD(buffer + RMSWSEG) =  getcs();
   1.200  #endif
   1.201 -				mem.base =
   1.202 -					* (unsigned long *) (buffer + SYSTEMCODE);
   1.203 -				* (unsigned short *) (buffer + HEAPPTR) = 
   1.204 -					0x9B00;
   1.205 +				mem.base = LONG(buffer + SYSTEMCODE);
   1.206 +				WORD(buffer + HEAPPTR) = 0x9B00;
   1.207  				// buffer[LOADFLAGS] |= 0x80;
   1.208 -				* (unsigned short *) (buffer + LOADERTYPE) |= 
   1.209 -					0x80FF;
   1.210 +				WORD(buffer + LOADERTYPE) |= 0x80FF;
   1.211  			}
   1.212 +#ifdef LINUX001_SUPPORT
   1.213 +	linux001:
   1.214 +#endif
   1.215  			if (!setup_version || !(buffer[LOADFLAGS] & 1)) {
   1.216 -#ifdef ZIMAGE_SUPPORT
   1.217  				zimage = getss() + 0x1000;
   1.218  				mem.base = zimage * 16L; 
   1.219  				if (mem.base + syssize > setupseg*16L - 32) {
   1.220 -#ifdef FULL_ZIMAGE
   1.221 -					zimage = 0x11;
   1.222 +					zimage = 0x9311;
   1.223  					mem.base = 0x110000L;	// 1M + 64K HMA 
   1.224 -#else
   1.225 -					die("Out of memory");
   1.226 -#endif
   1.227  				}
   1.228 -#else
   1.229 -				die("Not a bzImage format");
   1.230 -#endif
   1.231  			}
   1.232  		}
   1.233  		movesetup();
   1.234 @@ -296,25 +313,24 @@
   1.235  		mov	si, #0x200
   1.236  		cmp	si, _setup_version
   1.237  		jae	noversion
   1.238 -		push	ds
   1.239 -		mov	ds, _setupseg		// setup > 2.00 => 386+
   1.240 -		xor	eax, eax
   1.241 -		cdq				// clear edx
   1.242 +		mov	es, _setupseg
   1.243 +		seg	es
   1.244  		add	si, [si+14]
   1.245 -		mov	cx, #3
   1.246 +		mov	bx, #2
   1.247 +		mov	cl, #4
   1.248 +nextnumber:
   1.249 +		xor	ax, ax
   1.250  nextdigit:
   1.251 -		shl	al, #4
   1.252 -		shl	ax, #4
   1.253 -next:
   1.254 +		shl	al, cl
   1.255 +		shl	ax, cl
   1.256 +		seg	es
   1.257  		lodsb
   1.258  		sub	al, #0x30
   1.259  		cmp	al, #9
   1.260  		jbe	nextdigit
   1.261 -		shl	eax, #16
   1.262 -		shld	edx, eax, #8
   1.263 -		loop	next
   1.264 -		pop	ds
   1.265 -		mov	_kernel_version, edx
   1.266 +		mov	[bx+_kernel_version], ah
   1.267 +		dec	bx
   1.268 +		jns	nextnumber
   1.269  noversion:
   1.270  		pop	si
   1.271  #endasm
   1.272 @@ -332,52 +348,48 @@
   1.273  {
   1.274  	dosshutdown();
   1.275  #asm
   1.276 +	cld
   1.277  	mov	es, _setupseg
   1.278 -#endasm
   1.279 -	if (cmdline) {
   1.280 -		if (setup_version <= 0x201) {
   1.281 -#asm
   1.282 +	mov	ax, _setup_version
   1.283 +	cmp	ax, #0x200
   1.284 +	jb	noinitrd
   1.285 +		mov	di, #0x218
   1.286 +		mov	si, #_initrd_addr
   1.287 +		movsw
   1.288 +		movsw
   1.289 +		mov	si, #_initrd_size
   1.290 +		movsw
   1.291 +		movsw
   1.292 +noinitrd:
   1.293 +	pop	si	// return address
   1.294 +	pop	si	// .bootlinux.cmdline[bp]
   1.295 +	or	si, si
   1.296 +	jz	nocmdline
   1.297 +		cmp	ax, #0x201
   1.298  		mov	di, #0x0020
   1.299  		mov	ax, #0xA33F
   1.300 +		mov	bx, #CMDLINE_OFFSET
   1.301 +		push	bx
   1.302 +		jbe	oldcmdline
   1.303 +		mov	di, #0x0228
   1.304 +		mov	ax, es
   1.305 +		mov	cl, #12
   1.306 +		shr	ax, cl
   1.307 +		xchg	ax, bx
   1.308 +oldcmdline:
   1.309  		stosw
   1.310 -		mov	ax, #CMDLINE_OFFSET
   1.311 +		xchg	ax, bx
   1.312  		stosw
   1.313 -#endasm
   1.314 -		}
   1.315 -		else {
   1.316 -#asm
   1.317 -		mov	di, #0x0228
   1.318 -		mov	eax, #SETUP_SEGMENT*16+CMDLINE_OFFSET
   1.319 -		stosd
   1.320 -#endasm
   1.321 -		}
   1.322 -#asm
   1.323 -		xchg	ax, di
   1.324 -		mov	si, .bootlinux.cmdline[bp]
   1.325 +		pop	di
   1.326  copy:
   1.327  		lodsb
   1.328  		stosb
   1.329  		or	al,al
   1.330  		jne	copy
   1.331 -#endasm
   1.332 -	}
   1.333 -	if (setup_version >= 0x200) {
   1.334 -#asm
   1.335 -		mov	eax, _initrd_addr
   1.336 -		mov	di, #0x218
   1.337 -		stosd
   1.338 -		mov	eax, _initrd_size
   1.339 -		stosd
   1.340 -#endasm
   1.341 -	}
   1.342 -#asm
   1.343 +nocmdline:
   1.344  	push	es
   1.345  	pop	ss
   1.346  	mov	sp, #CMDLINE_OFFSET
   1.347 -#endasm
   1.348 -#ifdef ZIMAGE_SUPPORT
   1.349 -#asm
   1.350 -	cld
   1.351  	mov	ax, _mem
   1.352  	mov	dx, _mem+2
   1.353  	mov	bx, _zimage
   1.354 @@ -395,7 +407,6 @@
   1.355  		  movsb
   1.356  		retf
   1.357  sysmove:
   1.358 -#ifdef FULL_ZIMAGE
   1.359  		cmp	dx, #0x0010
   1.360  		jb	lowsys
   1.361  // bx first 64k page, dx:ax last byte+1
   1.362 @@ -413,7 +424,7 @@
   1.363  		mov	[si+0x10], cx	// limit = -1
   1.364  		mov	[si+0x18], cx	// limit = -1
   1.365  		mov	cx, #0x9300+SYSTEM_SEGMENT/0x1000
   1.366 -		mov	bh, #0x93
   1.367 +		//mov	bh, #0x93
   1.368  mvdown:
   1.369  		mov	[si+0x12+2], bx	// srce
   1.370  		mov	[si+0x1A+2], cx	// dest
   1.371 @@ -427,14 +438,12 @@
   1.372  		cmp	dl, bl
   1.373  		ja	mvdown
   1.374  		jmp	notzimage
   1.375 -#endif
   1.376  lowsys:
   1.377  // bx first segment, dx:ax last byte+1 (paragraph aligned)
   1.378 -		mov	cl, #4
   1.379 +		mov	cl, #4		// elks may run on a 8086
   1.380  		shr	ax, cl
   1.381 -		mov	cl, #12
   1.382  		shl	dx, cl
   1.383 -		or	ax, dx		// last segment+1
   1.384 +		or	ah, dl		// last segment+1
   1.385  		mov	dx, #SYSTEM_SEGMENT
   1.386  		sub	ax, bx		// ax = paragraph count
   1.387  		sub	bx, dx
   1.388 @@ -443,44 +452,45 @@
   1.389  		dec	dx
   1.390  sysmovelp:		// move ax paragraphs from bx+dx:0 to dx:0
   1.391  		mov	es, dx
   1.392 -		mov	cx, dx
   1.393 -		add	cx, bx
   1.394 -		mov	ds, cx
   1.395 -		sbb	cx, cx		// cx = 0 : -1
   1.396 +		mov	si, dx
   1.397 +		add	si, bx
   1.398 +		mov	ds, si
   1.399 +		sbb	si, si		// si = 0 : -1
   1.400  		cmc			// C  = 1 :  0
   1.401 -		adc	dx, cx
   1.402 +		adc	dx, si
   1.403 +		mov	cl, #8
   1.404  		xor	di, di
   1.405  		xor	si, si
   1.406 -		mov	cx, #8
   1.407  		rep
   1.408  		  movsw
   1.409  		dec	ax
   1.410  		jne	sysmovelp
   1.411  notzimage:
   1.412 -	or	bp, bp
   1.413 -	jz	notelks
   1.414 +	mov	ax, ss
   1.415 +	mov	ds, ax
   1.416 +	dec	bp
   1.417 +	jnz	notelks
   1.418 +	mov	ah, #0x1
   1.419 +	mov	ss, ax
   1.420 +notelks:
   1.421  	push	ss
   1.422 -	pop	ds
   1.423 -	mov	cx, #0x100
   1.424 -	mov	es, cx
   1.425 -	mov	ch, #0x78	// do not overload SYSTEM_SEGMENT
   1.426 +	pop	es
   1.427 +	xor	di, di
   1.428  	xor	si, si
   1.429 -	xor	di, di
   1.430 -	push	es
   1.431 +#ifdef LINUX001_SUPPORT
   1.432 +	mov	cx, #0x0042
   1.433 +	cmp	word ptr [si+0x3F], #0x3AE8
   1.434 +	je	islinux001
   1.435 +#endif
   1.436 +	mov	cx, #0x7800	// do not overload SYSTEM_SEGMENT
   1.437  	rep
   1.438  	  movsw
   1.439 -	pop	ss
   1.440 -notelks:
   1.441 -#endasm
   1.442 -#endif
   1.443 -#asm
   1.444 -	mov	ax, ss
   1.445 -	mov	ds, ax
   1.446 -	mov	es, ax
   1.447 -	add	ax, #0x20
   1.448 +	push	es
   1.449 +	pop	ds
   1.450 +	xor	al, #0x20
   1.451 +islinux001:
   1.452  	push	ax
   1.453 -	xor	dx, dx
   1.454 -	push	dx
   1.455 +	push	cx
   1.456  	retf
   1.457  endsysmove:
   1.458  #endasm