diff -u -p linux/include/net/irda/irqueue.d1.h linux/include/net/irda/irqueue.h
--- linux/include/net/irda/irqueue.d1.h	Tue Jun 18 16:02:27 2002
+++ linux/include/net/irda/irqueue.h	Tue Jun 18 15:58:08 2002
@@ -67,7 +67,7 @@ struct irda_queue {
 	struct irda_queue *q_prev;
 
 	char   q_name[NAME_SIZE];
-	__u32  q_hash;
+	int    q_hash;
 };
 typedef struct irda_queue irda_queue_t;
 
@@ -84,10 +84,10 @@ typedef struct hashbin_t {
 hashbin_t *hashbin_new(int type);
 int      hashbin_delete(hashbin_t* hashbin, FREE_FUNC func);
 int      hashbin_clear(hashbin_t* hashbin, FREE_FUNC free_func);
-void     hashbin_insert(hashbin_t* hashbin, irda_queue_t* entry, __u32 hashv, 
+void     hashbin_insert(hashbin_t* hashbin, irda_queue_t* entry, int hashv, 
 			char* name);
-void*    hashbin_find(hashbin_t* hashbin, __u32 hashv, char* name);
-void*    hashbin_remove(hashbin_t* hashbin, __u32 hashv, char* name);
+void*    hashbin_find(hashbin_t* hashbin, int hashv, char* name);
+void*    hashbin_remove(hashbin_t* hashbin, int hashv, char* name);
 void*    hashbin_remove_first(hashbin_t *hashbin);
 void*	 hashbin_remove_this( hashbin_t* hashbin, irda_queue_t* entry);
 irda_queue_t *hashbin_get_first(hashbin_t *hashbin);
diff -u -p linux/include/net/irda/irlmp.d1.h linux/include/net/irda/irlmp.h
--- linux/include/net/irda/irlmp.d1.h	Tue Jun 18 15:44:28 2002
+++ linux/include/net/irda/irlmp.h	Tue Jun 18 16:00:48 2002
@@ -197,12 +197,12 @@ struct lsap_cb *irlmp_open_lsap(__u8 sls
 void irlmp_close_lsap( struct lsap_cb *self);
 
 __u16 irlmp_service_to_hint(int service);
-__u32 irlmp_register_service(__u16 hints);
-int irlmp_unregister_service(__u32 handle);
-__u32 irlmp_register_client(__u16 hint_mask, DISCOVERY_CALLBACK1 disco_clb,
+void *irlmp_register_service(__u16 hints);
+int irlmp_unregister_service(void *handle);
+void *irlmp_register_client(__u16 hint_mask, DISCOVERY_CALLBACK1 disco_clb,
 			    DISCOVERY_CALLBACK1 expir_clb, void *priv);
-int irlmp_unregister_client(__u32 handle);
-int irlmp_update_client(__u32 handle, __u16 hint_mask, 
+int irlmp_unregister_client(void *handle);
+int irlmp_update_client(void *handle, __u16 hint_mask, 
 			DISCOVERY_CALLBACK1 disco_clb,
 			DISCOVERY_CALLBACK1 expir_clb, void *priv);
 
diff -u -p linux/include/net/irda/af_irda.d1.h linux/include/net/irda/af_irda.h
--- linux/include/net/irda/af_irda.d1.h	Tue Jun 18 16:06:21 2002
+++ linux/include/net/irda/af_irda.h	Tue Jun 18 16:06:47 2002
@@ -55,8 +55,8 @@ struct irda_sock {
 	__u16 mask;           /* Hint bits mask */
 	__u16 hints;          /* Hint bits */
 
-	__u32 ckey;           /* IrLMP client handle */
-	__u32 skey;           /* IrLMP service handle */
+	void *ckey;           /* IrLMP client handle */
+	void *skey;           /* IrLMP service handle */
 
 	struct ias_object *ias_obj;   /* Our service name + lsap in IAS */
 	struct iriap_cb *iriap;	      /* Used to query remote IAS */
diff -u -p linux/include/net/irda/ircomm_tty.d1.h linux/include/net/irda/ircomm_tty.h
--- linux/include/net/irda/ircomm_tty.d1.h	Tue Jun 18 16:09:54 2002
+++ linux/include/net/irda/ircomm_tty.h	Tue Jun 18 16:10:59 2002
@@ -86,8 +86,8 @@ struct ircomm_tty_cb {
 
 	struct iriap_cb *iriap; /* Instance used for querying remote IAS */
 	struct ias_object* obj;
-	int skey;
-	int ckey;
+	void *skey;
+	void *ckey;
 
 	struct termios	  normal_termios;
 	struct termios	  callout_termios;
diff -u -p linux/net/irda/irqueue.d1.c linux/net/irda/irqueue.c
--- linux/net/irda/irqueue.d1.c	Tue Jun 18 15:21:53 2002
+++ linux/net/irda/irqueue.c	Tue Jun 18 16:58:38 2002
@@ -34,6 +34,21 @@
  *     
  ********************************************************************/
 
+/*
+ * NOTE :
+ * There are various problems with this package :
+ *	o the hash function for ints is pathetic (but could be changed)
+ *	o locking is sometime suspicious (especially during enumeration)
+ *	o most users have only a few elements (== overhead)
+ *	o most users never use seach, so don't benefit from hashing
+ * Problem already fixed :
+ *	o not 64 bit compliant (most users do hashv = (int) self)
+ *	o hashbin_remove() is broken => use hashbin_remove_this()
+ * I think most users would be better served by a simple linked list
+ * (like include/linux/list.h) with a global spinlock per list.
+ * Jean II
+ */
+
 #include <net/irda/irda.h>
 #include <net/irda/irqueue.h>
 
@@ -148,7 +163,7 @@ int hashbin_delete( hashbin_t* hashbin, 
  *    Insert an entry into the hashbin
  *
  */
-void hashbin_insert(hashbin_t* hashbin, irda_queue_t* entry, __u32 hashv, char* name)
+void hashbin_insert(hashbin_t* hashbin, irda_queue_t* entry, int hashv, char* name)
 {
 	unsigned long flags = 0;
 	int bin;
@@ -209,7 +224,7 @@ void hashbin_insert(hashbin_t* hashbin, 
  *    Find item with the given hashv or name
  *
  */
-void* hashbin_find( hashbin_t* hashbin, __u32 hashv, char* name )
+void* hashbin_find( hashbin_t* hashbin, int hashv, char* name )
 {
 	int bin, found = FALSE;
 	unsigned long flags = 0;
@@ -300,8 +315,16 @@ void *hashbin_remove_first( hashbin_t *h
  *
  *    Remove entry with the given name
  *
+ *  The use of this function is highly discouraged, because the whole
+ *  concept behind hashbin_remove() is broken. In many cases, it's not
+ *  possible to guarantee the unicity of the index (either hashv or name),
+ *  leading to removing the WRONG entry.
+ *  The only simple safe use is :
+ *		hashbin_remove(hasbin, (int) self, NULL);
+ *  In other case, you must think hard to guarantee unicity of the index.
+ *  Jean II
  */
-void* hashbin_remove( hashbin_t* hashbin, __u32 hashv, char* name)
+void* hashbin_remove( hashbin_t* hashbin, int hashv, char* name)
 {
 	int bin, found = FALSE;
 	unsigned long flags = 0;
@@ -404,7 +427,7 @@ void* hashbin_remove_this( hashbin_t* ha
 {
 	unsigned long flags = 0;
 	int	bin;
-	__u32	hashv;
+	int	hashv;
 
 	IRDA_DEBUG( 4, __FUNCTION__ "()\n");
 
diff -u -p linux/net/irda/irlmp.d1.c linux/net/irda/irlmp.c
--- linux/net/irda/irlmp.d1.c	Tue Jun 18 15:44:12 2002
+++ linux/net/irda/irlmp.c	Tue Jun 18 16:35:33 2002
@@ -1414,20 +1414,12 @@ __u16 irlmp_service_to_hint(int service)
  *    Register local service with IrLMP
  *
  */
-__u32 irlmp_register_service(__u16 hints)
+void *irlmp_register_service(__u16 hints)
 {
 	irlmp_service_t *service;
-	__u32 handle;
 
 	IRDA_DEBUG(4, __FUNCTION__ "(), hints = %04x\n", hints);
 
-	/* Get a unique handle for this service */
-	get_random_bytes(&handle, sizeof(handle));
-	while (hashbin_find(irlmp->services, handle, NULL) || !handle)
-		get_random_bytes(&handle, sizeof(handle));
-
-	irlmp->hints.word |= hints;
-
 	/* Make a new registration */
 	service = kmalloc(sizeof(irlmp_service_t), GFP_ATOMIC);
 	if (!service) {
@@ -1435,9 +1427,11 @@ __u32 irlmp_register_service(__u16 hints
 		return 0;
 	}
 	service->hints = hints;
-	hashbin_insert(irlmp->services, (irda_queue_t *) service, handle, NULL);
+	hashbin_insert(irlmp->services, (irda_queue_t *) service, (int) service, NULL);
 
-	return handle;
+	irlmp->hints.word |= hints;
+
+	return (void *)service;
 }
 
 /*
@@ -1447,7 +1441,7 @@ __u32 irlmp_register_service(__u16 hints
  *
  *    Returns: 0 on success, -1 on error
  */
-int irlmp_unregister_service(__u32 handle)
+int irlmp_unregister_service(void *handle)
 {
 	irlmp_service_t *service;
 
@@ -1456,15 +1450,15 @@ int irlmp_unregister_service(__u32 handl
 	if (!handle)
 		return -1;
 
-	service = hashbin_find(irlmp->services, handle, NULL);
+	/* Caller may call with invalid handle (it's legal) - Jean II */
+	service = hashbin_find(irlmp->services, (int) handle, NULL);
 	if (!service) {
 		IRDA_DEBUG(1, __FUNCTION__ "(), Unknown service!\n");
 		return -1;
 	}
 
-	service = hashbin_remove(irlmp->services, handle, NULL);
-	if (service)
-		kfree(service);
+	hashbin_remove_this(irlmp->services, (irda_queue_t *) service);
+	kfree(service);
 
 	/* Remove old hint bits */
 	irlmp->hints.word = 0;
@@ -1488,20 +1482,14 @@ int irlmp_unregister_service(__u32 handl
  *
  *    Returns: handle > 0 on success, 0 on error
  */
-__u32 irlmp_register_client(__u16 hint_mask, DISCOVERY_CALLBACK1 disco_clb,
+void *irlmp_register_client(__u16 hint_mask, DISCOVERY_CALLBACK1 disco_clb,
 			    DISCOVERY_CALLBACK1 expir_clb, void *priv)
 {
 	irlmp_client_t *client;
-	__u32 handle;
 
 	IRDA_DEBUG(1, __FUNCTION__ "()\n");
 	ASSERT(irlmp != NULL, return 0;);
 
-	/* Get a unique handle for this client */
-	get_random_bytes(&handle, sizeof(handle));
-	while (hashbin_find(irlmp->clients, handle, NULL) || !handle)
-		get_random_bytes(&handle, sizeof(handle));
-
 	/* Make a new registration */
 	client = kmalloc(sizeof(irlmp_client_t), GFP_ATOMIC);
 	if (!client) {
@@ -1515,9 +1503,9 @@ __u32 irlmp_register_client(__u16 hint_m
 	client->expir_callback = expir_clb;
 	client->priv = priv;
 
-	hashbin_insert(irlmp->clients, (irda_queue_t *) client, handle, NULL);
+	hashbin_insert(irlmp->clients, (irda_queue_t *) client, (int) client, NULL);
 
-	return handle;
+	return (void *) client;
 }
 
 /*
@@ -1528,7 +1516,7 @@ __u32 irlmp_register_client(__u16 hint_m
  *
  *    Returns: 0 on success, -1 on error
  */
-int irlmp_update_client(__u32 handle, __u16 hint_mask,
+int irlmp_update_client(void *handle, __u16 hint_mask,
 			DISCOVERY_CALLBACK1 disco_clb,
 			DISCOVERY_CALLBACK1 expir_clb, void *priv)
 {
@@ -1537,7 +1525,7 @@ int irlmp_update_client(__u32 handle, __
 	if (!handle)
 		return -1;
 
-	client = hashbin_find(irlmp->clients, handle, NULL);
+	client = hashbin_find(irlmp->clients, (int) handle, NULL);
 	if (!client) {
 		IRDA_DEBUG(1, __FUNCTION__ "(), Unknown client!\n");
 		return -1;
@@ -1557,7 +1545,7 @@ int irlmp_update_client(__u32 handle, __
  *    Returns: 0 on success, -1 on error
  *
  */
-int irlmp_unregister_client(__u32 handle)
+int irlmp_unregister_client(void *handle)
 {
 	struct irlmp_client *client;
 
@@ -1566,16 +1554,16 @@ int irlmp_unregister_client(__u32 handle
 	if (!handle)
 		return -1;
 
-	client = hashbin_find(irlmp->clients, handle, NULL);
+	/* Caller may call with invalid handle (it's legal) - Jean II */
+	client = hashbin_find(irlmp->clients, (int) handle, NULL);
 	if (!client) {
 		IRDA_DEBUG(1, __FUNCTION__ "(), Unknown client!\n");
 		return -1;
 	}
 
 	IRDA_DEBUG( 4, __FUNCTION__ "(), removing client!\n");
-	client = hashbin_remove( irlmp->clients, handle, NULL);
-	if (client)
-		kfree(client);
+	hashbin_remove_this(irlmp->clients, (irda_queue_t *) client);
+	kfree(client);
 
 	return 0;
 }
diff -u -p linux/net/irda/iriap.d1.c linux/net/irda/iriap.c
--- linux/net/irda/iriap.d1.c	Tue Jun 18 16:04:58 2002
+++ linux/net/irda/iriap.c	Tue Jun 18 16:05:13 2002
@@ -58,7 +58,7 @@ static const char *ias_charset_types[] =
 #endif	/* CONFIG_IRDA_DEBUG */
 
 static hashbin_t *iriap = NULL;
-static __u32 service_handle;
+static void *service_handle;
 
 extern char *lmp_reasons[];
 
diff -u -p linux/net/irda/irias_object.d1.c linux/net/irda/irias_object.c
--- linux/net/irda/irias_object.d1.c	Tue Jun 18 15:19:21 2002
+++ linux/net/irda/irias_object.c	Tue Jun 18 16:46:36 2002
@@ -147,7 +147,7 @@ int irias_delete_object(struct ias_objec
 	ASSERT(obj != NULL, return -1;);
 	ASSERT(obj->magic == IAS_OBJECT_MAGIC, return -1;);
 
-	node = hashbin_remove(objects, 0, obj->name);
+	node = hashbin_remove_this(objects, (irda_queue_t *) obj);
 	if (!node)
 		return 0; /* Already removed */
 
@@ -172,7 +172,7 @@ int irias_delete_attrib(struct ias_objec
 	ASSERT(attrib != NULL, return -1;);
 
 	/* Remove attribute from object */
-	node = hashbin_remove(obj->attribs, 0, attrib->name);
+	node = hashbin_remove_this(obj->attribs, (irda_queue_t *) attrib);
 	if (!node)
 		return 0; /* Already removed or non-existent */
 
diff -u -p linux/net/irda/irlan/irlan_common.d1.c linux/net/irda/irlan/irlan_common.c
--- linux/net/irda/irlan/irlan_common.d1.c	Tue Jun 18 16:12:19 2002
+++ linux/net/irda/irlan/irlan_common.c	Tue Jun 18 16:12:43 2002
@@ -64,7 +64,8 @@
  *  Master structure
  */
 hashbin_t *irlan = NULL;
-static __u32 ckey, skey;
+static void *ckey;
+static void *skey;
 
 /* Module parameters */
 static int eth = 0; /* Use "eth" or "irlan" name for devices */
diff -u -p linux/net/irda/irnet/irnet.d1.h linux/net/irda/irnet/irnet.h
--- linux/net/irda/irnet/irnet.d1.h	Tue Jun 18 16:13:34 2002
+++ linux/net/irda/irnet/irnet.h	Tue Jun 18 16:14:46 2002
@@ -434,7 +434,7 @@ typedef struct irnet_socket
 
   /* ------------------- IrLMP and IrIAS part ------------------- */
   /* Used for IrDA Discovery and socket name resolution */
-  __u32			ckey;		/* IrLMP client handle */
+  void *		ckey;		/* IrLMP client handle */
   __u16			mask;		/* Hint bits mask (filter discov.)*/
   int			nslots;		/* Number of slots for discovery */
 
diff -u -p linux/net/irda/irnet/irnet_irda.d1.h linux/net/irda/irnet/irnet_irda.h
--- linux/net/irda/irnet/irnet_irda.d1.h	Tue Jun 18 16:13:27 2002
+++ linux/net/irda/irnet/irnet_irda.h	Tue Jun 18 16:15:25 2002
@@ -53,7 +53,7 @@ typedef struct irnet_root
    * reentrant, beware... So, we blindly protect all with spinlock */
 
   /* Handle for the hint bit advertised in IrLMP */
-  __u32			skey;
+  void *		skey;
 
   /* Server socket part */
   struct ias_object *	ias_obj;	/* Our service name + lsap in IAS */
diff -u -p linux/net/irda/irsyms.d1.c linux/net/irda/irsyms.c
--- linux/net/irda/irsyms.d1.c	Tue Jun 18 17:12:31 2002
+++ linux/net/irda/irsyms.c	Tue Jun 18 17:15:33 2002
@@ -328,7 +328,8 @@ void __exit irda_cleanup(void)
  * On the other hand, it needs to be initialised *after* the basic
  * networking, the /proc/net filesystem and sysctl module. Those are
  * currently initialised in .../init/main.c (before initcalls).
- * Also, it needs to be initialised *after* the random number generator.
+ * Also, IrDA drivers needs to be initialised *after* the random number
+ * generator (main stack and higher layer init don't need it anymore).
  *
  * Jean II
  */
