mirror of
https://github.com/ipxe/ipxe
synced 2025-12-14 16:01:38 +03:00
236 lines
4.3 KiB
ArmAsm
236 lines
4.3 KiB
ArmAsm
FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL )
|
|
|
|
#include <librm.h>
|
|
|
|
#define BZI_LOAD_HIGH_ADDR 0x100000
|
|
|
|
.text
|
|
.arch i386
|
|
.code16
|
|
.section ".prefix", "ax", @progbits
|
|
.globl _lkrn_start
|
|
_lkrn_start:
|
|
|
|
/*****************************************************************************
|
|
*
|
|
* Kernel header
|
|
*
|
|
* We place our prefix (i.e. our .prefix and .text16.early sections)
|
|
* within the bzImage real-mode portion which gets loaded at
|
|
* 1000:0000, and our payload (i.e. everything else) within the
|
|
* bzImage protected-mode portion which gets loaded at 0x100000
|
|
* upwards.
|
|
*
|
|
*/
|
|
|
|
.org 0x1f1
|
|
setup_sects:
|
|
.byte -1 /* Allow for initial "boot sector" */
|
|
.section ".zinfo.fixup", "a", @progbits /* Compressor fixups */
|
|
.ascii "ADHL"
|
|
.long setup_sects
|
|
.long 512
|
|
.long 0
|
|
.previous
|
|
root_flags:
|
|
.word 0
|
|
syssize:
|
|
.long 0
|
|
.section ".zinfo.fixup", "a", @progbits /* Compressor fixups */
|
|
.ascii "ADPL"
|
|
.long syssize
|
|
.long 16
|
|
.long 0
|
|
.previous
|
|
ram_size:
|
|
.word 0
|
|
vid_mode:
|
|
.word 0
|
|
root_dev:
|
|
.word 0
|
|
boot_flag:
|
|
.word 0xaa55
|
|
jump:
|
|
/* Manually specify a two-byte jmp instruction here rather
|
|
* than leaving it up to the assembler.
|
|
*/
|
|
.byte 0xeb, ( setup - header )
|
|
header:
|
|
.byte 'H', 'd', 'r', 'S'
|
|
version:
|
|
.word 0x0207 /* 2.07 */
|
|
realmode_swtch:
|
|
.long 0
|
|
start_sys:
|
|
.word 0
|
|
kernel_version:
|
|
.word version_string - 0x200
|
|
type_of_loader:
|
|
.byte 0
|
|
loadflags:
|
|
.byte 0x01 /* LOADED_HIGH */
|
|
setup_move_size:
|
|
.word 0
|
|
code32_start:
|
|
.long 0
|
|
ramdisk_image:
|
|
.long 0
|
|
ramdisk_size:
|
|
.long 0
|
|
bootsect_kludge:
|
|
.long 0
|
|
heap_end_ptr:
|
|
.word 0
|
|
ext_loader_ver:
|
|
.byte 0
|
|
ext_loader_type:
|
|
.byte 0
|
|
cmd_line_ptr:
|
|
.long 0
|
|
initrd_addr_max:
|
|
.long 0xffffffff
|
|
kernel_alignment:
|
|
.long 0
|
|
relocatable_kernel:
|
|
.byte 0
|
|
min_alignment:
|
|
.byte 0
|
|
xloadflags:
|
|
.word 0
|
|
cmdline_size:
|
|
.long 0x7ff
|
|
hardware_subarch:
|
|
.long 0
|
|
hardware_subarch_data:
|
|
.byte 0, 0, 0, 0, 0, 0, 0, 0
|
|
|
|
version_string:
|
|
.asciz VERSION
|
|
|
|
/*****************************************************************************
|
|
*
|
|
* Setup code
|
|
*
|
|
*/
|
|
|
|
setup:
|
|
/* Fix up code segment */
|
|
pushw %ds
|
|
pushw $1f
|
|
lret
|
|
1:
|
|
/* Set up stack just below 0x7c00 and clear direction flag */
|
|
xorw %ax, %ax
|
|
movw %ax, %ss
|
|
movw $0x7c00, %sp
|
|
cld
|
|
|
|
/* Retrieve command-line pointer */
|
|
movl cmd_line_ptr, %edx
|
|
testl %edx, %edx
|
|
jz no_cmd_line
|
|
|
|
/* Set up %es:%di to point to command line */
|
|
movl %edx, %edi
|
|
andl $0xf, %edi
|
|
rorl $4, %edx
|
|
movw %dx, %es
|
|
|
|
/* Find length of command line */
|
|
pushw %di
|
|
movw $0xffff, %cx
|
|
repnz scasb
|
|
notw %cx
|
|
popw %si
|
|
|
|
/* Make space for command line on stack */
|
|
movw %sp, %di
|
|
subw %cx, %di
|
|
andw $~0xf, %di
|
|
movw %di, %sp
|
|
|
|
/* Copy command line to stack */
|
|
pushw %ds
|
|
pushw %es
|
|
popw %ds
|
|
pushw %ss
|
|
popw %es
|
|
rep movsb
|
|
popw %ds
|
|
|
|
/* Store new command-line pointer */
|
|
movzwl %sp, %edx
|
|
no_cmd_line:
|
|
|
|
/* Calculate maximum relocation address */
|
|
movl ramdisk_image, %ebp
|
|
testl %ebp, %ebp
|
|
jnz 1f
|
|
orl $0xffffffff, %ebp /* Allow arbitrary relocation if no initrd */
|
|
1:
|
|
/* Install iPXE */
|
|
call alloc_basemem
|
|
xorl %esi, %esi
|
|
xorl %edi, %edi
|
|
call install_prealloc
|
|
|
|
/* Set up real-mode stack */
|
|
movw %bx, %ss
|
|
movw $_estack16, %sp
|
|
|
|
/* Jump to .text16 segment */
|
|
pushw %ax
|
|
pushw $1f
|
|
lret
|
|
.section ".text16", "awx", @progbits
|
|
1:
|
|
/* Retrieve initrd pointer and size */
|
|
movl ramdisk_image, %ebp
|
|
movl ramdisk_size, %ecx
|
|
|
|
/* Set up %ds for access to .data16 */
|
|
movw %bx, %ds
|
|
|
|
/* Store command-line pointer */
|
|
movl %edx, cmdline_phys
|
|
|
|
/* Store initrd pointer and size */
|
|
movl %ebp, initrd_phys
|
|
movl %ecx, initrd_len
|
|
|
|
/* Run iPXE */
|
|
virtcall main
|
|
|
|
/* Uninstall iPXE */
|
|
call uninstall
|
|
|
|
/* Boot next device */
|
|
int $0x18
|
|
|
|
/*****************************************************************************
|
|
*
|
|
* Open payload (called by libprefix)
|
|
*
|
|
* Parameters:
|
|
* %ds:0000 : Prefix
|
|
* %esi : Buffer for copy of image source (or zero if no buffer available)
|
|
* %ecx : Expected offset within buffer of first payload block
|
|
* Returns:
|
|
* %esi : Valid image source address (buffered or unbuffered)
|
|
* %ecx : Actual offset within buffer of first payload block
|
|
* CF set on error
|
|
*/
|
|
|
|
.section ".text16.early", "awx", @progbits
|
|
.globl open_payload
|
|
open_payload:
|
|
|
|
/* Our payload will always end up at BZI_LOAD_HIGH_ADDR */
|
|
movl $BZI_LOAD_HIGH_ADDR, %esi
|
|
xorl %ecx, %ecx
|
|
lret
|
|
|
|
/* Payload must be aligned to a whole number of setup sectors */
|
|
.globl _payload_align
|
|
.equ _payload_align, 512
|