Index: uspace/drv/uhci-hcd/iface.c
===================================================================
--- uspace/drv/uhci-hcd/iface.c	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/iface.c	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -110,5 +110,5 @@
 
 	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_INTERRUPT,
-	    max_packet_size, speed, data, size, NULL, callback, arg);
+	    max_packet_size, speed, data, size, NULL, 0, NULL, callback, arg);
 	if (!tracker)
 		return ENOMEM;
@@ -125,5 +125,5 @@
 
 	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_INTERRUPT,
-	    max_packet_size, speed, data, size, callback, NULL, arg);
+	    max_packet_size, speed, data, size, NULL, 0, callback, NULL, arg);
 	if (!tracker)
 		return ENOMEM;
@@ -140,8 +140,9 @@
 
 	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
-	    max_packet_size, speed, data, size, NULL, callback, arg);
-	if (!tracker)
-		return ENOMEM;
-	tracker_control_write(tracker, setup_data, setup_size);
+	    max_packet_size, speed, data, size, setup_data, setup_size,
+	    NULL, callback, arg);
+	if (!tracker)
+		return ENOMEM;
+	tracker_control_write(tracker);
 	return EOK;
 }
@@ -155,8 +156,9 @@
 
 	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
-	    max_packet_size, speed, data, size, callback, NULL, arg);
-	if (!tracker)
-		return ENOMEM;
-	tracker_control_read(tracker, setup_data, setup_size);
+	    max_packet_size, speed, data, size, setup_data, setup_size, callback,
+	    NULL, arg);
+	if (!tracker)
+		return ENOMEM;
+	tracker_control_read(tracker);
 	return EOK;
 }
@@ -166,7 +168,10 @@
     usbhc_iface_transfer_out_callback_t callback, void *arg)
 {
-	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
-	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
-	    8, FULL_SPEED, data, size, NULL, callback, arg);
+	size_t max_packet_size = 8;
+	dev_speed_t speed = FULL_SPEED;
+
+	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
+	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
+	    max_packet_size, speed, NULL, 0, data, size, NULL, callback, arg);
 	if (!tracker)
 		return ENOMEM;
@@ -179,7 +184,10 @@
     usbhc_iface_transfer_out_callback_t callback, void *arg)
 {
-	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
-	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
-	    size, FULL_SPEED, data, size, NULL, callback, arg);
+	size_t max_packet_size = 8;
+	dev_speed_t speed = FULL_SPEED;
+
+	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
+	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
+	    max_packet_size, speed, data, size, NULL, 0, NULL, callback, arg);
 	if (!tracker)
 		return ENOMEM;
@@ -191,7 +199,10 @@
     usbhc_iface_transfer_in_callback_t callback, void *arg)
 {
-	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
-	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
-	    0, FULL_SPEED, NULL, 0, callback, NULL, arg);
+	size_t max_packet_size = 8;
+	dev_speed_t speed = FULL_SPEED;
+
+	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
+	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
+	    max_packet_size, speed, NULL, 0, NULL, 0, callback, NULL, arg);
 	if (!tracker)
 		return ENOMEM;
@@ -204,7 +215,10 @@
     usbhc_iface_transfer_out_callback_t callback, void *arg)
 {
-	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
-	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
-	    8, FULL_SPEED, data, size, NULL, callback, arg);
+	size_t max_packet_size = 8;
+	dev_speed_t speed = FULL_SPEED;
+
+	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
+	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
+	    max_packet_size, speed, NULL, 0, data, size, NULL, callback, arg);
 	if (!tracker)
 		return ENOMEM;
@@ -217,7 +231,10 @@
     usbhc_iface_transfer_in_callback_t callback, void *arg)
 {
-	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
-	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
-	    size, FULL_SPEED, data, size, callback, NULL, arg);
+	size_t max_packet_size = 8;
+	dev_speed_t speed = FULL_SPEED;
+
+	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
+	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
+	    max_packet_size, speed, data, size, NULL, 0, callback, NULL, arg);
 	if (!tracker)
 		return ENOMEM;
@@ -229,7 +246,10 @@
     usbhc_iface_transfer_out_callback_t callback, void *arg)
 {
-	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
-	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
-	    0, FULL_SPEED, NULL, 0, NULL, callback, arg);
+	size_t max_packet_size = 8;
+	dev_speed_t speed = FULL_SPEED;
+
+	usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
+	tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
+	    max_packet_size, speed, NULL, 0, NULL, 0, NULL, callback, arg);
 	if (!tracker)
 		return ENOMEM;
Index: uspace/drv/uhci-hcd/main.c
===================================================================
--- uspace/drv/uhci-hcd/main.c	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/main.c	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -134,5 +134,5 @@
 	 */
 	sleep(5);
-	usb_log_enable(USB_LOG_LEVEL_INFO, NAME);
+	usb_log_enable(USB_LOG_LEVEL_DEBUG2, NAME);
 
 	return driver_main(&uhci_driver);
Index: uspace/drv/uhci-hcd/tracker.c
===================================================================
--- uspace/drv/uhci-hcd/tracker.c	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/tracker.c	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -41,15 +41,7 @@
 #include "utils/malloc32.h"
 
-#define SETUP_PACKET_DATA_SIZE 8
 #define DEFAULT_ERROR_COUNT 3
-#define MAX(a,b) ((a > b) ? a : b)
-#define MIN(a,b) ((a < b) ? a : b)
 
 static int tracker_schedule(tracker_t *instance);
