Merge branch 'master' into pathbased
authorH. Peter Anvin <hpa@linux.intel.com>
Tue, 30 Mar 2010 00:34:22 +0000 (17:34 -0700)
committerH. Peter Anvin <hpa@linux.intel.com>
Tue, 30 Mar 2010 00:34:22 +0000 (17:34 -0700)
Resolved Conflicts:
MCONFIG.embedded
com32/MCONFIG
com32/include/com32.h
core/com32.inc
core/pxelinux.asm
doc/comboot.txt

Signed-off-by: H. Peter Anvin <hpa@linux.intel.com>
1  2 
MCONFIG.embedded
com32/MCONFIG
com32/include/com32.h
com32/lib/sys/entry.S
com32/mboot/mboot.c
core/cmdline.inc
core/com32.inc
core/isolinux.asm
core/pxelinux.asm
doc/comboot.txt

  
  include $(topdir)/MCONFIG
  
 -GCCOPT    := $(call gcc_ok,-m32,)                                     \
 -           $(call gcc_ok,-ffreestanding,)                             \
 -           $(call gcc_ok,-fno-stack-protector,)                       \
 -           $(call gcc_ok,-falign-functions=0,-malign-functions=0)     \
 -           $(call gcc_ok,-falign-jumps=0,-malign-jumps=0)             \
 -           $(call gcc_ok,-falign-loops=0,-malign-loops=0)             \
 -           $(call gcc_ok,-mpreferred-stack-boundary=2,)               \
 -           $(call gcc_ok,-mincoming-stack-boundary=2,)                \
 -           -march=i386 -Os -fomit-frame-pointer -mregparm=3 -DREGPARM=3 \
 +GCCOPT    := $(call gcc_ok,-m32,)
 +GCCOPT    += $(call gcc_ok,-ffreestanding,)
 +GCCOPT          += $(call gcc_ok,-fno-stack-protector,)
 +GCCOPT          += $(call gcc_ok,-fwrapv,)
 +GCCOPT          += $(call gcc_ok,-freg-struct-return,)
 +GCCOPT    += -march=i386 -Os -fomit-frame-pointer -mregparm=3 -DREGPARM=3 \
             -msoft-float
 +GCCOPT    += $(call gcc_ok,-fno-exceptions,)
 +GCCOPT          += $(call gcc_ok,-fno-asynchronous-unwind-tables,)
 +GCCOPT          += $(call gcc_ok,-fno-strict-aliasing,)
 +GCCOPT          += $(call gcc_ok,-falign-functions=0,-malign-functions=0)
 +GCCOPT    += $(call gcc_ok,-falign-jumps=0,-malign-jumps=0)
 +GCCOPT    += $(call gcc_ok,-falign-labels=0,-malign-labels=0)
 +GCCOPT    += $(call gcc_ok,-falign-loops=0,-malign-loops=0)
 +GCCOPT    += $(call gcc_ok,-mpreferred-stack-boundary=2,)
++GCCOPT    += $(call gcc_ok,-mincoming-stack-boundary=2,)
  
  LIBGCC    := $(shell $(CC) $(GCCOPT) --print-libgcc)
  
