[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] [xen-3.1-testing] x86: Fix management support on HP ProLiant systems.
# HG changeset patch # User Keir Fraser <keir.fraser@xxxxxxxxxx> # Date 1197133676 0 # Node ID 0069a86da1040fd6ebba5734f28f8dee56cc5eaf # Parent 4e16701e94b1516d451b688ffd78202bc002ed15 x86: Fix management support on HP ProLiant systems. Adds support to allow host-platform-specific handling of I/O port traps. Specifically adds support to handle an HP ProLiant I/O port in a special way. Signed-off-by: Mike Garrett <michael.garrett@xxxxxx> Signed-off-by: Keir Fraser <keir.fraser@xxxxxxxxxx> xen-unstable changeset: 16542:1936e6a79f85 xen-unstable date: Thu Dec 06 11:23:04 2007 +0000 x86: Change proliant io emulation stub to use pushf/popf instead of pushfw/popfw. Signed-off-by: Keir Fraser <keir.fraser@xxxxxxxxxx> xen-unstable changeset: 16562:35890b260971 xen-unstable date: Fri Dec 07 17:05:15 2007 +0000 --- xen/arch/x86/Makefile | 1 xen/arch/x86/ioport_emulate.c | 123 ++++++++++++++++++++++++++++++++++++++++++ xen/arch/x86/traps.c | 7 ++ 3 files changed, 130 insertions(+), 1 deletion(-) diff -r 4e16701e94b1 -r 0069a86da104 xen/arch/x86/Makefile --- a/xen/arch/x86/Makefile Fri Dec 07 12:45:57 2007 +0000 +++ b/xen/arch/x86/Makefile Sat Dec 08 17:07:56 2007 +0000 @@ -24,6 +24,7 @@ obj-y += i387.o obj-y += i387.o obj-y += i8259.o obj-y += io_apic.o +obj-y += ioport_emulate.o obj-y += irq.o obj-y += microcode.o obj-y += mm.o diff -r 4e16701e94b1 -r 0069a86da104 xen/arch/x86/ioport_emulate.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/xen/arch/x86/ioport_emulate.c Sat Dec 08 17:07:56 2007 +0000 @@ -0,0 +1,123 @@ +/****************************************************************************** + * ioport_emulate.c + * + * Handle I/O port access quirks of various platforms. + */ + +#include <xen/config.h> +#include <xen/init.h> +#include <xen/sched.h> +#include <xen/dmi.h> + +/* Function pointer used to handle platform specific I/O port emulation. */ +extern void (*ioemul_handle_quirk)( + u8 opcode, char *io_emul_stub, struct cpu_user_regs *regs); + +static void ioemul_handle_proliant_quirk( + u8 opcode, char *io_emul_stub, struct cpu_user_regs *regs) +{ + uint16_t port = regs->edx; + uint8_t value = regs->eax; + + if ( (opcode != 0xee) || (port != 0xcd4) || !(value & 0x80) ) + return; + + /* pushf */ + io_emul_stub[0] = 0x9c; + /* cli */ + io_emul_stub[1] = 0xfa; + /* out %al,%dx */ + io_emul_stub[2] = 0xee; + /* 1: in %dx,%al */ + io_emul_stub[3] = 0xec; + /* test $0x80,%al */ + io_emul_stub[4] = 0xa8; + io_emul_stub[5] = 0x80; + /* jnz 1b */ + io_emul_stub[6] = 0x75; + io_emul_stub[7] = 0xfb; + /* popf */ + io_emul_stub[8] = 0x9d; + /* ret */ + io_emul_stub[9] = 0xc3; +} + +int __init proliant_quirk(struct dmi_system_id *d) +{ + ioemul_handle_quirk = ioemul_handle_proliant_quirk; + return 0; +} + +/* This table is the set of system-specific I/O emulation hooks. */ +static struct dmi_system_id __initdata ioport_quirks_tbl[] = { + /* + * I/O emulation hook for certain HP ProLiant servers with + * 'special' SMM goodness. + */ + { + .callback = proliant_quirk, + .ident = "HP ProLiant DL3xx", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR, "HP"), + DMI_MATCH(DMI_PRODUCT_NAME, "ProLiant DL3"), + }, + }, + { + .callback = proliant_quirk, + .ident = "HP ProLiant DL5xx", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR, "HP"), + DMI_MATCH(DMI_PRODUCT_NAME, "ProLiant DL5"), + }, + }, + { + .callback = proliant_quirk, + .ident = "HP ProLiant ML3xx", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR, "HP"), + DMI_MATCH(DMI_PRODUCT_NAME, "ProLiant ML3"), + }, + }, + { + .callback = proliant_quirk, + .ident = "HP ProLiant ML5xx", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR, "HP"), + DMI_MATCH(DMI_PRODUCT_NAME, "ProLiant ML5"), + }, + }, + { + .callback = proliant_quirk, + .ident = "HP ProLiant BL4xx", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR, "HP"), + DMI_MATCH(DMI_PRODUCT_NAME, "ProLiant BL4"), + }, + }, + { + .callback = proliant_quirk, + .ident = "HP ProLiant BL6xx", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR, "HP"), + DMI_MATCH(DMI_PRODUCT_NAME, "ProLiant BL6"), + }, + }, + { } +}; + +int __init ioport_quirks_init(void) +{ + dmi_check_system(ioport_quirks_tbl); + return 0; +} +__initcall(ioport_quirks_init); + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff -r 4e16701e94b1 -r 0069a86da104 xen/arch/x86/traps.c --- a/xen/arch/x86/traps.c Fri Dec 07 12:45:57 2007 +0000 +++ b/xen/arch/x86/traps.c Sat Dec 08 17:07:56 2007 +0000 @@ -107,6 +107,8 @@ DECLARE_TRAP_HANDLER(spurious_interrupt_ long do_set_debugreg(int reg, unsigned long value); unsigned long do_get_debugreg(int reg); +void (*ioemul_handle_quirk)( + u8 opcode, char *io_emul_stub, struct cpu_user_regs *regs); static int debug_stack_lines = 20; integer_param("debug_stack_lines", debug_stack_lines); @@ -1217,7 +1219,7 @@ static int emulate_privileged_op(struct ? (*(u32 *)®s->reg = (val)) \ : (*(u16 *)®s->reg = (val))) unsigned long code_base, code_limit; - char io_emul_stub[16]; + char io_emul_stub[32]; void (*io_emul)(struct cpu_user_regs *) __attribute__((__regparm__(1))); u32 l, h, eax, edx; @@ -1468,6 +1470,9 @@ static int emulate_privileged_op(struct /* Handy function-typed pointer to the stub. */ io_emul = (void *)io_emul_stub; + if ( ioemul_handle_quirk ) + ioemul_handle_quirk(opcode, &io_emul_stub[12], regs); + /* I/O Port and Interrupt Flag instructions. */ switch ( opcode ) { _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |