Index: uspace/drv/bus/usb/usbhid/generic/hiddev.c
===================================================================
--- uspace/drv/bus/usb/usbhid/generic/hiddev.c	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/drv/bus/usb/usbhid/generic/hiddev.c	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -201,4 +201,7 @@
 	}
 	usb_log_debug2("%s unbound.\n", fun->name);
+	/* We did not allocate this, so leave this alone
+	 * the device would take care of it */
+	fun->driver_data = NULL;
 	ddf_fun_destroy(fun);
 }
@@ -223,5 +226,4 @@
 
 	fun->ops = &usb_generic_hid_ops;
-	fun->driver_data = hid_dev;
 
 	int rc = ddf_fun_bind(fun);
@@ -232,4 +234,7 @@
 		return rc;
 	}
+	/* This is nasty both device and this function have the same
+	 * driver data, thus destruction would lead to double free */
+	fun->driver_data = hid_dev;
 
 	usb_log_debug("HID function created. Handle: %" PRIun "\n", fun->handle);
Index: uspace/drv/bus/usb/usbhid/main.c
===================================================================
--- uspace/drv/bus/usb/usbhid/main.c	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/drv/bus/usb/usbhid/main.c	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -77,10 +77,9 @@
 	assert(dev != NULL);
 
-	/* 
-	 * Initialize device (get and process descriptors, get address, etc.)
-	 */
+	/* Initialize device (get and process descriptors, get address, etc.) */
 	usb_log_debug("Initializing USB/HID device...\n");
 
-	usb_hid_dev_t *hid_dev = usb_hid_new();
+	usb_hid_dev_t *hid_dev =
+	    usb_device_data_alloc(dev, sizeof(usb_hid_dev_t));
 	if (hid_dev == NULL) {
 		usb_log_error("Error while creating USB/HID device "
Index: uspace/drv/bus/usb/usbhid/usbhid.c
===================================================================
--- uspace/drv/bus/usb/usbhid/usbhid.c	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/drv/bus/usb/usbhid/usbhid.c	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -412,12 +412,20 @@
 /*----------------------------------------------------------------------------*/
 
-usb_hid_dev_t *usb_hid_new(void)
-{
-	usb_hid_dev_t *hid_dev = (usb_hid_dev_t *)calloc(1,
-	    sizeof(usb_hid_dev_t));
+int usb_hid_init(usb_hid_dev_t *hid_dev, usb_device_t *dev)
+{
+	int rc, i;
+
+	usb_log_debug("Initializing HID structure...\n");
 
 	if (hid_dev == NULL) {
-		usb_log_error("No memory!\n");
-		return NULL;
+		usb_log_error("Failed to init HID structure: no structure given"
+		    ".\n");
+		return EINVAL;
+	}
+
+	if (dev == NULL) {
+		usb_log_error("Failed to init HID structure: no USB device"
+		    " given.\n");
+		return EINVAL;
 	}
 
@@ -426,37 +434,11 @@
 	if (hid_dev->report == NULL) {
 		usb_log_error("No memory!\n");
-		free(hid_dev);
-		return NULL;
-	}
-
-	hid_dev->poll_pipe_index = -1;
-
-	return hid_dev;
-}
-
-/*----------------------------------------------------------------------------*/
-
-int usb_hid_init(usb_hid_dev_t *hid_dev, usb_device_t *dev)
-{
-	int rc, i;
-
-	usb_log_debug("Initializing HID structure...\n");
-
-	if (hid_dev == NULL) {
-		usb_log_error("Failed to init HID structure: no structure given"
-		    ".\n");
-		return EINVAL;
-	}
-
-	if (dev == NULL) {
-		usb_log_error("Failed to init HID structure: no USB device"
-		    " given.\n");
-		return EINVAL;
-	}
-
+		return ENOMEM;
+	}
 	usb_hid_report_init(hid_dev->report);
 
 	/* The USB device should already be initialized, save it in structure */
 	hid_dev->usb_dev = dev;
+	hid_dev->poll_pipe_index = -1;
 
 	rc = usb_hid_check_pipes(hid_dev, dev);
Index: uspace/drv/bus/usb/usbhid/usbhid.h
===================================================================
--- uspace/drv/bus/usb/usbhid/usbhid.h	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/drv/bus/usb/usbhid/usbhid.h	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -145,6 +145,4 @@
 /*----------------------------------------------------------------------------*/
 
-usb_hid_dev_t *usb_hid_new(void);
-
 int usb_hid_init(usb_hid_dev_t *hid_dev, usb_device_t *dev);
 
Index: uspace/drv/bus/usb/usbhub/usbhub.c
===================================================================
--- uspace/drv/bus/usb/usbhub/usbhub.c	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/drv/bus/usb/usbhub/usbhub.c	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -117,6 +117,4 @@
 	ddf_fun_destroy(hub->hub_fun);
 
-	free(hub);
-	usb_dev->driver_data = NULL;
 	usb_log_info("USB hub driver, stopped and cleaned.\n");
 	return EOK;
@@ -254,10 +252,10 @@
 {
 	assert(usb_dev);
-	usb_hub_dev_t *hub_dev = malloc(sizeof(usb_hub_dev_t));
+	usb_hub_dev_t *hub_dev =
+	    usb_device_data_alloc(usb_dev, sizeof(usb_hub_dev_t));
 	if (!hub_dev)
 	    return NULL;
 
 	hub_dev->usb_device = usb_dev;
-
 	hub_dev->ports = NULL;
 	hub_dev->port_count = 0;
@@ -266,5 +264,4 @@
 	fibril_mutex_initialize(&hub_dev->pending_ops_mutex);
 	fibril_condvar_initialize(&hub_dev->pending_ops_cv);
-	usb_dev->driver_data = hub_dev;
 
 	return hub_dev;
Index: uspace/drv/bus/usb/usbmast/main.c
===================================================================
--- uspace/drv/bus/usb/usbmast/main.c	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/drv/bus/usb/usbmast/main.c	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -103,5 +103,4 @@
 	}
 	free(mdev->luns);
-	free(mdev);
 	return EOK;
 }
@@ -119,5 +118,5 @@
 
 	/* Allocate softstate */
-	dev->driver_data = mdev = malloc(sizeof(usbmast_dev_t));
+	mdev = usb_device_data_alloc(dev, sizeof(usbmast_dev_t));
 	if (mdev == NULL) {
 		usb_log_error("Failed allocating softstate.\n");
Index: uspace/drv/bus/usb/usbmid/explore.c
===================================================================
--- uspace/drv/bus/usb/usbmid/explore.c	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/drv/bus/usb/usbmid/explore.c	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -163,5 +163,5 @@
 	}
 
-	usb_mid_t *usb_mid = malloc(sizeof(usb_mid_t));
+	usb_mid_t *usb_mid = usb_device_data_alloc(dev, sizeof(usb_mid_t));
 	if (!usb_mid) {
 		usb_log_error("Failed to create USB MID structure.\n");
@@ -173,5 +173,4 @@
 	if (usb_mid->ctl_fun == NULL) {
 		usb_log_error("Failed to create control function.\n");
-		free(usb_mid);
 		return false;
 	}
@@ -184,5 +183,4 @@
 		    str_error(rc));
 		ddf_fun_destroy(usb_mid->ctl_fun);
-		free(usb_mid);
 		return false;
 	}
@@ -209,5 +207,4 @@
 		}
 	}