diff --cc com32/MCONFIG
  
  include $(topdir)/MCONFIG
  
 -GCCOPT          := $(call gcc_ok,-std=gnu99,)                                 \
 -           $(call gcc_ok,-m32,)                                       \
 -           $(call gcc_ok,-fno-stack-protector,)                       \
 -           $(call gcc_ok,-falign-functions=0,-malign-functions=0)     \
 -           $(call gcc_ok,-falign-jumps=0,-malign-jumps=0)             \
 -           $(call gcc_ok,-falign-loops=0,-malign-loops=0)             \
 -           $(call gcc_ok,-mpreferred-stack-boundary=2,)               \
 -           $(call gcc_ok,-mincoming-stack-boundary=2,)                \
 -           -march=i386 -Os -fomit-frame-pointer -mregparm=3 -DREGPARM=3
 -
 -com32 = $(topdir)/com32
 +GCCOPT := $(call gcc_ok,-std=gnu99,)
 +GCCOPT += $(call gcc_ok,-m32,)
 +GCCOPT += $(call gcc_ok,-fno-stack-protector,)
 +GCCOPT += $(call gcc_ok,-fwrapv,)
 +GCCOPT += $(call gcc_ok,-freg-struct-return,)
 +GCCOPT += -mregparm=3 -DREGPARM=3 -march=i386 -Os
 +GCCOPT += $(call gcc_ok,-fPIE,-fPIC)
 +GCCOPT += $(call gcc_ok,-fno-exceptions,)
 +GCCOPT += $(call gcc_ok,-fno-asynchronous-unwind-tables,)
 +GCCOPT += $(call gcc_ok,-fno-strict-aliasing,)
 +GCCOPT += $(call gcc_ok,-falign-functions=0,-malign-functions=0)
 +GCCOPT += $(call gcc_ok,-falign-jumps=0,-malign-jumps=0)
 +GCCOPT += $(call gcc_ok,-falign-labels=0,-malign-labels=0)
 +GCCOPT += $(call gcc_ok,-falign-loops=0,-malign-loops=0)
 +GCCOPT += $(call gcc_ok,-mpreferred-stack-boundary=2,)
++GCCOPT += $(call gcc_ok,-incoming-stack-boundary=2,)
 +
 +com32  := $(topdir)/com32
 +RELOCS := $(com32)/tools/relocs
  
  ifneq ($(NOGPL),1)
  GPLLIB     = $(com32)/gpllib/libcom32gpl.a
@@@ -97,13 -95,13 +97,14 @@@ struct com32_pmapi
  extern struct com32_sys_args {
      uint32_t cs_sysargs;
      char *cs_cmdline;
-     void __cdecl(*cs_intcall) (uint8_t, const com32sys_t *, com32sys_t *);
+     void __cdecl (*cs_intcall)(uint8_t, const com32sys_t *, com32sys_t *);
      void *cs_bounce;
      uint32_t cs_bounce_size;
-     void __cdecl(*cs_farcall) (uint32_t, const com32sys_t *, com32sys_t *);
-     int __cdecl(*cs_cfarcall) (uint32_t, const void *, uint32_t);
+     void __cdecl (*cs_farcall)(uint32_t, const com32sys_t *, com32sys_t *);
+     int __cdecl (*cs_cfarcall)(uint32_t, const void *, uint32_t);
      uint32_t cs_memsize;
+     const char *cs_name;
 +    const struct com32_pmapi *cs_pm;
  } __com32;
  
  /*
@@@ -30,7 -30,7 +30,7 @@@
   */
  
  /* Number of arguments in our version of the entry structure */
--#define COM32_ARGS 8
++#define COM32_ARGS 9
  
                .section ".init","ax"
                .globl _start
Simple merge
@@@ -19,6 -19,6 +19,8 @@@
  ;; Not used by plain kernel due to BOOT_IMAGE= etc.
  ;;
  
++              section .text16
++
  ;
  ; Assumes DS == CS
  ;
diff --cc core/com32.inc
@@@ -47,9 -65,13 +47,13 @@@ is_com32_image
                sub cx,si
                fs rep movsb
  
 -              mov si,KernelCName
++              mov si,KernelName
+               mov di,Com32Name
+               call strcpy
                call comboot_setup_api  ; Set up the COMBOOT-style API
  
 -              mov edi,pm_entry        ; Load address
 +              mov edi,com32_entry     ; Load address
                pop eax                 ; File length
                pop si                  ; File handle
                xor dx,dx               ; No padding
