aboutsummaryrefslogtreecommitdiffstats
path: root/core
diff options
context:
space:
mode:
authorH. Peter Anvin <hpa@zytor.com>2011-04-25 20:08:32 -0700
committerH. Peter Anvin <hpa@zytor.com>2011-04-25 20:25:02 -0700
commit3953ca3532ca3281cc248f9985d9276c6f8486f0 (patch)
treea03065fdb9d42e0d60867136b7abe25bbea99732 /core
parent57b7af7df6599a8cdb318d7adeda1cd6fb981626 (diff)
downloadsyslinux-3953ca3532ca3281cc248f9985d9276c6f8486f0.tar.gz
syslinux-3953ca3532ca3281cc248f9985d9276c6f8486f0.tar.xz
syslinux-3953ca3532ca3281cc248f9985d9276c6f8486f0.zip
Generalize ipappend handling as "sysappend", and move to PM code
Generalize the ipappend handling to cover all the derivatives, and rename it "sysappend" ("ipappend" is a valid alias for all derivatives.) Move all the string handling to protected mode. Currently only pxelinux exports strings, but the plan is to change that in the future. Signed-off-by: H. Peter Anvin <hpa@zytor.com>
Diffstat (limited to 'core')
-rw-r--r--core/cmdline.inc57
-rw-r--r--core/comboot.inc16
-rw-r--r--core/diskfs.inc19
-rw-r--r--core/extern.inc3
-rw-r--r--core/fs/pxe/pxe.c53
-rw-r--r--core/fs/pxe/pxe.h3
-rw-r--r--core/head.inc1
-rw-r--r--core/include/core.h6
-rw-r--r--core/isolinux.asm17
-rw-r--r--core/keywords1
-rw-r--r--core/keywords.inc5
-rw-r--r--core/parseconfig.inc42
-rw-r--r--core/pmapi.c3
-rw-r--r--core/pxelinux.asm19
-rw-r--r--core/runkernel.inc2
-rw-r--r--core/sysappend.c61
-rw-r--r--core/ui.inc32
-rw-r--r--core/vkernel.inc35
18 files changed, 168 insertions, 207 deletions
diff --git a/core/cmdline.inc b/core/cmdline.inc
index 3e63f9ab..c2bc95f7 100644
--- a/core/cmdline.inc
+++ b/core/cmdline.inc
@@ -31,7 +31,7 @@ make_plain_cmdline:
mov es,ax
mov di,[CmdLinePtr]
- call do_ip_append
+ pm_call do_sysappend
mov si,[CmdOptPtr]
@@ -44,58 +44,3 @@ make_plain_cmdline:
pop es
ret
-;
-; Actual IPAppend strings...
-;
-%if IS_PXELINUX
- extern IPOption, BOOTIFStr, SYSUUIDStr
- global IPAppends, numIPAppends
-
- section .data16
- alignz 2
-IPAppends dw IPOption
- dw BOOTIFStr
- dw SYSUUIDStr
-numIPAppends equ ($-IPAppends)/2
-%else
-IPAppends equ 0
-numIPAppends equ 0
-%endif
-
-;
-; Handle "ipappend" strings, if applicable
-;
-; Assumes DS == CS; pushes output to ES:DI
-;
- section .text16
-
-do_ip_append:
-%ifndef DEPEND
- %if numIPAppends > 0
- push cx
- push bx
- push si
-
- mov bx,IPAppends
- mov cx,[IPAppend]
- and cx,(1 << numIPAppends)-1
-.loop:
- jcxz .done
- mov si,[bx]
- inc bx
- inc bx
- test cl,1
- jz .not_this
-
- call strcpy
- mov byte [es:di-1],' ' ; Replace final null with space
-.not_this:
- shr cx,1
- jmp .loop
-.done:
- pop si
- pop bx
- pop cx
- %endif
-%endif
- ret
diff --git a/core/comboot.inc b/core/comboot.inc
index d6f670c9..9f5e3ea7 100644
--- a/core/comboot.inc
+++ b/core/comboot.inc
@@ -677,14 +677,8 @@ comapi_configfile:
ret
;
-; INT 22h AX=000Fh Get IPAPPEND strings
+; INT 22h AX=000Fh Obsolete
;
-comapi_ipappend:
- mov P_ES,cs
- mov P_CX,numIPAppends
- mov P_BX,IPAppends
- clc
- ret
;
; INT 22h AX=0010h Resolve hostname
@@ -770,10 +764,8 @@ comapi_runkernel:
mov [Kernel_SI],si
mov [Kernel_EAX],eax
-%if IS_PXELINUX
- mov al,P_CL
- mov [IPAppend],al
-%endif
+ mov eax,P_ECX
+ mov [SysAppends],eax
call comboot_exit
@@ -952,7 +944,7 @@ int22_table:
dw comapi_cleanup ; 000C perform final cleanup
dw comapi_err ; 000D clean up then bootstrap
dw comapi_configfile ; 000E get name of config file
- dw comapi_ipappend ; 000F get ipappend strings
+ dw comapi_err ; 000F get ipappend strings
dw comapi_dnsresolv ; 0010 resolve hostname
dw comapi_err ; 0011 maximum shuffle descriptors
dw comapi_err ; 0012 cleanup, shuffle and boot
diff --git a/core/diskfs.inc b/core/diskfs.inc
index 41391e7f..24f7e38c 100644
--- a/core/diskfs.inc
+++ b/core/diskfs.inc
@@ -33,25 +33,6 @@ BS_MAGIC_VER equ 0x1b << 9
MIN_SECTOR_SHIFT equ 9
MIN_SECTOR_SIZE equ (1 << MIN_SECTOR_SHIFT)
-;
-; The following structure is used for "virtual kernels"; i.e. LILO-style
-; option labels. The options we permit here are `kernel' and `append
-; Since there is no room in the bottom 64K for all of these, we
-; stick them in high memory and copy them down before we need them.
-;
- struc vkernel
-vk_vname: resb FILENAME_MAX ; Virtual name **MUST BE FIRST!**
-vk_rname: resb FILENAME_MAX ; Real name
-vk_appendlen: resw 1
-vk_type: resb 1 ; Type of file
- alignb 4
-vk_append: resb max_cmd_len+1 ; Command line
- alignb 4
-vk_end: equ $ ; Should be <= vk_size
- endstruc
-
-
-
; ---------------------------------------------------------------------------
; BEGIN CODE
; ---------------------------------------------------------------------------
diff --git a/core/extern.inc b/core/extern.inc
index b40d8491..433d55e7 100644
--- a/core/extern.inc
+++ b/core/extern.inc
@@ -27,6 +27,9 @@
; mem/init.c
extern MallocStart, mem_init
+ ; sysappend.c
+ extern do_sysappend, print_sysappend
+
%if IS_PXELINUX
; pxe.c
extern unload_pxe, reset_pxe
diff --git a/core/fs/pxe/pxe.c b/core/fs/pxe/pxe.c
index 7ac3519b..c1b84766 100644
--- a/core/fs/pxe/pxe.c
+++ b/core/fs/pxe/pxe.c
@@ -20,14 +20,8 @@ uint8_t MAC[MAC_MAX]; /* Actual MAC address */
uint8_t MAC_len; /* MAC address len */
uint8_t MAC_type; /* MAC address type */
-char __bss16 BOOTIFStr[7+3*(MAC_MAX+1)];
-#define MAC_str (BOOTIFStr+7) /* The actual hardware address */
-char __bss16 SYSUUIDStr[8+32+5];
-#define UUID_str (SYSUUIDStr+8) /* The actual UUID */
-
char boot_file[256]; /* From DHCP */
char path_prefix[256]; /* From DHCP */
-char dot_quad_buf[16];
static bool has_gpxe;
static uint32_t gpxe_funcs;
@@ -550,14 +544,14 @@ static int pxe_load_config(void)
config_file = stpcpy(ConfigName, cfgprefix);
/* Try loading by UUID */
- if (have_uuid) {
- strcpy(config_file, UUID_str);
+ if (sysappend_strings[SYSAPPEND_UUID]) {
+ strcpy(config_file, sysappend_strings[SYSAPPEND_UUID]+8);
if (try_load(ConfigName))
return 0;
}
/* Try loading by MAC address */
- strcpy(config_file, MAC_str);
+ strcpy(config_file, sysappend_strings[SYSAPPEND_BOOTIF]+7);
if (try_load(ConfigName))
return 0;
@@ -586,30 +580,32 @@ static int pxe_load_config(void)
*/
static void make_bootif_string(void)
{
+ static char bootif_str[7+3*(MAC_MAX+1)];
const uint8_t *src;
- char *dst = BOOTIFStr;
+ char *dst = bootif_str;
int i;
dst += sprintf(dst, "BOOTIF=%02x", MAC_type);
src = MAC;
for (i = MAC_len; i; i--)
dst += sprintf(dst, "-%02x", *src++);
+
+ sysappend_strings[SYSAPPEND_BOOTIF] = bootif_str;
}
/*
* Generate the SYSUUID string, if we have one...
*/
static void make_sysuuid_string(void)
{
+ static char sysuuid_str[8+32+5];
static const uint8_t uuid_dashes[] = {4, 2, 2, 2, 6, 0};
const uint8_t *src = uuid;
const uint8_t *uuid_ptr = uuid_dashes;
char *dst;
- SYSUUIDStr[0] = '\0'; /* If nothing there... */
-
/* Try loading by UUID */
if (have_uuid) {
- dst = stpcpy(SYSUUIDStr, "SYSUUID=");
+ dst = stpcpy(sysuuid_str, "SYSUUID=");
while (*uuid_ptr) {
int len = *uuid_ptr;
@@ -622,6 +618,8 @@ static void make_sysuuid_string(void)
}
/* Remove last dash and zero-terminate */
*--dst = '\0';
+
+ sysappend_strings[SYSAPPEND_UUID] = sysuuid_str;
}
}
@@ -630,21 +628,22 @@ static void make_sysuuid_string(void)
* option into IPOption based on a DHCP packet in trackbuf.
*
*/
-char __bss16 IPOption[3+4*16];
-
static void genipopt(void)
{
- char *p = IPOption;
+ static char ip_option[3+4*16];
const uint32_t *v = &IPInfo.myip;
+ char *p;
int i;
- p = stpcpy(p, "ip=");
+ p = stpcpy(ip_option, "ip=");
for (i = 0; i < 4; i++) {
p += gendotquad(p, *v++);
*p++ = ':';
}
*--p = '\0';
+
+ sysappend_strings[SYSAPPEND_IP] = ip_option;
}
@@ -652,6 +651,7 @@ static void genipopt(void)
static void ip_init(void)
{
uint32_t ip = IPInfo.myip;
+ char dot_quad_buf[16];
genipopt();
gendotquad(dot_quad_buf, ip);
@@ -661,23 +661,6 @@ static void ip_init(void)
}
/*
- * Print the IPAPPEND strings, in order
- */
-extern const uint16_t IPAppends[];
-extern const char numIPAppends[];
-
-static void print_ipappend(void)
-{
- size_t i;
-
- for (i = 0; i < (size_t)numIPAppends; i++) {
- const char *p = (const char *)(size_t)IPAppends[i];
- if (*p)
- printf("%s\n", p);
- }
-}
-
-/*
* Validity check on possible !PXE structure in buf
* return 1 for success, 0 for failure.
*
@@ -956,7 +939,7 @@ static void network_init(void)
make_bootif_string();
make_sysuuid_string();
ip_init();
- print_ipappend();
+ print_sysappend();
/*
* Check to see if we got any PXELINUX-specific DHCP options; in particular,
diff --git a/core/fs/pxe/pxe.h b/core/fs/pxe/pxe.h
index 94bc58d7..d3e74996 100644
--- a/core/fs/pxe/pxe.h
+++ b/core/fs/pxe/pxe.h
@@ -155,9 +155,6 @@ extern char boot_file[];
extern char path_prefix[];
extern char LocalDomain[];
-extern char IPOption[];
-extern char dot_quad_buf[];
-
extern uint32_t dns_server[];
extern uint16_t APIVer;
diff --git a/core/head.inc b/core/head.inc
index 71eb5744..286b9b4e 100644
--- a/core/head.inc
+++ b/core/head.inc
@@ -34,5 +34,6 @@
%include "tracers.inc"
%include "stack.inc"
%include "io.inc"
+%include "vkernel.inc"
%endif ; _HEAD_INC
diff --git a/core/include/core.h b/core/include/core.h
index cfb82133..4420fec1 100644
--- a/core/include/core.h
+++ b/core/include/core.h
@@ -4,6 +4,7 @@
#include <klibc/compiler.h>
#include <com32.h>
#include <syslinux/pmapi.h>
+#include <syslinux/sysappend.h>
#include <kaboom.h>
#include <timer.h>
@@ -43,6 +44,11 @@ extern void *zalloc(size_t);
extern void free(void *);
extern void mem_init(void);
+/* sysappend.c */
+extern void print_sysappend(void);
+extern const char *sysappend_strings[SYSAPPEND_MAX];
+extern uint32_t SysAppends;
+
void __cdecl core_intcall(uint8_t, const com32sys_t *, com32sys_t *);
void __cdecl core_farcall(uint32_t, const com32sys_t *, com32sys_t *);
int __cdecl core_cfarcall(uint32_t, const void *, uint32_t);
diff --git a/core/isolinux.asm b/core/isolinux.asm
index 7a871f0e..3470c208 100644
--- a/core/isolinux.asm
+++ b/core/isolinux.asm
@@ -35,23 +35,6 @@ SECTOR_SIZE equ (1 << SECTOR_SHIFT)
ROOT_DIR_WORD equ 0x002F
-;
-; The following structure is used for "virtual kernels"; i.e. LILO-style
-; option labels. The options we permit here are `kernel' and `append
-; Since there is no room in the bottom 64K for all of these, we
-; stick them in high memory and copy them down before we need them.
-;
- struc vkernel
-vk_vname: resb FILENAME_MAX ; Virtual name **MUST BE FIRST!**
-vk_rname: resb FILENAME_MAX ; Real name
-vk_appendlen: resw 1
-vk_type: resb 1 ; Type of file
- alignb 4
-vk_append: resb max_cmd_len+1 ; Command line
- alignb 4
-vk_end: equ $ ; Should be <= vk_size
- endstruc
-
; ---------------------------------------------------------------------------
; BEGIN CODE
; ---------------------------------------------------------------------------
diff --git a/core/keywords b/core/keywords
index 7f585b48..80972ad2 100644
--- a/core/keywords
+++ b/core/keywords
@@ -34,6 +34,7 @@ onerror
noescape
nocomplete
nohalt
+sysappend
f0
f1
f2
diff --git a/core/keywords.inc b/core/keywords.inc
index 08d77c64..64417406 100644
--- a/core/keywords.inc
+++ b/core/keywords.inc
@@ -92,9 +92,8 @@ keywd_table:
keyword f0, pc_filename, FKeyN(10)
keyword f11, pc_filename, FKeyN(11)
keyword f12, pc_filename, FKeyN(12)
-%if IS_PXELINUX
- keyword ipappend, pc_ipappend
-%endif
+ keyword ipappend, pc_sysappend
+ keyword sysappend, pc_sysappend
keyword localboot, pc_localboot
keywd_count equ ($-keywd_table)/keywd_size
diff --git a/core/parseconfig.inc b/core/parseconfig.inc
index 512f16b4..51a6d8de 100644
--- a/core/parseconfig.inc
+++ b/core/parseconfig.inc
@@ -69,18 +69,16 @@ pc_append: cmp byte [VKernel],0
ret
;
-; "ipappend" command (PXELINUX only)
+; "sysappend" command
;
-%if IS_PXELINUX
-pc_ipappend: call getint
+pc_sysappend: call getint
jc .err
cmp byte [VKernel],0
jne .vk
- mov [IPAppend],bl
+ mov [SysAppends],ebx
.err: ret
-.vk: mov [VKernelBuf+vk_ipappend],bl
+.vk: mov [VKernelBuf+vk_sysappend],ebx
ret
-%endif
;
; "localboot" command
@@ -131,11 +129,19 @@ pc_totaltimeout:
pc_setint16:
push ax
call getint
- pop si
+ pop di
jc .err
mov [si],bx
.err: ret
+pc_setint32:
+ push ax
+ call getint
+ pop di
+ jc .err
+ mov [si],ebx
+.err: ret
+
;
; Generic file-processing commands:
; "font", "kbdmap",
@@ -311,15 +317,13 @@ pc_label: call commit_vk ; Commit any current vkernel
mov si,VKernelBuf+vk_vname ; By default, rname == mangled vname
mov di,VKernelBuf+vk_rname
pm_call pm_mangle_name
- mov si,AppendBuf ; Default append==global append
+ mov si,AppendBuf ; append <- global append
mov di,VKernelBuf+vk_append
mov cx,[AppendLen]
mov [VKernelBuf+vk_appendlen],cx
rep movsb
-%if IS_PXELINUX ; PXELINUX only
- mov al,[IPAppend] ; Default ipappend==global ipappend
- mov [VKernelBuf+vk_ipappend],al
-%endif
+ mov eax,[SysAppends] ; sysappend <- global sysappend
+ mov [VKernelBuf+vk_sysappend],eax
ret
;
@@ -435,6 +439,14 @@ commit_vk:
vk_overflow_msg db 'Out of memory parsing config file', CR, LF, 0
SerialNotice db 1 ; Only print this once
+%if IS_PXELINUX
+; This is a global option and is not reset when a config file is loaded
+; Is this the right thing to do?
+ alignz 4
+ global SendCookies
+SendCookies dd -1 ; Send all cookies
+%endif
+
section .bss16
alignb 4
VKernelEnd resd 1 ; Lowest high memory address used
@@ -444,9 +456,11 @@ VKernelEnd resd 1 ; Lowest high memory address used
HighMemRsvd equ VKernelEnd
; by vkernels
section .config
+ global SysAppends
alignz 4
KbdTimeout dd 0 ; Keyboard timeout (if any)
TotalTimeout dd 0 ; Total timeout (if any)
+SysAppends dd 0 ; Default SYSAPPEND option
AppendLen dw 0 ; Bytes in append= command
OntimeoutLen dw 0 ; Bytes in ontimeout command
OnerrorLen dw 0 ; Bytes in onerror command
@@ -462,10 +476,6 @@ DefaultLevel dw 0 ; The current level of default
PXERetry dw 0 ; Extra PXE retries
VKernel db 0 ; Have we seen any "label" statements?
-%if IS_PXELINUX
-IPAppend db 0 ; Default IPAPPEND option
-%endif
-
section .uibss
alignb 4 ; For the good of REP MOVSD
command_line resb max_cmd_len+2 ; Command line buffer
diff --git a/core/pmapi.c b/core/pmapi.c
index 4b1ccbb1..60d5ba43 100644
--- a/core/pmapi.c
+++ b/core/pmapi.c
@@ -40,4 +40,7 @@ const struct com32_pmapi pm_api_vector =
.jiffies = &__jiffies,
.ms_timer = &__ms_timer,
+
+ .sysappend_count = SYSAPPEND_MAX,
+ .sysappend_strings = sysappend_strings,
};
diff --git a/core/pxelinux.asm b/core/pxelinux.asm
index be304be2..d39234d1 100644
--- a/core/pxelinux.asm
+++ b/core/pxelinux.asm
@@ -39,25 +39,6 @@ TFTP_BLOCKSIZE equ (1 << TFTP_BLOCKSIZE_LG2)
SECTOR_SHIFT equ TFTP_BLOCKSIZE_LG2
SECTOR_SIZE equ TFTP_BLOCKSIZE
-;
-; The following structure is used for "virtual kernels"; i.e. LILO-style
-; option labels. The options we permit here are `kernel' and `append
-; Since there is no room in the bottom 64K for all of these, we
-; stick them in high memory and copy them down before we need them.
-;
- struc vkernel
-vk_vname: resb FILENAME_MAX ; Virtual name **MUST BE FIRST!**
-vk_rname: resb FILENAME_MAX ; Real name
-vk_ipappend: resb 1 ; "IPAPPEND" flag
-vk_type: resb 1 ; Type of file
-vk_appendlen: resw 1
- alignb 4
-vk_append: resb max_cmd_len+1 ; Command line
- alignb 4
-vk_end: equ $ ; Should be <= vk_size
- endstruc
-
-
; ---------------------------------------------------------------------------
; BEGIN CODE
; ---------------------------------------------------------------------------
diff --git a/core/runkernel.inc b/core/runkernel.inc
index 2e943465..3fa4dfa7 100644
--- a/core/runkernel.inc
+++ b/core/runkernel.inc
@@ -81,7 +81,7 @@ construct_cmdline:
call strcpy
mov byte [es:di-1],' ' ; Follow by space
- call do_ip_append ; Handle IPAppend
+ pm_call do_sysappend ; Handle sysappend
mov si,[CmdOptPtr] ; Options from user input
call strcpy
diff --git a/core/sysappend.c b/core/sysappend.c
new file mode 100644
index 00000000..ac35b226
--- /dev/null
+++ b/core/sysappend.c
@@ -0,0 +1,61 @@
+/* ----------------------------------------------------------------------- *
+ *
+ * Copyright 2011 Intel Corporation; author: H. Peter Anvin
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
+ * Boston MA 02110-1301, USA; either version 2 of the License, or
+ * (at your option) any later version; incorporated herein by reference.
+ *
+ * ----------------------------------------------------------------------- */
+
+#include <string.h>
+#include <stdio.h>
+#include "core.h"
+
+/*
+ * sysappend.c
+ *
+ */
+
+extern uint32_t SysAppends; /* Configuration variable */
+const char *sysappend_strings[SYSAPPEND_MAX];
+
+/*
+ * Handle sysappend strings for the old real-mode command line generator...
+ * this code should be replaced when all that code is coverted to C.
+ *
+ * Writes the output to ES:DI with a space after each option,
+ * and updates DI to point to the final null.
+ */
+void do_sysappend(com32sys_t *regs)
+{
+ char *q = MK_PTR(regs->es, regs->ebx.w[0]);
+ int i;
+ uint32_t mask = SysAppends;
+
+ for (i = 0; i < SYSAPPEND_MAX; i++) {
+ if (mask & 1) {
+ q = stpcpy(q, sysappend_strings[i]);
+ *q++ = ' ';
+ }
+ mask >>= 1;
+ }
+ *q = '\0';
+
+ regs->ebx.w[0] = OFFS_WRT(q, regs->es);
+}
+
+/*
+ * Print the sysappend strings, in order
+ */
+void print_sysappend(void)
+{
+ int i;
+
+ for (i = 0; i < SYSAPPEND_MAX; i++) {
+ if (sysappend_strings[i])
+ printf("%s\n", sysappend_strings[i]);
+ }
+}
diff --git a/core/ui.inc b/core/ui.inc
index f1e046ed..6ef24984 100644
--- a/core/ui.inc
+++ b/core/ui.inc
@@ -115,10 +115,8 @@ not_ascii:
je display_labels
cmp al,'F' & 1Fh ; <Ctrl-F>
je set_func_flag
-%if IS_PXELINUX
cmp al,'N' & 1Fh ; <Ctrl-N>
- je show_network_info
-%endif
+ je show_system_info
cmp al,'U' & 1Fh ; <Ctrl-U>
je kill_command ; Kill input line
cmp al,'V' & 1Fh ; <Ctrl-V>
@@ -269,24 +267,12 @@ fk_nofile: pop di
jmp get_char
;
-; Show network info (in the form of the ipappend strings)
+; Show system info (in the form of the sysappend strings)
;
-%if IS_PXELINUX
-show_network_info:
- push di ; Command line write pointer
+show_system_info:
call crlf
- mov si,IPAppends ; See comboot.doc
- mov cx,numIPAppends
-.loop:
- lodsw
- push si
- mov si,ax
- call writestr
- call crlf
- pop si
- loop .loop
+ pm_call print_sysappend
jmp fk_wrcmd
-%endif
;
; Jump here to run the default command line
@@ -406,10 +392,8 @@ vk_check:
mov cx,FILENAME_MAX ; We need ECX == CX later
rep movsb
pop di
-%if IS_PXELINUX
- mov al,[VKernelBuf+vk_ipappend]
- mov [IPAppend],al
-%endif
+ mov eax,[VKernelBuf+vk_sysappend]
+ mov [SysAppends],eax
xor bx,bx ; Try only one version
mov al,[VKernelBuf+vk_type]
@@ -643,10 +627,6 @@ is_unknown_filetype:
je is_comboot_image
cmp ecx,'.c32'
je is_com32_image
-%if IS_ISOLINUX
- cmp ecx,'.img'
- je is_disk_image
-%endif
cmp ecx,'.bss'
je is_bss_sector
cmp ecx,'.bin'
diff --git a/core/vkernel.inc b/core/vkernel.inc
new file mode 100644
index 00000000..278344e4
--- /dev/null
+++ b/core/vkernel.inc
@@ -0,0 +1,35 @@
+;; -----------------------------------------------------------------------
+;;
+;; Copyright 1994-2008 H. Peter Anvin - All Rights Reserved
+;; Copyright 2009-2011 Intel Corporation; author: H. Peter Anvin
+;;
+;; This program is free software; you can redistribute it and/or modify
+;; it under the terms of the GNU General Public License as published by
+;; the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
+;; Boston MA 02110-1301, USA; either version 2 of the License, or
+;; (at your option) any later version; incorporated herein by reference.
+;;
+;; -----------------------------------------------------------------------
+
+%ifndef _VKERNEL_INC
+%define _VKERNEL_INC
+
+;
+; The following structure is used for "virtual kernels"; i.e. LILO-style
+; option labels. The options we permit here are `kernel' and `append
+; Since there is no room in the bottom 64K for all of these, we
+; stick them in high memory and copy them down before we need them.
+;
+ struc vkernel
+vk_vname: resb FILENAME_MAX ; Virtual name **MUST BE FIRST!**
+vk_rname: resb FILENAME_MAX ; Real name
+vk_sysappend: resd 1 ; Sysappend option
+vk_appendlen: resw 1
+vk_type: resb 1 ; Type of file
+ alignb 4
+vk_append: resb max_cmd_len+1 ; Command line
+ alignb 4
+vk_end: equ $ ; Should be <= vk_size
+ endstruc
+
+%endif ; _VKERNEL_INC