diff mbox

staging:ti dspbridge: use node id instead of kernel address

Message ID 1280351097-3346-2-git-send-email-ernesto@ti.com (mailing list archive)
State New, archived
Headers show

Commit Message

Ramos Falcon, Ernesto July 28, 2010, 9:04 p.m. UTC
None
diff mbox

Patch

diff --git a/drivers/staging/tidspbridge/include/dspbridge/drv.h b/drivers/staging/tidspbridge/include/dspbridge/drv.h
index 28541f7..0b36a11 100644
--- a/drivers/staging/tidspbridge/include/dspbridge/drv.h
+++ b/drivers/staging/tidspbridge/include/dspbridge/drv.h
@@ -24,6 +24,7 @@ 
 #include <dspbridge/devdefs.h>
 
 #include <dspbridge/drvdefs.h>
+#include <linux/idr.h>
 
 #define DRV_ASSIGN     1
 #define DRV_RELEASE    0
@@ -81,7 +82,7 @@  struct node_res_object {
 	s32 node_allocated;	/* Node status */
 	s32 heap_allocated;	/* Heap status */
 	s32 streams_allocated;	/* Streams status */
-	struct node_res_object *next;
+	int id;
 };
 
 /* used to cache dma mapping information */
@@ -158,8 +159,7 @@  struct process_context {
 	void *hprocessor;
 
 	/* DSP Node resources */
-	struct node_res_object *node_list;
-	struct mutex node_mutex;
+	struct idr *node_id;
 
 	/* DMM mapped memory resources */
 	struct list_head dmm_map_list;
diff --git a/drivers/staging/tidspbridge/include/dspbridge/node.h b/drivers/staging/tidspbridge/include/dspbridge/node.h
index 61d2d9b..49ed5c1 100644
--- a/drivers/staging/tidspbridge/include/dspbridge/node.h
+++ b/drivers/staging/tidspbridge/include/dspbridge/node.h
@@ -36,7 +36,7 @@ 
  *      pargs:              Optional arguments to be passed to the node.
  *      attr_in:            Optional pointer to node attributes (priority,
  *                          timeout...)
- *      ph_node:             Location to store node handle on output.
+ *      noderes:             Location to store node resource info.
  *  Returns:
  *      0:            Success.
  *      -ENOMEM:        Insufficient memory on GPP.
@@ -50,17 +50,17 @@ 
  *      node_init(void) called.
  *      hprocessor != NULL.
  *      node_uuid != NULL.
- *      ph_node != NULL.
+ *      noderes != NULL.
  *  Ensures:
  *      0:            IsValidNode(*ph_node).
- *      error:              *ph_node == NULL.
+ *      error:              *noderes == NULL.
  */
 extern int node_allocate(struct proc_object *hprocessor,
 				const struct dsp_uuid *node_uuid,
 				const struct dsp_cbdata
 				*pargs, const struct dsp_nodeattrin
 				*attr_in,
-				struct node_object **ph_node,
+				struct node_res_object **noderes,
 				struct process_context *pr_ctxt);
 
 /*
@@ -242,7 +242,9 @@  extern int node_create_mgr(struct node_mgr **node_man,
  *      delete function. Loads the node's delete function if necessary.
  *      GPP side resources are freed after node's delete function returns.
  *  Parameters:
- *      hnode:              Node handle returned from node_allocate().
+ *      noderes:              Node resource info handle returned from
+ *                                 node_allocate().
+ *      pr_ctxt:                Poninter to process context data.
  *  Returns:
  *      0:            Success.
  *      -EFAULT:        Invalid hnode.
@@ -254,7 +256,7 @@  extern int node_create_mgr(struct node_mgr **node_man,
  *  Ensures:
  *      0:            hnode is invalid.
  */
-extern int node_delete(struct node_object *hnode,
+extern int node_delete(struct node_res_object *noderes,
 			      struct process_context *pr_ctxt);
 
 /*
diff --git a/drivers/staging/tidspbridge/include/dspbridge/resourcecleanup.h b/drivers/staging/tidspbridge/include/dspbridge/resourcecleanup.h
index 4e1b8a2..d17c7fb 100644
--- a/drivers/staging/tidspbridge/include/dspbridge/resourcecleanup.h
+++ b/drivers/staging/tidspbridge/include/dspbridge/resourcecleanup.h
@@ -34,17 +34,11 @@  extern int drv_remove_all_resources(void *process_ctxt);
 extern int drv_remove_proc_context(struct drv_object *driver_obj,
 					  void *pr_ctxt);
 
-extern int drv_get_node_res_element(void *hnode, void *node_resource,
-					   void *process_ctx);
-
 extern int drv_insert_node_res_element(void *hnode, void *node_resource,
 					      void *process_ctxt);
 
 extern void drv_proc_node_update_heap_status(void *node_resource, s32 status);
 
-extern int drv_remove_node_res_element(void *node_resource,
-						void *process_ctxt);
-
 extern void drv_proc_node_update_status(void *node_resource, s32 status);
 
 extern int drv_proc_update_strm_res(u32 num_bufs, void *strm_resources);
diff --git a/drivers/staging/tidspbridge/pmgr/dspapi.c b/drivers/staging/tidspbridge/pmgr/dspapi.c
index da08dfc..6eda7c5 100644
--- a/drivers/staging/tidspbridge/pmgr/dspapi.c
+++ b/drivers/staging/tidspbridge/pmgr/dspapi.c
@@ -1052,6 +1052,20 @@  u32 procwrap_stop(union trapped_args *args, void *pr_ctxt)
 }
 
 /*
+ * ======== find_handle =========
+ */
+inline void find_node_handle(struct node_res_object **noderes,
+				void *pr_ctxt, void *hnode)
+{
+	rcu_read_lock();
+	*noderes = idr_find(((struct process_context *)pr_ctxt)->node_id,
+								(int)hnode);
+	rcu_read_unlock();
+	return;
+}
+
+
+/*
  * ======== nodewrap_allocate ========
  */
 u32 nodewrap_allocate(union trapped_args *args, void *pr_ctxt)
@@ -1062,7 +1076,7 @@  u32 nodewrap_allocate(union trapped_args *args, void *pr_ctxt)
 	u32 __user *psize = (u32 __user *) args->args_node_allocate.pargs;
 	u8 *pargs = NULL;
 	struct dsp_nodeattrin proc_attr_in, *attr_in = NULL;
-	struct node_object *hnode;
+	struct node_res_object *node_res;
 
 	/* Optional argument */
 	if (psize) {
@@ -1095,13 +1109,14 @@  u32 nodewrap_allocate(union trapped_args *args, void *pr_ctxt)
 	if (!status) {
 		status = node_allocate(args->args_node_allocate.hprocessor,
 				       &node_uuid, (struct dsp_cbdata *)pargs,
-				       attr_in, &hnode, pr_ctxt);
+				       attr_in, &node_res, pr_ctxt);
 	}
 	if (!status) {
-		CP_TO_USR(args->args_node_allocate.ph_node, &hnode, status, 1);
+		CP_TO_USR(args->args_node_allocate.ph_node, &node_res->id,
+			status, 1);
 		if (status) {
 			status = -EFAULT;
-			node_delete(hnode, pr_ctxt);
+			node_delete(node_res, pr_ctxt);
 		}
 	}
 func_cont:
@@ -1119,6 +1134,13 @@  u32 nodewrap_alloc_msg_buf(union trapped_args *args, void *pr_ctxt)
 	struct dsp_bufferattr *pattr = NULL;
 	struct dsp_bufferattr attr;
 	u8 *pbuffer = NULL;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res,  pr_ctxt,
+				args->args_node_allocmsgbuf.hnode);
+
+	if (!node_res)
+		return -EFAULT;
 
 	if (!args->args_node_allocmsgbuf.usize)
 		return -EINVAL;
@@ -1132,7 +1154,7 @@  u32 nodewrap_alloc_msg_buf(union trapped_args *args, void *pr_ctxt)
 	/* argument */
 	CP_FM_USR(&pbuffer, args->args_node_allocmsgbuf.pbuffer, status, 1);
 	if (!status) {
-		status = node_alloc_msg_buf(args->args_node_allocmsgbuf.hnode,
+		status = node_alloc_msg_buf(node_res->hnode,
 					    args->args_node_allocmsgbuf.usize,
 					    pattr, &pbuffer);
 	}
@@ -1146,8 +1168,15 @@  u32 nodewrap_alloc_msg_buf(union trapped_args *args, void *pr_ctxt)
 u32 nodewrap_change_priority(union trapped_args *args, void *pr_ctxt)
 {
 	u32 ret;
+	struct node_res_object *node_res;
 
-	ret = node_change_priority(args->args_node_changepriority.hnode,
+	find_node_handle(&node_res, pr_ctxt,
+				args->args_node_changepriority.hnode);
+
+	if (!node_res)
+		return -EFAULT;
+
+	ret = node_change_priority(node_res->hnode,
 				   args->args_node_changepriority.prio);
 
 	return ret;
@@ -1164,6 +1193,29 @@  u32 nodewrap_connect(union trapped_args *args, void *pr_ctxt)
 	u32 cb_data_size;
 	u32 __user *psize = (u32 __user *) args->args_node_connect.conn_param;
 	u8 *pargs = NULL;
+	struct node_res_object *node_res1, *node_res2;
+	struct node_object *node1 = NULL, *node2 = NULL;
+
+	if ((int)args->args_node_connect.hnode != DSP_HGPPNODE) {
+		find_node_handle(&node_res1, pr_ctxt,
+				args->args_node_connect.hnode);
+		if (node_res1)
+			node1 = node_res1->hnode;
+	} else {
+		node1 = args->args_node_connect.hnode;
+	}
+
+	if ((int)args->args_node_connect.other_node != DSP_HGPPNODE) {
+		find_node_handle(&node_res2, pr_ctxt,
+				args->args_node_connect.other_node);
+		if (node_res2)
+			node2 = node_res2->hnode;
+	} else {
+		node2 = args->args_node_connect.other_node;
+	}
+
+	if (!node1 || !node2)
+		return -EFAULT;
 
 	/* Optional argument */
 	if (psize) {
@@ -1191,9 +1243,9 @@  u32 nodewrap_connect(union trapped_args *args, void *pr_ctxt)
 
 	}
 	if (!status) {
-		status = node_connect(args->args_node_connect.hnode,
+		status = node_connect(node1,
 				      args->args_node_connect.stream_id,
-				      args->args_node_connect.other_node,
+				      node2,
 				      args->args_node_connect.other_stream,
 				      pattrs, (struct dsp_cbdata *)pargs);
 	}
@@ -1209,8 +1261,14 @@  func_cont:
 u32 nodewrap_create(union trapped_args *args, void *pr_ctxt)
 {
 	u32 ret;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt, args->args_node_create.hnode);
 
-	ret = node_create(args->args_node_create.hnode);
+	if (!node_res)
+		return -EFAULT;
+
+	ret = node_create(node_res->hnode);
 
 	return ret;
 }
@@ -1221,8 +1279,14 @@  u32 nodewrap_create(union trapped_args *args, void *pr_ctxt)
 u32 nodewrap_delete(union trapped_args *args, void *pr_ctxt)
 {
 	u32 ret;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt, args->args_node_delete.hnode);
+
+	if (!node_res)
+		return -EFAULT;
 
-	ret = node_delete(args->args_node_delete.hnode, pr_ctxt);
+	ret = node_delete(node_res, pr_ctxt);
 
 	return ret;
 }
@@ -1235,6 +1299,13 @@  u32 nodewrap_free_msg_buf(union trapped_args *args, void *pr_ctxt)
 	int status = 0;
 	struct dsp_bufferattr *pattr = NULL;
 	struct dsp_bufferattr attr;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt, args->args_node_freemsgbuf.hnode);
+
+	if (!node_res)
+		return -EFAULT;
+
 	if (args->args_node_freemsgbuf.pattr) {	/* Optional argument */
 		CP_FM_USR(&attr, args->args_node_freemsgbuf.pattr, status, 1);
 		if (!status)
@@ -1246,7 +1317,7 @@  u32 nodewrap_free_msg_buf(union trapped_args *args, void *pr_ctxt)
 		return -EFAULT;
 
 	if (!status) {
-		status = node_free_msg_buf(args->args_node_freemsgbuf.hnode,
+		status = node_free_msg_buf(node_res->hnode,
 					   args->args_node_freemsgbuf.pbuffer,
 					   pattr);
 	}
@@ -1261,8 +1332,14 @@  u32 nodewrap_get_attr(union trapped_args *args, void *pr_ctxt)
 {
 	int status = 0;
 	struct dsp_nodeattr attr;
+	struct node_res_object *node_res;
 
-	status = node_get_attr(args->args_node_getattr.hnode, &attr,
+	find_node_handle(&node_res, pr_ctxt, args->args_node_getattr.hnode);
+
+	if (!node_res)
+		return -EFAULT;
+
+	status = node_get_attr(node_res->hnode, &attr,
 			       args->args_node_getattr.attr_size);
 	CP_TO_USR(args->args_node_getattr.pattr, &attr, status, 1);
 
@@ -1276,8 +1353,14 @@  u32 nodewrap_get_message(union trapped_args *args, void *pr_ctxt)
 {
 	int status;
 	struct dsp_msg msg;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt, args->args_node_getmessage.hnode);
 
-	status = node_get_message(args->args_node_getmessage.hnode, &msg,
+	if (!node_res)
+		return -EFAULT;
+
+	status = node_get_message(node_res->hnode, &msg,
 				  args->args_node_getmessage.utimeout);
 
 	CP_TO_USR(args->args_node_getmessage.message, &msg, status, 1);
@@ -1291,8 +1374,14 @@  u32 nodewrap_get_message(union trapped_args *args, void *pr_ctxt)
 u32 nodewrap_pause(union trapped_args *args, void *pr_ctxt)
 {
 	u32 ret;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt, args->args_node_pause.hnode);
+
+	if (!node_res)
+		return -EFAULT;
 
-	ret = node_pause(args->args_node_pause.hnode);
+	ret = node_pause(node_res->hnode);
 
 	return ret;
 }
@@ -1304,12 +1393,18 @@  u32 nodewrap_put_message(union trapped_args *args, void *pr_ctxt)
 {
 	int status = 0;
 	struct dsp_msg msg;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt, args->args_node_putmessage.hnode);
+
+	if (!node_res)
+		return -EFAULT;
 
 	CP_FM_USR(&msg, args->args_node_putmessage.message, status, 1);
 
 	if (!status) {
 		status =
-		    node_put_message(args->args_node_putmessage.hnode, &msg,
+		    node_put_message(node_res->hnode, &msg,
 				     args->args_node_putmessage.utimeout);
 	}
 
@@ -1323,6 +1418,13 @@  u32 nodewrap_register_notify(union trapped_args *args, void *pr_ctxt)
 {
 	int status = 0;
 	struct dsp_notification notification;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt,
+			args->args_node_registernotify.hnode);
+
+	if (!node_res)
+		return -EFAULT;
 
 	/* Initialize the notification data structure */
 	notification.ps_name = NULL;
@@ -1333,7 +1435,7 @@  u32 nodewrap_register_notify(union trapped_args *args, void *pr_ctxt)
 			  args->args_proc_register_notify.hnotification,
 			  status, 1);
 
-	status = node_register_notify(args->args_node_registernotify.hnode,
+	status = node_register_notify(node_res->hnode,
 				      args->args_node_registernotify.event_mask,
 				      args->args_node_registernotify.
 				      notify_type, &notification);
@@ -1348,8 +1450,14 @@  u32 nodewrap_register_notify(union trapped_args *args, void *pr_ctxt)
 u32 nodewrap_run(union trapped_args *args, void *pr_ctxt)
 {
 	u32 ret;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt, args->args_node_run.hnode);
+
+	if (!node_res)
+		return -EFAULT;
 
-	ret = node_run(args->args_node_run.hnode);
+	ret = node_run(node_res->hnode);
 
 	return ret;
 }
@@ -1361,8 +1469,14 @@  u32 nodewrap_terminate(union trapped_args *args, void *pr_ctxt)
 {
 	int status;
 	int tempstatus;
+	struct node_res_object *node_res;
 
-	status = node_terminate(args->args_node_terminate.hnode, &tempstatus);
+	find_node_handle(&node_res, pr_ctxt, args->args_node_terminate.hnode);
+
+	if (!node_res)
+		return -EFAULT;
+
+	status = node_terminate(node_res->hnode, &tempstatus);
 
 	CP_TO_USR(args->args_node_terminate.pstatus, &tempstatus, status, 1);
 
@@ -1548,6 +1662,12 @@  u32 strmwrap_open(union trapped_args *args, void *pr_ctxt)
 	struct strm_attr attr;
 	struct strm_object *strm_obj;
 	struct dsp_streamattrin strm_attr_in;
+	struct node_res_object *node_res;
+
+	find_node_handle(&node_res, pr_ctxt, args->args_strm_open.hnode);
+
+	if (!node_res)
+		return -EFAULT;
 
 	CP_FM_USR(&attr, args->args_strm_open.attr_in, status, 1);
 
@@ -1560,7 +1680,7 @@  u32 strmwrap_open(union trapped_args *args, void *pr_ctxt)
 		}
 
 	}
-	status = strm_open(args->args_strm_open.hnode,
+	status = strm_open(node_res->hnode,
 			   args->args_strm_open.direction,
 			   args->args_strm_open.index, &attr, &strm_obj,
 			   pr_ctxt);
diff --git a/drivers/staging/tidspbridge/rmgr/drv.c b/drivers/staging/tidspbridge/rmgr/drv.c
index 12c270a..c8d9d25 100644
--- a/drivers/staging/tidspbridge/rmgr/drv.c
+++ b/drivers/staging/tidspbridge/rmgr/drv.c
@@ -73,7 +73,7 @@  static int request_bridge_resources(struct cfg_hostres *res);
 
 /* GPP PROCESS CLEANUP CODE */
 
-static int drv_proc_free_node_res(void *process_ctxt);
+static int drv_proc_free_node_res(int id, void *p, void *data);
 
 /* Allocate and add a node resource element
 * This function is called from .Node_Allocate. */
@@ -84,88 +84,61 @@  int drv_insert_node_res_element(void *hnode, void *node_resource,
 	    (struct node_res_object **)node_resource;
 	struct process_context *ctxt = (struct process_context *)process_ctxt;
 	int status = 0;
-	struct node_res_object *temp_node_res = NULL;
+	int retval;
 
 	*node_res_obj = kzalloc(sizeof(struct node_res_object), GFP_KERNEL);
-	if (*node_res_obj == NULL)
-		status = -EFAULT;
+	if (!*node_res_obj) {
+		status = -ENOMEM;
+		goto func_end;
+	}
 
-	if (!status) {
-		if (mutex_lock_interruptible(&ctxt->node_mutex)) {
-			kfree(*node_res_obj);
-			return -EPERM;
+	(*node_res_obj)->hnode = hnode;
+	retval = idr_get_new(ctxt->node_id, *node_res_obj,
+						&(*node_res_obj)->id);
+	if (retval == -EAGAIN) {
+		if (!idr_pre_get(ctxt->node_id, GFP_KERNEL)) {
+			pr_err("%s: OUT OF MEMORY\n", __func__);
+			status = -ENOMEM;
+			goto func_end;
 		}
-		(*node_res_obj)->hnode = hnode;
-		if (ctxt->node_list != NULL) {
-			temp_node_res = ctxt->node_list;
-			while (temp_node_res->next != NULL)
-				temp_node_res = temp_node_res->next;
 
-			temp_node_res->next = *node_res_obj;
-		} else {
-			ctxt->node_list = *node_res_obj;
-		}
-		mutex_unlock(&ctxt->node_mutex);
+		retval = idr_get_new(ctxt->node_id, *node_res_obj,
+						&(*node_res_obj)->id);
+	}
+	if (retval) {
+		pr_err("%s: FAILED, IDR is FULL\n", __func__);
+		status = -EFAULT;
 	}
+func_end:
+	if (status)
+		kfree(*node_res_obj);
 
 	return status;
 }
 
 /* Release all Node resources and its context
-* This is called from .Node_Delete. */
-int drv_remove_node_res_element(void *node_resource, void *process_ctxt)
+ * Actual Node De-Allocation */
+static int drv_proc_free_node_res(int id, void *p, void *data)
 {
-	struct node_res_object *node_res_obj =
-	    (struct node_res_object *)node_resource;
-	struct process_context *ctxt = (struct process_context *)process_ctxt;
-	struct node_res_object *temp_node;
-	int status = 0;
-
-	if (mutex_lock_interruptible(&ctxt->node_mutex))
-		return -EPERM;
-	temp_node = ctxt->node_list;
-	if (temp_node == node_res_obj) {
-		ctxt->node_list = node_res_obj->next;
-	} else {
-		while (temp_node && temp_node->next != node_res_obj)
-			temp_node = temp_node->next;
-		if (!temp_node)
-			status = -ENOENT;
-		else
-			temp_node->next = node_res_obj->next;
-	}
-	mutex_unlock(&ctxt->node_mutex);
-	kfree(node_res_obj);
-	return status;
-}
-
-/* Actual Node De-Allocation */
-static int drv_proc_free_node_res(void *process_ctxt)
-{
-	struct process_context *ctxt = (struct process_context *)process_ctxt;
-	int status = 0;
-	struct node_res_object *node_list = NULL;
-	struct node_res_object *node_res_obj = NULL;
+	struct process_context *ctxt = data;
+	int status;
+	struct node_res_object *node_res_obj = p;
 	u32 node_state;
 
-	node_list = ctxt->node_list;
-	while (node_list != NULL) {
-		node_res_obj = node_list;
-		node_list = node_list->next;
-		if (node_res_obj->node_allocated) {
-			node_state = node_get_state(node_res_obj->hnode);
-			if (node_state <= NODE_DELETING) {
-				if ((node_state == NODE_RUNNING) ||
-				    (node_state == NODE_PAUSED) ||
-				    (node_state == NODE_TERMINATING))
-					status = node_terminate
-					    (node_res_obj->hnode, &status);
-
-				status = node_delete(node_res_obj->hnode, ctxt);
-			}
+	if (node_res_obj->node_allocated) {
+		node_state = node_get_state(node_res_obj->hnode);
+		if (node_state <= NODE_DELETING) {
+			if ((node_state == NODE_RUNNING) ||
+			    (node_state == NODE_PAUSED) ||
+			    (node_state == NODE_TERMINATING))
+				node_terminate
+				    (node_res_obj->hnode, &status);
+
+			node_delete(node_res_obj, ctxt);
 		}
 	}
-	return status;
+
+	return 0;
 }
 
 /* Release all Mapped and Reserved DMM resources */
@@ -220,50 +193,12 @@  void drv_proc_node_update_heap_status(void *node_resource, s32 status)
  */
 int drv_remove_all_node_res_elements(void *process_ctxt)
 {
-	struct process_context *ctxt = (struct process_context *)process_ctxt;
-	int status = 0;
-	struct node_res_object *temp_node2 = NULL;
-	struct node_res_object *temp_node = NULL;
-
-	drv_proc_free_node_res(ctxt);
-	temp_node = ctxt->node_list;
-	while (temp_node != NULL) {
-		temp_node2 = temp_node;
-		temp_node = temp_node->next;
-		kfree(temp_node2);
-	}
-	ctxt->node_list = NULL;
-	return status;
-}
+	struct process_context *ctxt = process_ctxt;
 
-/* Getting the node resource element */
-int drv_get_node_res_element(void *hnode, void *node_resource,
-				    void *process_ctxt)
-{
-	struct node_res_object **node_res =
-				     (struct node_res_object **)node_resource;
-	struct process_context *ctxt = (struct process_context *)process_ctxt;
-	int status = 0;
-	struct node_res_object *temp_node2 = NULL;
-	struct node_res_object *temp_node = NULL;
-
-	if (mutex_lock_interruptible(&ctxt->node_mutex))
-		return -EPERM;
-
-	temp_node = ctxt->node_list;
-	while ((temp_node != NULL) && (temp_node->hnode != hnode)) {
-		temp_node2 = temp_node;
-		temp_node = temp_node->next;
-	}
+	idr_for_each(ctxt->node_id, drv_proc_free_node_res, ctxt);
+	idr_destroy(ctxt->node_id);
 
-	mutex_unlock(&ctxt->node_mutex);
-
-	if (temp_node != NULL)
-		*node_res = temp_node;
-	else
-		status = -ENOENT;
-
-	return status;
+	return 0;
 }
 
 /* Allocate the STRM resource element
diff --git a/drivers/staging/tidspbridge/rmgr/drv_interface.c b/drivers/staging/tidspbridge/rmgr/drv_interface.c
index aec7cf7..900cdd3 100644
--- a/drivers/staging/tidspbridge/rmgr/drv_interface.c
+++ b/drivers/staging/tidspbridge/rmgr/drv_interface.c
@@ -511,8 +511,13 @@  static int bridge_open(struct inode *ip, struct file *filp)
 		INIT_LIST_HEAD(&pr_ctxt->dmm_map_list);
 		spin_lock_init(&pr_ctxt->dmm_rsv_lock);
 		INIT_LIST_HEAD(&pr_ctxt->dmm_rsv_list);
-		mutex_init(&pr_ctxt->node_mutex);
 		mutex_init(&pr_ctxt->strm_mutex);
+
+		pr_ctxt->node_id = kzalloc(sizeof(struct idr), GFP_KERNEL);
+		if (pr_ctxt->node_id)
+			idr_init(pr_ctxt->node_id);
+		else
+			status = -ENOMEM;
 	} else {
 		status = -ENOMEM;
 	}
diff --git a/drivers/staging/tidspbridge/rmgr/node.c b/drivers/staging/tidspbridge/rmgr/node.c
index e2d02c4..6e9441e 100644
--- a/drivers/staging/tidspbridge/rmgr/node.c
+++ b/drivers/staging/tidspbridge/rmgr/node.c
@@ -291,11 +291,11 @@  enum node_state node_get_state(void *hnode)
  *      Allocate GPP resources to manage a node on the DSP.
  */
 int node_allocate(struct proc_object *hprocessor,
-			 const struct dsp_uuid *node_uuid,
-			 const struct dsp_cbdata *pargs,
-			 const struct dsp_nodeattrin *attr_in,
-			 struct node_object **ph_node,
-			 struct process_context *pr_ctxt)
+			const struct dsp_uuid *node_uuid,
+			const struct dsp_cbdata *pargs,
+			const struct dsp_nodeattrin *attr_in,
+			struct node_res_object **noderes,
+			struct process_context *pr_ctxt)
 {
 	struct node_mgr *hnode_mgr;
 	struct dev_object *hdev_obj;
@@ -327,10 +327,10 @@  int node_allocate(struct proc_object *hprocessor,
 
 	DBC_REQUIRE(refs > 0);
 	DBC_REQUIRE(hprocessor != NULL);
-	DBC_REQUIRE(ph_node != NULL);
+	DBC_REQUIRE(noderes != NULL);
 	DBC_REQUIRE(node_uuid != NULL);
 
-	*ph_node = NULL;
+	*noderes = NULL;
 
 	status = proc_get_processor_id(hprocessor, &proc_id);
 
@@ -653,9 +653,6 @@  func_cont:
 		 * (for overlay and dll) */
 		pnode->phase_split = true;
 
-		if (!status)
-			*ph_node = pnode;
-
 		/* Notify all clients registered for DSP_NODESTATECHANGE. */
 		proc_notify_all_clients(hprocessor, DSP_NODESTATECHANGE);
 	} else {
@@ -666,16 +663,21 @@  func_cont:
 	}
 
 	if (!status) {
-		drv_insert_node_res_element(*ph_node, &node_res, pr_ctxt);
+		status = drv_insert_node_res_element(pnode, &node_res, pr_ctxt);
+		if (status) {
+			delete_node(pnode, pr_ctxt);
+			goto func_end;
+		}
+
+		*noderes = (struct node_res_object *)node_res;
 		drv_proc_node_update_heap_status(node_res, true);
 		drv_proc_node_update_status(node_res, true);
 	}
-	DBC_ENSURE((status && (*ph_node == NULL)) ||
-			(!status && *ph_node));
+	DBC_ENSURE((status && *noderes == NULL) || (!status && *noderes));
 func_end:
-	dev_dbg(bridge, "%s: hprocessor: %p node_uuid: %p pargs: %p attr_in:"
-		" %p ph_node: %p status: 0x%x\n", __func__, hprocessor,
-		node_uuid, pargs, attr_in, ph_node, status);
+	dev_dbg(bridge, "%s: hprocessor: %p pNodeId: %p pargs: %p attr_in: %p "
+		"node_res: %p status: 0x%x\n", __func__, hprocessor,
+		node_uuid, pargs, attr_in, noderes, status);
 	return status;
 }
 
@@ -1433,10 +1435,10 @@  int node_create_mgr(struct node_mgr **node_man,
  *      Loads the node's delete function if necessary. Free GPP side resources
  *      after node's delete function returns.
  */
-int node_delete(struct node_object *hnode,
+int node_delete(struct node_res_object *noderes,
 		       struct process_context *pr_ctxt)
 {
-	struct node_object *pnode = (struct node_object *)hnode;
+	struct node_object *pnode = noderes->hnode;
 	struct node_mgr *hnode_mgr;
 	struct proc_object *hprocessor;
 	struct disp_object *disp_obj;
@@ -1449,32 +1451,32 @@  int node_delete(struct node_object *hnode,
 	u32 proc_id;
 	struct bridge_drv_interface *intf_fxns;
 
-	void *node_res;
+	void *node_res = noderes;
 
 	struct dsp_processorstate proc_state;
 	DBC_REQUIRE(refs > 0);
 
-	if (!hnode) {
+	if (!pnode) {
 		status = -EFAULT;
 		goto func_end;
 	}
 	/* create struct dsp_cbdata struct for PWR call */
 	cb_data.cb_data = PWR_TIMEOUT;
-	hnode_mgr = hnode->hnode_mgr;
-	hprocessor = hnode->hprocessor;
+	hnode_mgr = pnode->hnode_mgr;
+	hprocessor = pnode->hprocessor;
 	disp_obj = hnode_mgr->disp_obj;
-	node_type = node_get_type(hnode);
+	node_type = node_get_type(pnode);
 	intf_fxns = hnode_mgr->intf_fxns;
 	/* Enter critical section */
 	mutex_lock(&hnode_mgr->node_mgr_lock);
 
-	state = node_get_state(hnode);
+	state = node_get_state(pnode);
 	/*  Execute delete phase code for non-device node in all cases
 	 *  except when the node was only allocated. Delete phase must be
 	 *  executed even if create phase was executed, but failed.
 	 *  If the node environment pointer is non-NULL, the delete phase
 	 *  code must be  executed. */
-	if (!(state == NODE_ALLOCATED && hnode->node_env == (u32) NULL) &&
+	if (!(state == NODE_ALLOCATED && pnode->node_env == (u32) NULL) &&
 	    node_type != NODE_DEVICE) {
 		status = proc_get_processor_id(pnode->hprocessor, &proc_id);
 		if (status)
@@ -1487,26 +1489,26 @@  int node_delete(struct node_object *hnode,
 			 *  is now ok to unload it. If the node is running, we
 			 *  will unload the execute phase only after deleting
 			 *  the node. */
-			if (state == NODE_PAUSED && hnode->loaded &&
-			    hnode->phase_split) {
+			if (state == NODE_PAUSED && pnode->loaded &&
+			    pnode->phase_split) {
 				/* Ok to unload execute code as long as node
 				 * is not * running */
 				status1 =
 				    hnode_mgr->nldr_fxns.
-				    pfn_unload(hnode->nldr_node_obj,
+				    pfn_unload(pnode->nldr_node_obj,
 					       NLDR_EXECUTE);
-				hnode->loaded = false;
-				NODE_SET_STATE(hnode, NODE_DONE);
+				pnode->loaded = false;
+				NODE_SET_STATE(pnode, NODE_DONE);
 			}
 			/* Load delete phase code if not loaded or if haven't
 			 * * unloaded EXECUTE phase */
-			if ((!(hnode->loaded) || (state == NODE_RUNNING)) &&
-			    hnode->phase_split) {
+			if ((!(pnode->loaded) || (state == NODE_RUNNING)) &&
+			    pnode->phase_split) {
 				status =
 				    hnode_mgr->nldr_fxns.
-				    pfn_load(hnode->nldr_node_obj, NLDR_DELETE);
+				    pfn_load(pnode->nldr_node_obj, NLDR_DELETE);
 				if (!status)
-					hnode->loaded = true;
+					pnode->loaded = true;
 				else
 					pr_err("%s: fail - load delete code:"
 					       " 0x%x\n", __func__, status);
@@ -1515,14 +1517,14 @@  int node_delete(struct node_object *hnode,
 func_cont1:
 		if (!status) {
 			/* Unblock a thread trying to terminate the node */
-			(void)sync_set_event(hnode->sync_done);
+			(void)sync_set_event(pnode->sync_done);
 			if (proc_id == DSP_UNIT) {
 				/* ul_delete_fxn = address of node's delete
 				 * function */
-				status = get_fxn_address(hnode, &ul_delete_fxn,
+				status = get_fxn_address(pnode, &ul_delete_fxn,
 							 DELETEPHASE);
 			} else if (proc_id == IVA_UNIT)
-				ul_delete_fxn = (u32) hnode->node_env;
+				ul_delete_fxn = (u32) pnode->node_env;
 			if (!status) {
 				status = proc_get_state(hprocessor,
 						&proc_state,
@@ -1530,22 +1532,22 @@  func_cont1:
 						       dsp_processorstate));
 				if (proc_state.proc_state != PROC_ERROR) {
 					status =
-					    disp_node_delete(disp_obj, hnode,
+					    disp_node_delete(disp_obj, pnode,
 							     hnode_mgr->
 							     ul_fxn_addrs
 							     [RMSDELETENODE],
 							     ul_delete_fxn,
-							     hnode->node_env);
+							     pnode->node_env);
 				} else
-					NODE_SET_STATE(hnode, NODE_DONE);
+					NODE_SET_STATE(pnode, NODE_DONE);
 
 				/* Unload execute, if not unloaded, and delete
 				 * function */
 				if (state == NODE_RUNNING &&
-				    hnode->phase_split) {
+				    pnode->phase_split) {
 					status1 =
 					    hnode_mgr->nldr_fxns.
-					    pfn_unload(hnode->nldr_node_obj,
+					    pfn_unload(pnode->nldr_node_obj,
 						       NLDR_EXECUTE);
 				}
 				if (status1)
@@ -1553,10 +1555,10 @@  func_cont1:
 					       " 0x%x\n", __func__, status1);
 
 				status1 =
-				    hnode_mgr->nldr_fxns.pfn_unload(hnode->
+				    hnode_mgr->nldr_fxns.pfn_unload(pnode->
 							    nldr_node_obj,
 							    NLDR_DELETE);
-				hnode->loaded = false;
+				pnode->loaded = false;
 				if (status1)
 					pr_err("%s: fail - unload delete code: "
 					       "0x%x\n", __func__, status1);
@@ -1565,25 +1567,28 @@  func_cont1:
 	}
 	/* Free host side resources even if a failure occurred */
 	/* Remove node from hnode_mgr->node_list */
-	lst_remove_elem(hnode_mgr->node_list, (struct list_head *)hnode);
+	lst_remove_elem(hnode_mgr->node_list, (struct list_head *)pnode);
 	hnode_mgr->num_nodes--;
 	/* Decrement count of nodes created on DSP */
 	if ((state != NODE_ALLOCATED) || ((state == NODE_ALLOCATED) &&
-					  (hnode->node_env != (u32) NULL)))
+					  (pnode->node_env != (u32) NULL)))
 		hnode_mgr->num_created--;
 	/*  Free host-side resources allocated by node_create()
 	 *  delete_node() fails if SM buffers not freed by client! */
-	if (drv_get_node_res_element(hnode, &node_res, pr_ctxt) !=
-	    -ENOENT)
-		drv_proc_node_update_status(node_res, false);
-	delete_node(hnode, pr_ctxt);
+	drv_proc_node_update_status(node_res, false);
+	delete_node(pnode, pr_ctxt);
+
+	/*
+	 * Release all Node resources and its context
+	 */
+	idr_remove(pr_ctxt->node_id, ((struct node_res_object *)node_res)->id);
+	kfree(node_res);
 
-	drv_remove_node_res_element(node_res, pr_ctxt);
 	/* Exit critical section */
 	mutex_unlock(&hnode_mgr->node_mgr_lock);
 	proc_notify_clients(hprocessor, DSP_NODESTATECHANGE);
 func_end:
-	dev_dbg(bridge, "%s: hnode: %p status 0x%x\n", __func__, hnode, status);
+	dev_dbg(bridge, "%s: pnode: %p status 0x%x\n", __func__, pnode, status);
 	return status;
 }