@@@ -79,56 -124,317 +83,63 @@@ com32_start
  ; This is invoked right before the actually starting the COM32
  ; progam, in 32-bit mode...
  ;
 -com32_call_start:
 -              ;
 -              ; Point the stack to the end of (permitted) high memory
 -              ;
 -              mov esp,[word HighMemRsvd]
 -              xor sp,sp               ; Align to a 64K boundary
 -
 -              ;
 -              ; Set up the protmode IDT and the interrupt jump buffers
 -              ; We set these up in the system area at 0x100000,
 -              ; but we could also put them beyond the stack.
 -              ;
 -              mov edi,pm_idt
 -
 -              ; Form an interrupt gate descriptor
 -              mov eax,0x00200000+((pm_idt+8*256)&0x0000ffff)
 -              mov ebx,0x0000ee00+((pm_idt+8*256)&0xffff0000)
 -              xor ecx,ecx
 -              inc ch                          ; ecx <- 256
 -
 -              push ecx
 -.make_idt:
 -              stosd
 -              add eax,8
 -              xchg eax,ebx
 -              stosd
 -              xchg eax,ebx
 -              loop .make_idt
 -
 -              pop ecx
 -
 -              ; Each entry in the interrupt jump buffer contains
 -              ; the following instructions:
 -              ;
 -              ; 00000000 60                pushad
 -              ; 00000001 B0xx              mov al,<interrupt#>
 -              ; 00000003 E9xxxxxxxx        jmp com32_handle_interrupt
 -
 -              mov eax,0e900b060h
 -              mov ebx,com32_handle_interrupt-(pm_idt+8*256+8)
 -
 -.make_ijb:
 -              stosd
 -              sub [edi-2],cl                  ; Interrupt #
 -              xchg eax,ebx
 -              stosd
 -              sub eax,8
 -              xchg eax,ebx
 -              loop .make_ijb
 -
 -              ; Now everything is set up for interrupts...
 +              bits 32
 +              section .text
 +.pm:
 +              ; Set up the calling stack frame
  
 +              push dword pm_api_vector
+               push dword Com32Name            ; Module filename
                push dword [HighMemSize]        ; Memory managed by Syslinux
 -              push dword com32_cfarcall       ; Cfarcall entry point
 -              push dword com32_farcall        ; Farcall entry point
 +              push dword core_cfarcall        ; Cfarcall entry point
 +              push dword core_farcall         ; Farcall entry point
                push dword (1 << 16)            ; 64K bounce buffer
 -              push dword (xfer_buf_seg << 4)  ; Bounce buffer address
 -              push dword com32_intcall        ; Intcall entry point
 +              push dword core_real_mode       ; Bounce buffer address
 +              push dword core_intcall         ; Intcall entry point
                push dword command_line         ; Command line pointer
