Permalink
Browse files

HBSD: bhyve obfuscation, part 1 of many

Give users the ability to obfuscate away the bhyve identification
string.

This is just one commit in a series of commits that will enhance bhyve
with the ability to obfuscate the identification of the hypervisor. This
is especially useful when running untrusted code in untrusted virtual
machines (ie, malware).

Signed-off-by:	Shawn Webb <shawn.webb@hardenedbsd.org>
Sponsored-by:	G2, Inc
(cherry picked from commit a52c62a5ed5d375b816482b5be6771ecdeaa4a02)
  • Loading branch information...
lattera committed Aug 14, 2017
1 parent 1ccbcb2 commit 59eabffdca53275086493836f732f24195f3a91d
View
@@ -1197,6 +1197,17 @@ vm_gla2gpa(struct vmctx *ctx, int vcpu, struct vm_guest_paging *paging,
return (error);
}
int
vm_set_bhyve_id(struct vmctx *ctx, const char *bhyve_id)
{
struct vm_bhyve_id vmid;
int error;
memcpy(vmid.bhyve_id, bhyve_id, 12);
error = ioctl(ctx->fd, VM_SET_BHYVE_ID, &vmid);
return (error);
}
#ifndef min
#define min(a,b) (((a) < (b)) ? (a) : (b))
#endif
@@ -1444,7 +1455,7 @@ vm_get_ioctls(size_t *len)
VM_GET_HPET_CAPABILITIES, VM_GET_GPA_PMAP, VM_GLA2GPA,
VM_ACTIVATE_CPU, VM_GET_CPUS, VM_SET_INTINFO, VM_GET_INTINFO,
VM_RTC_WRITE, VM_RTC_READ, VM_RTC_SETTIME, VM_RTC_GETTIME,
VM_RESTART_INSTRUCTION };
VM_RESTART_INSTRUCTION, VM_SET_BHYVE_ID };
if (len == NULL) {
cmds = malloc(sizeof(vm_ioctl_cmds));
View
@@ -111,6 +111,7 @@ void *vm_map_gpa(struct vmctx *ctx, vm_paddr_t gaddr, size_t len);
int vm_get_gpa_pmap(struct vmctx *, uint64_t gpa, uint64_t *pte, int *num);
int vm_gla2gpa(struct vmctx *, int vcpuid, struct vm_guest_paging *paging,
uint64_t gla, int prot, uint64_t *gpa, int *fault);
int vm_set_bhyve_id(struct vmctx *ctx, const char *bhyve_id);
uint32_t vm_get_lowmem_limit(struct vmctx *ctx);
void vm_set_lowmem_limit(struct vmctx *ctx, uint32_t limit);
void vm_set_memflags(struct vmctx *ctx, int flags);
View
@@ -105,6 +105,7 @@ enum x2apic_state {
#ifdef _KERNEL
#define VM_MAX_NAMELEN 32
#define VM_BHYVE_ID "bhyve bhyve "
struct vm;
struct vm_exception;
@@ -321,6 +322,8 @@ struct vatpic *vm_atpic(struct vm *vm);
struct vatpit *vm_atpit(struct vm *vm);
struct vpmtmr *vm_pmtmr(struct vm *vm);
struct vrtc *vm_rtc(struct vm *vm);
char *vm_get_bhyve_id(struct vm *vm);
int vm_set_bhyve_id(struct vm *vm, char *bhyve_id);
/*
* Inject exception 'vector' into the guest vcpu. This function returns 0 on
@@ -216,6 +216,10 @@ struct vm_rtc_data {
uint8_t value;
};
struct vm_bhyve_id {
char bhyve_id[12];
};
enum {
/* general routines */
IOCNUM_ABIVERS = 0,
@@ -286,6 +290,9 @@ enum {
IOCNUM_RTC_WRITE = 101,
IOCNUM_RTC_SETTIME = 102,
IOCNUM_RTC_GETTIME = 103,
/* Hypervisor emulation */
IOCNUM_SET_BHYVE_ID = 200,
};
#define VM_RUN \
@@ -382,4 +389,6 @@ enum {
_IOR('v', IOCNUM_RTC_GETTIME, struct vm_rtc_time)
#define VM_RESTART_INSTRUCTION \
_IOW('v', IOCNUM_RESTART_INSTRUCTION, int)
#define VM_SET_BHYVE_ID \
_IOW('v', IOCNUM_SET_BHYVE_ID, struct vm_bhyve_id)
#endif
View
@@ -162,6 +162,7 @@ struct vm {
struct vmspace *vmspace; /* (o) guest's address space */
char name[VM_MAX_NAMELEN]; /* (o) virtual machine name */
struct vcpu vcpu[VM_MAXCPU]; /* (i) guest vcpus */
char bhyve_id[12]; /* (o) hypervisor ID */

This comment has been minimized.

Show comment
Hide comment
@keltia

keltia Aug 15, 2017

Why the bare 12? Why not using a symbol for that?
Why 12 and not 13? :)

@keltia

keltia Aug 15, 2017

Why the bare 12? Why not using a symbol for that?
Why 12 and not 13? :)

This comment has been minimized.

Show comment
Hide comment
@lattera

lattera Aug 15, 2017

Member

I should use the macro I created. Either way, it's a pre-determined size set by the architecture.

@lattera

lattera Aug 15, 2017

Member

I should use the macro I created. Either way, it's a pre-determined size set by the architecture.

};
static int vmm_initialized;
@@ -441,6 +442,7 @@ vm_create(const char *name, struct vm **retvm)
vm = malloc(sizeof(struct vm), M_VM, M_WAITOK | M_ZERO);
strcpy(vm->name, name);
memcpy(vm->bhyve_id, VM_BHYVE_ID, 12);
vm->vmspace = vmspace;
mtx_init(&vm->rendezvous_mtx, "vm rendezvous lock", 0, MTX_DEF);
@@ -2449,6 +2451,20 @@ vm_rtc(struct vm *vm)
return (vm->vrtc);
}
char *vm_get_bhyve_id(struct vm *vm)
{
return (vm->bhyve_id);
}
int
vm_set_bhyve_id(struct vm *vm, char *bhyve_id)
{
memcpy(vm->bhyve_id, bhyve_id, 12);
return (0);
}
enum vm_reg_name
vm_segment_name(int seg)
{
View
@@ -312,6 +312,7 @@ vmmdev_ioctl(struct cdev *cdev, u_long cmd, caddr_t data, int fflag,
struct vm_intinfo *vmii;
struct vm_rtc_time *rtctime;
struct vm_rtc_data *rtcdata;
struct vm_bhyve_id *bhyveid;
struct vm_memmap *mm;
sc = vmmdev_lookup2(cdev);
@@ -640,6 +641,10 @@ vmmdev_ioctl(struct cdev *cdev, u_long cmd, caddr_t data, int fflag,
case VM_RESTART_INSTRUCTION:
error = vm_restart_instruction(sc->vm, vcpu);
break;
case VM_SET_BHYVE_ID:
bhyveid = (struct vm_bhyve_id *)data;
error = vm_set_bhyve_id(sc->vm, bhyveid->bhyve_id);
break;
default:
error = ENOTTY;
break;
View
@@ -52,8 +52,6 @@ static SYSCTL_NODE(_hw_vmm, OID_AUTO, topology, CTLFLAG_RD, 0, NULL);
#define CPUID_VM_HIGH 0x40000000
static const char bhyve_id[12] = "bhyve bhyve ";
static uint64_t bhyve_xcpuids;
SYSCTL_ULONG(_hw_vmm, OID_AUTO, bhyve_xcpuids, CTLFLAG_RW, &bhyve_xcpuids, 0,
"Number of times an unknown cpuid leaf was accessed");
@@ -93,6 +91,7 @@ x86_emulate_cpuid(struct vm *vm, int vcpu_id,
int error, enable_invpcid, level, width, x2apic_id;
unsigned int func, regs[4], logical_cpus;
enum x2apic_state x2apic_state;
char *bhyve_id;
VCPU_CTR2(vm, vcpu_id, "cpuid %#x,%#x", *eax, *ecx);
@@ -473,6 +472,7 @@ x86_emulate_cpuid(struct vm *vm, int vcpu_id,
case 0x40000000:
regs[0] = CPUID_VM_HIGH;
bhyve_id = vm_get_bhyve_id(vm);
bcopy(bhyve_id, &regs[1], 4);
bcopy(bhyve_id + 4, &regs[2], 4);
bcopy(bhyve_id + 8, &regs[3], 4);
View
@@ -794,6 +794,7 @@ main(int argc, char *argv[])
uint64_t rip;
size_t memsize;
char *optstr;
const char *bhyve_id;
bvmcons = 0;
progname = basename(argv[0]);
@@ -803,8 +804,9 @@ main(int argc, char *argv[])
mptgen = 1;
rtc_localtime = 1;
memflags = 0;
bhyve_id = NULL;
optstr = "abehuwxACHIPSWYp:g:c:s:m:l:U:";
optstr = "abehuwxACHIPSWYB:i:p:g:c:s:m:l:U:";
while ((c = getopt(argc, argv, optstr)) != -1) {
switch (c) {
case 'a':
@@ -816,6 +818,9 @@ main(int argc, char *argv[])
case 'b':
bvmcons = 1;
break;
case 'B':
bhyve_id = optarg;
break;
case 'p':
if (pincpu_parse(optarg) != 0) {
errx(EX_USAGE, "invalid vcpu pinning "
@@ -831,6 +836,12 @@ main(int argc, char *argv[])
case 'g':
gdb_port = atoi(optarg);
break;
case 'i':
if (strlen(optarg) != 12) {
errx(EX_USAGE, "hypervisor id must "
"be exactly 12 characters long");
}
break;
case 'l':
if (lpc_device_parse(optarg) != 0) {
errx(EX_USAGE, "invalid lpc device "
@@ -913,6 +924,15 @@ main(int argc, char *argv[])
exit(1);
}
if (bhyve_id != NULL) {
err = vm_set_bhyve_id(ctx, bhyve_id);
if (err != 0) {
fprintf(stderr, "Unable to set the hypervisor "
"id (%d)\n", errno);
exit(1);
}
}
fbsdrun_set_capabilities(ctx, BSP);
vm_set_memflags(ctx, memflags);

0 comments on commit 59eabff

Please sign in to comment.