-
-static void tracker_control_read_data(tracker_t *instance);
-static void tracker_control_write_data(tracker_t *instance);
-static void tracker_control_read_status(tracker_t *instance);
-static void tracker_control_write_status(tracker_t *instance);
 
 static void tracker_call_in(tracker_t *instance);
@@ -62,4 +54,5 @@
     usb_transfer_type_t transfer_type, size_t max_packet_size,
     dev_speed_t speed, char *buffer, size_t size,
+    char* setup_buffer, size_t setup_size,
     usbhc_iface_transfer_in_callback_t func_in,
     usbhc_iface_transfer_out_callback_t func_out, void *arg)
@@ -69,29 +62,59 @@
 
 	tracker_t *instance = malloc(sizeof(tracker_t));
-	if (!instance) {
-		usb_log_error("Failed to allocate tracker isntance.\n");
-		return NULL;
-	}
-
-	instance->td = malloc32(sizeof(transfer_descriptor_t));
-	if (!instance->td) {
-		usb_log_error("Failed to allocate transfer descriptor.\n");
+	if (instance == NULL) {
+		usb_log_error("Failed to allocate tracker instance.\n");
+		return NULL;
+	}
+
+	instance->qh = queue_head_get();
+	if (instance->qh == NULL) {
+		usb_log_error("Failed to allocate queue head.\n");
 		free(instance);
 		return NULL;
 	}
-	bzero(instance->td, sizeof(transfer_descriptor_t));
-
-	instance->packet = max_packet_size ? malloc32(max_packet_size) : NULL;
-	if (max_packet_size && !instance->packet) {
-		usb_log_error("Failed to allocate device acessible buffer.\n");
-		free32(instance->td);
+
+	instance->packets = (size + max_packet_size - 1) / max_packet_size;
+	if (transfer_type == USB_TRANSFER_CONTROL) {
+		instance->packets += 2;
+	}
+
+	instance->tds = malloc32(sizeof(transfer_descriptor_t) * instance->packets);
+	if (instance->tds == NULL) {
+		usb_log_error("Failed to allocate transfer descriptors.\n");
+		queue_head_dispose(instance->qh);
 		free(instance);
 		return NULL;
 	}
+	bzero(instance->tds, sizeof(transfer_descriptor_t) * instance->packets);
+
+	const size_t transport_size = max_packet_size * instance->packets;
+
+	instance->transport_buffer =
+	   (size > 0) ? malloc32(transport_size) : NULL;
+	if ((size > 0) && (instance->transport_buffer == NULL)) {
+		usb_log_error("Failed to allocate device accessible buffer.\n");
+		queue_head_dispose(instance->qh);
+		free32(instance->tds);
+		free(instance);
+		return NULL;
+	}
+
+	instance->setup_buffer = setup_buffer ? malloc32(setup_size) : NULL;
+	if ((setup_size > 0) && (instance->setup_buffer == NULL)) {
+		usb_log_error("Failed to allocate device accessible setup buffer.\n");
+		queue_head_dispose(instance->qh);
+		free32(instance->tds);
+		free32(instance->transport_buffer);
+		free(instance);
+		return NULL;
+	}
+	if (instance->setup_buffer) {
+		memcpy(instance->setup_buffer, setup_buffer, setup_size);
+	}
+
 	instance->max_packet_size = max_packet_size;
-	instance->packet_size = 0;
-	instance->buffer_offset = 0;
 
 	link_initialize(&instance->link);
+
 	instance->target = target;
 	instance->transfer_type = transfer_type;
@@ -101,253 +124,146 @@
 	if (func_in)
 		instance->callback_in = func_in;
+
 	instance->buffer = buffer;
 	instance->buffer_size = size;
+	instance->setup_size = setup_size;
 	instance->dev = dev;
 	instance->arg = arg;
-	instance->toggle = 0;
 	instance->speed = speed;
 
+	queue_head_element_td(instance->qh, addr_to_phys(instance->tds));
 	return instance;
 }
 /*----------------------------------------------------------------------------*/
-void tracker_control_write(
-    tracker_t *instance, char* setup_buffer, size_t setup_size)
-{
-	assert(instance);
-	assert(instance->buffer_offset == 0);
-	assert(setup_size == 8);
-
-	instance->packet_size = 0;
-	memcpy(instance->packet, setup_buffer, setup_size);
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    setup_size, instance->toggle++, false, instance->target,
-	    USB_PID_SETUP, instance->packet);
-
-	instance->next_step = tracker_control_write_data;
-
-	tracker_schedule(instance);
-}
-/*----------------------------------------------------------------------------*/
-void tracker_control_read(
-    tracker_t *instance, char* setup_buffer, size_t setup_size)
-{
-	assert(instance);
-	assert(instance->buffer_offset == 0);
-	assert(setup_size == 8);
-
-	memcpy(instance->packet, setup_buffer, setup_size);
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    setup_size, instance->toggle++, false, instance->target,
-	    USB_PID_SETUP, instance->packet);
-
-	instance->next_step = tracker_control_read_data;
-
-	tracker_schedule(instance);
-}
-/*----------------------------------------------------------------------------*/
-void tracker_control_read_data(tracker_t *instance)
-{
-	assert(instance);
-
-	/* check for errors */
-	int err = transfer_descriptor_status(instance->td);
-	if (err != EOK) {
-		tracker_call_in_and_dispose(instance);
-		return;
-	}
-
-	/* we are data in, we want data from our device */
-	if (instance->packet_size) {
-		memcpy(instance->buffer + instance->buffer_offset, instance->packet,
-		    instance->packet_size);
-	}
-	instance->buffer_offset += instance->packet_size;
-
-	/* prepare next packet, no copy, we are receiving data */
-	instance->packet_size =	MIN(instance->max_packet_size,
-	    instance->buffer_size - instance->buffer_offset);
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, instance->toggle++, false, instance->target,
-	    USB_PID_IN, instance->packet);
-
-	tracker_schedule(instance);
-
-	/* set next step */
-	if ((instance->buffer_offset + instance->packet_size)
-	    >= instance->buffer_size) {
-		/* that's all, end coomunication */
-		instance->next_step = tracker_control_read_status;
-	}
-}
-/*----------------------------------------------------------------------------*/
-void tracker_control_write_data(tracker_t *instance)
-{
-	assert(instance);
-
-	/* check for errors */
-	int err = transfer_descriptor_status(instance->td);
-	if (err != EOK) {
-		tracker_call_out_and_dispose(instance);
-		return;
-	}
-
-	/* we are data out, we don't want data from our device */
-	instance->buffer_offset += instance->packet_size;
-
-	/* prepare next packet, copy data to packet */
-	instance->packet_size =	MIN(instance->max_packet_size,
-	    instance->buffer_size - instance->buffer_offset);
-	memcpy(instance->packet, instance->buffer + instance->buffer_offset,
-	    instance->packet_size);
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, instance->toggle++, false, instance->target,
-	    USB_PID_OUT, instance->packet);
-
-	tracker_schedule(instance);
-
-	/* set next step */
-	if ((instance->buffer_offset + instance->packet_size)
-	    >= instance->buffer_size) {
-		/* that's all, end coomunication */
-		instance->next_step = tracker_control_write_status;
-	}
-}
-/*----------------------------------------------------------------------------*/
-void tracker_control_read_status(tracker_t *instance)
-{
-	assert(instance);
-
-	/* check for errors */
-	int err = transfer_descriptor_status(instance->td);
-	if (err != EOK) {
-		tracker_call_in_and_dispose(instance);
-		return;
-	}
-
-	/* we are data in, we want data from our device */
-	memcpy(instance->buffer + instance->buffer_offset, instance->packet,
-	    instance->packet_size);
-	instance->buffer_offset += instance->packet_size;
-	assert(instance->buffer_offset = instance->buffer_size);
-
-	/* prepare next packet, no nothing, just an empty packet */
-	instance->packet_size =	0;
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, 1, false, instance->target, USB_PID_OUT, NULL);
-
-	tracker_schedule(instance);
-
-	/* set next step, callback and cleanup */
+bool tracker_is_complete(tracker_t *instance)
+{
+	assert(instance);
+	usb_log_debug("Checking(%p) %d packet for completion.\n",
+	    instance, instance->packets);
+	/* This is just an ugly trick to support the old API */
+	instance->transfered_size = -instance->setup_size;
+	size_t i = 0;
+	for (;i < instance->packets; ++i) {
+		if (transfer_descriptor_is_active(&instance->tds[i]))
+			return false;
+		instance->error = transfer_descriptor_status(&instance->tds[i]);
+		if (instance->error != EOK) {
+			return true;
+		}
+		instance->transfered_size +=
+		    transfer_descriptor_actual_size(&instance->tds[i]);
+	}
+	return true;
+}
+/*----------------------------------------------------------------------------*/
+void tracker_control_write(tracker_t *instance)
+{
+	assert(instance);
+
+	/* we are data out, we are supposed to provide data */
+	memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size);
+
+	int toggle = 0;
+	/* setup stage */
+	transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
+	    instance->setup_size, toggle, false, instance->target,
+	    USB_PID_SETUP, instance->setup_buffer, &instance->tds[1]);
+
+	/* data stage */
+	size_t i = 1;
+	for (;i < instance->packets - 1; ++i) {
+		char *data =
+		    instance->transport_buffer + ((i - 1) * instance->max_packet_size);
+		toggle = 1 - toggle;
+
+		transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
+		    instance->max_packet_size, toggle++, false, instance->target,
+		    USB_PID_OUT, data, &instance->tds[i + 1]);
+	}
+
+	/* status stage */
+	i = instance->packets - 1;
+	transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
+	    0, 1, false, instance->target, USB_PID_IN, NULL, NULL);
+
+	instance->next_step = tracker_call_out_and_dispose;
+	tracker_schedule(instance);
+}
+/*----------------------------------------------------------------------------*/
+void tracker_control_read(tracker_t *instance)
+{
+	assert(instance);
+
+	int toggle = 0;
+	/* setup stage */
+	transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
+	    instance->setup_size, toggle, false, instance->target,
+	    USB_PID_SETUP, instance->setup_buffer, &instance->tds[1]);
+
+	/* data stage */
+	size_t i = 1;
+	for (;i < instance->packets - 1; ++i) {
+		char *data =
+		    instance->transport_buffer + ((i - 1) * instance->max_packet_size);
+		toggle = 1 - toggle;
+
+		transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
+		    instance->max_packet_size, toggle, false, instance->target,
+		    USB_PID_IN, data, &instance->tds[i + 1]);
+	}
+
+	/* status stage */
+	i = instance->packets - 1;
+	transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
+	    0, 1, false, instance->target, USB_PID_OUT, NULL, NULL);
+
 	instance->next_step = tracker_call_in_and_dispose;