--              push dword 8                    ; Argument count
++              push dword 9                    ; Argument count
                sti                             ; Interrupts OK now
 -              call pm_entry                   ; Run the program...
 +              call com32_entry                ; Run the program...
                ; ... on return, fall through to com32_exit ...
 -
  com32_exit:
 -              mov bx,com32_done       ; Return to command loop
 -
 -com32_enter_rm:
 -              cli
 -              cld
 -              mov [PMESP],esp         ; Save exit %esp
 -              xor esp,esp             ; Make sure the high bits are zero
 -              jmp PM_CS16:.in_pm16    ; Return to 16-bit mode first
 +              mov bx,comboot_return
 +              jmp enter_rm
  
                bits 16
 -.in_pm16:
 -              mov ax,PM_DS16          ; Real-mode-like segment
 -              mov es,ax
 -              mov ds,ax
 -              mov ss,ax
 -              mov fs,ax
 -              mov gs,ax
 -
 -              lidt [com32_rmidt]      ; Real-mode IDT (rm needs no GDT)
 -              mov eax,cr0
 -              and al,~1
 -              mov cr0,eax
 -              jmp 0:.in_rm
 -
 -.in_rm:                                       ; Back in real mode
 -              mov ax,cs               ; Set up sane segments
 -              mov ds,ax
 -              mov es,ax
 -              mov fs,ax
 -              mov gs,ax
 -              lss sp,[RealModeSSSP]   ; Restore stack
 -              jmp bx                  ; Go to whereever we need to go...
 -
 -com32_done:
 -              sti
 +              section .text16
 +not_com32r:
 +              mov si,KernelName
 +              call writestr
 +              mov si,not_com32r_msg
 +              call writestr
                jmp enter_command
  
 -;
 -; 16-bit support code
 -;
 -              bits 16
 -
 -;
 -; 16-bit interrupt-handling code
 -;
 -com32_int_rm:
 -              pushf                           ; Flags on stack
 -              push cs                         ; Return segment
 -              push word .cont                 ; Return address
 -              push dword edx                  ; Segment:offset of IVT entry
 -              retf                            ; Invoke IVT routine
 -.cont:                ; ... on resume ...
 -              mov ebx,com32_int_resume
 -              jmp com32_enter_pm              ; Go back to PM
 -
 -;
 -; 16-bit intcall/farcall handling code
 -;
 -com32_sys_rm:
 -              pop gs
 -              pop fs
 -              pop es
 -              pop ds
 -              popad
 -              popfd
 -              mov [cs:Com32SysSP],sp
 -              retf                            ; Invoke routine
 -.return:
 -              ; We clean up SP here because we don't know if the
 -              ; routine returned with RET, RETF or IRET
 -              mov sp,[cs:Com32SysSP]
 -              pushfd
 -              pushad
 -              push ds
 -              push es
 -              push fs
 -              push gs
 -              mov ebx,com32_syscall.resume
 -              jmp com32_enter_pm
 -
 -;
 -; 16-bit cfarcall handing code
 -;
 -com32_cfar_rm:
 -              retf
 -.return:
 -              mov sp,[cs:Com32SysSP]
 -              mov [cs:RealModeEAX],eax
 -              mov ebx,com32_cfarcall.resume
 -              jmp com32_enter_pm
 -
 -;
 -; 32-bit support code
 -;
 -              bits 32
 -
 -;
 -; This is invoked on getting an interrupt in protected mode.  At
 -; this point, we need to context-switch to real mode and invoke
 -; the interrupt routine.
 -;
 -; When this gets invoked, the registers are saved on the stack and
 -; AL contains the register number.
 -;
 -com32_handle_interrupt:
 -              movzx eax,al
 -              xor ebx,ebx             ; Actually makes the code smaller
 -              mov edx,[ebx+eax*4]     ; Get the segment:offset of the routine
 -              mov bx,com32_int_rm
 -              jmp com32_enter_rm      ; Go to real mode
 -
 -com32_int_resume:
 -              popad
 -              iret
 -
 -;
 -; Intcall/farcall invocation.  We manifest a structure on the real-mode stack,
 -; containing the com32sys_t structure from <com32.h> as well as
 -; the following entries (from low to high address):
 -; - Target offset
 -; - Target segment
 -; - Return offset
 -; - Return segment (== real mode cs == 0)
 -; - Return flags
 -;
 -com32_farcall:
 -              pushfd                          ; Save IF among other things...
 -              pushad                          ; We only need to save some, but...
 -
 -              mov eax,[esp+10*4]              ; CS:IP
 -              jmp com32_syscall
 -
 +              section .data16
 +not_com32r_msg        db ': not a COM32R image', CR, LF, 0
  
 -com32_intcall:
 -              pushfd                          ; Save IF among other things...
 -              pushad                          ; We only need to save some, but...
 -
 -              movzx eax,byte [esp+10*4]       ; INT number
 -              mov eax,[eax*4]                 ; Get CS:IP from low memory
 -
 -com32_syscall:
 -              cld
 -
 -              movzx edi,word [word RealModeSSSP]
 -              movzx ebx,word [word RealModeSSSP+2]
 -              sub edi,54              ; Allocate 54 bytes
 -              mov [word RealModeSSSP],di
 -              shl ebx,4
 -              add edi,ebx             ; Create linear address
 -
 -              mov esi,[esp+11*4]      ; Source regs
 -              xor ecx,ecx
 -              mov cl,11               ; 44 bytes to copy
 -              rep movsd
 -
 -              ; EAX is already set up to be CS:IP
 -              stosd                   ; Save in stack frame
 -              mov eax,com32_sys_rm.return     ; Return seg:offs
 -              stosd                   ; Save in stack frame
 -              mov eax,[edi-12]        ; Return flags
 -              and eax,0x200cd7        ; Mask (potentially) unsafe flags
 -              mov [edi-12],eax        ; Primary flags entry
 -              stosw                   ; Return flags
 -
 -              mov bx,com32_sys_rm
 -              jmp com32_enter_rm      ; Go to real mode
 -
 -              ; On return, the 44-byte return structure is on the
 -              ; real-mode stack, plus the 10 additional bytes used
 -              ; by the target address (see above.)
 -.resume:
 -              movzx esi,word [word RealModeSSSP]
 -              movzx eax,word [word RealModeSSSP+2]
 -              mov edi,[esp+12*4]      ; Dest regs
 -              shl eax,4
 -              add esi,eax             ; Create linear address
 -              and edi,edi             ; NULL pointer?
 -              jnz .do_copy
 -.no_copy:     mov edi,esi             ; Do a dummy copy-to-self
 -.do_copy:     xor ecx,ecx
 -              mov cl,11               ; 44 bytes
 -              rep movsd               ; Copy register block
 -
 -              add dword [word RealModeSSSP],54        ; Remove from stack
 -
 -              popad
 -              popfd
 -              ret                     ; Return to 32-bit program
 -
 -;
 -; Cfarcall invocation.  We copy the stack frame to the real-mode stack,
 -; followed by the return CS:IP and the CS:IP of the target function.
 -;
 -com32_cfarcall:
 -              pushfd
 -              pushad
 -
 -              cld
 -              mov ecx,[esp+12*4]              ; Size of stack frame
 -
 -              movzx edi,word [word RealModeSSSP]
 -              movzx ebx,word [word RealModeSSSP+2]
 -              mov [word Com32SysSP],di
 -              sub edi,ecx             ; Allocate space for stack frame
 -              and edi,~3              ; Round
 -              sub edi,4*2             ; Return pointer, return value
 -              mov [word RealModeSSSP],di
 -              shl ebx,4
 -              add edi,ebx             ; Create linear address
 -
 -              mov eax,[esp+10*4]      ; CS:IP
 -              stosd                   ; Save to stack frame
 -              mov eax,com32_cfar_rm.return    ; Return seg:off
 -              stosd
 -              mov esi,[esp+11*4]      ; Stack frame
 -              mov eax,ecx             ; Copy the stack frame
 -              shr ecx,2
 -              rep movsd
 -              mov ecx,eax
 -              and ecx,3
 -              rep movsb
 -
 -              mov bx,com32_cfar_rm
 -              jmp com32_enter_rm
 -
 -.resume:
 -              popad
 -              mov eax,[word RealModeEAX]
 -              popfd
 -              ret
 -
 -              bits 16
 -
 -              section .bss1
 -              alignb 4
 -RealModeSSSP  resd 1                  ; Real-mode SS:SP
 -RealModeEAX   resd 1                  ; Real mode EAX
 -PMESP         resd 1                  ; Protected-mode ESP
 -Com32SysSP    resw 1                  ; SP saved during COM32 syscall
 +              ; Ersatz com32 invocation structure, to make libcom32
 +              ; code run the same if linked to the core.  This is in
 +              ; the .data16 segment so HighMemSize can live here.
 +              ;
 +              ; Danger, Will Robinson: it's not clear the use of
 +              ; core_xfer_buf is safe here.
 +              global __entry_esp, __com32
 +              alignz 4
 +__entry_esp:
 +              dd 0                            ; Dummy to avoid _exit issues
 +__com32:
