summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorH. Peter Anvin <hpa@zytor.com>2009-06-07 20:59:52 -0700
committerH. Peter Anvin <hpa@zytor.com>2009-06-07 20:59:52 -0700
commit69bb4b204e8d29c89597961e94807d1acba2cd4b (patch)
tree143b21d9e0956d443165ac97ab8ba410f1b4cd97
parent1e4de8c54d7e007cf6002a87658f3d03c796bfc6 (diff)
downloadsyslinux-69bb4b204e8d29c89597961e94807d1acba2cd4b.tar.gz
memdisk: additional cleanups
Additional stylistic cleanups. Rename "syscall" to "intcall" (we can't call it __intcall without clashing with com32.h); use macros instead of copying variables to different places with only the type being different. Also, only change the rm/pm jump instructions when actually relocating the code. Signed-off-by: H. Peter Anvin <hpa@zytor.com>
-rw-r--r--memdisk/conio.c2
-rw-r--r--memdisk/memdisk.h52
-rw-r--r--memdisk/memdisk16.asm28
-rw-r--r--memdisk/msetup.c8
-rw-r--r--memdisk/setup.c77
-rw-r--r--memdisk/start32.S8
6 files changed, 87 insertions, 88 deletions
diff --git a/memdisk/conio.c b/memdisk/conio.c
index 0e75bd72..d1f0862c 100644
--- a/memdisk/conio.c
+++ b/memdisk/conio.c
@@ -30,7 +30,7 @@ int putchar(int ch)
}
regs.eax.w[0] = 0x0e00 | (ch & 0xff);
- syscall(0x10, &regs, NULL);
+ intcall(0x10, &regs, NULL);
return ch;
}
diff --git a/memdisk/memdisk.h b/memdisk/memdisk.h
index 6bfeb903..b6b277a8 100644
--- a/memdisk/memdisk.h
+++ b/memdisk/memdisk.h
@@ -26,9 +26,55 @@
#define __cdecl __attribute__((cdecl,regparm(0)))
-typedef void (*syscall_t) (uint8_t, com32sys_t *, com32sys_t *);
-extern __cdecl syscall_t syscall;
-extern void *sys_bounce;
+void __cdecl intcall(uint8_t, com32sys_t *, com32sys_t *);
+
+/* Structure passed in from the real-mode code */
+struct real_mode_args {
+ uint32_t rm_return;
+ uint32_t rm_intcall;
+ uint32_t rm_bounce;
+ uint32_t rm_base;
+ uint32_t rm_handle_interrupt;
+ uint32_t rm_gdt;
+ uint32_t rm_size;
+ uint32_t rm_pmjmp;
+ uint32_t rm_rmjmp;
+};
+extern struct real_mode_args rm_args;
+#define sys_bounce ((void *)rm_args.rm_bounce)
+
+/* This is the header in the boot sector/setup area */
+struct setup_header {
+ char cmdline[0x1f1];
+ uint8_t setup_secs;
+ uint16_t syssize;
+ uint16_t swap_dev;
+ uint16_t ram_size;
+ uint16_t vid_mode;
+ uint16_t root_dev;
+ uint16_t boot_flag;
+ uint16_t jump;
+ char header[4];
+ uint16_t version;
+ uint32_t realmode_swtch;
+ uint32_t start_sys;
+ uint8_t type_of_loader;
+ uint8_t loadflags;
+ uint16_t setup_move_size;
+ uint32_t code32_start;
+ uint32_t ramdisk_image;
+ uint32_t ramdisk_size;
+ uint32_t bootsect_kludge;
+ uint16_t head_end_ptr;
+ uint16_t pad1;
+ uint32_t cmd_line_ptr;
+ uint32_t initrd_addr_max;
+ uint32_t esdi;
+ uint32_t edx;
+ uint32_t sssp;
+ uint32_t csip;
+};
+#define shdr ((struct setup_header *)rm_args.rm_base)
/* Standard routines */
void *memcpy(void *, const void *, size_t);
diff --git a/memdisk/memdisk16.asm b/memdisk/memdisk16.asm
index 1a22ff6f..0c5b9973 100644
--- a/memdisk/memdisk16.asm
+++ b/memdisk/memdisk16.asm
@@ -562,17 +562,14 @@ call32_enter_pm:
mov [SavedSP],sp
cld
call enable_a20
- lea eax,[ebp+.in_pm]
- mov [.pm_jmp+2],eax ; Patch the PM jump
- jmp .sync
-.sync:
mov byte [call32_gdt+8+5],89h ; Mark TSS unbusy
o32 lgdt [call32_gdt] ; Set up GDT
o32 lidt [call32_pmidt] ; Set up IDT
mov eax,cr0
or al,1
mov cr0,eax ; Enter protected mode
-.pm_jmp: jmp 20h:strict dword 0
+ jmp 20h:strict dword .in_pm+CS_BASE
+.pm_jmp equ $-6
bits 32
@@ -604,6 +601,8 @@ call32_call_start:
;
mov esp, (BOUNCE_SEG << 4) + 0x10000
+ push dword call32_enter_rm.rm_jmp+CS_BASE
+ push dword call32_enter_pm.pm_jmp+CS_BASE
push dword stack_end ; RM size
push dword call32_gdt+CS_BASE
push dword call32_handle_interrupt+CS_BASE
@@ -627,11 +626,6 @@ call32_enter_rm:
call .here
.here: pop ebp
sub ebp,.here
- mov ecx,ebp
- shr ecx,4
- mov [ebp+.rm_jmp+3],cx ; Set segment
- jmp .sync
-.sync:
o32 sidt [ebp+call32_pmidt]
cli
cld
@@ -652,14 +646,16 @@ call32_enter_rm:
mov eax,cr0
and al,~1
mov cr0,eax
-.rm_jmp: jmp MY_CS:.in_rm
+ jmp MY_CS:.in_rm
+.rm_jmp equ $-2
.in_rm: ; Back in real mode
- mov ds,cx
- mov es,cx
- mov fs,cx
- mov gs,cx
- mov ss,cx
+ mov ax,cs
+ mov ds,ax
+ mov es,ax
+ mov fs,ax
+ mov gs,ax
+ mov ss,ax
mov sp,[SavedSP] ; Restore stack
jmp bx ; Go to whereever we need to go...
diff --git a/memdisk/msetup.c b/memdisk/msetup.c
index 3674b288..f40a2c66 100644
--- a/memdisk/msetup.c
+++ b/memdisk/msetup.c
@@ -53,7 +53,7 @@ static inline int get_e820(void)
regs.edi.w[0] = OFFS(buf);
regs.es = SEG(buf);
- syscall(0x15, &regs, &regs);
+ intcall(0x15, &regs, &regs);
copied = (regs.eflags.l & 1) ? 0 : regs.ecx.l;
if (regs.eax.l != 0x534d4150 || copied < 20)
@@ -76,7 +76,7 @@ static inline void get_dos_mem(void)
com32sys_t regs;
memset(&regs, 0, sizeof regs);
- syscall(0x12, &regs, &regs);
+ intcall(0x12, &regs, &regs);
insertrange(0, (uint64_t) ((uint32_t) regs.eax.w[0] << 10), 1);
printf(" DOS: %d K\n", regs.eax.w[0]);
}
@@ -89,7 +89,7 @@ static inline int get_e801(void)
memset(&regs, 0, sizeof regs);
regs.eax.w[0] = 0xe801;
- syscall(0x15, &regs, &regs);
+ intcall(0x15, &regs, &regs);
if (!(err = regs.eflags.l & 1)) {
if (regs.eax.w[0]) {
@@ -115,7 +115,7 @@ static inline int get_88(void)
memset(&regs, 0, sizeof regs);
regs.eax.b[1] = 0x88;
- syscall(0x15, &regs, &regs);
+ intcall(0x15, &regs, &regs);
if (!(err = regs.eflags.l & 1)) {
if (regs.eax.w[0]) {
diff --git a/memdisk/setup.c b/memdisk/setup.c
index 0a7c8c6b..98c4b69d 100644
--- a/memdisk/setup.c
+++ b/memdisk/setup.c
@@ -123,54 +123,6 @@ struct patch_area {
struct edd_dpt edd_dpt;
};
-/* This is the header in the boot sector/setup area */
-struct setup_header {
- char cmdline[0x1f1];
- uint8_t setup_secs;
- uint16_t syssize;
- uint16_t swap_dev;
- uint16_t ram_size;
- uint16_t vid_mode;
- uint16_t root_dev;
- uint16_t boot_flag;
- uint16_t jump;
- char header[4];
- uint16_t version;
- uint32_t realmode_swtch;
- uint32_t start_sys;
- uint8_t type_of_loader;
- uint8_t loadflags;
- uint16_t setup_move_size;
- uint32_t code32_start;
- uint32_t ramdisk_image;
- uint32_t ramdisk_size;
- uint32_t bootsect_kludge;
- uint16_t head_end_ptr;
- uint16_t pad1;
- uint32_t cmd_line_ptr;
- uint32_t initrd_addr_max;
- uint32_t esdi;
- uint32_t edx;
- uint32_t sssp;
- uint32_t csip;
-};
-struct setup_header *shdr;
-
-/* Structure passed in from the real-mode code */
-struct real_mode_args {
- uint32_t rm_return;
- uint32_t rm_syscall;
- uint32_t rm_bounce;
- uint32_t rm_base;
- uint32_t rm_handle_interrupt;
- uint32_t rm_gdt;
- uint32_t rm_size;
-};
-struct real_mode_args rm_args;
-
-__cdecl syscall_t syscall;
-void *sys_bounce;
-
/* Access to high memory */
/* Access to objects in the zero page */
@@ -706,13 +658,6 @@ static uint32_t pnp_install_check(void)
return 0;
}
-static void update_global_vars(void)
-{
- syscall = (__cdecl syscall_t) rm_args.rm_syscall;
- sys_bounce = (void *)rm_args.rm_bounce;
- shdr = (void *)rm_args.rm_base;
-}
-
/*
* Relocate the real-mode code to a new segment
*/
@@ -738,11 +683,12 @@ static void relocate_rm_code(uint32_t newbase)
memmove((void *)newbase, (void *)oldbase, rm_args.rm_size);
rm_args.rm_return += delta;
- rm_args.rm_syscall += delta;
+ rm_args.rm_intcall += delta;
rm_args.rm_bounce += delta;
rm_args.rm_base += delta;
rm_args.rm_gdt += delta;
- rm_args.rm_handle_interrupt += delta;
+ rm_args.rm_pmjmp += delta;
+ rm_args.rm_rmjmp += delta;
gdt_base = rm_args.rm_gdt;
@@ -753,13 +699,19 @@ static void relocate_rm_code(uint32_t newbase)
set_seg_base(gdt_base, 0x18, rm_args.rm_base);
asm volatile("lgdtl %0" : : "m" (*(char *)gdt_base));
- sti();
- update_global_vars();
+ *(uint32_t *)rm_args.rm_pmjmp += delta;
+ *(uint16_t *)rm_args.rm_rmjmp += delta >> 4;
+
+ rm_args.rm_handle_interrupt += delta;
+
+ sti();
}
#define STACK_NEEDED 512 /* Number of bytes of stack */
+struct real_mode_args rm_args;
+
/*
* Actual setup routine
* Returns the drive number (which is then passed in %dl to the
@@ -791,9 +743,6 @@ void setup(const struct real_mode_args *rm_args_ptr)
memcpy(&rm_args, rm_args_ptr, sizeof rm_args);
sti(); /* ... then interrupts are safe */
- /* Set up global variables */
- update_global_vars();
-
/* Show signs of life */
printf("%s %s\n", memdisk_version, copyright);
@@ -1021,7 +970,7 @@ void setup(const struct real_mode_args *rm_args_ptr)
regs.es = 0;
regs.eax.b[1] = 0x08;
regs.edx.b[0] = geometry->driveno & 0x80;
- syscall(0x13, &regs, &regs);
+ intcall(0x13, &regs, &regs);
/* Note: per suggestion from the Interrupt List, consider
INT 13 08 to have failed if the sector count in CL is zero. */
@@ -1151,7 +1100,7 @@ void setup(const struct real_mode_args *rm_args_ptr)
if (getcmditem("pause") != CMD_NOTFOUND) {
puts("press any key to boot... ");
regs.eax.w[0] = 0;
- syscall(0x16, &regs, NULL);
+ intcall(0x16, &regs, NULL);
}
puts("booting...\n");
diff --git a/memdisk/start32.S b/memdisk/start32.S
index 8fcebcc6..4fb05374 100644
--- a/memdisk/start32.S
+++ b/memdisk/start32.S
@@ -72,8 +72,16 @@ _start:
jmp *(rm_args) /* First argument is return */
.section ".text","ax"
+ .globl intcall
+ .type intcall, @function
+intcall:
+ jmp *(rm_args+1*4) /* Intcall is argument 1 */
+ .size intcall, .-intcall
+
+ .type handle_interrupt, @function
handle_interrupt:
jmp *(rm_args+4*4) /* Interrupt pointer is argument 4 */
+ .size handle_interrupt, .-handle_interrupt
.section ".rodata","a"
idt_ptr: