svn commit: r251732 - in head/sys: kern sys

Lawrence Stewart lstewart at FreeBSD.org
Fri Jun 14 04:10:35 UTC 2013


Author: lstewart
Date: Fri Jun 14 04:10:34 2013
New Revision: 251732
URL: http://svnweb.freebsd.org/changeset/base/251732

Log:
  Add support for non-virtualised hhook points, which are uniquely identified by
  type and id, as compared to virtualised hook points which are now uniquely
  identified by type, id and a vid (which for vimage is the pointer to the vnet
  that the hhook resides in).
  
  All hhook_head structs for both virtualised and non-virtualised hook points
  coexist in hhook_head_list, and a separate list is maintained for hhook points
  within each vnet to simplify some vimage-related housekeeping.
  
  Reviewed by:	scottl
  MFC after:	1 week

Modified:
  head/sys/kern/kern_hhook.c
  head/sys/sys/hhook.h

Modified: head/sys/kern/kern_hhook.c
==============================================================================
--- head/sys/kern/kern_hhook.c	Fri Jun 14 03:58:52 2013	(r251731)
+++ head/sys/kern/kern_hhook.c	Fri Jun 14 04:10:34 2013	(r251732)
@@ -61,8 +61,9 @@ struct hhook {
 static MALLOC_DEFINE(M_HHOOK, "hhook", "Helper hooks are linked off hhook_head lists");
 
 LIST_HEAD(hhookheadhead, hhook_head);
-VNET_DEFINE(struct hhookheadhead, hhook_head_list);
-#define	V_hhook_head_list VNET(hhook_head_list)
+struct hhookheadhead hhook_head_list;
+VNET_DEFINE(struct hhookheadhead, hhook_vhead_list);
+#define	V_hhook_vhead_list VNET(hhook_vhead_list)
 
 static struct mtx hhook_head_list_lock;
 MTX_SYSINIT(hhookheadlistlock, &hhook_head_list_lock, "hhook_head list lock",
@@ -245,13 +246,6 @@ hhook_head_register(int32_t hhook_type, 
 		return (EEXIST);
 	}
 
-	/* XXXLAS: Need to implement support for non-virtualised hooks. */
-	if ((flags & HHOOK_HEADISINVNET) == 0) {
-		printf("%s: only vnet-style virtualised hooks can be used\n",
-		    __func__);
-		return (EINVAL);
-	}
-
 	tmphhh = malloc(sizeof(struct hhook_head), M_HHOOK,
 	    M_ZERO | ((flags & HHOOK_WAITOK) ? M_WAITOK : M_NOWAIT));
 
@@ -270,14 +264,15 @@ hhook_head_register(int32_t hhook_type, 
 	} else
 		refcount_init(&tmphhh->hhh_refcount, 0);
 
+	HHHLIST_LOCK();
 	if (flags & HHOOK_HEADISINVNET) {
 		tmphhh->hhh_flags |= HHH_ISINVNET;
-		HHHLIST_LOCK();
-		LIST_INSERT_HEAD(&V_hhook_head_list, tmphhh, hhh_next);
-		HHHLIST_UNLOCK();
-	} else {
-		/* XXXLAS: Add tmphhh to the non-virtualised list. */
+		KASSERT(curvnet != NULL, ("curvnet is NULL"));
+		tmphhh->hhh_vid = (uintptr_t)curvnet;
+		LIST_INSERT_HEAD(&V_hhook_vhead_list, tmphhh, hhh_vnext);
 	}
+	LIST_INSERT_HEAD(&hhook_head_list, tmphhh, hhh_next);
+	HHHLIST_UNLOCK();
 
 	return (0);
 }
@@ -290,6 +285,8 @@ hhook_head_destroy(struct hhook_head *hh
 	HHHLIST_LOCK_ASSERT();
 
 	LIST_REMOVE(hhh, hhh_next);
+	if (hhook_head_is_virtualised(hhh) == HHOOK_HEADISINVNET)
+		LIST_REMOVE(hhh, hhh_vnext);
 	HHH_WLOCK(hhh);
 	STAILQ_FOREACH_SAFE(tmp, &hhh->hhh_hooks, hhk_next, tmp2)
 		free(tmp, M_HHOOK);
@@ -347,10 +344,15 @@ hhook_head_get(int32_t hhook_type, int32
 {
 	struct hhook_head *hhh;
 
-	/* XXXLAS: Pick hhook_head_list based on hhook_head flags. */
 	HHHLIST_LOCK();
-	LIST_FOREACH(hhh, &V_hhook_head_list, hhh_next) {
+	LIST_FOREACH(hhh, &hhook_head_list, hhh_next) {
 		if (hhh->hhh_type == hhook_type && hhh->hhh_id == hhook_id) {
+			if (hhook_head_is_virtualised(hhh) ==
+			    HHOOK_HEADISINVNET) {
+				KASSERT(curvnet != NULL, ("curvnet is NULL"));
+				if (hhh->hhh_vid != (uintptr_t)curvnet)
+					continue;
+			}
 			refcount_acquire(&hhh->hhh_refcount);
 			break;
 		}
@@ -412,7 +414,7 @@ static void
 hhook_vnet_init(const void *unused __unused)
 {
 
-	LIST_INIT(&V_hhook_head_list);
+	LIST_INIT(&V_hhook_vhead_list);
 }
 
 /*
@@ -429,7 +431,7 @@ hhook_vnet_uninit(const void *unused __u
 	 * subsystem should have already called hhook_head_deregister().
 	 */
 	HHHLIST_LOCK();
-	LIST_FOREACH_SAFE(hhh, &V_hhook_head_list, hhh_next, tmphhh) {
+	LIST_FOREACH_SAFE(hhh, &V_hhook_vhead_list, hhh_vnext, tmphhh) {
 		printf("%s: hhook_head type=%d, id=%d cleanup required\n",
 		    __func__, hhh->hhh_type, hhh->hhh_id);
 		hhook_head_destroy(hhh);
@@ -439,7 +441,7 @@ hhook_vnet_uninit(const void *unused __u
 
 
 /*
- * When a vnet is created and being initialised, init the V_hhook_head_list.
+ * When a vnet is created and being initialised, init the V_hhook_vhead_list.
  */
 VNET_SYSINIT(hhook_vnet_init, SI_SUB_PROTO_BEGIN, SI_ORDER_FIRST,
     hhook_vnet_init, NULL);

Modified: head/sys/sys/hhook.h
==============================================================================
--- head/sys/sys/hhook.h	Fri Jun 14 03:58:52 2013	(r251731)
+++ head/sys/sys/hhook.h	Fri Jun 14 04:10:34 2013	(r251732)
@@ -91,12 +91,14 @@ struct hookinfo {
 struct hhook_head {
 	STAILQ_HEAD(hhook_list, hhook)	hhh_hooks;
 	struct rmlock			hhh_lock;
+	uintptr_t			hhh_vid;
 	int32_t				hhh_id;
 	int32_t				hhh_nhooks;
 	int32_t				hhh_type;
 	uint32_t			hhh_flags;
 	volatile uint32_t		hhh_refcount;
 	LIST_ENTRY(hhook_head)		hhh_next;
+	LIST_ENTRY(hhook_head)		hhh_vnext;
 };
 
 /* Public KPI functions. */


More information about the svn-src-all mailing list