-}
-/*----------------------------------------------------------------------------*/
-void tracker_control_write_status(tracker_t *instance)
-{
-	assert(instance);
-
-	/* check for errors */
-	int err = transfer_descriptor_status(instance->td);
-	if (err != EOK) {
-		tracker_call_out_and_dispose(instance);
-		return;
-	}
-
-	/* we are data in, we want data from our device */
-	assert(
-	    instance->buffer_offset + instance->packet_size <= instance->buffer_size);
-	memcpy(instance->buffer + instance->buffer_offset, instance->packet,
-	    instance->packet_size);
-	instance->buffer_offset += instance->packet_size;
-	assert(instance->buffer_offset = instance->buffer_size);
-
-	/* prepare next packet, no nothing, just an empty packet */
-	instance->packet_size =	0;
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, 1, false, instance->target, USB_PID_IN, NULL);
-
-	tracker_schedule(instance);
-
-	/* set next step, callback and cleanup */
+	tracker_schedule(instance);
+}
+/*----------------------------------------------------------------------------*/
+void tracker_interrupt_in(tracker_t *instance)
+{
+	assert(instance);
+
+	int toggle = 1;
+	size_t i = 0;
+	for (;i < instance->packets; ++i) {
+		char *data =
+		    instance->transport_buffer + (i  * instance->max_packet_size);
+		transfer_descriptor_t *next = (i + 1) < instance->packets ?
+		    &instance->tds[i + 1] : NULL;
+		toggle = 1 - toggle;
+
+		transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
+		    instance->max_packet_size, toggle, false, instance->target,
+		    USB_PID_IN, data, next);
+	}
+
+	instance->next_step = tracker_call_in_and_dispose;
+	tracker_schedule(instance);
+}
+/*----------------------------------------------------------------------------*/
+void tracker_interrupt_out(tracker_t *instance)
+{
+	assert(instance);
+
+	memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size);
+
+	int toggle = 1;
+	size_t i = 0;
+	for (;i < instance->packets; ++i) {
+		char *data =
+		    instance->transport_buffer + (i  * instance->max_packet_size);
+		transfer_descriptor_t *next = (i + 1) < instance->packets ?
+		    &instance->tds[i + 1] : NULL;
+		toggle = 1 - toggle;
+
+		transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
+		    instance->max_packet_size, toggle++, false, instance->target,
+		    USB_PID_OUT, data, next);
+	}
+
 	instance->next_step = tracker_call_out_and_dispose;
-}
-/*----------------------------------------------------------------------------*/
-void tracker_interrupt_in(tracker_t *instance)
-{
-	assert(instance);
-
-	/* check for errors */
-	int err = transfer_descriptor_status(instance->td);
-	if (err != EOK) {
-		tracker_call_in_and_dispose(instance);
-		return;
-	}
-
-	assert(instance->packet_size <= instance->max_packet_size);
-	if (instance->packet_size) {
-		/* we are data in, we want data from our device. if there is data */
-		memcpy(instance->buffer + instance->buffer_offset, instance->packet,
-				instance->packet_size);
-		instance->buffer_offset += instance->packet_size;
-	}
-
-	/* prepare next packet, no copy, we are receiving data */
-	instance->packet_size =	MIN(instance->max_packet_size,
-			instance->buffer_size - instance->buffer_offset);
-	assert(instance->packet_size <= instance->max_packet_size);
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, instance->toggle++, false, instance->target,
-	    USB_PID_IN, instance->packet);
-
-	tracker_schedule(instance);
-
-	/* set next step */
-	if ((instance->buffer_offset + instance->packet_size)
-	    >= instance->buffer_size) {
-		/* that's all, end coomunication */
-		instance->next_step = tracker_call_in_and_dispose;
-	} else {
-		instance->next_step = tracker_interrupt_in;
-	}
-}
-/*----------------------------------------------------------------------------*/
-void tracker_interrupt_out(tracker_t *instance)
-{
-	assert(instance);
-
-	/* check for errors */
-	int err = transfer_descriptor_status(instance->td);
-	if (err != EOK) {
-		tracker_call_out_and_dispose(instance);
-		return;
-	}
-
-	/* we are data out, we don't want data from our device */
-	instance->buffer_offset += instance->packet_size;
-
-	/* prepare next packet, copy data to packet */
-	instance->packet_size =	MIN(instance->max_packet_size,
-	    instance->buffer_size - instance->buffer_offset);
-	memcpy(instance->packet, instance->buffer + instance->buffer_offset,
-	    instance->packet_size);
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, instance->toggle++, false, instance->target,
-	    USB_PID_OUT, instance->packet);
-
-	tracker_schedule(instance);
-
-	/* set next step */
-	if ((instance->buffer_offset + instance->packet_size)
-	    >= instance->buffer_size) {
-		/* that's all, end coomunication */
-		instance->next_step = tracker_call_out_and_dispose;
-	} else {
-		instance->next_step = tracker_interrupt_out;
-	}
+	tracker_schedule(instance);
 }
 /*----------------------------------------------------------------------------*/
@@ -357,15 +273,12 @@
 	assert(instance->callback_in);
 
-	/* check for errors */
-	int err = transfer_descriptor_status(instance->td);
-	if (err == EOK && instance->packet_size) {
-		memcpy(instance->buffer + instance->buffer_offset, instance->packet,
-		    instance->packet_size);
-		instance->buffer_offset += instance->packet_size;
-	}
-	usb_log_debug("Callback IN(%d): %d, %zu.\n", instance->transfer_type,
-	    err, instance->buffer_offset);
+	memcpy(instance->buffer, instance->transport_buffer, instance->buffer_size);
+
+	int err = instance->error;
+	usb_log_info("Callback IN(%d): %d, %zu.\n", instance->transfer_type,
+	    err, instance->transfered_size);
+
 	instance->callback_in(instance->dev,
-	    err ? USB_OUTCOME_CRCERROR : USB_OUTCOME_OK, instance->buffer_offset,
+	    err, instance->transfered_size,
 	    instance->arg);
 }
