userspace: add _k_object_recycle()

This is used to reset the permissions on an object while
also initializing it.

Signed-off-by: Andrew Boie <andrew.p.boie@intel.com>
diff --git a/kernel/include/syscall_handler.h b/kernel/include/syscall_handler.h
index eb0c1f1..a0d5950 100644
--- a/kernel/include/syscall_handler.h
+++ b/kernel/include/syscall_handler.h
@@ -126,6 +126,25 @@
 void _k_object_uninit(void *obj);
 
 /**
+ * Initialize and reset permissions to only access by the caller
+ *
+ * Intended for scenarios where objects are fetched from slab pools
+ * and may have had different permissions set during prior usage.
+ *
+ * This is only intended for pools of objects, where such objects are
+ * acquired and released to the pool. If an object has already been used,
+ * we do not want stale permission information hanging around, the object
+ * should only have permissions on the caller. Objects which are not
+ * managed by a pool-like mechanism should not use this API.
+ *
+ * The object will be marked as initialized and the calling thread
+ * granted access to it.
+ *
+ * @param object Address of the kernel object
+ */
+void _k_object_recycle(void *obj);
+
+/**
  * @brief Obtain the size of a C string passed from user mode
  *
  * Given a C string pointer and a maximum size, obtain the true
diff --git a/kernel/userspace.c b/kernel/userspace.c
index 0053028..fce86b4 100644
--- a/kernel/userspace.c
+++ b/kernel/userspace.c
@@ -546,6 +546,17 @@
 	ko->flags |= K_OBJ_FLAG_INITIALIZED;
 }
 
+void _k_object_recycle(void *object)
+{
+	struct _k_object *ko = _k_object_find(object);
+
+	if (ko) {
+		memset(ko->perms, 0, sizeof(ko->perms));
+		_thread_perms_set(ko, k_current_get());
+		ko->flags |= K_OBJ_FLAG_INITIALIZED;
+	}
+}
+
 void _k_object_uninit(void *object)
 {
 	struct _k_object *ko;