-               dd 8                            ; Argument count
++              dd 9                            ; Argument count
 +              dd 0                            ; No command line
 +              dd core_intcall                 ; Intcall entry point
 +              dd 0                            ; Bounce buffer address
 +              dd 0                            ; 64K bounce buffer
 +              dd core_farcall                 ; Farcall entry point
 +              dd core_cfarcall                ; Cfarcall entry point
 +HighMemSize   dd 0                            ; End of memory pointer (bytes)
++              dd 0                            ; No module name
 +              dd pm_api_vector                ; Protected mode functions
+               section .uibss
 -%if IS_SYSLINUX
 -Com32Name     resb FILENAME_MAX+2
 -%else
+ Com32Name     resb FILENAME_MAX
 -%endif
 -              section .text
++              section .text16
Simple merge
@@@ -500,9 -2849,36 +500,9 @@@ copyright_str   db ' Copyright (C) 1994
                db ' H. Peter Anvin et al', CR, LF, 0
  err_bootfailed        db CR, LF, 'Boot failed: press a key to retry, or wait for reset...', CR, LF, 0
  bailmsg               equ err_bootfailed
 -err_nopxe     db "No !PXE or PXENV+ API found; we're dead...", CR, LF, 0
 -err_pxefailed db 'PXE API call failed, error ', 0
 -err_udpinit   db 'Failed to initialize UDP stack', CR, LF, 0
 -err_noconfig  db 'Unable to locate configuration file', CR, LF, 0
 -err_damage    db 'TFTP server sent an incomprehesible reply', CR, LF, 0
 -found_pxenv   db 'Found PXENV+ structure', CR, LF, 0
 -apiver_str    db 'PXE API version is ',0
 -pxeentry_msg  db '!PXE entry point found (we hope) at ', 0
 -pxenventry_msg        db 'PXENV+ entry point found (we hope) at ', 0
 -viaplan_msg   db ' via plan '
 -plan          db 'A', CR, LF, 0
 -trymempxe_msg db 'Scanning memory for !PXE structure... ', 0
 -trymempxenv_msg       db 'Scanning memory for PXENV+ structure... ', 0
 -undi_data_msg db 'UNDI data segment at ',0
 -undi_code_msg db 'UNDI code segment at ',0
 -len_msg               db ' len ', 0
 -cant_free_msg db 'Failed to free base memory, error ', 0
 -notfound_msg  db 'not found', CR, LF, 0
 -myipaddr_msg  db 'My IP address seems to be ',0
 -tftpprefix_msg        db 'TFTP prefix: ', 0
  localboot_msg db 'Booting from local disk...', CR, LF, 0
