Index: uspace/Makefile
===================================================================
--- uspace/Makefile	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/Makefile	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -142,4 +142,5 @@
 	LIBS += lib/pci
 	LIBS += lib/usb
+	LIBS += lib/usbvirt
 endif
 
@@ -147,4 +148,5 @@
 	LIBS += lib/pci
 	LIBS += lib/usb
+	LIBS += lib/usbvirt
 endif
 
Index: uspace/Makefile.common
===================================================================
--- uspace/Makefile.common	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/Makefile.common	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -88,4 +88,5 @@
 LIBPCI_PREFIX = $(LIB_PREFIX)/pci
 LIBUSB_PREFIX = $(LIB_PREFIX)/usb
+LIBUSBVIRT_PREFIX = $(LIB_PREFIX)/usbvirt
 
 LIBSOCKET_PREFIX = $(LIB_PREFIX)/socket
Index: uspace/app/virtusbkbd/Makefile
===================================================================
--- uspace/app/virtusbkbd/Makefile	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/app/virtusbkbd/Makefile	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -31,6 +31,8 @@
 # (it is really annoying to write long names)
 BINARY = vuk
-LIBS = $(LIBUSB_PREFIX)/libusb.a
+
+LIBS = $(LIBUSB_PREFIX)/libusb.a $(LIBUSBVIRT_PREFIX)/libusbvirt.a
 EXTRA_CFLAGS = -I$(LIB_PREFIX)
+
 SOURCES = \
 	virtusbkbd.c
Index: uspace/app/virtusbkbd/virtusbkbd.c
===================================================================
--- uspace/app/virtusbkbd/virtusbkbd.c	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/app/virtusbkbd/virtusbkbd.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -46,5 +46,7 @@
 
 #include <usb/hcd.h>
-#include <usb/virtdev.h>
+#include <usbvirt/device.h>
+#include <usbvirt/hub.h>
+#include <usbvirt/ids.h>
 
 #define LOOPS 5
@@ -59,4 +61,28 @@
 	(printf("%s: %s" fmt "\n", NAME, _QUOTEME(cmd), __VA_ARGS__), cmd(__VA_ARGS__))
 
+static int on_incoming_data(struct usbvirt_device *dev,
+    usb_endpoint_t endpoint, void *buffer, size_t size)
+{
+	printf("%s: ignoring incomming data to endpoint %d\n", NAME, endpoint);
+	
+	return EOK;
+}
+
+/** Keyboard callbacks.
+ * We abuse the fact that static variables are zero-filled.
+ */
+static usbvirt_device_ops_t keyboard_ops = {
+	.on_data = on_incoming_data
+};
+
+/** Keyboard device.
+ * Rest of the items will be initialized later.
+ */
+static usbvirt_device_t keyboard_dev = {
+	.ops = &keyboard_ops,
+	.device_id_ = USBVIRT_DEV_KEYBOARD_ID
+};
+
+
 static void fibril_sleep(size_t sec)
 {
@@ -66,21 +92,13 @@
 }
 
-static void on_data_from_host(usb_endpoint_t endpoint, void *buffer, size_t len)
-{
-	printf("%s: ignoring incomming data to endpoint %d\n", NAME, endpoint);
-}
 
 int main(int argc, char * argv[])
 {
-	int vhcd_phone = usb_virtdev_connect(DEV_HCD_NAME,
-	    USB_VIRTDEV_KEYBOARD_ID, on_data_from_host);
-	
-	if (vhcd_phone < 0) {
+	int rc = usbvirt_connect(&keyboard_dev, DEV_HCD_NAME);
+	if (rc != EOK) {
 		printf("%s: Unable to start comunication with VHCD at usb://%s (%s).\n",
-		    NAME, DEV_HCD_NAME, str_error(vhcd_phone));
-		return vhcd_phone;
+		    NAME, DEV_HCD_NAME, str_error(rc));
+		return rc;
 	}
-	
-	
 	
 	size_t i;
@@ -94,5 +112,5 @@
 		
 		printf("%s: Will send data to VHCD...\n", NAME);
-		int rc = usb_virtdev_data_to_host(vhcd_phone, 0, data, size);
+		int rc = keyboard_dev.send_data(&keyboard_dev, 0, data, size);
 		printf("%s:   ...data sent (%s).\n", NAME, str_error(rc));
 	}
