1dd1aab02SCyrill Gorcunov/* 2dd1aab02SCyrill Gorcunov * Our pretty trivial BIOS emulation 3dd1aab02SCyrill Gorcunov */ 4dd1aab02SCyrill Gorcunov 5dd1aab02SCyrill Gorcunov#include <kvm/bios.h> 628ce0d66SCyrill Gorcunov#include <kvm/assembly.h> 728ce0d66SCyrill Gorcunov 828ce0d66SCyrill Gorcunov .org 0 9dd1aab02SCyrill Gorcunov .code16gcc 1028ce0d66SCyrill Gorcunov 115682ea77SPekka Enberg#define EFLAGS_CF (1 << 0) 125682ea77SPekka Enberg 13dd1aab02SCyrill Gorcunov#include "macro.S" 14dd1aab02SCyrill Gorcunov 155682ea77SPekka Enberg/* If you change these macros, remember to update 'struct biosregs' */ 165682ea77SPekka Enberg.macro SAVE_BIOSREGS 17193d2030SPekka Enberg pushl %fs 185682ea77SPekka Enberg pushl %es 19b4eab05eSPekka Enberg pushl %ds 205682ea77SPekka Enberg pushl %edi 215682ea77SPekka Enberg pushl %esi 225682ea77SPekka Enberg pushl %ebp 235682ea77SPekka Enberg pushl %esp 245682ea77SPekka Enberg pushl %edx 255682ea77SPekka Enberg pushl %ecx 265682ea77SPekka Enberg pushl %ebx 275682ea77SPekka Enberg pushl %eax 285682ea77SPekka Enberg.endm 295682ea77SPekka Enberg 305682ea77SPekka Enberg.macro RESTORE_BIOSREGS 315682ea77SPekka Enberg popl %eax 325682ea77SPekka Enberg popl %ebx 335682ea77SPekka Enberg popl %ecx 345682ea77SPekka Enberg popl %edx 355682ea77SPekka Enberg popl %esp 365682ea77SPekka Enberg popl %ebp 375682ea77SPekka Enberg popl %esi 385682ea77SPekka Enberg popl %edi 39b4eab05eSPekka Enberg popl %ds 405682ea77SPekka Enberg popl %es 41193d2030SPekka Enberg popl %fs 425682ea77SPekka Enberg.endm 4324a93433SPekka Enberg 44dd1aab02SCyrill Gorcunov/* 45dd1aab02SCyrill Gorcunov * fake interrupt handler, nothing can be faster ever 46dd1aab02SCyrill Gorcunov */ 47dd1aab02SCyrill GorcunovENTRY(bios_intfake) 4824a93433SPekka Enberg /* 4924a93433SPekka Enberg * Set CF to indicate failure. We don't want callers to think that the 5024a93433SPekka Enberg * interrupt handler succeeded and then treat the return values in 5124a93433SPekka Enberg * registers as valid data. 5224a93433SPekka Enberg */ 5324a93433SPekka Enberg orl $EFLAGS_CF, 0x4(%esp) 5424a93433SPekka Enberg 55dd1aab02SCyrill Gorcunov IRET 56dd1aab02SCyrill GorcunovENTRY_END(bios_intfake) 57dd1aab02SCyrill Gorcunov 58dd1aab02SCyrill Gorcunov/* 59dd1aab02SCyrill Gorcunov * int 10 - video - service 60dd1aab02SCyrill Gorcunov */ 61dd1aab02SCyrill GorcunovENTRY(bios_int10) 625682ea77SPekka Enberg SAVE_BIOSREGS 63dd1aab02SCyrill Gorcunov 64dd1aab02SCyrill Gorcunov movl %esp, %eax 65dd1aab02SCyrill Gorcunov /* this is way easier than doing it in assembly */ 66dd1aab02SCyrill Gorcunov /* just push all the regs and jump to a C handler */ 67dd1aab02SCyrill Gorcunov call int10_handler 68dd1aab02SCyrill Gorcunov 695682ea77SPekka Enberg RESTORE_BIOSREGS 70dd1aab02SCyrill Gorcunov 7124a93433SPekka Enberg /* Clear CF to indicate success. */ 7224a93433SPekka Enberg andl $~EFLAGS_CF, 0x4(%esp) 7324a93433SPekka Enberg 74dd1aab02SCyrill Gorcunov IRET 75dd1aab02SCyrill GorcunovENTRY_END(bios_int10) 76dd1aab02SCyrill Gorcunov 77dd1aab02SCyrill GorcunovENTRY(bios_int15) 788f8e0548SPekka Enberg SAVE_BIOSREGS 79dd1aab02SCyrill Gorcunov 80677a2bf1SPekka Enberg movl %esp, %eax 81677a2bf1SPekka Enberg call int15_handler 82dd1aab02SCyrill Gorcunov 838f8e0548SPekka Enberg RESTORE_BIOSREGS 84677a2bf1SPekka Enberg 85dd1aab02SCyrill Gorcunov IRET 86dd1aab02SCyrill GorcunovENTRY_END(bios_int15) 87dd1aab02SCyrill Gorcunov 88dd1aab02SCyrill GorcunovGLOBAL(__locals) 89dd1aab02SCyrill Gorcunov 90dd1aab02SCyrill Gorcunov#include "local.S" 91dd1aab02SCyrill Gorcunov 92dd1aab02SCyrill GorcunovEND(__locals) 93*a68a52cdSMartin Radev 94*a68a52cdSMartin Radev/* 95*a68a52cdSMartin Radev * Add this section to ensure final binary has a non-executable stack. 96*a68a52cdSMartin Radev */ 97*a68a52cdSMartin Radev.section .note.GNU-stack,"",@progbits 98