
From: Jean Tourrilhes <jt@bougret.hpl.hp.com>

o [FEATURE] Make optional the del of IAS object when del IAS attrib
o [FEATURE] Clarify when/why it's safe to to the above

Signed-off-by: Jean Tourrilhes <jt@hpl.hp.com>
Signed-off-by: Andrew Morton <akpm@osdl.org>
---

 /dev/null                               |    0 
 25-akpm/include/net/irda/irias_object.h |    3 ++-
 25-akpm/net/irda/af_irda.c              |    2 +-
 25-akpm/net/irda/irias_object.c         |   18 +++++++++++++-----
 4 files changed, 16 insertions(+), 7 deletions(-)

diff -L include/net/irda/irias_object.d0.h -puN /dev/null /dev/null
diff -puN include/net/irda/irias_object.h~irda-ias-safety-comments include/net/irda/irias_object.h
--- 25/include/net/irda/irias_object.h~irda-ias-safety-comments	Wed Oct 20 15:50:19 2004
+++ 25-akpm/include/net/irda/irias_object.h	Wed Oct 20 15:50:19 2004
@@ -81,7 +81,8 @@ struct ias_attrib {
 struct ias_object *irias_new_object(char *name, int id);
 void irias_insert_object(struct ias_object *obj);
 int  irias_delete_object(struct ias_object *obj);
-int  irias_delete_attrib(struct ias_object *obj, struct ias_attrib *attrib);
+int  irias_delete_attrib(struct ias_object *obj, struct ias_attrib *attrib,
+			 int cleanobject);
 void __irias_delete_object(struct ias_object *obj);
 
 void irias_add_integer_attrib(struct ias_object *obj, char *name, int value,
diff -puN net/irda/af_irda.c~irda-ias-safety-comments net/irda/af_irda.c
--- 25/net/irda/af_irda.c~irda-ias-safety-comments	Wed Oct 20 15:50:19 2004
+++ 25-akpm/net/irda/af_irda.c	Wed Oct 20 15:50:19 2004
@@ -2005,7 +2005,7 @@ static int irda_setsockopt(struct socket
 		}
 
 		/* Remove the attribute (and maybe the object) */
-		irias_delete_attrib(ias_obj, ias_attr);
+		irias_delete_attrib(ias_obj, ias_attr, 1);
 		kfree(ias_opt);
 		break;
 	case IRLMP_MAX_SDU_SIZE:
diff -L net/irda/af_irda.d0.c -puN /dev/null /dev/null
diff -puN net/irda/irias_object.c~irda-ias-safety-comments net/irda/irias_object.c
--- 25/net/irda/irias_object.c~irda-ias-safety-comments	Wed Oct 20 15:50:19 2004
+++ 25-akpm/net/irda/irias_object.c	Wed Oct 20 15:50:19 2004
@@ -159,11 +159,14 @@ int irias_delete_object(struct ias_objec
 	ASSERT(obj != NULL, return -1;);
 	ASSERT(obj->magic == IAS_OBJECT_MAGIC, return -1;);
 
+	/* Remove from list */
 	node = hashbin_remove_this(irias_objects, (irda_queue_t *) obj);
 	if (!node)
-		return 0; /* Already removed */
+		IRDA_DEBUG( 0, "%s(), object already removed!\n",
+			    __FUNCTION__);
 
-	__irias_delete_object(node);
+	/* Destroy */
+	__irias_delete_object(obj);
 
 	return 0;
 }
@@ -176,7 +179,8 @@ EXPORT_SYMBOL(irias_delete_object);
  *    the object, remove the object as well.
  *
  */
-int irias_delete_attrib(struct ias_object *obj, struct ias_attrib *attrib)
+int irias_delete_attrib(struct ias_object *obj, struct ias_attrib *attrib,
+			int cleanobject)
 {
 	struct ias_attrib *node;
 
@@ -192,9 +196,13 @@ int irias_delete_attrib(struct ias_objec
 	/* Deallocate attribute */
 	__irias_delete_attrib(node);
 
-	/* Check if object has still some attributes */
+	/* Check if object has still some attributes, destroy it if none.
+	 * At first glance, this look dangerous, as the kernel reference
+	 * various IAS objects. However, we only use this function on
+	 * user attributes, not kernel attributes, so there is no risk
+	 * of deleting a kernel object this way. Jean II */
 	node = (struct ias_attrib *) hashbin_get_first(obj->attribs);
-	if (!node)
+	if (cleanobject && !node)
 		irias_delete_object(obj);
 
 	return 0;
diff -L net/irda/irias_object.d0.c -puN /dev/null /dev/null
_