@@ -376,10 +289,8 @@
 	assert(instance->callback_out);
 
-	/* check for errors */
-	int err = transfer_descriptor_status(instance->td);
-	usb_log_debug("Callback OUT(%d): %d, %zu.\n", instance->transfer_type,
-	    err, instance->buffer_offset);
+	int err = instance->error;
+	usb_log_info("Callback OUT(%d): %d.\n", instance->transfer_type, err);
 	instance->callback_out(instance->dev,
-	    err ? USB_OUTCOME_CRCERROR : USB_OUTCOME_OK, instance->arg);
+	    err, instance->arg);
 }
 /*----------------------------------------------------------------------------*/
@@ -388,7 +299,9 @@
 	assert(instance);
 	tracker_call_in(instance);
-	transfer_list_remove_tracker(instance->scheduled_list, instance);
-	free32(instance->td);
-	free32(instance->packet);
+	usb_log_debug("Disposing tracker: %p.\n", instance);
+	free32(instance->tds);
+	free32(instance->qh);
+	free32(instance->setup_buffer);
+	free32(instance->transport_buffer);
 	free(instance);
 }
@@ -398,8 +311,9 @@
 	assert(instance);
 	tracker_call_out(instance);
-	assert(instance->scheduled_list);
-	transfer_list_remove_tracker(instance->scheduled_list, instance);
-	free32(instance->td);
-	free32(instance->packet);
+	usb_log_debug("Disposing tracker: %p.\n", instance);
+	free32(instance->tds);
+	free32(instance->qh);
+	free32(instance->setup_buffer);
+	free32(instance->transport_buffer);
 	free(instance);
 }
@@ -417,82 +331,46 @@
 {
 	assert(instance);
-	assert(instance->buffer_offset == 0);
-
-	instance->packet_size = SETUP_PACKET_DATA_SIZE;
-	memcpy(instance->packet, instance->buffer, SETUP_PACKET_DATA_SIZE);
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    SETUP_PACKET_DATA_SIZE, 0, false, instance->target, USB_PID_SETUP,
-	    instance->packet);
-
-	instance->buffer_offset += SETUP_PACKET_DATA_SIZE;
+	instance->packets = 1;
+
+	/* setup stage */
+	transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
+	    instance->setup_size, 0, false, instance->target,
+	    USB_PID_SETUP, instance->setup_buffer, NULL);
+
 	instance->next_step = tracker_call_out_and_dispose;
-
-	tracker_schedule(instance);
-}
-
+	tracker_schedule(instance);
+}
+/*----------------------------------------------------------------------------*/
 void tracker_control_write_data_old(tracker_t *instance)
 {
 	assert(instance);
-	assert(instance->max_packet_size == instance->buffer_size);
-
-	memcpy(instance->packet, instance->buffer, instance->max_packet_size);
-	instance->packet_size = instance->max_packet_size;
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, 1, false, instance->target, USB_PID_OUT,
-	    instance->packet);
+	instance->packets -= 2;
+	tracker_interrupt_out(instance);
+}
+/*----------------------------------------------------------------------------*/
+void tracker_control_read_data_old(tracker_t *instance)
+{
+	assert(instance);
+	instance->packets -= 2;
+	tracker_interrupt_in(instance);
+}
+/*----------------------------------------------------------------------------*/
+void tracker_control_write_status_old(tracker_t *instance)
+{
+	assert(instance);
+	instance->packets = 1;
+	transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
+	    0, 1, false, instance->target, USB_PID_IN, NULL, NULL);
+	instance->next_step = tracker_call_in_and_dispose;
+	tracker_schedule(instance);
+}
+/*----------------------------------------------------------------------------*/
+void tracker_control_read_status_old(tracker_t *instance)
+{
+	assert(instance);
+	instance->packets = 1;
+	transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
+	    0, 1, false, instance->target, USB_PID_OUT, NULL, NULL);
 	instance->next_step = tracker_call_out_and_dispose;
-
-	tracker_schedule(instance);
-}
-
-void tracker_control_read_data_old(tracker_t *instance)
-{
-	assert(instance);
-	assert(instance->max_packet_size == instance->buffer_size);
-
-	instance->packet_size = instance->max_packet_size;
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, 1, false, instance->target, USB_PID_IN,
-	    instance->packet);
-
-	instance->next_step = tracker_call_in_and_dispose;
-
-	tracker_schedule(instance);
-}
-
-void tracker_control_write_status_old(tracker_t *instance)
-{
-	assert(instance);
-	assert(instance->max_packet_size == 0);
-	assert(instance->buffer_size == 0);
-	assert(instance->packet == NULL);
-
-	instance->packet_size = instance->max_packet_size;
-	instance->next_step = tracker_call_in_and_dispose;
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, 1, false, instance->target, USB_PID_IN,
-	    instance->packet);
-
-	tracker_schedule(instance);
-}
-
-void tracker_control_read_status_old(tracker_t *instance)
-{
-	assert(instance);
-	assert(instance->max_packet_size == 0);
-	assert(instance->buffer_size == 0);
-	assert(instance->packet == NULL);
-
-	instance->packet_size = instance->max_packet_size;
-	instance->next_step = tracker_call_out_and_dispose;
-
-	transfer_descriptor_init(instance->td, DEFAULT_ERROR_COUNT,
-	    instance->packet_size, 1, false, instance->target, USB_PID_OUT,
-	    instance->packet);
-
 	tracker_schedule(instance);
 }