@@ -101,5 +119,5 @@
 	printf("%s: Terminating...\n", NAME);
 	
-	ipc_hangup(vhcd_phone);
+	usbvirt_disconnect();
 	
 	return 0;
Index: uspace/lib/usb/Makefile
===================================================================
--- uspace/lib/usb/Makefile	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/lib/usb/Makefile	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -31,6 +31,5 @@
 
 SOURCES = \
-	hcd.c \
-	virtdev.c
+	hcd.c
 
 include $(USPACE_PREFIX)/Makefile.common
Index: uspace/lib/usb/devreq.h
===================================================================
--- uspace/lib/usb/devreq.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usb/devreq.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2010 Vojtech Horky
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup libusb usb
+ * @{
+ */
+/** @file
+ * @brief Standard USB device requests.
+ */
+#ifndef LIBUSB_DEVREQ_H_
+#define LIBUSB_DEVREQ_H_
+
+#include <ipc/ipc.h>
+#include <async.h>
+
+/** Standard device request. */
+typedef enum {
+	USB_DEVREQ_GET_STATUS = 0,
+	USB_DEVREQ_CLEAR_FEATURE = 1,
+	USB_DEVREQ_SET_FEATURE = 3,
+	USB_DEVREQ_SET_ADDRESS = 5,
+	USB_DEVREQ_GET_DESCRIPTOR = 6,
+	USB_DEVREQ_SET_DESCRIPTOR = 7,
+	USB_DEVREQ_GET_CONFIGURATION = 8,
+	USB_DEVREQ_SET_CONFIGURATION = 9,
+	USB_DEVREQ_GET_INTERFACE = 10,
+	USB_DEVREQ_SET_INTERFACE = 11,
+	USB_DEVREQ_SYNCH_FRAME = 12
+} usb_stddevreq_t;
+
+
+
+#endif
+/**
+ * @}
+ */
Index: uspace/lib/usb/virtdev.c
===================================================================
--- uspace/lib/usb/virtdev.c	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ 	(revision )
@@ -1,178 +1,0 @@
-/*
- * Copyright (c) 2010 Vojtech Horky
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * - Redistributions of source code must retain the above copyright
- *   notice, this list of conditions and the following disclaimer.
- * - Redistributions in binary form must reproduce the above copyright
- *   notice, this list of conditions and the following disclaimer in the
- *   documentation and/or other materials provided with the distribution.
- * - The name of the author may not be used to endorse or promote products
- *   derived from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
- * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
- * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
- * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
- * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
- * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
- * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-/** @addtogroup libusb usb
- * @{
- */
-/** @file
- * @brief Virtual USB device (implementation).
- */
-#include "virtdev.h"
-#include <devmap.h>
-#include <fcntl.h>
-#include <vfs/vfs.h>
-#include <errno.h>
-#include <stdlib.h>
-
-#define NAMESPACE "usb"
-
-static usb_virtdev_on_data_from_host_t on_data_from_host = NULL;
-
-static void handle_data_to_device(ipc_callid_t iid, ipc_call_t icall)
-{
-	usb_endpoint_t endpoint = IPC_GET_ARG1(icall);
-	
-	size_t len;
-	void * buffer;
-	int rc = async_data_write_accept(&buffer, false,
-	    1, USB_MAX_PAYLOAD_SIZE,
-	    0, &len);
-	
-	if (rc != EOK) {
-		ipc_answer_0(iid, rc);
-		return;
-	}
-	
-	on_data_from_host(endpoint, buffer, len);
-	
-	free(buffer);
-	
-	ipc_answer_0(iid, EOK);
-}
-
-static void callback_connection(ipc_callid_t iid, ipc_call_t *icall)
-{
-	ipc_answer_0(iid, EOK);
-	
-	while (true) {
-		ipc_callid_t callid; 
-		ipc_call_t call; 
-		
-		callid = async_get_call(&call);
-		switch (IPC_GET_METHOD(call)) {
-			case IPC_M_PHONE_HUNGUP:
-				ipc_answer_0(callid, EOK);
-				return;
-			
-			case IPC_M_USB_VIRTDEV_DATA_TO_DEVICE:
-				handle_data_to_device(callid, call);
-				break;
-			
-			default:
-				ipc_answer_0(callid, EINVAL);
-				break;
-		}
-	}
-}
-
-/** Create necessary phones for comunication with virtual HCD.
- * This function wraps following calls:
- * -# open <code>/dev/usb/<i>hcd_path</i></code> for reading
- * -# access phone of file opened in previous step
- * -# create callback through just opened phone
- * -# create handler for calling on data from host to function
- * -# return the (outgoing) phone
- *
- * @warning This function is wrapper for several actions and therefore
- * it is not possible - in case of error - to determine at which point
- * error occured.
- *
- * @param hcd_path HCD identification under devfs
- *     (without <code>/dev/usb/</code>).
- * @param device_id Internal device identification (used by HCD).
- * @param callback Handler for callbacks from HCD.
- * @return Phone for comunicating with HCD or error code from errno.h.
- */
-int usb_virtdev_connect(const char *hcd_path, int device_id,
-    usb_virtdev_on_data_from_host_t callback)
-{
-	char dev_path[DEVMAP_NAME_MAXLEN + 1];
-	snprintf(dev_path, DEVMAP_NAME_MAXLEN,
-	    "/dev/%s/%s", NAMESPACE, hcd_path);
-	
-	int fd = open(dev_path, O_RDONLY);
-	if (fd < 0) {
-		return fd;
-	}
-	
-	int hcd_phone = fd_phone(fd);
-	
-	if (hcd_phone < 0) {
-		return hcd_phone;
-	}
-	
-	ipcarg_t phonehash;
-	int rc = ipc_connect_to_me(hcd_phone, 1, device_id, 0, &phonehash);
-	if (rc != EOK) {
-		return rc;
-	}
-	on_data_from_host = callback;
-	async_new_connection(phonehash, 0, NULL, callback_connection);
-	
-	return hcd_phone;
-}
-
-int usb_virtdev_data_to_host(int phone,
-    usb_endpoint_t endpoint,
-    void * buffer, size_t size)
-{
-	if (phone < 0) {
-		return EINVAL;
-	}
-	if ((buffer == NULL) || (size == 0)) {
-		return EINVAL;
-	}
-
-	ipc_call_t answer_data;
-	ipcarg_t answer_rc;
-	aid_t req;
-	int rc;
-	
-	req = async_send_1(phone,
-	    IPC_M_USB_VIRTDEV_DATA_FROM_DEVICE,
-	    endpoint,
-	    &answer_data);
-	
-	rc = async_data_write_start(phone, buffer, size);
-	if (rc != EOK) {
-		async_wait_for(req, NULL);
-		return rc;
-	}
-	
-	async_wait_for(req, &answer_rc);
-	rc = (int)answer_rc;
-	if (rc != EOK) {
-		return rc;
-	}
-	
-	return EOK;
-}
-
-/**
- * @}
- */
Index: uspace/lib/usb/virtdev.h
===================================================================
--- uspace/lib/usb/virtdev.h	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ 	(revision )
@@ -1,59 +1,0 @@
-/*
- * Copyright (c) 2010 Vojtech Horky
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * - Redistributions of source code must retain the above copyright
- *   notice, this list of conditions and the following disclaimer.
- * - Redistributions in binary form must reproduce the above copyright
- *   notice, this list of conditions and the following disclaimer in the
- *   documentation and/or other materials provided with the distribution.
- * - The name of the author may not be used to endorse or promote products
- *   derived from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
- * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
- * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
- * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
- * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
- * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
- * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-/** @addtogroup libusb usb
- * @{
- */
-/** @file
- * @brief Virtual USB device.
- */
-#ifndef LIBUSB_VIRTDEV_H_
-#define LIBUSB_VIRTDEV_H_
-
-#include <ipc/ipc.h>
-#include <async.h>
-#include "hcd.h"
-
-#define USB_VIRTDEV_KEYBOARD_ID 1
-#define USB_VIRTDEV_KEYBOARD_ADDRESS 1
-
-typedef void (*usb_virtdev_on_data_from_host_t)(usb_endpoint_t, void *, size_t);
-
-int usb_virtdev_connect(const char *, int, usb_virtdev_on_data_from_host_t);
-int usb_virtdev_data_to_host(int, usb_endpoint_t,
-    void *, size_t);
-
-typedef enum {
-	IPC_M_USB_VIRTDEV_DATA_TO_DEVICE = IPC_FIRST_USER_METHOD,
-	IPC_M_USB_VIRTDEV_DATA_FROM_DEVICE
-} usb_virtdev_method_t;
-
-#endif
-/**
- * @}
- */
Index: uspace/lib/usbvirt/Makefile
===================================================================
--- uspace/lib/usbvirt/Makefile	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usbvirt/Makefile	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,40 @@
+#
+# Copyright (c) 2010 Vojtech Horky
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+#
+# - Redistributions of source code must retain the above copyright
+#   notice, this list of conditions and the following disclaimer.
+# - Redistributions in binary form must reproduce the above copyright
+#   notice, this list of conditions and the following disclaimer in the
+#   documentation and/or other materials provided with the distribution.
+# - The name of the author may not be used to endorse or promote products
+#   derived from this software without specific prior written permission.
+#
+# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+# OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+# IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+# NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+#
+
+USPACE_PREFIX = ../..
+LIBRARY = libusbvirt
+
+LIBS = $(LIBUSB_PREFIX)/libusb.a
+EXTRA_CFLAGS = -I$(LIB_PREFIX)
+
+SOURCES = \
+	ctrlpipe.c \
+	incoming.c \
+	main.c
+
+include $(USPACE_PREFIX)/Makefile.common
Index: uspace/lib/usbvirt/ctrlpipe.c
===================================================================
--- uspace/lib/usbvirt/ctrlpipe.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usbvirt/ctrlpipe.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,47 @@
+/*
+ * Copyright (c) 2010 Vojtech Horky
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup libusbvirt usb
+ * @{
+ */
+/** @file
+ * @brief Device control pipe.
+ */
+#include <errno.h>
+
+#include "private.h"
+
+int control_pipe(void *buffer, size_t size)
+{
+	// TODO
+	return EOK;
+}
+
+/**
+ * @}
+ */
Index: uspace/lib/usbvirt/device.h
===================================================================
--- uspace/lib/usbvirt/device.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usbvirt/device.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,81 @@
+/*
+ * Copyright (c) 2010 Vojtech Horky
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup libusbvirt usb
+ * @{
+ */
+/** @file
+ * @brief Virtual USB device.
+ */
+#ifndef LIBUSBVIRT_DEVICE_H_
+#define LIBUSBVIRT_DEVICE_H_
+
+#include <usb/hcd.h>
+#include <usb/devreq.h>
+
+struct usbvirt_device;
+
+typedef int (*usbvirt_on_devreq_t)(struct usbvirt_device *dev,
+    usb_direction_t, int recipient,
+    usb_stddevreq_t, int value, int index, int length);
+
+typedef struct {
+	usbvirt_on_devreq_t on_devreq_std;
+	usbvirt_on_devreq_t on_devreq_class;
+	int (*on_data)(struct usbvirt_device *dev,
+	    usb_endpoint_t endpoint, void *buffer, size_t size);
+} usbvirt_device_ops_t;
+
+typedef struct usbvirt_device {
+	/** Callback device operations. */
+	usbvirt_device_ops_t *ops;
+	
+	/** Send data to HC.
+	 * @warning Do not change after initializing with
+	 * usbvirt_device_init().
+	 * This function is here merely to make the interface more OOP.
+	 */
+	int (*send_data)(struct usbvirt_device *dev,
+	    usb_endpoint_t endpoint, void *buffer, size_t size);
+	
+	/** Phone to HC.
+	 * @warning Do not change, this is private variable.
+	 */
+	int vhcd_phone_;
+	
+	/** Device id.
+	 * This item will be removed when device enumeration and
+	 * recognition is implemented.
+	 */
+	int device_id_;
+} usbvirt_device_t;
+
+#endif
+/**
+ * @}
+ */
Index: uspace/lib/usbvirt/hub.h
===================================================================
--- uspace/lib/usbvirt/hub.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usbvirt/hub.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 2010 Vojtech Horky
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup libusbvirt usb
+ * @{
+ */
+/** @file
+ * @brief Virtual USB device.
+ */
+#ifndef LIBUSBVIRT_HUB_H_
+#define LIBUSBVIRT_HUB_H_
+
+#include "device.h"
+
+
+typedef enum {
+	IPC_M_USBVIRT_DATA_TO_DEVICE = IPC_FIRST_USER_METHOD,
+	IPC_M_USBVIRT_DATA_FROM_DEVICE
+} usbvirt_device_method_t;
+
+int usbvirt_connect(usbvirt_device_t *, const char *);
+int usbvirt_disconnect(void);
+
+#endif
+/**
+ * @}
+ */
Index: uspace/lib/usbvirt/ids.h
===================================================================
--- uspace/lib/usbvirt/ids.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usbvirt/ids.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2010 Vojtech Horky
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup libusbvirt usb
+ * @{
+ */
+/** @file
+ * @brief Virtual USB device.
+ */
+#ifndef LIBUSBVIRT_IDS_H_
+#define LIBUSBVIRT_IDS_H_
+
+#include "device.h"
+
+#define USBVIRT_DEV_KEYBOARD_ID 1
+#define USBVIRT_DEV_KEYBOARD_ADDRESS 1
+
+int usbvirt_connect(usbvirt_device_t *, const char *);
+int usbvirt_disconnect(void);
+
+#endif
+/**
+ * @}
+ */
Index: uspace/lib/usbvirt/incoming.c
===================================================================
--- uspace/lib/usbvirt/incoming.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usbvirt/incoming.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2010 Vojtech Horky
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup libusbvirt usb
+ * @{
+ */
+/** @file
+ * @brief General handling of data transfer.
+ */
+#include <errno.h>
+
+#include "device.h"
+#include "private.h"
+
+int handle_incoming_data(usb_endpoint_t endpoint, void *buffer, size_t size)
+{
+	/*
+	 * Endpoint zero is device control pipe.
+	 */
+	if (endpoint == 0) {
+		return control_pipe(buffer, size);
+	}
+	
+	/*
+	 * Any other endpoint will be handled by general handler.
+	 */
+	if (device->ops->on_data) {
+		return device->ops->on_data(device, endpoint, buffer, size);
+	} else {
+		return ENOTSUP;
+	}
+}
+
+/**
+ * @}
+ */
Index: uspace/lib/usbvirt/main.c
===================================================================
--- uspace/lib/usbvirt/main.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usbvirt/main.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,198 @@
+/*
+ * Copyright (c) 2010 Vojtech Horky
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup libusbvirt usb
+ * @{
+ */
+/** @file
+ * @brief Main handler for virtual USB device.
+ */
+#include <devmap.h>
+#include <fcntl.h>
+#include <vfs/vfs.h>
+#include <errno.h>
+#include <stdlib.h>
+
+#include "hub.h"
+#include "device.h"
+#include "private.h"
+
+#define NAMESPACE "usb"
+
+usbvirt_device_t *device = NULL;
+
+
+static void handle_data_to_device(ipc_callid_t iid, ipc_call_t icall)
+{
+	usb_endpoint_t endpoint = IPC_GET_ARG1(icall);
+	
+	size_t len;
+	void * buffer;
+	int rc = async_data_write_accept(&buffer, false,
+	    1, USB_MAX_PAYLOAD_SIZE,
+	    0, &len);
+	
+	if (rc != EOK) {
+		ipc_answer_0(iid, rc);
+		return;
+	}
+	
+	handle_incoming_data(endpoint, buffer, len);
+	
+	free(buffer);
+	
+	ipc_answer_0(iid, EOK);
+}
+
+static void callback_connection(ipc_callid_t iid, ipc_call_t *icall)
+{
+	ipc_answer_0(iid, EOK);
+	
+	while (true) {
+		ipc_callid_t callid; 
+		ipc_call_t call; 
+		
+		callid = async_get_call(&call);
+		switch (IPC_GET_METHOD(call)) {
+			case IPC_M_PHONE_HUNGUP:
+				ipc_answer_0(callid, EOK);
+				return;
+			
+			case IPC_M_USBVIRT_DATA_TO_DEVICE:
+				handle_data_to_device(callid, call);
+				break;
+			
+			default:
+				ipc_answer_0(callid, EINVAL);
+				break;
+		}
+	}
+}
+
+int usbvirt_data_to_host(struct usbvirt_device *dev,
+    usb_endpoint_t endpoint, void *buffer, size_t size)
+{
+	int phone = dev->vhcd_phone_;
+	
+	if (phone < 0) {
+		return EINVAL;
+	}
+	if ((buffer == NULL) || (size == 0)) {
+		return EINVAL;
+	}
+
+	ipc_call_t answer_data;
+	ipcarg_t answer_rc;
+	aid_t req;
+	int rc;
+	
+	req = async_send_1(phone,
+	    IPC_M_USBVIRT_DATA_FROM_DEVICE,
+	    endpoint,
+	    &answer_data);
+	
+	rc = async_data_write_start(phone, buffer, size);
+	if (rc != EOK) {
+		async_wait_for(req, NULL);
+		return rc;
+	}
+	
+	async_wait_for(req, &answer_rc);
+	rc = (int)answer_rc;
+	if (rc != EOK) {
+		return rc;
+	}
+	
+	return EOK;
+}
+
+/** Create necessary phones for comunication with virtual HCD.
+ * This function wraps following calls:
+ * -# open <code>/dev/usb/<i>hcd_path</i></code> for reading
+ * -# access phone of file opened in previous step
+ * -# create callback through just opened phone
+ * -# create handler for calling on data from host to function
+ * -# return the (outgoing) phone
+ *
+ * @warning This function is wrapper for several actions and therefore
+ * it is not possible - in case of error - to determine at which point
+ * error occured.
+ *
+ * @param hcd_path HCD identification under devfs
+ *     (without <code>/dev/usb/</code>).
+ * @param device_id Internal device identification (used by HCD).
+ * @param callback Handler for callbacks from HCD.
+ * @return EOK on success or error code from errno.h.
+ */
+int usbvirt_connect(usbvirt_device_t *dev, const char *hcd_path)
+{
+	char dev_path[DEVMAP_NAME_MAXLEN + 1];
+	snprintf(dev_path, DEVMAP_NAME_MAXLEN,
+	    "/dev/%s/%s", NAMESPACE, hcd_path);
+	
+	int fd = open(dev_path, O_RDONLY);
+	if (fd < 0) {
+		return fd;
+	}
+	
+	int hcd_phone = fd_phone(fd);
+	
+	if (hcd_phone < 0) {
+		return hcd_phone;
+	}
+	
+	ipcarg_t phonehash;
+	int rc = ipc_connect_to_me(hcd_phone, 1, dev->device_id_, 0, &phonehash);
+	if (rc != EOK) {
+		return rc;
+	}
+	
+	dev->vhcd_phone_ = hcd_phone;
+	dev->send_data = usbvirt_data_to_host;
+	
+	device = dev;
+	
+	async_new_connection(phonehash, 0, NULL, callback_connection);
+	
+	return EOK;
+}
+
+
+int usbvirt_disconnect(void)
+{
+	ipc_hangup(device->vhcd_phone_);
+	
+	device = NULL;
+	
+	return EOK;
+}
+
+
+/**
+ * @}
+ */
Index: uspace/lib/usbvirt/private.h
===================================================================
--- uspace/lib/usbvirt/private.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
+++ uspace/lib/usbvirt/private.h	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -0,0 +1,54 @@
+/*
+ * Copyright (c) 2010 Vojtech Horky
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ *   derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup libusbvirt usb
+ * @{
+ */
+/** @file
+ * @brief Virtual USB private header.
+ */
+#ifndef LIBUSBVIRT_PRIVATE_H_
+#define LIBUSBVIRT_PRIVATE_H_
+
+#include "device.h"
+#include "hub.h"
+
+extern usbvirt_device_t *device;
+
+
+int usbvirt_data_to_host(struct usbvirt_device *dev,
+    usb_endpoint_t endpoint, void *buffer, size_t size);
+
+int handle_incoming_data(usb_endpoint_t endpoint, void *buffer, size_t size);
+
+int control_pipe(void *buffer, size_t size);
+
+#endif
+/**
+ * @}
+ */
Index: uspace/srv/hw/bus/usb/hcd/virtual/conndev.c
===================================================================
--- uspace/srv/hw/bus/usb/hcd/virtual/conndev.c	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/srv/hw/bus/usb/hcd/virtual/conndev.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -36,5 +36,5 @@
 #include <assert.h>
 #include <errno.h>
-#include <usb/virtdev.h>
+#include <usbvirt/hub.h>
 
 #include "conn.h"
@@ -101,5 +101,5 @@
 				break;
 			
-			case IPC_M_USB_VIRTDEV_DATA_FROM_DEVICE:
+			case IPC_M_USBVIRT_DATA_FROM_DEVICE:
 				handle_data_from_device(callid, call, dev);
 				break;
Index: uspace/srv/hw/bus/usb/hcd/virtual/devices.c
===================================================================
--- uspace/srv/hw/bus/usb/hcd/virtual/devices.c	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/srv/hw/bus/usb/hcd/virtual/devices.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -43,5 +43,5 @@
 #include <str_error.h>
 
-#include <usb/virtdev.h>
+#include <usbvirt/ids.h>
 
 #include "devices.h"
@@ -62,7 +62,7 @@
 	virtdev_connection_t * dev = NULL;
 	switch (id) {
-		case USB_VIRTDEV_KEYBOARD_ID:
+		case USBVIRT_DEV_KEYBOARD_ID:
 			dev = virtdev_add_device(
-			    USB_VIRTDEV_KEYBOARD_ADDRESS, phone);
+			    USBVIRT_DEV_KEYBOARD_ADDRESS, phone);
 			break;
 		default:
Index: uspace/srv/hw/bus/usb/hcd/virtual/hc.c
===================================================================
--- uspace/srv/hw/bus/usb/hcd/virtual/hc.c	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/srv/hw/bus/usb/hcd/virtual/hc.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -43,5 +43,5 @@
 #include <str_error.h>
 
-#include <usb/virtdev.h>
+#include <usbvirt/hub.h>
 
 #include "vhcd.h"
@@ -155,5 +155,5 @@
 			
 			req = async_send_2(dev->phone,
-			    IPC_M_USB_VIRTDEV_DATA_TO_DEVICE,
+			    IPC_M_USBVIRT_DATA_TO_DEVICE,
 			    transaction->target.endpoint,
 			    transaction->type,
Index: uspace/srv/hw/bus/usb/hcd/virtual/hcd.c
===================================================================
--- uspace/srv/hw/bus/usb/hcd/virtual/hcd.c	(revision b3718443703dd0cd113ce025bb4884a81207993a)
+++ uspace/srv/hw/bus/usb/hcd/virtual/hcd.c	(revision b8100da862d7faddeef79335833e685b1bc3b497)
@@ -45,5 +45,4 @@
 
 #include <usb/hcd.h>
-#include <usb/virtdev.h>
 #include "vhcd.h"
 #include "hc.h"
