socsvn commit: r289681 - in soc2015/stefano/ptnetmap/stable/10/sys/amd64: include vmm

stefano at FreeBSD.org stefano at FreeBSD.org
Thu Aug 13 09:47:14 UTC 2015


Author: stefano
Date: Thu Aug 13 09:47:12 2015
New Revision: 289681
URL: http://svnweb.FreeBSD.org/socsvn/?view=rev&rev=289681

Log:
  vmm-ptnetmap: cleanup and documentation

Modified:
  soc2015/stefano/ptnetmap/stable/10/sys/amd64/include/vmm_dev.h
  soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_ioport.c
  soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_ioport.h
  soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_usermem.c

Modified: soc2015/stefano/ptnetmap/stable/10/sys/amd64/include/vmm_dev.h
==============================================================================
--- soc2015/stefano/ptnetmap/stable/10/sys/amd64/include/vmm_dev.h	Thu Aug 13 09:37:29 2015	(r289680)
+++ soc2015/stefano/ptnetmap/stable/10/sys/amd64/include/vmm_dev.h	Thu Aug 13 09:47:12 2015	(r289681)
@@ -118,13 +118,13 @@
 };
 
 struct vm_io_reg_handler {
-	uint16_t		port;
-	uint16_t		in;
-	uint32_t		mask_data; /* 0 means match anything */
-	uint32_t		data;
-	enum vm_io_regh_type	type;
-	void			*arg;
-};
+	uint16_t		port;		/* I/O address */
+	uint16_t		in;		/* 0 out, 1 in */
+	uint32_t		mask_data;	/* 0 means match anything */
+	uint32_t		data;		/* data to match */
+	enum vm_io_regh_type	type;		/* handler type */
+	void			*arg;		/* handler argument */
+};a specific value that mathces
 
 struct vm_pptdev_msi {
 	int		vcpu;

Modified: soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_ioport.c
==============================================================================
--- soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_ioport.c	Thu Aug 13 09:37:29 2015	(r289680)
+++ soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_ioport.c	Thu Aug 13 09:47:12 2015	(r289681)
@@ -114,16 +114,26 @@
 
 #define IOPORT_MAX_REG_HANDLER	12
 
-typedef int (*ioport_reg_handler_func_t)(struct vm *vm, struct ioport_reg_handler *regh,
-    uint32_t *val);
+/*
+ * ioport_reg_handler functions allows us to to catch VM write/read
+ * on specific I/O address and send notification.
+ *
+ * When the VM writes or reads a specific value on I/O address, if the address
+ * and the value matches with the info stored durign the handler registration,
+ * then we send a notification (we can have multiple type of notification,
+ * but for now is implemented only the VM_IO_REGH_KWEVENTS handler.
+ */
+
+typedef int (*ioport_reg_handler_func_t)(struct vm *vm,
+		struct ioport_reg_handler *regh, uint32_t *val);
 
 struct ioport_reg_handler {
-	uint16_t port;
-	uint16_t in;
-	uint32_t mask_data;
-	uint32_t data;
-	ioport_reg_handler_func_t handler;
-	void *handler_arg;
+	uint16_t port;i				/* I/O address */
+	uint16_t in;				/* 0 out, 1 in */
+	uint32_t mask_data;			/* 0 means match anything */
+	uint32_t data;				/* data to match */
+	ioport_reg_handler_func_t handler;	/* handler pointer */
+	void *handler_arg;			/* handler argument */
 };
 
 struct ioregh {
@@ -134,7 +144,12 @@
 
 /* ----- I/O reg handlers ----- */
 
-/* VM_IO_REGH_KWEVENTS handler */
+/*
+ * VM_IO_REGH_KWEVENTS handler
+ *
+ * wakeup() on specified address that uniquely identifies the event
+ *
+ */
 static int
 vmm_ioport_reg_wakeup(struct vm *vm, struct ioport_reg_handler *regh, uint32_t *val)
 {
@@ -142,9 +157,17 @@
 	return (0);
 }
 
+/*
+ * TODO:
+ * - VM_IO_REGH_CONDSIGNAL:	pthread_cond_signal
+ * - VM_IO_REGH_WRITEFD:	write on fd
+ * - VM_IO_REGH_IOCTL:		ioctl on fd
+ */
+
 /* call with ioregh->mtx held */
 static struct ioport_reg_handler *
-vmm_ioport_find_handler(struct ioregh *ioregh, uint16_t port, uint16_t in, uint32_t mask_data, uint32_t data)
+vmm_ioport_find_handler(struct ioregh *ioregh, uint16_t port, uint16_t in,
+		uint32_t mask_data, uint32_t data)
 {
 	struct ioport_reg_handler *regh;
 	uint32_t mask;
@@ -183,8 +206,8 @@
 
 
 static int
-vmm_ioport_add_handler(struct vm *vm, uint16_t port, uint16_t in, uint32_t mask_data, uint32_t data,
-		ioport_reg_handler_func_t handler, void *handler_arg)
+vmm_ioport_add_handler(struct vm *vm, uint16_t port, uint16_t in, uint32_t mask_data,
+	uint32_t data, ioport_reg_handler_func_t handler, void *handler_arg)
 {
 	struct ioport_reg_handler *regh;
 	struct ioregh *ioregh;
@@ -196,7 +219,8 @@
 
 	regh = vmm_ioport_find_handler(ioregh, port, in, mask_data, data);
 	if (regh != NULL) {
-		printf("%s: handler for port %d in %d mask_data %d data %d already registered\n",
+		printf("%s: handler for port %d in %d mask_data %d data %d \
+				already registered\n",
 				__FUNCTION__, port, in,  mask_data, data);
 		ret = EEXIST;
 		goto err;
@@ -222,7 +246,8 @@
 }
 
 static int
-vmm_ioport_del_handler(struct vm *vm, uint16_t port, uint16_t in, uint32_t mask_data, uint32_t data)
+vmm_ioport_del_handler(struct vm *vm, uint16_t port, uint16_t in,
+	uint32_t mask_data, uint32_t data)
 {
 	struct ioport_reg_handler *regh;
 	struct ioregh *ioregh;
@@ -245,9 +270,12 @@
 	return (ret);
 }
 
+/*
+ * register or delete a new I/O event handler.
+ */
 int
-vmm_ioport_reg_handler(struct vm *vm, uint16_t port, uint16_t in, uint32_t mask_data, uint32_t data,
-		enum vm_io_regh_type type, void *arg)
+vmm_ioport_reg_handler(struct vm *vm, uint16_t port, uint16_t in,
+	uint32_t mask_data, uint32_t data, enum vm_io_regh_type type, void *arg)
 {
 	int ret = 0;
 
@@ -256,7 +284,8 @@
 		ret = vmm_ioport_del_handler(vm, port, in, mask_data, data);
 		break;
 	case VM_IO_REGH_KWEVENTS:
-		ret = vmm_ioport_add_handler(vm, port, in, mask_data, data, vmm_ioport_reg_wakeup, arg);
+		ret = vmm_ioport_add_handler(vm, port, in, mask_data, data,
+				vmm_ioport_reg_wakeup, arg);
 		break;
 	default:
 		printf("%s: unknown reg_handler type\n", __FUNCTION__);
@@ -267,8 +296,12 @@
 	return (ret);
 }
 
+/*
+ * Invoke an handler, if the data matches.
+ */
 static int
-invoke_reg_handler(struct vm *vm, int vcpuid, struct vm_exit *vmexit, uint32_t *val, int *error)
+invoke_reg_handler(struct vm *vm, int vcpuid, struct vm_exit *vmexit,
+	uint32_t *val, int *error)
 {
 	struct ioport_reg_handler *regh;
 	struct ioregh *ioregh;
@@ -278,13 +311,12 @@
 	ioregh = vm_ioregh(vm);
 
 	IOREGH_LOCK(ioregh);
-	regh = vmm_ioport_find_handler(ioregh, vmexit->u.inout.port, vmexit->u.inout.in,
-			mask_data, vmexit->u.inout.eax);
+	regh = vmm_ioport_find_handler(ioregh, vmexit->u.inout.port,
+			vmexit->u.inout.in, mask_data, vmexit->u.inout.eax);
 	if (regh == NULL) {
 		IOREGH_UNLOCK(ioregh);
 		return (0);
 	}
-	/* XXX: maybe is better to use refcount and lock only find */
 	*error = (*(regh->handler))(vm, regh, val);
 	IOREGH_UNLOCK(ioregh);
 	return (1);

Modified: soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_ioport.h
==============================================================================
--- soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_ioport.h	Thu Aug 13 09:37:29 2015	(r289680)
+++ soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_ioport.h	Thu Aug 13 09:47:12 2015	(r289681)
@@ -30,7 +30,6 @@
 #define	_VMM_IOPORT_H_
 
 #define VMM_IOPORT_REG_HANDLER
-
 #ifdef VMM_IOPORT_REG_HANDLER
 struct ioport_reg_handler;
 struct ioregh;
@@ -38,9 +37,8 @@
 struct ioregh *ioregh_init(struct vm *vm);
 void ioregh_cleanup(struct ioregh *ioregh);
 
-int
-vmm_ioport_reg_handler(struct vm *vm, uint16_t port, uint16_t in, uint32_t mask_data, uint32_t data,
-     enum vm_io_regh_type type, void *arg);
+int vmm_ioport_reg_handler(struct vm *vm, uint16_t port, uint16_t in,
+	uint32_t mask_data, uint32_t data, enum vm_io_regh_type type, void *arg);
 #else /* !VMM_IOPORT_REG_HANDLER */
 #define ioregh_init(_1)	(NULL)
 #define ioregh_cleanup(_1)

Modified: soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_usermem.c
==============================================================================
--- soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_usermem.c	Thu Aug 13 09:37:29 2015	(r289680)
+++ soc2015/stefano/ptnetmap/stable/10/sys/amd64/vmm/vmm_usermem.c	Thu Aug 13 09:47:12 2015	(r289681)
@@ -50,11 +50,20 @@
 #include "vmm_mem.h"
 #include "vmm_usermem.h"
 
+/*
+ * usermem functions allow us to map an host userspace buffer (eg. from bhyve)
+ * in the guest VM.
+ *
+ * This feature is used to implement ptnetmap on bhyve, mapping the netmap memory
+ * (returned by the mmap() in the byvhe userspace application) in the guest VM.
+ */
+
+/* TODO: we can create a dynamical list of usermem */
 #define MAX_USERMEMS	64
 
 static struct usermem {
-	struct vmspace   *vmspace;       /* guest address space */
-	vm_paddr_t	gpa;
+	struct vmspace   *vmspace;	/* guest address space */
+	vm_paddr_t	gpa;		/* guest physical address */
 	size_t		len;
 } usermems[MAX_USERMEMS];
 
@@ -128,7 +137,6 @@
 	error = vm_map_lookup(&map, (unsigned long)buf, VM_PROT_RW, &entry,
 		&obj, &index, &prot, &wired);
 
-	printf("---- guest MAP vm_object_t: %p vm_pindex: %ld ----\n", obj, index);
 	/* map th vm_object in the vmspace */
 	if (obj != NULL) {
 		error = vm_map_find(&vmspace->vm_map, obj, index, &gpa, len, 0,


More information about the svn-soc-all mailing list