[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] Re: [PATCH][SEABIOS] Move qemu config port access functions
From: |
Gleb Natapov |
Subject: |
[Qemu-devel] Re: [PATCH][SEABIOS] Move qemu config port access functions into separate file. |
Date: |
Thu, 1 Oct 2009 18:35:55 +0200 |
> As an aside, it would be good to have a conversation on general BIOS
> configuration options. These types of settings are going to be useful
> on real hardware also - it would be nice to come up with a scheme that
> would work on qemu and coreboot. Maybe something like
> get_config_u32("ShowBootMenu") - where on qemu it would get the info
> from the qemu port but on coreboot it would pull the setting from the
> coreboot flash filesystem.
>
I started to implement this approach, but found a serious disadvantage:
What if config option is not known to qemu or coreboot? What is it
present only in qemu and meaningful default behaviour is required
for coreboot? Like ShowBootMenu for instance. We want to return qemu
setting or coreboot setting or 1 if neither is present. This kind
of logic does not belong to general function like get_config_u32().
So how about another approach: qemu and core boot provide functions like
void cfg_get_uuid(u8 *uuid);
int cfg_show_boot_menu(void);
...
with all necessary fall-back logic and we use coreboot or qemu file during
build time depending what our target is. Something like attached patch.
diff --git a/Makefile b/Makefile
index c4016e8..8d5c913 100644
--- a/Makefile
+++ b/Makefile
@@ -10,11 +10,20 @@ VERSION=pre-0.4.3-$(shell date +"%Y%m%d_%H%M%S")-$(shell
hostname)
# Output directory
OUT=out/
+# Configure as a coreboot payload.
+COREBOOT=y
+
+ifdef COREBOOT
+CFGSRC=cbcfg.c
+else
+CFGSRC=pv.c
+endif
+
# Source files
SRCBOTH=output.c util.c block.c floppy.c ata.c misc.c mouse.c kbd.c pci.c \
serial.c clock.c pic.c cdrom.c ps2port.c smp.c resume.c \
pnpbios.c pirtable.c vgahooks.c pmm.c ramdisk.c \
- usb.c usb-uhci.c usb-hid.c
+ usb.c usb-uhci.c usb-hid.c $(CFGSRC)
SRC16=$(SRCBOTH) system.c disk.c apm.c pcibios.c font.c
SRC32=$(SRCBOTH) post.c shadow.c memmap.c coreboot.c boot.c \
acpi.c smm.c mptable.c smbios.c pciinit.c optionroms.c mtrr.c \
diff --git a/src/boot.c b/src/boot.c
index 7b74007..71d6e27 100644
--- a/src/boot.c
+++ b/src/boot.c
@@ -12,6 +12,7 @@
#include "bregs.h" // struct bregs
#include "boot.h" // struct ipl_s
#include "cmos.h" // inb_cmos
+#include "cfg.h"
struct ipl_s IPL;
@@ -206,7 +207,7 @@ menu_show_cbfs(struct ipl_entry_s *ie, int menupos)
static void
interactive_bootmenu()
{
- if (! CONFIG_BOOTMENU)
+ if (! CONFIG_BOOTMENU || ! cfg_show_boot_menu())
return;
while (get_keystroke(0) >= 0)
diff --git a/src/cbcfg.c b/src/cbcfg.c
new file mode 100644
index 0000000..56b6076
--- /dev/null
+++ b/src/cbcfg.c
@@ -0,0 +1,13 @@
+#include "config.h"
+#include "util.h"
+#include "cfg.h"
+
+void cfg_get_uuid(u8 *uuid)
+{
+ memset(uuid, 0, 16);
+}
+
+int cfg_show_boot_menu(void)
+{
+ return 1;
+}
diff --git a/src/cfg.h b/src/cfg.h
new file mode 100644
index 0000000..1f6b488
--- /dev/null
+++ b/src/cfg.h
@@ -0,0 +1,6 @@
+#ifndef __CFG_H
+#define __CFG_H
+
+void cfg_get_uuid(u8 *uuid);
+int cfg_show_boot_menu(void);
+#endif
diff --git a/src/post.c b/src/post.c
index f72e134..e8ae3f0 100644
--- a/src/post.c
+++ b/src/post.c
@@ -20,6 +20,7 @@
#include "mptable.h" // mptable_init
#include "boot.h" // IPL
#include "usb.h" // usb_setup
+#include "pv.h"
void
__set_irq(int vector, void *loc)
@@ -184,6 +185,8 @@ post()
serial_setup();
mouse_setup();
+ qemu_cfg_port_probe();
+
init_bios_tables();
boot_setup();
diff --git a/src/pv.c b/src/pv.c
new file mode 100644
index 0000000..fa57b5b
--- /dev/null
+++ b/src/pv.c
@@ -0,0 +1,67 @@
+#include "config.h"
+#include "ioport.h"
+#include "pv.h"
+
+int qemu_cfg_present;
+
+static void
+qemu_cfg_select(u16 f)
+{
+ outw(f, PORT_QEMU_CFG_CTL);
+}
+
+static void
+qemu_cfg_read(u8 *buf, int len)
+{
+ while (len--)
+ *(buf++) = inb(PORT_QEMU_CFG_DATA);
+}
+
+static void
+qemu_cfg_read_entry(void *buf, int e, int len)
+{
+ qemu_cfg_select(e);
+ qemu_cfg_read(buf, len);
+}
+
+void qemu_cfg_port_probe(void)
+{
+ char *sig = "QEMU";
+ int i;
+
+ if (CONFIG_COREBOOT)
+ return;
+
+ qemu_cfg_present = 1;
+
+ qemu_cfg_select(QEMU_CFG_SIGNATURE);
+
+ for (i = 0; i < 4; i++)
+ if (inb(PORT_QEMU_CFG_DATA) != sig[i]) {
+ qemu_cfg_present = 0;
+ break;
+ }
+ dprintf(4, "qemu_cfg_present=%d\n", qemu_cfg_present);
+}
+
+void cfg_get_uuid(u8 *uuid)
+{
+ memset(uuid, 0, 16);
+
+ if (!qemu_cfg_present || !CONFIG_UUID_BACKDOOR)
+ return;
+
+ qemu_cfg_read_entry(uuid, QEMU_CFG_UUID, 16);
+}
+
+int cfg_show_boot_menu(void)
+{
+ u16 v;
+ if (!qemu_cfg_present)
+ return 1;
+
+ qemu_cfg_read_entry(&v, QEMU_CFG_BOOT_MENU, sizeof(v));
+
+ return v;
+}
+
diff --git a/src/pv.h b/src/pv.h
new file mode 100644
index 0000000..632a29c
--- /dev/null
+++ b/src/pv.h
@@ -0,0 +1,42 @@
+#ifndef __PV_H
+#define __PV_H
+
+#include "util.h"
+
+/* This CPUID returns the signature 'KVMKVMKVM' in ebx, ecx, and edx. It
+ * should be used to determine that a VM is running under KVM.
+ */
+#define KVM_CPUID_SIGNATURE 0x40000000
+
+static inline int kvm_para_available(void)
+{
+ unsigned int eax, ebx, ecx, edx;
+ char signature[13];
+
+ cpuid(KVM_CPUID_SIGNATURE, &eax, &ebx, &ecx, &edx);
+ memcpy(signature + 0, &ebx, 4);
+ memcpy(signature + 4, &ecx, 4);
+ memcpy(signature + 8, &edx, 4);
+ signature[12] = 0;
+
+ if (strcmp(signature, "KVMKVMKVM") == 0)
+ return 1;
+
+ return 0;
+}
+
+#define QEMU_CFG_SIGNATURE 0x00
+#define QEMU_CFG_ID 0x01
+#define QEMU_CFG_UUID 0x02
+#define QEMU_CFG_NUMA 0x0d
+#define QEMU_CFG_BOOT_MENU 0x0e
+#define QEMU_CFG_MAX_CPUS 0x0f
+#define QEMU_CFG_ARCH_LOCAL 0x8000
+#define QEMU_CFG_ACPI_TABLES (QEMU_CFG_ARCH_LOCAL + 0)
+#define QEMU_CFG_SMBIOS_ENTRIES (QEMU_CFG_ARCH_LOCAL + 1)
+
+extern int qemu_cfg_present;
+
+void qemu_cfg_port_probe(void);
+
+#endif
diff --git a/src/smbios.c b/src/smbios.c
index 6fbddd9..4caab19 100644
--- a/src/smbios.c
+++ b/src/smbios.c
@@ -7,50 +7,7 @@
#include "util.h" // dprintf
#include "biosvar.h" // GET_EBDA
-
-
-/****************************************************************
- * UUID probe
- ****************************************************************/
-
-#define QEMU_CFG_SIGNATURE 0x00
-#define QEMU_CFG_ID 0x01
-#define QEMU_CFG_UUID 0x02
-
-static void
-qemu_cfg_read(u8 *buf, u16 f, int len)
-{
- outw(f, PORT_QEMU_CFG_CTL);
- while (len--)
- *(buf++) = inb(PORT_QEMU_CFG_DATA);
-}
-
-static int
-qemu_cfg_port_probe()
-{
- u8 sig[4] = "QEMU";
- u8 buf[4];
- qemu_cfg_read(buf, QEMU_CFG_SIGNATURE, 4);
- return *(u32*)buf == *(u32*)sig;
-}
-
-static void
-uuid_probe(u8 *bios_uuid)
-{
- // Default to UUID not set
- memset(bios_uuid, 0, 16);
-
- if (! CONFIG_UUID_BACKDOOR)
- return;
- if (CONFIG_COREBOOT)
- return;
- if (! qemu_cfg_port_probe())
- // Feature not available
- return;
-
- qemu_cfg_read(bios_uuid, QEMU_CFG_UUID, 16);
-}
-
+#include "cfg.h"
/****************************************************************
* smbios tables
@@ -304,7 +261,7 @@ smbios_type_1_init(void *start)
p->version_str = 0;
p->serial_number_str = 0;
- uuid_probe(p->uuid);
+ cfg_get_uuid(p->uuid);
p->wake_up_type = 0x06; /* power switch */
p->sku_number_str = 0;
--
Gleb.
- [Qemu-devel] Re: [PATCH][SEABIOS] Move qemu config port access functions into separate file.,
Gleb Natapov <=