Index: uspace/drv/uhci-hcd/tracker.h
===================================================================
--- uspace/drv/uhci-hcd/tracker.h	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/tracker.h	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -41,4 +41,5 @@
 
 #include "uhci_struct/transfer_descriptor.h"
+#include "uhci_struct/queue_head.h"
 
 typedef enum {
@@ -47,9 +48,8 @@
 } dev_speed_t;
 
-struct transfer_list;
-
 typedef struct tracker
 {
 	link_t link;
+	dev_speed_t speed;
 	usb_target_t target;
 	usb_transfer_type_t transfer_type;
@@ -59,31 +59,31 @@
 	};
 	void *arg;
+	char *transport_buffer;
+	char *setup_buffer;
+	size_t setup_size;
 	char *buffer;
-	char *packet;
 	size_t buffer_size;
 	size_t max_packet_size;
-	size_t packet_size;
-	size_t buffer_offset;
-	dev_speed_t speed;
+	size_t packets;
+	size_t transfered_size;
+	int error;
 	device_t *dev;
-	transfer_descriptor_t *td;
+	queue_head_t *qh;
+	transfer_descriptor_t *tds;
 	void (*next_step)(struct tracker*);
-	unsigned toggle:1;
-
-	struct transfer_list *scheduled_list;
 } tracker_t;
-
 
 tracker_t * tracker_get(device_t *dev, usb_target_t target,
     usb_transfer_type_t transfer_type, size_t max_packet_size,
     dev_speed_t speed, char *buffer, size_t size,
+		char *setup_buffer, size_t setup_size,
     usbhc_iface_transfer_in_callback_t func_in,
     usbhc_iface_transfer_out_callback_t func_out, void *arg);
 
-void tracker_control_write(
-    tracker_t *instance, char* setup_buffer, size_t setup_size);
+bool tracker_is_complete(tracker_t *instance);
 
-void tracker_control_read(
-    tracker_t *instance, char* setup_buffer, size_t setup_size);
+void tracker_control_write(tracker_t *instance);
+
+void tracker_control_read(tracker_t *instance);
 
 void tracker_interrupt_in(tracker_t *instance);
Index: uspace/drv/uhci-hcd/transfer_list.c
===================================================================
--- uspace/drv/uhci-hcd/transfer_list.c	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/transfer_list.c	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -51,4 +51,5 @@
 
 	queue_head_init(instance->queue_head);
+	list_initialize(&instance->tracker_list);
 	return EOK;
 }
@@ -58,8 +59,7 @@
 	assert(instance);
 	assert(next);
-	instance->next = next;
 	if (!instance->queue_head)
 		return;
-	queue_head_add_next(instance->queue_head, next->queue_head_pa);
+	queue_head_append_qh(instance->queue_head, next->queue_head_pa);
 }
 /*----------------------------------------------------------------------------*/
@@ -69,46 +69,64 @@
 	assert(tracker);
 
-	uint32_t pa = (uintptr_t)addr_to_phys(tracker->td);
+	uint32_t pa = (uintptr_t)addr_to_phys(tracker->qh);
 	assert((pa & LINK_POINTER_ADDRESS_MASK) == pa);
+	pa |= LINK_POINTER_QUEUE_HEAD_FLAG;
 
 
-	if (instance->queue_head->element & LINK_POINTER_TERMINATE_FLAG) {
-		usb_log_debug2("Adding td(%X:%X) to queue %s first.\n",
-			tracker->td->status, tracker->td->device, instance->name);
+	if ((instance->queue_head->element & LINK_POINTER_TERMINATE_FLAG) != 0) {
 		/* there is nothing scheduled */
-		instance->last_tracker = tracker;
+		list_append(&tracker->link, &instance->tracker_list);
 		instance->queue_head->element = pa;
-		usb_log_debug2("Added td(%X:%X) to queue %s first.\n",
-			tracker->td->status, tracker->td->device, instance->name);
+		usb_log_debug2("Added tracker(%p) to queue %s first.\n",
+			tracker, instance->name);
 		return;
 	}
-	usb_log_debug2("Adding td(%X:%X) to queue %s last.%p\n",
-	    tracker->td->status, tracker->td->device, instance->name,
-	    instance->last_tracker);
-	/* now we can be sure that last_tracker is a valid pointer */
-	instance->last_tracker->td->next = pa;
-	instance->last_tracker = tracker;
-
-	usb_log_debug2("Added td(%X:%X) to queue %s last.\n",
-		tracker->td->status, tracker->td->device, instance->name);
-
-	/* check again, may be use atomic compare and swap */
-	if (instance->queue_head->element & LINK_POINTER_TERMINATE_FLAG) {
-		instance->queue_head->element = pa;
-		usb_log_debug2("Added td(%X:%X) to queue first2 %s.\n",
-			tracker->td->status, tracker->td->device, instance->name);
-	}
+	/* now we can be sure that there is someting scheduled */
+	assert(!list_empty(&instance->tracker_list));
+	tracker_t *first = list_get_instance(
+	          instance->tracker_list.next, tracker_t, link);
+	tracker_t *last = list_get_instance(
+	    instance->tracker_list.prev, tracker_t, link);
+	queue_head_append_qh(last->qh, pa);
+	list_append(&tracker->link, &instance->tracker_list);
+	usb_log_debug2("Added tracker(%p) to queue %s last, first is %p.\n",
+		tracker, instance->name, first );
 }
 /*----------------------------------------------------------------------------*/