- syslinux_banner       db CR, LF, 'PXELINUX ', VERSION_STR, ' ', DATE_STR, ' ', 0
 -trying_msg    db 'Trying to load: ', 0
 -default_str   db 'default', 0
+ syslinux_banner       db CR, LF, MY_NAME, ' ', VERSION_STR, ' ', DATE_STR, ' ', 0
 -cfgprefix     db 'pxelinux.cfg/'              ; No final null!
 -cfgprefix_len equ ($-cfgprefix)
  
 -; This one we make ourselves
 -bootif_str    db 'BOOTIF='
 -bootif_str_len        equ $-bootif_str
  ;
  ; Config file keyword table
  ;
diff --cc doc/comboot.txt
@@@ -90,22 -87,7 +90,24 @@@ The following arguments are passed to t
   [ESP+24] dword Pointer to FAR call helper function (new in 2.05)
   [ESP+28] dword Pointer to CDECL helper function (new in 3.54)
   [ESP+32] dword Amount of memory controlled by the Syslinux core (new in 3.74)
-  [ESP+36] dword       Pointer to protected-mode functions (new in 4.00)
+  [ESP+36] dword Pointer to the filename of the com32 module (new in 3.86)
++ [ESP+40] dword       Pointer to protected-mode functions (new in 4.00)
 +
 +The libcom32 startup code loads this into a structure named __com32,
 +defined in <com32.h>:
 +
 +extern struct com32_sys_args {
 +    uint32_t cs_sysargs;
 +    char *cs_cmdline;
 +    void __cdecl(*cs_intcall)(uint8_t, const com32sys_t *, com32sys_t *);
 +    void *cs_bounce;
 +    uint32_t cs_bounce_size;
 +    void __cdecl(*cs_farcall)(uint32_t, const com32sys_t *, com32sys_t *);
 +    int __cdecl(*cs_cfarcall)(uint32_t, const void *, uint32_t);
 +    uint32_t cs_memsize;
-     struct com32_pmapi *cs_pm;
++    const char *cs_name;
++    const struct com32_pmapi *cs_pm;
 +} __com32;
  
  The intcall helper function can be used to issue BIOS or Syslinux API
  calls, and takes the interrupt number as first argument.  The second