mirror of
https://github.com/clearlinux/kvmtool.git
synced 2026-08-28 09:55:57 +00:00
kvm: Hardcode a "reset vector" at f000:fff0
It seems that if we attempt to run code at any other location than f000:fff0, we get an KVM_EXIT_UNKNOWN error. To work around that, hardcode a "reset vector" at f000:fff0 that jumps to 0000:0x7c000 and load the kernel at the latter location. Signed-off-by: Pekka Enberg <penberg@cs.helsinki.fi>
This commit is contained in:
committed by
Will Deacon
parent
e93ab78a73
commit
2a601aafee
@@ -153,8 +153,13 @@ static inline uint32_t segment_to_flat(uint16_t selector, uint16_t offset)
|
||||
return ((uint32_t)selector << 4) + (uint32_t) offset;
|
||||
}
|
||||
|
||||
#define BIN_BOOT_LOADER_CS 0xf000
|
||||
#define BIN_BOOT_LOADER_IP 0xfff0
|
||||
#define RESET_CS 0xf000
|
||||
#define RESET_IP 0xfff0
|
||||
|
||||
#define BIN_BOOT_LOADER_CS 0x0000
|
||||
#define BIN_BOOT_LOADER_IP 0x7c00
|
||||
|
||||
static unsigned char reset_code[] = { 0xea, 0x00, 0x7c, 0x00, 0x00 };
|
||||
|
||||
static int load_flat_binary(struct kvm *kvm, int fd)
|
||||
{
|
||||
@@ -169,8 +174,12 @@ static int load_flat_binary(struct kvm *kvm, int fd)
|
||||
while ((nr = read(fd, p, 65536)) > 0)
|
||||
p += nr;
|
||||
|
||||
kvm->boot_cs = BIN_BOOT_LOADER_CS;
|
||||
kvm->boot_ip = BIN_BOOT_LOADER_IP;
|
||||
p = guest_addr_to_host(kvm, segment_to_flat(RESET_CS, RESET_IP));
|
||||
|
||||
memcpy(p, reset_code, ARRAY_SIZE(reset_code));
|
||||
|
||||
kvm->boot_cs = RESET_CS;
|
||||
kvm->boot_ip = RESET_IP;
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -230,8 +239,12 @@ static bool load_bzimage(struct kvm *kvm, int fd)
|
||||
while ((nr = read(fd, p, 65536)) > 0)
|
||||
p += nr;
|
||||
|
||||
kvm->boot_cs = 0;
|
||||
kvm->boot_ip = BZ_BOOT_LOADER_START;
|
||||
p = guest_addr_to_host(kvm, segment_to_flat(RESET_CS, RESET_IP));
|
||||
|
||||
memcpy(p, reset_code, ARRAY_SIZE(reset_code));
|
||||
|
||||
kvm->boot_cs = RESET_CS;
|
||||
kvm->boot_ip = RESET_IP;
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -457,6 +470,12 @@ void kvm__show_code(struct kvm *self)
|
||||
unsigned int i;
|
||||
uint8_t *ip;
|
||||
|
||||
if (ioctl(self->vcpu_fd, KVM_GET_REGS, &self->regs) < 0)
|
||||
die("KVM_GET_REGS failed");
|
||||
|
||||
if (ioctl(self->vcpu_fd, KVM_GET_SREGS, &self->sregs) < 0)
|
||||
die("KVM_GET_SREGS failed");
|
||||
|
||||
ip = guest_addr_to_host(self, ip_real_to_flat(self, self->regs.rip) - code_prologue);
|
||||
|
||||
printf("Code: ");
|
||||
|
||||
Reference in New Issue
Block a user