-void transfer_list_remove_tracker(transfer_list_t *instance, tracker_t *tracker)
+static void transfer_list_remove_tracker(
+    transfer_list_t *instance, tracker_t *tracker)
 {
 	assert(instance);
 	assert(tracker);
 	assert(instance->queue_head);
-	assert(tracker->td);
+	assert(tracker->qh);
 
-	uint32_t pa = (uintptr_t)addr_to_phys(tracker->td);
-	if ((instance->queue_head->element & LINK_POINTER_ADDRESS_MASK) == pa) {
-		instance->queue_head->element = tracker->td->next;
+	/* I'm the first one here */
+	if (tracker->link.next == &instance->tracker_list) {
+		usb_log_debug("Removing tracer %p was first, next element %x.\n",
+			tracker, tracker->qh->next_queue);
+		instance->queue_head->element = tracker->qh->next_queue;
+	} else {
+		usb_log_debug("Removing tracer %p was NOT first, next element %x.\n",
+			tracker, tracker->qh->next_queue);
+		tracker_t *prev = list_get_instance(tracker->link.prev, tracker_t, link);
+		prev->qh->next_queue = tracker->qh->next_queue;
+	}
+	list_remove(&tracker->link);
+}
+/*----------------------------------------------------------------------------*/
+void transfer_list_check(transfer_list_t *instance)
+{
+	assert(instance);
+	link_t *current = instance->tracker_list.next;
+	while (current != &instance->tracker_list) {
+		link_t *next = current->next;
+		tracker_t *tracker = list_get_instance(current, tracker_t, link);
+
+		if (tracker_is_complete(tracker)) {
+			transfer_list_remove_tracker(instance, tracker);
+			tracker->next_step(tracker);
+		}
+		current = next;
 	}
 }
Index: uspace/drv/uhci-hcd/transfer_list.h
===================================================================
--- uspace/drv/uhci-hcd/transfer_list.h	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/transfer_list.h	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -41,10 +41,9 @@
 typedef struct transfer_list
 {
-	tracker_t *last_tracker;
-
 	queue_head_t *queue_head;
 	uint32_t queue_head_pa;
 	struct transfer_list *next;
 	const char *name;
+	link_t tracker_list;
 } transfer_list_t;
 
@@ -59,9 +58,7 @@
 	queue_head_dispose(instance->queue_head);
 }
+void transfer_list_check(transfer_list_t *instance);
 
 void transfer_list_add_tracker(transfer_list_t *instance, tracker_t *tracker);
-
-void transfer_list_remove_tracker(transfer_list_t *instance, tracker_t *track);
-
 #endif
 /**
Index: uspace/drv/uhci-hcd/uhci.c
===================================================================
--- uspace/drv/uhci-hcd/uhci.c	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/uhci.c	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -158,17 +158,11 @@
 	const int low_speed = (tracker->speed == LOW_SPEED);
 	if (!allowed_usb_packet(
-	    low_speed, tracker->transfer_type, tracker->packet_size)) {
+	    low_speed, tracker->transfer_type, tracker->max_packet_size)) {
 		usb_log_warning("Invalid USB packet specified %s SPEED %d %zu.\n",
 			  low_speed ? "LOW" : "FULL" , tracker->transfer_type,
-		    tracker->packet_size);
+		    tracker->max_packet_size);
 		return ENOTSUP;
 	}
 	/* TODO: check available bandwith here */
-
-	usb_log_debug2("Scheduler(%d) acquiring tracker list mutex.\n",
-	    fibril_get_id());
-	fibril_mutex_lock(&instance->tracker_list_mutex);
-	usb_log_debug2("Scheduler(%d) acquired tracker list mutex.\n",
-	    fibril_get_id());
 
 	transfer_list_t *list =
@@ -176,13 +170,4 @@
 	assert(list);
 	transfer_list_add_tracker(list, tracker);
-	list_append(&tracker->link, &instance->tracker_list);
-
-	tracker->scheduled_list = list;
-
-	usb_log_debug2("Scheduler(%d) releasing tracker list mutex.\n",
-	    fibril_get_id());
-	fibril_mutex_unlock(&instance->tracker_list_mutex);
-	usb_log_debug2("Scheduler(%d) released tracker list mutex.\n",
-	    fibril_get_id());
 
 	return EOK;
@@ -196,46 +181,8 @@
 
 	while(1) {
-		LIST_INITIALIZE(done_trackers);
-		/* tracker iteration */
-
-		usb_log_debug2("Cleaner(%d) acquiring tracker list mutex.\n",
-		    fibril_get_id());
-		fibril_mutex_lock(&instance->tracker_list_mutex);
-		usb_log_debug2("Cleaner(%d) acquired tracker list mutex.\n",
-		    fibril_get_id());
-
-		link_t *current = instance->tracker_list.next;
-		while (current != &instance->tracker_list)
-		{
-
-			link_t *next = current->next;
-			tracker_t *tracker = list_get_instance(current, tracker_t, link);
-
-			assert(current == &tracker->link);
-			assert(tracker);
-			assert(tracker->next_step);
-			assert(tracker->td);
-
-			if (!transfer_descriptor_is_active(tracker->td)) {
-				usb_log_info("Found inactive tracker with status: %x:%x.\n",
-				    tracker->td->status, tracker->td->device);
-				list_remove(current);
-				list_append(current, &done_trackers);
-			}
-			current = next;
-		}
-
-		usb_log_debug2("Cleaner(%d) releasing tracker list mutex.\n",
-		    fibril_get_id());
-		fibril_mutex_unlock(&instance->tracker_list_mutex);
-		usb_log_debug2("Cleaner(%d) released tracker list mutex.\n",
-		    fibril_get_id());
-
-		while (!list_empty(&done_trackers)) {
-			tracker_t *tracker = list_get_instance(
-			  done_trackers.next, tracker_t, link);
-			list_remove(&tracker->link);
-			tracker->next_step(tracker);
-		}
+		transfer_list_check(&instance->transfers_interrupt);
+		transfer_list_check(&instance->transfers_control_slow);
+		transfer_list_check(&instance->transfers_control_full);
+		transfer_list_check(&instance->transfers_bulk_full);
 		async_usleep(UHCI_CLEANER_TIMEOUT);
 	}