-	dev->driver_data = usb_mid;
 
 	return true;
Index: uspace/drv/bus/usb/usbmid/main.c
===================================================================
--- uspace/drv/bus/usb/usbmid/main.c	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/drv/bus/usb/usbmid/main.c	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -103,5 +103,4 @@
 		}
 	}
-	free(usb_mid);
 	return ret;
 }
Index: uspace/lib/usbdev/include/usb/dev/driver.h
===================================================================
--- uspace/lib/usbdev/include/usb/dev/driver.h	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/lib/usbdev/include/usb/dev/driver.h	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -173,4 +173,5 @@
 int usb_device_create(ddf_dev_t *, usb_endpoint_description_t **, usb_device_t **, const char **);
 void usb_device_destroy(usb_device_t *);
+void * usb_device_data_alloc(usb_device_t *, size_t);
 
 size_t usb_interface_count_alternates(const uint8_t *, size_t, uint8_t);
Index: uspace/lib/usbdev/src/devdrv.c
===================================================================
--- uspace/lib/usbdev/src/devdrv.c	(revision 7c95d6f581cca56abbce43deed7b2c4c3e46e2b2)
+++ uspace/lib/usbdev/src/devdrv.c	(revision 065064e6a50bbc4c53be7985e161ce57985dd86b)
@@ -152,5 +152,8 @@
 	gen_dev->driver_data = dev;
 
-	return driver->ops->device_add(dev);
+	rc = driver->ops->device_add(dev);
+	if (rc != EOK)
+		usb_device_destroy(dev);
+	return rc;
 }
 /*----------------------------------------------------------------------------*/
@@ -185,7 +188,8 @@
 	if (driver->ops->device_gone == NULL)
 		return ENOTSUP;
-	const int ret = driver->ops->device_gone(gen_dev->driver_data);
+	usb_device_t *usb_dev = gen_dev->driver_data;
+	const int ret = driver->ops->device_gone(usb_dev);
 	if (ret == EOK)
-		usb_device_destroy(gen_dev->driver_data);
+		usb_device_destroy(usb_dev);
 
 	return ret;
@@ -595,6 +599,5 @@
 
 	/* Ignore errors and hope for the best. */
-	usb_device_destroy_pipes(dev->ddf_dev, dev->pipes, dev->pipes_count);
-	free(dev->descriptors.configuration);
+	destroy_current_pipes(dev);
 
 	if (dev->alternate_interfaces != NULL) {
@@ -602,6 +605,14 @@
 	}
 	free(dev->alternate_interfaces);
-
-	free(dev);
+	free(dev->descriptors.configuration);
+	free(dev->driver_data);
+}
+
+void * usb_device_data_alloc(usb_device_t *usb_dev, size_t size)
+{
+	assert(usb_dev);
+	assert(usb_dev->driver_data == NULL);
+	return usb_dev->driver_data = calloc(1, size);
+
 }
 