Index: uspace/drv/uhci-hcd/uhci.h
===================================================================
--- uspace/drv/uhci-hcd/uhci.h	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/uhci.h	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -72,5 +72,5 @@
 
 #define UHCI_FRAME_LIST_COUNT 1024
-#define UHCI_CLEANER_TIMEOUT 1000
+#define UHCI_CLEANER_TIMEOUT 1000000
 #define UHCI_DEBUGER_TIMEOUT 5000000
 
Index: uspace/drv/uhci-hcd/uhci_struct/queue_head.h
===================================================================
--- uspace/drv/uhci-hcd/uhci_struct/queue_head.h	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/uhci_struct/queue_head.h	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -55,14 +55,33 @@
 }
 
-static inline void queue_head_add_next(queue_head_t *instance, uint32_t next_queue_pa)
+static inline void queue_head_append_qh(queue_head_t *instance, uint32_t pa)
 {
-	if (next_queue_pa) {
-		instance->next_queue = (next_queue_pa & LINK_POINTER_ADDRESS_MASK)
-		  | LINK_POINTER_QUEUE_HEAD_FLAG;
+	if (pa) {
+		instance->next_queue = (pa & LINK_POINTER_ADDRESS_MASK)
+		    | LINK_POINTER_QUEUE_HEAD_FLAG;
 	}
 }
 
-static inline queue_head_t * queue_head_get()
-	{ return malloc32(sizeof(queue_head_t)); }
+static inline void queue_head_element_qh(queue_head_t *instance, uint32_t pa)
+{
+	if (pa) {
+		instance->next_queue = (pa & LINK_POINTER_ADDRESS_MASK)
+		    | LINK_POINTER_QUEUE_HEAD_FLAG;
+	}
+}
+
+static inline void queue_head_element_td(queue_head_t *instance, uint32_t pa)
+{
+	if (pa) {
+		instance->element = (pa & LINK_POINTER_ADDRESS_MASK);
+	}
+}
+
+static inline queue_head_t * queue_head_get() {
+	queue_head_t *ret = malloc32(sizeof(queue_head_t));
+	if (ret)
+		queue_head_init(ret);
+	return ret;
+}
 
 static inline void queue_head_dispose(queue_head_t *head)
Index: uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.c
===================================================================
--- uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.c	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.c	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -40,9 +40,10 @@
 void transfer_descriptor_init(transfer_descriptor_t *instance,
     int error_count, size_t size, bool toggle, bool isochronous,
-    usb_target_t target, int pid, void *buffer)
+    usb_target_t target, int pid, void *buffer, transfer_descriptor_t *next)
 {
 	assert(instance);
 
-	instance->next = 0 | LINK_POINTER_TERMINATE_FLAG;
+	instance->next =
+	    (next != NULL) ? addr_to_phys(next) : LINK_POINTER_TERMINATE_FLAG;
 
 	instance->status = 0
Index: uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.h
===================================================================
--- uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.h	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.h	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -93,7 +93,15 @@
 void transfer_descriptor_init(transfer_descriptor_t *instance,
     int error_count, size_t size, bool toggle, bool isochronous,
-    usb_target_t target, int pid, void *buffer);
+    usb_target_t target, int pid, void *buffer, transfer_descriptor_t * next);
 
 int transfer_descriptor_status(transfer_descriptor_t *instance);
+
+static inline size_t transfer_descriptor_actual_size(
+    transfer_descriptor_t *instance)
+{
+	assert(instance);
+	return
+	    ((instance->status >> TD_STATUS_ACTLEN_POS) + 1) & TD_STATUS_ACTLEN_MASK;
+}
 
 static inline bool transfer_descriptor_is_active(
Index: uspace/drv/uhci-hcd/utils/malloc32.h
===================================================================
--- uspace/drv/uhci-hcd/utils/malloc32.h	(revision f6309b65e6fe0aa5377536ac1f12c5eeafc99ac6)
+++ uspace/drv/uhci-hcd/utils/malloc32.h	(revision 7dd3318d27ef639ceb71f338262b6270c0fd4459)
@@ -45,5 +45,5 @@
 #define UHCI_REQUIRED_PAGE_SIZE 4096
 
-static inline void * addr_to_phys(void *addr)
+static inline uintptr_t addr_to_phys(void *addr)
 {
 	uintptr_t result;
@@ -51,5 +51,5 @@
 
 	assert(ret == 0);
-	return (void*)(result | ((uintptr_t)addr & 0xfff));
+	return (result | ((uintptr_t)addr & 0xfff));
 }
 
