Statistics
| Branch: | Revision:

root / usb-linux.c @ 67d8cec3

History | View | Annotate | Download (38 kB)

1 bb36d470 bellard
/*
2 bb36d470 bellard
 * Linux host USB redirector
3 bb36d470 bellard
 *
4 bb36d470 bellard
 * Copyright (c) 2005 Fabrice Bellard
5 5fafdf24 ths
 *
6 64838171 aliguori
 * Copyright (c) 2008 Max Krasnyansky
7 64838171 aliguori
 *      Support for host device auto connect & disconnect
8 5d0c5750 aliguori
 *      Major rewrite to support fully async operation
9 4b096fc9 aliguori
 *
10 bb36d470 bellard
 * Permission is hereby granted, free of charge, to any person obtaining a copy
11 bb36d470 bellard
 * of this software and associated documentation files (the "Software"), to deal
12 bb36d470 bellard
 * in the Software without restriction, including without limitation the rights
13 bb36d470 bellard
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
14 bb36d470 bellard
 * copies of the Software, and to permit persons to whom the Software is
15 bb36d470 bellard
 * furnished to do so, subject to the following conditions:
16 bb36d470 bellard
 *
17 bb36d470 bellard
 * The above copyright notice and this permission notice shall be included in
18 bb36d470 bellard
 * all copies or substantial portions of the Software.
19 bb36d470 bellard
 *
20 bb36d470 bellard
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
21 bb36d470 bellard
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22 bb36d470 bellard
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
23 bb36d470 bellard
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
24 bb36d470 bellard
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
25 bb36d470 bellard
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
26 bb36d470 bellard
 * THE SOFTWARE.
27 bb36d470 bellard
 */
28 446ab128 aliguori
29 87ecb68b pbrook
#include "qemu-common.h"
30 1f3870ab aliguori
#include "qemu-timer.h"
31 87ecb68b pbrook
#include "console.h"
32 bb36d470 bellard
33 bb36d470 bellard
#if defined(__linux__)
34 bb36d470 bellard
#include <dirent.h>
35 bb36d470 bellard
#include <sys/ioctl.h>
36 b9dc033c balrog
#include <signal.h>
37 bb36d470 bellard
38 446ab128 aliguori
#include <linux/usbdevice_fs.h>
39 446ab128 aliguori
#include <linux/version.h>
40 446ab128 aliguori
#include "hw/usb.h"
41 bb36d470 bellard
42 d9cf1578 blueswir1
/* We redefine it to avoid version problems */
43 d9cf1578 blueswir1
struct usb_ctrltransfer {
44 d9cf1578 blueswir1
    uint8_t  bRequestType;
45 d9cf1578 blueswir1
    uint8_t  bRequest;
46 d9cf1578 blueswir1
    uint16_t wValue;
47 d9cf1578 blueswir1
    uint16_t wIndex;
48 d9cf1578 blueswir1
    uint16_t wLength;
49 d9cf1578 blueswir1
    uint32_t timeout;
50 d9cf1578 blueswir1
    void *data;
51 d9cf1578 blueswir1
};
52 d9cf1578 blueswir1
53 d9cf1578 blueswir1
struct usb_ctrlrequest {
54 d9cf1578 blueswir1
    uint8_t bRequestType;
55 d9cf1578 blueswir1
    uint8_t bRequest;
56 d9cf1578 blueswir1
    uint16_t wValue;
57 d9cf1578 blueswir1
    uint16_t wIndex;
58 d9cf1578 blueswir1
    uint16_t wLength;
59 d9cf1578 blueswir1
};
60 d9cf1578 blueswir1
61 a594cfbf bellard
typedef int USBScanFunc(void *opaque, int bus_num, int addr, int class_id,
62 5fafdf24 ths
                        int vendor_id, int product_id,
63 a594cfbf bellard
                        const char *product_name, int speed);
64 5fafdf24 ths
static int usb_host_find_device(int *pbus_num, int *paddr,
65 1f6e24e7 bellard
                                char *product_name, int product_name_size,
66 a594cfbf bellard
                                const char *devname);
67 a594cfbf bellard
//#define DEBUG
68 64838171 aliguori
69 64838171 aliguori
#ifdef DEBUG
70 64838171 aliguori
#define dprintf printf
71 64838171 aliguori
#else
72 64838171 aliguori
#define dprintf(...)
73 64838171 aliguori
#endif
74 bb36d470 bellard
75 bb36d470 bellard
#define USBDEVFS_PATH "/proc/bus/usb"
76 1f6e24e7 bellard
#define PRODUCT_NAME_SZ 32
77 b9dc033c balrog
#define MAX_ENDPOINTS 16
78 bb36d470 bellard
79 b9dc033c balrog
/* endpoint association data */
80 b9dc033c balrog
struct endp_data {
81 b9dc033c balrog
    uint8_t type;
82 64838171 aliguori
    uint8_t halted;
83 b9dc033c balrog
};
84 b9dc033c balrog
85 446ab128 aliguori
enum {
86 446ab128 aliguori
    CTRL_STATE_IDLE = 0,
87 446ab128 aliguori
    CTRL_STATE_SETUP,
88 446ab128 aliguori
    CTRL_STATE_DATA,
89 446ab128 aliguori
    CTRL_STATE_ACK
90 446ab128 aliguori
};
91 446ab128 aliguori
92 446ab128 aliguori
/*
93 446ab128 aliguori
 * Control transfer state.
94 446ab128 aliguori
 * Note that 'buffer' _must_ follow 'req' field because 
95 446ab128 aliguori
 * we need contigious buffer when we submit control URB.
96 446ab128 aliguori
 */ 
97 446ab128 aliguori
struct ctrl_struct {
98 446ab128 aliguori
    uint16_t len;
99 446ab128 aliguori
    uint16_t offset;
100 446ab128 aliguori
    uint8_t  state;
101 446ab128 aliguori
    struct   usb_ctrlrequest req;
102 446ab128 aliguori
    uint8_t  buffer[1024];
103 446ab128 aliguori
};
104 446ab128 aliguori
105 bb36d470 bellard
typedef struct USBHostDevice {
106 bb36d470 bellard
    USBDevice dev;
107 64838171 aliguori
    int       fd;
108 64838171 aliguori
109 64838171 aliguori
    uint8_t   descr[1024];
110 64838171 aliguori
    int       descr_len;
111 64838171 aliguori
    int       configuration;
112 446ab128 aliguori
    int       ninterfaces;
113 24772c1e aliguori
    int       closing;
114 64838171 aliguori
115 446ab128 aliguori
    struct ctrl_struct ctrl;
116 b9dc033c balrog
    struct endp_data endp_table[MAX_ENDPOINTS];
117 4b096fc9 aliguori
118 4b096fc9 aliguori
    /* Host side address */
119 4b096fc9 aliguori
    int bus_num;
120 4b096fc9 aliguori
    int addr;
121 4b096fc9 aliguori
122 4b096fc9 aliguori
    struct USBHostDevice *next;
123 bb36d470 bellard
} USBHostDevice;
124 bb36d470 bellard
125 64838171 aliguori
static int is_isoc(USBHostDevice *s, int ep)
126 64838171 aliguori
{
127 64838171 aliguori
    return s->endp_table[ep - 1].type == USBDEVFS_URB_TYPE_ISO;
128 64838171 aliguori
}
129 64838171 aliguori
130 64838171 aliguori
static int is_halted(USBHostDevice *s, int ep)
131 64838171 aliguori
{
132 64838171 aliguori
    return s->endp_table[ep - 1].halted;
133 64838171 aliguori
}
134 64838171 aliguori
135 64838171 aliguori
static void clear_halt(USBHostDevice *s, int ep)
136 64838171 aliguori
{
137 64838171 aliguori
    s->endp_table[ep - 1].halted = 0;
138 64838171 aliguori
}
139 64838171 aliguori
140 64838171 aliguori
static void set_halt(USBHostDevice *s, int ep)
141 64838171 aliguori
{
142 64838171 aliguori
    s->endp_table[ep - 1].halted = 1;
143 64838171 aliguori
}
144 64838171 aliguori
145 4b096fc9 aliguori
static USBHostDevice *hostdev_list;
146 4b096fc9 aliguori
147 4b096fc9 aliguori
static void hostdev_link(USBHostDevice *dev)
148 4b096fc9 aliguori
{
149 4b096fc9 aliguori
    dev->next = hostdev_list;
150 4b096fc9 aliguori
    hostdev_list = dev;
151 4b096fc9 aliguori
}
152 4b096fc9 aliguori
153 4b096fc9 aliguori
static void hostdev_unlink(USBHostDevice *dev)
154 4b096fc9 aliguori
{
155 4b096fc9 aliguori
    USBHostDevice *pdev = hostdev_list;
156 4b096fc9 aliguori
    USBHostDevice **prev = &hostdev_list;
157 4b096fc9 aliguori
158 4b096fc9 aliguori
    while (pdev) {
159 4b096fc9 aliguori
        if (pdev == dev) {
160 4b096fc9 aliguori
            *prev = dev->next;
161 4b096fc9 aliguori
            return;
162 4b096fc9 aliguori
        }
163 4b096fc9 aliguori
164 4b096fc9 aliguori
        prev = &pdev->next;
165 4b096fc9 aliguori
        pdev = pdev->next;
166 4b096fc9 aliguori
    }
167 4b096fc9 aliguori
}
168 4b096fc9 aliguori
169 4b096fc9 aliguori
static USBHostDevice *hostdev_find(int bus_num, int addr)
170 4b096fc9 aliguori
{
171 4b096fc9 aliguori
    USBHostDevice *s = hostdev_list;
172 4b096fc9 aliguori
    while (s) {
173 4b096fc9 aliguori
        if (s->bus_num == bus_num && s->addr == addr)
174 4b096fc9 aliguori
            return s;
175 4b096fc9 aliguori
        s = s->next;
176 4b096fc9 aliguori
    }
177 4b096fc9 aliguori
    return NULL;
178 4b096fc9 aliguori
}
179 4b096fc9 aliguori
180 64838171 aliguori
/* 
181 64838171 aliguori
 * Async URB state.
182 64838171 aliguori
 * We always allocate one isoc descriptor even for bulk transfers
183 64838171 aliguori
 * to simplify allocation and casts. 
184 64838171 aliguori
 */
185 64838171 aliguori
typedef struct AsyncURB
186 64838171 aliguori
{
187 64838171 aliguori
    struct usbdevfs_urb urb;
188 64838171 aliguori
    struct usbdevfs_iso_packet_desc isocpd;
189 b9dc033c balrog
190 64838171 aliguori
    USBPacket     *packet;
191 64838171 aliguori
    USBHostDevice *hdev;
192 64838171 aliguori
} AsyncURB;
193 b9dc033c balrog
194 64838171 aliguori
static AsyncURB *async_alloc(void)
195 b9dc033c balrog
{
196 64838171 aliguori
    return (AsyncURB *) qemu_mallocz(sizeof(AsyncURB));
197 b9dc033c balrog
}
198 b9dc033c balrog
199 64838171 aliguori
static void async_free(AsyncURB *aurb)
200 b9dc033c balrog
{
201 64838171 aliguori
    qemu_free(aurb);
202 64838171 aliguori
}
203 b9dc033c balrog
204 446ab128 aliguori
static void async_complete_ctrl(USBHostDevice *s, USBPacket *p)
205 446ab128 aliguori
{
206 446ab128 aliguori
    switch(s->ctrl.state) {
207 446ab128 aliguori
    case CTRL_STATE_SETUP:
208 446ab128 aliguori
        if (p->len < s->ctrl.len)
209 446ab128 aliguori
            s->ctrl.len = p->len;
210 446ab128 aliguori
        s->ctrl.state = CTRL_STATE_DATA;
211 446ab128 aliguori
        p->len = 8;
212 446ab128 aliguori
        break;
213 446ab128 aliguori
214 446ab128 aliguori
    case CTRL_STATE_ACK:
215 446ab128 aliguori
        s->ctrl.state = CTRL_STATE_IDLE;
216 446ab128 aliguori
        p->len = 0;
217 446ab128 aliguori
        break;
218 446ab128 aliguori
219 446ab128 aliguori
    default:
220 446ab128 aliguori
        break;
221 446ab128 aliguori
    }
222 446ab128 aliguori
}
223 446ab128 aliguori
224 64838171 aliguori
static void async_complete(void *opaque)
225 64838171 aliguori
{
226 64838171 aliguori
    USBHostDevice *s = opaque;
227 64838171 aliguori
    AsyncURB *aurb;
228 64838171 aliguori
229 64838171 aliguori
    while (1) {
230 64838171 aliguori
            USBPacket *p;
231 b9dc033c balrog
232 64838171 aliguori
        int r = ioctl(s->fd, USBDEVFS_REAPURBNDELAY, &aurb);
233 64838171 aliguori
        if (r < 0) {
234 64838171 aliguori
            if (errno == EAGAIN)
235 64838171 aliguori
                return;
236 64838171 aliguori
237 24772c1e aliguori
            if (errno == ENODEV && !s->closing) {
238 64838171 aliguori
                printf("husb: device %d.%d disconnected\n", s->bus_num, s->addr);
239 64838171 aliguori
                usb_device_del_addr(0, s->dev.addr);
240 64838171 aliguori
                return;
241 64838171 aliguori
            }
242 64838171 aliguori
243 64838171 aliguori
            dprintf("husb: async. reap urb failed errno %d\n", errno);
244 64838171 aliguori
            return;
245 b9dc033c balrog
        }
246 64838171 aliguori
247 64838171 aliguori
        p = aurb->packet;
248 64838171 aliguori
249 64838171 aliguori
        dprintf("husb: async completed. aurb %p status %d alen %d\n", 
250 64838171 aliguori
                aurb, aurb->urb.status, aurb->urb.actual_length);
251 64838171 aliguori
252 64838171 aliguori
        if (p) {
253 64838171 aliguori
            switch (aurb->urb.status) {
254 64838171 aliguori
            case 0:
255 64838171 aliguori
                p->len = aurb->urb.actual_length;
256 446ab128 aliguori
                if (aurb->urb.type == USBDEVFS_URB_TYPE_CONTROL)
257 446ab128 aliguori
                    async_complete_ctrl(s, p);
258 64838171 aliguori
                break;
259 64838171 aliguori
260 64838171 aliguori
            case -EPIPE:
261 64838171 aliguori
                set_halt(s, p->devep);
262 64838171 aliguori
                /* fall through */
263 64838171 aliguori
            default:
264 64838171 aliguori
                p->len = USB_RET_NAK;
265 64838171 aliguori
                break;
266 64838171 aliguori
            }
267 64838171 aliguori
268 64838171 aliguori
            usb_packet_complete(p);
269 64838171 aliguori
        }
270 64838171 aliguori
271 64838171 aliguori
        async_free(aurb);
272 b9dc033c balrog
    }
273 b9dc033c balrog
}
274 b9dc033c balrog
275 64838171 aliguori
static void async_cancel(USBPacket *unused, void *opaque)
276 b9dc033c balrog
{
277 64838171 aliguori
    AsyncURB *aurb = opaque;
278 64838171 aliguori
    USBHostDevice *s = aurb->hdev;
279 b9dc033c balrog
280 64838171 aliguori
    dprintf("husb: async cancel. aurb %p\n", aurb);
281 64838171 aliguori
282 64838171 aliguori
    /* Mark it as dead (see async_complete above) */
283 64838171 aliguori
    aurb->packet = NULL;
284 b9dc033c balrog
285 64838171 aliguori
    int r = ioctl(s->fd, USBDEVFS_DISCARDURB, aurb);
286 64838171 aliguori
    if (r < 0) {
287 64838171 aliguori
        dprintf("husb: async. discard urb failed errno %d\n", errno);
288 b9dc033c balrog
    }
289 b9dc033c balrog
}
290 b9dc033c balrog
291 446ab128 aliguori
static int usb_host_claim_interfaces(USBHostDevice *dev, int configuration)
292 b9dc033c balrog
{
293 b9dc033c balrog
    int dev_descr_len, config_descr_len;
294 b9dc033c balrog
    int interface, nb_interfaces, nb_configurations;
295 b9dc033c balrog
    int ret, i;
296 b9dc033c balrog
297 b9dc033c balrog
    if (configuration == 0) /* address state - ignore */
298 b9dc033c balrog
        return 1;
299 b9dc033c balrog
300 446ab128 aliguori
    dprintf("husb: claiming interfaces. config %d\n", configuration);
301 446ab128 aliguori
302 b9dc033c balrog
    i = 0;
303 b9dc033c balrog
    dev_descr_len = dev->descr[0];
304 b9dc033c balrog
    if (dev_descr_len > dev->descr_len)
305 b9dc033c balrog
        goto fail;
306 b9dc033c balrog
    nb_configurations = dev->descr[17];
307 b9dc033c balrog
308 b9dc033c balrog
    i += dev_descr_len;
309 b9dc033c balrog
    while (i < dev->descr_len) {
310 64838171 aliguori
        dprintf("husb: i is %d, descr_len is %d, dl %d, dt %d\n", i, dev->descr_len,
311 b9dc033c balrog
               dev->descr[i], dev->descr[i+1]);
312 64838171 aliguori
313 b9dc033c balrog
        if (dev->descr[i+1] != USB_DT_CONFIG) {
314 b9dc033c balrog
            i += dev->descr[i];
315 b9dc033c balrog
            continue;
316 b9dc033c balrog
        }
317 b9dc033c balrog
        config_descr_len = dev->descr[i];
318 b9dc033c balrog
319 64838171 aliguori
        printf("husb: config #%d need %d\n", dev->descr[i + 5], configuration); 
320 1f3870ab aliguori
321 446ab128 aliguori
        if (configuration < 0 || configuration == dev->descr[i + 5]) {
322 446ab128 aliguori
            configuration = dev->descr[i + 5];
323 b9dc033c balrog
            break;
324 446ab128 aliguori
        }
325 b9dc033c balrog
326 b9dc033c balrog
        i += config_descr_len;
327 b9dc033c balrog
    }
328 b9dc033c balrog
329 b9dc033c balrog
    if (i >= dev->descr_len) {
330 0d380648 aliguori
        fprintf(stderr, "husb: update iface failed. no matching configuration\n");
331 b9dc033c balrog
        goto fail;
332 b9dc033c balrog
    }
333 b9dc033c balrog
    nb_interfaces = dev->descr[i + 4];
334 b9dc033c balrog
335 b9dc033c balrog
#ifdef USBDEVFS_DISCONNECT
336 b9dc033c balrog
    /* earlier Linux 2.4 do not support that */
337 b9dc033c balrog
    {
338 b9dc033c balrog
        struct usbdevfs_ioctl ctrl;
339 b9dc033c balrog
        for (interface = 0; interface < nb_interfaces; interface++) {
340 b9dc033c balrog
            ctrl.ioctl_code = USBDEVFS_DISCONNECT;
341 b9dc033c balrog
            ctrl.ifno = interface;
342 b9dc033c balrog
            ret = ioctl(dev->fd, USBDEVFS_IOCTL, &ctrl);
343 b9dc033c balrog
            if (ret < 0 && errno != ENODATA) {
344 b9dc033c balrog
                perror("USBDEVFS_DISCONNECT");
345 b9dc033c balrog
                goto fail;
346 b9dc033c balrog
            }
347 b9dc033c balrog
        }
348 b9dc033c balrog
    }
349 b9dc033c balrog
#endif
350 b9dc033c balrog
351 b9dc033c balrog
    /* XXX: only grab if all interfaces are free */
352 b9dc033c balrog
    for (interface = 0; interface < nb_interfaces; interface++) {
353 b9dc033c balrog
        ret = ioctl(dev->fd, USBDEVFS_CLAIMINTERFACE, &interface);
354 b9dc033c balrog
        if (ret < 0) {
355 b9dc033c balrog
            if (errno == EBUSY) {
356 64838171 aliguori
                printf("husb: update iface. device already grabbed\n");
357 b9dc033c balrog
            } else {
358 64838171 aliguori
                perror("husb: failed to claim interface");
359 b9dc033c balrog
            }
360 b9dc033c balrog
        fail:
361 b9dc033c balrog
            return 0;
362 b9dc033c balrog
        }
363 b9dc033c balrog
    }
364 b9dc033c balrog
365 64838171 aliguori
    printf("husb: %d interfaces claimed for configuration %d\n",
366 b9dc033c balrog
           nb_interfaces, configuration);
367 b9dc033c balrog
368 446ab128 aliguori
    dev->ninterfaces   = nb_interfaces;
369 446ab128 aliguori
    dev->configuration = configuration;
370 446ab128 aliguori
    return 1;
371 446ab128 aliguori
}
372 446ab128 aliguori
373 446ab128 aliguori
static int usb_host_release_interfaces(USBHostDevice *s)
374 446ab128 aliguori
{
375 446ab128 aliguori
    int ret, i;
376 446ab128 aliguori
377 446ab128 aliguori
    dprintf("husb: releasing interfaces\n");
378 446ab128 aliguori
379 446ab128 aliguori
    for (i = 0; i < s->ninterfaces; i++) {
380 446ab128 aliguori
        ret = ioctl(s->fd, USBDEVFS_RELEASEINTERFACE, &i);
381 446ab128 aliguori
        if (ret < 0) {
382 446ab128 aliguori
            perror("husb: failed to release interface");
383 446ab128 aliguori
            return 0;
384 446ab128 aliguori
        }
385 446ab128 aliguori
    }
386 446ab128 aliguori
387 b9dc033c balrog
    return 1;
388 b9dc033c balrog
}
389 b9dc033c balrog
390 059809e4 bellard
static void usb_host_handle_reset(USBDevice *dev)
391 bb36d470 bellard
{
392 446ab128 aliguori
    USBHostDevice *s = (USBHostDevice *) dev;
393 64838171 aliguori
394 64838171 aliguori
    dprintf("husb: reset device %u.%u\n", s->bus_num, s->addr);
395 64838171 aliguori
396 bb36d470 bellard
    ioctl(s->fd, USBDEVFS_RESET);
397 446ab128 aliguori
398 446ab128 aliguori
    usb_host_claim_interfaces(s, s->configuration);
399 5fafdf24 ths
}
400 bb36d470 bellard
401 059809e4 bellard
static void usb_host_handle_destroy(USBDevice *dev)
402 059809e4 bellard
{
403 059809e4 bellard
    USBHostDevice *s = (USBHostDevice *)dev;
404 059809e4 bellard
405 24772c1e aliguori
    s->closing = 1;
406 24772c1e aliguori
407 64838171 aliguori
    qemu_set_fd_handler(s->fd, NULL, NULL, NULL);
408 1f3870ab aliguori
409 4b096fc9 aliguori
    hostdev_unlink(s);
410 4b096fc9 aliguori
411 64838171 aliguori
    async_complete(s);
412 64838171 aliguori
413 059809e4 bellard
    if (s->fd >= 0)
414 059809e4 bellard
        close(s->fd);
415 1f3870ab aliguori
416 059809e4 bellard
    qemu_free(s);
417 059809e4 bellard
}
418 059809e4 bellard
419 b9dc033c balrog
static int usb_linux_update_endp_table(USBHostDevice *s);
420 b9dc033c balrog
421 446ab128 aliguori
static int usb_host_handle_data(USBHostDevice *s, USBPacket *p)
422 bb36d470 bellard
{
423 64838171 aliguori
    struct usbdevfs_urb *urb;
424 446ab128 aliguori
    AsyncURB *aurb;
425 bb36d470 bellard
    int ret;
426 bb36d470 bellard
427 64838171 aliguori
    aurb = async_alloc();
428 64838171 aliguori
    if (!aurb) {
429 64838171 aliguori
        dprintf("husb: async malloc failed\n");
430 64838171 aliguori
        return USB_RET_NAK;
431 b9dc033c balrog
    }
432 64838171 aliguori
    aurb->hdev   = s;
433 64838171 aliguori
    aurb->packet = p;
434 64838171 aliguori
435 64838171 aliguori
    urb = &aurb->urb;
436 b9dc033c balrog
437 4d611c9a pbrook
    if (p->pid == USB_TOKEN_IN)
438 64838171 aliguori
            urb->endpoint = p->devep | 0x80;
439 64838171 aliguori
    else
440 64838171 aliguori
            urb->endpoint = p->devep;
441 64838171 aliguori
442 64838171 aliguori
    if (is_halted(s, p->devep)) {
443 64838171 aliguori
        ret = ioctl(s->fd, USBDEVFS_CLEAR_HALT, &urb->endpoint);
444 64838171 aliguori
        if (ret < 0) {
445 64838171 aliguori
            dprintf("husb: failed to clear halt. ep 0x%x errno %d\n", 
446 64838171 aliguori
                   urb->endpoint, errno);
447 bb36d470 bellard
            return USB_RET_NAK;
448 bb36d470 bellard
        }
449 64838171 aliguori
        clear_halt(s, p->devep);
450 4d043a09 balrog
    }
451 4d043a09 balrog
452 64838171 aliguori
    urb->buffer        = p->data;
453 64838171 aliguori
    urb->buffer_length = p->len;
454 b9dc033c balrog
455 64838171 aliguori
    if (is_isoc(s, p->devep)) {
456 64838171 aliguori
        /* Setup ISOC transfer */
457 64838171 aliguori
        urb->type     = USBDEVFS_URB_TYPE_ISO;
458 64838171 aliguori
        urb->flags    = USBDEVFS_URB_ISO_ASAP;
459 64838171 aliguori
        urb->number_of_packets = 1;
460 64838171 aliguori
        urb->iso_frame_desc[0].length = p->len;
461 64838171 aliguori
    } else {
462 64838171 aliguori
        /* Setup bulk transfer */
463 64838171 aliguori
        urb->type     = USBDEVFS_URB_TYPE_BULK;
464 b9dc033c balrog
    }
465 b9dc033c balrog
466 64838171 aliguori
    urb->usercontext = s;
467 b9dc033c balrog
468 64838171 aliguori
    ret = ioctl(s->fd, USBDEVFS_SUBMITURB, urb);
469 b9dc033c balrog
470 64838171 aliguori
    dprintf("husb: data submit. ep 0x%x len %u aurb %p\n", urb->endpoint, p->len, aurb);
471 b9dc033c balrog
472 64838171 aliguori
    if (ret < 0) {
473 64838171 aliguori
        dprintf("husb: submit failed. errno %d\n", errno);
474 64838171 aliguori
        async_free(aurb);
475 b9dc033c balrog
476 b9dc033c balrog
        switch(errno) {
477 b9dc033c balrog
        case ETIMEDOUT:
478 b9dc033c balrog
            return USB_RET_NAK;
479 b9dc033c balrog
        case EPIPE:
480 b9dc033c balrog
        default:
481 b9dc033c balrog
            return USB_RET_STALL;
482 b9dc033c balrog
        }
483 b9dc033c balrog
    }
484 64838171 aliguori
485 64838171 aliguori
    usb_defer_packet(p, async_cancel, aurb);
486 b9dc033c balrog
    return USB_RET_ASYNC;
487 b9dc033c balrog
}
488 b9dc033c balrog
489 446ab128 aliguori
static int ctrl_error(void)
490 446ab128 aliguori
{
491 446ab128 aliguori
    if (errno == ETIMEDOUT)
492 446ab128 aliguori
        return USB_RET_NAK;
493 446ab128 aliguori
    else 
494 446ab128 aliguori
        return USB_RET_STALL;
495 446ab128 aliguori
}
496 446ab128 aliguori
497 446ab128 aliguori
static int usb_host_set_address(USBHostDevice *s, int addr)
498 446ab128 aliguori
{
499 446ab128 aliguori
    dprintf("husb: ctrl set addr %u\n", addr);
500 446ab128 aliguori
    s->dev.addr = addr;
501 446ab128 aliguori
    return 0;
502 446ab128 aliguori
}
503 446ab128 aliguori
504 446ab128 aliguori
static int usb_host_set_config(USBHostDevice *s, int config)
505 446ab128 aliguori
{
506 446ab128 aliguori
    usb_host_release_interfaces(s);
507 446ab128 aliguori
508 446ab128 aliguori
    int ret = ioctl(s->fd, USBDEVFS_SETCONFIGURATION, &config);
509 446ab128 aliguori
 
510 446ab128 aliguori
    dprintf("husb: ctrl set config %d ret %d errno %d\n", config, ret, errno);
511 446ab128 aliguori
    
512 446ab128 aliguori
    if (ret < 0)
513 446ab128 aliguori
        return ctrl_error();
514 446ab128 aliguori
 
515 446ab128 aliguori
    usb_host_claim_interfaces(s, config);
516 446ab128 aliguori
    return 0;
517 446ab128 aliguori
}
518 446ab128 aliguori
519 446ab128 aliguori
static int usb_host_set_interface(USBHostDevice *s, int iface, int alt)
520 446ab128 aliguori
{
521 446ab128 aliguori
    struct usbdevfs_setinterface si;
522 446ab128 aliguori
    int ret;
523 446ab128 aliguori
524 446ab128 aliguori
    si.interface  = iface;
525 446ab128 aliguori
    si.altsetting = alt;
526 446ab128 aliguori
    ret = ioctl(s->fd, USBDEVFS_SETINTERFACE, &si);
527 446ab128 aliguori
    
528 446ab128 aliguori
    dprintf("husb: ctrl set iface %d altset %d ret %d errno %d\n", 
529 446ab128 aliguori
            iface, alt, ret, errno);
530 446ab128 aliguori
    
531 446ab128 aliguori
    if (ret < 0)
532 446ab128 aliguori
        return ctrl_error();
533 446ab128 aliguori
534 446ab128 aliguori
    usb_linux_update_endp_table(s);
535 446ab128 aliguori
    return 0;
536 446ab128 aliguori
}
537 446ab128 aliguori
538 446ab128 aliguori
static int usb_host_handle_control(USBHostDevice *s, USBPacket *p)
539 446ab128 aliguori
{
540 446ab128 aliguori
    struct usbdevfs_urb *urb;
541 446ab128 aliguori
    AsyncURB *aurb;
542 446ab128 aliguori
    int ret, value, index;
543 446ab128 aliguori
544 446ab128 aliguori
    /* 
545 446ab128 aliguori
     * Process certain standard device requests.
546 446ab128 aliguori
     * These are infrequent and are processed synchronously.
547 446ab128 aliguori
     */
548 446ab128 aliguori
    value = le16_to_cpu(s->ctrl.req.wValue);
549 446ab128 aliguori
    index = le16_to_cpu(s->ctrl.req.wIndex);
550 446ab128 aliguori
551 446ab128 aliguori
    dprintf("husb: ctrl type 0x%x req 0x%x val 0x%x index %u len %u\n",
552 446ab128 aliguori
        s->ctrl.req.bRequestType, s->ctrl.req.bRequest, value, index, 
553 446ab128 aliguori
        s->ctrl.len);
554 446ab128 aliguori
555 446ab128 aliguori
    if (s->ctrl.req.bRequestType == 0) {
556 446ab128 aliguori
        switch (s->ctrl.req.bRequest) {
557 446ab128 aliguori
        case USB_REQ_SET_ADDRESS:
558 446ab128 aliguori
            return usb_host_set_address(s, value);
559 446ab128 aliguori
560 446ab128 aliguori
        case USB_REQ_SET_CONFIGURATION:
561 446ab128 aliguori
            return usb_host_set_config(s, value & 0xff);
562 446ab128 aliguori
        }
563 446ab128 aliguori
    }
564 446ab128 aliguori
565 446ab128 aliguori
    if (s->ctrl.req.bRequestType == 1 &&
566 446ab128 aliguori
                  s->ctrl.req.bRequest == USB_REQ_SET_INTERFACE)
567 446ab128 aliguori
        return usb_host_set_interface(s, index, value);
568 446ab128 aliguori
569 446ab128 aliguori
    /* The rest are asynchronous */
570 446ab128 aliguori
571 446ab128 aliguori
    aurb = async_alloc();
572 446ab128 aliguori
    if (!aurb) {
573 446ab128 aliguori
        dprintf("husb: async malloc failed\n");
574 446ab128 aliguori
        return USB_RET_NAK;
575 446ab128 aliguori
    }
576 446ab128 aliguori
    aurb->hdev   = s;
577 446ab128 aliguori
    aurb->packet = p;
578 446ab128 aliguori
579 446ab128 aliguori
    /* 
580 446ab128 aliguori
     * Setup ctrl transfer.
581 446ab128 aliguori
     *
582 446ab128 aliguori
     * s->ctrl is layed out such that data buffer immediately follows
583 446ab128 aliguori
     * 'req' struct which is exactly what usbdevfs expects.
584 446ab128 aliguori
     */ 
585 446ab128 aliguori
    urb = &aurb->urb;
586 446ab128 aliguori
587 446ab128 aliguori
    urb->type     = USBDEVFS_URB_TYPE_CONTROL;
588 446ab128 aliguori
    urb->endpoint = p->devep;
589 446ab128 aliguori
590 446ab128 aliguori
    urb->buffer        = &s->ctrl.req;
591 446ab128 aliguori
    urb->buffer_length = 8 + s->ctrl.len;
592 446ab128 aliguori
593 446ab128 aliguori
    urb->usercontext = s;
594 446ab128 aliguori
595 446ab128 aliguori
    ret = ioctl(s->fd, USBDEVFS_SUBMITURB, urb);
596 446ab128 aliguori
597 446ab128 aliguori
    dprintf("husb: submit ctrl. len %u aurb %p\n", urb->buffer_length, aurb);
598 446ab128 aliguori
599 446ab128 aliguori
    if (ret < 0) {
600 446ab128 aliguori
        dprintf("husb: submit failed. errno %d\n", errno);
601 446ab128 aliguori
        async_free(aurb);
602 446ab128 aliguori
603 446ab128 aliguori
        switch(errno) {
604 446ab128 aliguori
        case ETIMEDOUT:
605 446ab128 aliguori
            return USB_RET_NAK;
606 446ab128 aliguori
        case EPIPE:
607 446ab128 aliguori
        default:
608 446ab128 aliguori
            return USB_RET_STALL;
609 446ab128 aliguori
        }
610 446ab128 aliguori
    }
611 446ab128 aliguori
612 446ab128 aliguori
    usb_defer_packet(p, async_cancel, aurb);
613 446ab128 aliguori
    return USB_RET_ASYNC;
614 446ab128 aliguori
}
615 446ab128 aliguori
616 446ab128 aliguori
static int do_token_setup(USBDevice *dev, USBPacket *p)
617 446ab128 aliguori
{
618 446ab128 aliguori
    USBHostDevice *s = (USBHostDevice *) dev;
619 446ab128 aliguori
    int ret = 0;
620 446ab128 aliguori
621 446ab128 aliguori
    if (p->len != 8)
622 446ab128 aliguori
        return USB_RET_STALL;
623 446ab128 aliguori
 
624 446ab128 aliguori
    memcpy(&s->ctrl.req, p->data, 8);
625 446ab128 aliguori
    s->ctrl.len    = le16_to_cpu(s->ctrl.req.wLength);
626 446ab128 aliguori
    s->ctrl.offset = 0;
627 446ab128 aliguori
    s->ctrl.state  = CTRL_STATE_SETUP;
628 446ab128 aliguori
629 446ab128 aliguori
    if (s->ctrl.req.bRequestType & USB_DIR_IN) {
630 446ab128 aliguori
        ret = usb_host_handle_control(s, p);
631 446ab128 aliguori
        if (ret < 0)
632 446ab128 aliguori
            return ret;
633 446ab128 aliguori
634 446ab128 aliguori
        if (ret < s->ctrl.len)
635 446ab128 aliguori
            s->ctrl.len = ret;
636 446ab128 aliguori
        s->ctrl.state = CTRL_STATE_DATA;
637 446ab128 aliguori
    } else {
638 446ab128 aliguori
        if (s->ctrl.len == 0)
639 446ab128 aliguori
            s->ctrl.state = CTRL_STATE_ACK;
640 446ab128 aliguori
        else
641 446ab128 aliguori
            s->ctrl.state = CTRL_STATE_DATA;
642 446ab128 aliguori
    }
643 446ab128 aliguori
644 446ab128 aliguori
    return ret;
645 446ab128 aliguori
}
646 446ab128 aliguori
647 446ab128 aliguori
static int do_token_in(USBDevice *dev, USBPacket *p)
648 446ab128 aliguori
{
649 446ab128 aliguori
    USBHostDevice *s = (USBHostDevice *) dev;
650 446ab128 aliguori
    int ret = 0;
651 446ab128 aliguori
652 446ab128 aliguori
    if (p->devep != 0)
653 446ab128 aliguori
        return usb_host_handle_data(s, p);
654 446ab128 aliguori
655 446ab128 aliguori
    switch(s->ctrl.state) {
656 446ab128 aliguori
    case CTRL_STATE_ACK:
657 446ab128 aliguori
        if (!(s->ctrl.req.bRequestType & USB_DIR_IN)) {
658 446ab128 aliguori
            ret = usb_host_handle_control(s, p);
659 446ab128 aliguori
            if (ret == USB_RET_ASYNC)
660 446ab128 aliguori
                return USB_RET_ASYNC;
661 446ab128 aliguori
662 446ab128 aliguori
            s->ctrl.state = CTRL_STATE_IDLE;
663 446ab128 aliguori
            return ret > 0 ? 0 : ret;
664 446ab128 aliguori
        }
665 446ab128 aliguori
666 446ab128 aliguori
        return 0;
667 446ab128 aliguori
668 446ab128 aliguori
    case CTRL_STATE_DATA:
669 446ab128 aliguori
        if (s->ctrl.req.bRequestType & USB_DIR_IN) {
670 446ab128 aliguori
            int len = s->ctrl.len - s->ctrl.offset;
671 446ab128 aliguori
            if (len > p->len)
672 446ab128 aliguori
                len = p->len;
673 446ab128 aliguori
            memcpy(p->data, s->ctrl.buffer + s->ctrl.offset, len);
674 446ab128 aliguori
            s->ctrl.offset += len;
675 446ab128 aliguori
            if (s->ctrl.offset >= s->ctrl.len)
676 446ab128 aliguori
                s->ctrl.state = CTRL_STATE_ACK;
677 446ab128 aliguori
            return len;
678 446ab128 aliguori
        }
679 446ab128 aliguori
680 446ab128 aliguori
        s->ctrl.state = CTRL_STATE_IDLE;
681 446ab128 aliguori
        return USB_RET_STALL;
682 446ab128 aliguori
683 446ab128 aliguori
    default:
684 446ab128 aliguori
        return USB_RET_STALL;
685 446ab128 aliguori
    }
686 446ab128 aliguori
}
687 446ab128 aliguori
688 446ab128 aliguori
static int do_token_out(USBDevice *dev, USBPacket *p)
689 446ab128 aliguori
{
690 446ab128 aliguori
    USBHostDevice *s = (USBHostDevice *) dev;
691 446ab128 aliguori
692 446ab128 aliguori
    if (p->devep != 0)
693 446ab128 aliguori
        return usb_host_handle_data(s, p);
694 446ab128 aliguori
695 446ab128 aliguori
    switch(s->ctrl.state) {
696 446ab128 aliguori
    case CTRL_STATE_ACK:
697 446ab128 aliguori
        if (s->ctrl.req.bRequestType & USB_DIR_IN) {
698 446ab128 aliguori
            s->ctrl.state = CTRL_STATE_IDLE;
699 446ab128 aliguori
            /* transfer OK */
700 446ab128 aliguori
        } else {
701 446ab128 aliguori
            /* ignore additional output */
702 446ab128 aliguori
        }
703 446ab128 aliguori
        return 0;
704 446ab128 aliguori
705 446ab128 aliguori
    case CTRL_STATE_DATA:
706 446ab128 aliguori
        if (!(s->ctrl.req.bRequestType & USB_DIR_IN)) {
707 446ab128 aliguori
            int len = s->ctrl.len - s->ctrl.offset;
708 446ab128 aliguori
            if (len > p->len)
709 446ab128 aliguori
                len = p->len;
710 446ab128 aliguori
            memcpy(s->ctrl.buffer + s->ctrl.offset, p->data, len);
711 446ab128 aliguori
            s->ctrl.offset += len;
712 446ab128 aliguori
            if (s->ctrl.offset >= s->ctrl.len)
713 446ab128 aliguori
                s->ctrl.state = CTRL_STATE_ACK;
714 446ab128 aliguori
            return len;
715 446ab128 aliguori
        }
716 446ab128 aliguori
717 446ab128 aliguori
        s->ctrl.state = CTRL_STATE_IDLE;
718 446ab128 aliguori
        return USB_RET_STALL;
719 446ab128 aliguori
720 446ab128 aliguori
    default:
721 446ab128 aliguori
        return USB_RET_STALL;
722 446ab128 aliguori
    }
723 446ab128 aliguori
}
724 446ab128 aliguori
725 446ab128 aliguori
/*
726 446ab128 aliguori
 * Packet handler.
727 446ab128 aliguori
 * Called by the HC (host controller).
728 446ab128 aliguori
 *
729 446ab128 aliguori
 * Returns length of the transaction or one of the USB_RET_XXX codes.
730 446ab128 aliguori
 */
731 d9cf1578 blueswir1
static int usb_host_handle_packet(USBDevice *s, USBPacket *p)
732 446ab128 aliguori
{
733 446ab128 aliguori
    switch(p->pid) {
734 446ab128 aliguori
    case USB_MSG_ATTACH:
735 446ab128 aliguori
        s->state = USB_STATE_ATTACHED;
736 446ab128 aliguori
        return 0;
737 446ab128 aliguori
738 446ab128 aliguori
    case USB_MSG_DETACH:
739 446ab128 aliguori
        s->state = USB_STATE_NOTATTACHED;
740 446ab128 aliguori
        return 0;
741 446ab128 aliguori
742 446ab128 aliguori
    case USB_MSG_RESET:
743 446ab128 aliguori
        s->remote_wakeup = 0;
744 446ab128 aliguori
        s->addr = 0;
745 446ab128 aliguori
        s->state = USB_STATE_DEFAULT;
746 446ab128 aliguori
        s->handle_reset(s);
747 446ab128 aliguori
        return 0;
748 446ab128 aliguori
    }
749 446ab128 aliguori
750 446ab128 aliguori
    /* Rest of the PIDs must match our address */
751 446ab128 aliguori
    if (s->state < USB_STATE_DEFAULT || p->devaddr != s->addr)
752 446ab128 aliguori
        return USB_RET_NODEV;
753 446ab128 aliguori
754 446ab128 aliguori
    switch (p->pid) {
755 446ab128 aliguori
    case USB_TOKEN_SETUP:
756 446ab128 aliguori
        return do_token_setup(s, p);
757 446ab128 aliguori
758 446ab128 aliguori
    case USB_TOKEN_IN:
759 446ab128 aliguori
        return do_token_in(s, p);
760 446ab128 aliguori
761 446ab128 aliguori
    case USB_TOKEN_OUT:
762 446ab128 aliguori
        return do_token_out(s, p);
763 446ab128 aliguori
 
764 446ab128 aliguori
    default:
765 446ab128 aliguori
        return USB_RET_STALL;
766 446ab128 aliguori
    }
767 446ab128 aliguori
}
768 446ab128 aliguori
769 b9dc033c balrog
/* returns 1 on problem encountered or 0 for success */
770 b9dc033c balrog
static int usb_linux_update_endp_table(USBHostDevice *s)
771 b9dc033c balrog
{
772 b9dc033c balrog
    uint8_t *descriptors;
773 b9dc033c balrog
    uint8_t devep, type, configuration, alt_interface;
774 446ab128 aliguori
    struct usbdevfs_ctrltransfer ct;
775 b9dc033c balrog
    int interface, ret, length, i;
776 b9dc033c balrog
777 b9dc033c balrog
    ct.bRequestType = USB_DIR_IN;
778 b9dc033c balrog
    ct.bRequest = USB_REQ_GET_CONFIGURATION;
779 b9dc033c balrog
    ct.wValue = 0;
780 b9dc033c balrog
    ct.wIndex = 0;
781 b9dc033c balrog
    ct.wLength = 1;
782 b9dc033c balrog
    ct.data = &configuration;
783 b9dc033c balrog
    ct.timeout = 50;
784 b9dc033c balrog
785 b9dc033c balrog
    ret = ioctl(s->fd, USBDEVFS_CONTROL, &ct);
786 b9dc033c balrog
    if (ret < 0) {
787 b9dc033c balrog
        perror("usb_linux_update_endp_table");
788 b9dc033c balrog
        return 1;
789 b9dc033c balrog
    }
790 b9dc033c balrog
791 b9dc033c balrog
    /* in address state */
792 b9dc033c balrog
    if (configuration == 0)
793 b9dc033c balrog
        return 1;
794 b9dc033c balrog
795 b9dc033c balrog
    /* get the desired configuration, interface, and endpoint descriptors
796 b9dc033c balrog
     * from device description */
797 b9dc033c balrog
    descriptors = &s->descr[18];
798 b9dc033c balrog
    length = s->descr_len - 18;
799 b9dc033c balrog
    i = 0;
800 b9dc033c balrog
801 b9dc033c balrog
    if (descriptors[i + 1] != USB_DT_CONFIG ||
802 b9dc033c balrog
        descriptors[i + 5] != configuration) {
803 64838171 aliguori
        dprintf("invalid descriptor data - configuration\n");
804 b9dc033c balrog
        return 1;
805 b9dc033c balrog
    }
806 b9dc033c balrog
    i += descriptors[i];
807 b9dc033c balrog
808 b9dc033c balrog
    while (i < length) {
809 b9dc033c balrog
        if (descriptors[i + 1] != USB_DT_INTERFACE ||
810 b9dc033c balrog
            (descriptors[i + 1] == USB_DT_INTERFACE &&
811 b9dc033c balrog
             descriptors[i + 4] == 0)) {
812 b9dc033c balrog
            i += descriptors[i];
813 b9dc033c balrog
            continue;
814 b9dc033c balrog
        }
815 b9dc033c balrog
816 b9dc033c balrog
        interface = descriptors[i + 2];
817 b9dc033c balrog
818 b9dc033c balrog
        ct.bRequestType = USB_DIR_IN | USB_RECIP_INTERFACE;
819 b9dc033c balrog
        ct.bRequest = USB_REQ_GET_INTERFACE;
820 b9dc033c balrog
        ct.wValue = 0;
821 b9dc033c balrog
        ct.wIndex = interface;
822 b9dc033c balrog
        ct.wLength = 1;
823 b9dc033c balrog
        ct.data = &alt_interface;
824 b9dc033c balrog
        ct.timeout = 50;
825 b9dc033c balrog
826 b9dc033c balrog
        ret = ioctl(s->fd, USBDEVFS_CONTROL, &ct);
827 b9dc033c balrog
        if (ret < 0) {
828 b9dc033c balrog
            perror("usb_linux_update_endp_table");
829 b9dc033c balrog
            return 1;
830 b9dc033c balrog
        }
831 b9dc033c balrog
832 b9dc033c balrog
        /* the current interface descriptor is the active interface
833 b9dc033c balrog
         * and has endpoints */
834 b9dc033c balrog
        if (descriptors[i + 3] != alt_interface) {
835 b9dc033c balrog
            i += descriptors[i];
836 b9dc033c balrog
            continue;
837 b9dc033c balrog
        }
838 b9dc033c balrog
839 b9dc033c balrog
        /* advance to the endpoints */
840 b9dc033c balrog
        while (i < length && descriptors[i +1] != USB_DT_ENDPOINT)
841 b9dc033c balrog
            i += descriptors[i];
842 b9dc033c balrog
843 b9dc033c balrog
        if (i >= length)
844 b9dc033c balrog
            break;
845 b9dc033c balrog
846 b9dc033c balrog
        while (i < length) {
847 b9dc033c balrog
            if (descriptors[i + 1] != USB_DT_ENDPOINT)
848 b9dc033c balrog
                break;
849 b9dc033c balrog
850 b9dc033c balrog
            devep = descriptors[i + 2];
851 b9dc033c balrog
            switch (descriptors[i + 3] & 0x3) {
852 b9dc033c balrog
            case 0x00:
853 b9dc033c balrog
                type = USBDEVFS_URB_TYPE_CONTROL;
854 b9dc033c balrog
                break;
855 b9dc033c balrog
            case 0x01:
856 b9dc033c balrog
                type = USBDEVFS_URB_TYPE_ISO;
857 b9dc033c balrog
                break;
858 b9dc033c balrog
            case 0x02:
859 b9dc033c balrog
                type = USBDEVFS_URB_TYPE_BULK;
860 b9dc033c balrog
                break;
861 b9dc033c balrog
            case 0x03:
862 b9dc033c balrog
                type = USBDEVFS_URB_TYPE_INTERRUPT;
863 b9dc033c balrog
                break;
864 b9dc033c balrog
            default:
865 64838171 aliguori
                dprintf("usb_host: malformed endpoint type\n");
866 b9dc033c balrog
                type = USBDEVFS_URB_TYPE_BULK;
867 b9dc033c balrog
            }
868 b9dc033c balrog
            s->endp_table[(devep & 0xf) - 1].type = type;
869 64838171 aliguori
            s->endp_table[(devep & 0xf) - 1].halted = 0;
870 b9dc033c balrog
871 b9dc033c balrog
            i += descriptors[i];
872 b9dc033c balrog
        }
873 b9dc033c balrog
    }
874 b9dc033c balrog
    return 0;
875 b9dc033c balrog
}
876 b9dc033c balrog
877 4b096fc9 aliguori
static USBDevice *usb_host_device_open_addr(int bus_num, int addr, const char *prod_name)
878 bb36d470 bellard
{
879 b9dc033c balrog
    int fd = -1, ret;
880 b9dc033c balrog
    USBHostDevice *dev = NULL;
881 bb36d470 bellard
    struct usbdevfs_connectinfo ci;
882 a594cfbf bellard
    char buf[1024];
883 1f3870ab aliguori
884 b9dc033c balrog
    dev = qemu_mallocz(sizeof(USBHostDevice));
885 b9dc033c balrog
    if (!dev)
886 b9dc033c balrog
        goto fail;
887 b9dc033c balrog
888 4b096fc9 aliguori
    dev->bus_num = bus_num;
889 4b096fc9 aliguori
    dev->addr = addr;
890 4b096fc9 aliguori
891 64838171 aliguori
    printf("husb: open device %d.%d\n", bus_num, addr);
892 3b46e624 ths
893 5fafdf24 ths
    snprintf(buf, sizeof(buf), USBDEVFS_PATH "/%03d/%03d",
894 a594cfbf bellard
             bus_num, addr);
895 b9dc033c balrog
    fd = open(buf, O_RDWR | O_NONBLOCK);
896 bb36d470 bellard
    if (fd < 0) {
897 a594cfbf bellard
        perror(buf);
898 1f3870ab aliguori
        goto fail;
899 bb36d470 bellard
    }
900 bb36d470 bellard
901 b9dc033c balrog
    /* read the device description */
902 b9dc033c balrog
    dev->descr_len = read(fd, dev->descr, sizeof(dev->descr));
903 b9dc033c balrog
    if (dev->descr_len <= 0) {
904 64838171 aliguori
        perror("husb: reading device data failed");
905 bb36d470 bellard
        goto fail;
906 bb36d470 bellard
    }
907 3b46e624 ths
908 b9dc033c balrog
#ifdef DEBUG
909 868bfe2b bellard
    {
910 b9dc033c balrog
        int x;
911 b9dc033c balrog
        printf("=== begin dumping device descriptor data ===\n");
912 b9dc033c balrog
        for (x = 0; x < dev->descr_len; x++)
913 b9dc033c balrog
            printf("%02x ", dev->descr[x]);
914 b9dc033c balrog
        printf("\n=== end dumping device descriptor data ===\n");
915 bb36d470 bellard
    }
916 a594cfbf bellard
#endif
917 a594cfbf bellard
918 b9dc033c balrog
    dev->fd = fd;
919 b9dc033c balrog
920 446ab128 aliguori
    /* 
921 446ab128 aliguori
     * Initial configuration is -1 which makes us claim first 
922 446ab128 aliguori
     * available config. We used to start with 1, which does not
923 446ab128 aliguori
     * always work. I've seen devices where first config starts 
924 446ab128 aliguori
     * with 2.
925 446ab128 aliguori
     */
926 446ab128 aliguori
    if (!usb_host_claim_interfaces(dev, -1))
927 b9dc033c balrog
        goto fail;
928 bb36d470 bellard
929 bb36d470 bellard
    ret = ioctl(fd, USBDEVFS_CONNECTINFO, &ci);
930 bb36d470 bellard
    if (ret < 0) {
931 046833ea balrog
        perror("usb_host_device_open: USBDEVFS_CONNECTINFO");
932 bb36d470 bellard
        goto fail;
933 bb36d470 bellard
    }
934 bb36d470 bellard
935 64838171 aliguori
    printf("husb: grabbed usb device %d.%d\n", bus_num, addr);
936 bb36d470 bellard
937 b9dc033c balrog
    ret = usb_linux_update_endp_table(dev);
938 b9dc033c balrog
    if (ret)
939 bb36d470 bellard
        goto fail;
940 b9dc033c balrog
941 bb36d470 bellard
    if (ci.slow)
942 bb36d470 bellard
        dev->dev.speed = USB_SPEED_LOW;
943 bb36d470 bellard
    else
944 bb36d470 bellard
        dev->dev.speed = USB_SPEED_HIGH;
945 bb36d470 bellard
946 446ab128 aliguori
    dev->dev.handle_packet  = usb_host_handle_packet;
947 446ab128 aliguori
    dev->dev.handle_reset   = usb_host_handle_reset;
948 059809e4 bellard
    dev->dev.handle_destroy = usb_host_handle_destroy;
949 1f6e24e7 bellard
950 4b096fc9 aliguori
    if (!prod_name || prod_name[0] == '\0')
951 1f6e24e7 bellard
        snprintf(dev->dev.devname, sizeof(dev->dev.devname),
952 4b096fc9 aliguori
                 "host:%d.%d", bus_num, addr);
953 1f6e24e7 bellard
    else
954 1f6e24e7 bellard
        pstrcpy(dev->dev.devname, sizeof(dev->dev.devname),
955 4b096fc9 aliguori
                prod_name);
956 1f6e24e7 bellard
957 64838171 aliguori
    /* USB devio uses 'write' flag to check for async completions */
958 64838171 aliguori
    qemu_set_fd_handler(dev->fd, NULL, async_complete, dev);
959 1f3870ab aliguori
960 4b096fc9 aliguori
    hostdev_link(dev);
961 4b096fc9 aliguori
962 64838171 aliguori
    return (USBDevice *) dev;
963 4b096fc9 aliguori
964 b9dc033c balrog
fail:
965 24772c1e aliguori
    if (dev)
966 b9dc033c balrog
        qemu_free(dev);
967 24772c1e aliguori
968 b9dc033c balrog
    close(fd);
969 b9dc033c balrog
    return NULL;
970 a594cfbf bellard
}
971 bb36d470 bellard
972 5d0c5750 aliguori
static int usb_host_auto_add(const char *spec);
973 5d0c5750 aliguori
static int usb_host_auto_del(const char *spec);
974 5d0c5750 aliguori
975 4b096fc9 aliguori
USBDevice *usb_host_device_open(const char *devname)
976 4b096fc9 aliguori
{
977 4b096fc9 aliguori
    int bus_num, addr;
978 4b096fc9 aliguori
    char product_name[PRODUCT_NAME_SZ];
979 4b096fc9 aliguori
980 5d0c5750 aliguori
    if (strstr(devname, "auto:")) {
981 5d0c5750 aliguori
        usb_host_auto_add(devname);
982 4b096fc9 aliguori
        return NULL;
983 5d0c5750 aliguori
    }
984 4b096fc9 aliguori
985 5d0c5750 aliguori
    if (usb_host_find_device(&bus_num, &addr, product_name, sizeof(product_name),
986 5d0c5750 aliguori
                             devname) < 0)
987 4b096fc9 aliguori
        return NULL;
988 5d0c5750 aliguori
989 5d0c5750 aliguori
    if (hostdev_find(bus_num, addr)) {
990 5d0c5750 aliguori
       term_printf("husb: host usb device %d.%d is already open\n", bus_num, addr);
991 5d0c5750 aliguori
       return NULL;
992 5d0c5750 aliguori
    }
993 4b096fc9 aliguori
994 4b096fc9 aliguori
    return usb_host_device_open_addr(bus_num, addr, product_name);
995 4b096fc9 aliguori
}
996 5d0c5750 aliguori
997 5d0c5750 aliguori
int usb_host_device_close(const char *devname)
998 5d0c5750 aliguori
{
999 5d0c5750 aliguori
    char product_name[PRODUCT_NAME_SZ];
1000 5d0c5750 aliguori
    int bus_num, addr;
1001 5d0c5750 aliguori
    USBHostDevice *s;
1002 5d0c5750 aliguori
1003 5d0c5750 aliguori
    if (strstr(devname, "auto:"))
1004 5d0c5750 aliguori
        return usb_host_auto_del(devname);
1005 5d0c5750 aliguori
1006 5d0c5750 aliguori
    if (usb_host_find_device(&bus_num, &addr, product_name, sizeof(product_name),
1007 5d0c5750 aliguori
                             devname) < 0)
1008 5d0c5750 aliguori
        return -1;
1009 5d0c5750 aliguori
 
1010 5d0c5750 aliguori
    s = hostdev_find(bus_num, addr);
1011 5d0c5750 aliguori
    if (s) {
1012 5d0c5750 aliguori
        usb_device_del_addr(0, s->dev.addr);
1013 5d0c5750 aliguori
        return 0;
1014 5d0c5750 aliguori
    }
1015 5d0c5750 aliguori
1016 5d0c5750 aliguori
    return -1;
1017 5d0c5750 aliguori
}
1018 4b096fc9 aliguori
 
1019 a594cfbf bellard
static int get_tag_value(char *buf, int buf_size,
1020 5fafdf24 ths
                         const char *str, const char *tag,
1021 a594cfbf bellard
                         const char *stopchars)
1022 a594cfbf bellard
{
1023 a594cfbf bellard
    const char *p;
1024 a594cfbf bellard
    char *q;
1025 a594cfbf bellard
    p = strstr(str, tag);
1026 a594cfbf bellard
    if (!p)
1027 a594cfbf bellard
        return -1;
1028 a594cfbf bellard
    p += strlen(tag);
1029 a594cfbf bellard
    while (isspace(*p))
1030 a594cfbf bellard
        p++;
1031 a594cfbf bellard
    q = buf;
1032 a594cfbf bellard
    while (*p != '\0' && !strchr(stopchars, *p)) {
1033 a594cfbf bellard
        if ((q - buf) < (buf_size - 1))
1034 a594cfbf bellard
            *q++ = *p;
1035 a594cfbf bellard
        p++;
1036 a594cfbf bellard
    }
1037 a594cfbf bellard
    *q = '\0';
1038 a594cfbf bellard
    return q - buf;
1039 bb36d470 bellard
}
1040 bb36d470 bellard
1041 a594cfbf bellard
static int usb_host_scan(void *opaque, USBScanFunc *func)
1042 bb36d470 bellard
{
1043 a594cfbf bellard
    FILE *f;
1044 a594cfbf bellard
    char line[1024];
1045 bb36d470 bellard
    char buf[1024];
1046 a594cfbf bellard
    int bus_num, addr, speed, device_count, class_id, product_id, vendor_id;
1047 a594cfbf bellard
    int ret;
1048 a594cfbf bellard
    char product_name[512];
1049 3b46e624 ths
1050 a594cfbf bellard
    f = fopen(USBDEVFS_PATH "/devices", "r");
1051 a594cfbf bellard
    if (!f) {
1052 64838171 aliguori
        term_printf("husb: could not open %s\n", USBDEVFS_PATH "/devices");
1053 a594cfbf bellard
        return 0;
1054 a594cfbf bellard
    }
1055 a594cfbf bellard
    device_count = 0;
1056 a594cfbf bellard
    bus_num = addr = speed = class_id = product_id = vendor_id = 0;
1057 a594cfbf bellard
    ret = 0;
1058 bb36d470 bellard
    for(;;) {
1059 a594cfbf bellard
        if (fgets(line, sizeof(line), f) == NULL)
1060 bb36d470 bellard
            break;
1061 a594cfbf bellard
        if (strlen(line) > 0)
1062 a594cfbf bellard
            line[strlen(line) - 1] = '\0';
1063 a594cfbf bellard
        if (line[0] == 'T' && line[1] == ':') {
1064 38ca0f6d pbrook
            if (device_count && (vendor_id || product_id)) {
1065 38ca0f6d pbrook
                /* New device.  Add the previously discovered device.  */
1066 5fafdf24 ths
                ret = func(opaque, bus_num, addr, class_id, vendor_id,
1067 a594cfbf bellard
                           product_id, product_name, speed);
1068 a594cfbf bellard
                if (ret)
1069 a594cfbf bellard
                    goto the_end;
1070 a594cfbf bellard
            }
1071 a594cfbf bellard
            if (get_tag_value(buf, sizeof(buf), line, "Bus=", " ") < 0)
1072 a594cfbf bellard
                goto fail;
1073 a594cfbf bellard
            bus_num = atoi(buf);
1074 a594cfbf bellard
            if (get_tag_value(buf, sizeof(buf), line, "Dev#=", " ") < 0)
1075 a594cfbf bellard
                goto fail;
1076 a594cfbf bellard
            addr = atoi(buf);
1077 a594cfbf bellard
            if (get_tag_value(buf, sizeof(buf), line, "Spd=", " ") < 0)
1078 a594cfbf bellard
                goto fail;
1079 a594cfbf bellard
            if (!strcmp(buf, "480"))
1080 a594cfbf bellard
                speed = USB_SPEED_HIGH;
1081 a594cfbf bellard
            else if (!strcmp(buf, "1.5"))
1082 a594cfbf bellard
                speed = USB_SPEED_LOW;
1083 a594cfbf bellard
            else
1084 a594cfbf bellard
                speed = USB_SPEED_FULL;
1085 a594cfbf bellard
            product_name[0] = '\0';
1086 a594cfbf bellard
            class_id = 0xff;
1087 a594cfbf bellard
            device_count++;
1088 a594cfbf bellard
            product_id = 0;
1089 a594cfbf bellard
            vendor_id = 0;
1090 a594cfbf bellard
        } else if (line[0] == 'P' && line[1] == ':') {
1091 a594cfbf bellard
            if (get_tag_value(buf, sizeof(buf), line, "Vendor=", " ") < 0)
1092 a594cfbf bellard
                goto fail;
1093 a594cfbf bellard
            vendor_id = strtoul(buf, NULL, 16);
1094 a594cfbf bellard
            if (get_tag_value(buf, sizeof(buf), line, "ProdID=", " ") < 0)
1095 a594cfbf bellard
                goto fail;
1096 a594cfbf bellard
            product_id = strtoul(buf, NULL, 16);
1097 a594cfbf bellard
        } else if (line[0] == 'S' && line[1] == ':') {
1098 a594cfbf bellard
            if (get_tag_value(buf, sizeof(buf), line, "Product=", "") < 0)
1099 a594cfbf bellard
                goto fail;
1100 a594cfbf bellard
            pstrcpy(product_name, sizeof(product_name), buf);
1101 a594cfbf bellard
        } else if (line[0] == 'D' && line[1] == ':') {
1102 a594cfbf bellard
            if (get_tag_value(buf, sizeof(buf), line, "Cls=", " (") < 0)
1103 a594cfbf bellard
                goto fail;
1104 a594cfbf bellard
            class_id = strtoul(buf, NULL, 16);
1105 bb36d470 bellard
        }
1106 a594cfbf bellard
    fail: ;
1107 a594cfbf bellard
    }
1108 38ca0f6d pbrook
    if (device_count && (vendor_id || product_id)) {
1109 38ca0f6d pbrook
        /* Add the last device.  */
1110 5fafdf24 ths
        ret = func(opaque, bus_num, addr, class_id, vendor_id,
1111 a594cfbf bellard
                   product_id, product_name, speed);
1112 bb36d470 bellard
    }
1113 a594cfbf bellard
 the_end:
1114 a594cfbf bellard
    fclose(f);
1115 a594cfbf bellard
    return ret;
1116 bb36d470 bellard
}
1117 bb36d470 bellard
1118 4b096fc9 aliguori
struct USBAutoFilter {
1119 4b096fc9 aliguori
    struct USBAutoFilter *next;
1120 4b096fc9 aliguori
    int bus_num;
1121 4b096fc9 aliguori
    int addr;
1122 4b096fc9 aliguori
    int vendor_id;
1123 4b096fc9 aliguori
    int product_id;
1124 4b096fc9 aliguori
};
1125 4b096fc9 aliguori
1126 4b096fc9 aliguori
static QEMUTimer *usb_auto_timer;
1127 4b096fc9 aliguori
static struct USBAutoFilter *usb_auto_filter;
1128 4b096fc9 aliguori
1129 4b096fc9 aliguori
static int usb_host_auto_scan(void *opaque, int bus_num, int addr,
1130 4b096fc9 aliguori
                     int class_id, int vendor_id, int product_id,
1131 4b096fc9 aliguori
                     const char *product_name, int speed)
1132 4b096fc9 aliguori
{
1133 4b096fc9 aliguori
    struct USBAutoFilter *f;
1134 4b096fc9 aliguori
    struct USBDevice *dev;
1135 4b096fc9 aliguori
1136 4b096fc9 aliguori
    /* Ignore hubs */
1137 4b096fc9 aliguori
    if (class_id == 9)
1138 4b096fc9 aliguori
        return 0;
1139 4b096fc9 aliguori
1140 4b096fc9 aliguori
    for (f = usb_auto_filter; f; f = f->next) {
1141 4b096fc9 aliguori
        if (f->bus_num >= 0 && f->bus_num != bus_num)
1142 4b096fc9 aliguori
            continue;
1143 4b096fc9 aliguori
1144 4b096fc9 aliguori
        if (f->addr >= 0 && f->addr != addr)
1145 4b096fc9 aliguori
            continue;
1146 4b096fc9 aliguori
1147 4b096fc9 aliguori
        if (f->vendor_id >= 0 && f->vendor_id != vendor_id)
1148 4b096fc9 aliguori
            continue;
1149 4b096fc9 aliguori
1150 4b096fc9 aliguori
        if (f->product_id >= 0 && f->product_id != product_id)
1151 4b096fc9 aliguori
            continue;
1152 4b096fc9 aliguori
1153 4b096fc9 aliguori
        /* We got a match */
1154 4b096fc9 aliguori
1155 4b096fc9 aliguori
        /* Allredy attached ? */
1156 4b096fc9 aliguori
        if (hostdev_find(bus_num, addr))
1157 4b096fc9 aliguori
            return 0;
1158 4b096fc9 aliguori
1159 64838171 aliguori
        dprintf("husb: auto open: bus_num %d addr %d\n", bus_num, addr);
1160 4b096fc9 aliguori
1161 4b096fc9 aliguori
        dev = usb_host_device_open_addr(bus_num, addr, product_name);
1162 4b096fc9 aliguori
        if (dev)
1163 4b096fc9 aliguori
            usb_device_add_dev(dev);
1164 4b096fc9 aliguori
    }
1165 4b096fc9 aliguori
1166 4b096fc9 aliguori
    return 0;
1167 4b096fc9 aliguori
}
1168 4b096fc9 aliguori
1169 4b096fc9 aliguori
static void usb_host_auto_timer(void *unused)
1170 4b096fc9 aliguori
{
1171 4b096fc9 aliguori
    usb_host_scan(NULL, usb_host_auto_scan);
1172 4b096fc9 aliguori
    qemu_mod_timer(usb_auto_timer, qemu_get_clock(rt_clock) + 2000);
1173 4b096fc9 aliguori
}
1174 4b096fc9 aliguori
1175 4b096fc9 aliguori
/*
1176 5d0c5750 aliguori
 * Autoconnect filter
1177 5d0c5750 aliguori
 * Format:
1178 5d0c5750 aliguori
 *    auto:bus:dev[:vid:pid]
1179 5d0c5750 aliguori
 *    auto:bus.dev[:vid:pid]
1180 5d0c5750 aliguori
 *
1181 5d0c5750 aliguori
 *    bus  - bus number    (dec, * means any)
1182 5d0c5750 aliguori
 *    dev  - device number (dec, * means any)
1183 5d0c5750 aliguori
 *    vid  - vendor id     (hex, * means any)
1184 5d0c5750 aliguori
 *    pid  - product id    (hex, * means any)
1185 5d0c5750 aliguori
 *
1186 5d0c5750 aliguori
 *    See 'lsusb' output.
1187 4b096fc9 aliguori
 */
1188 5d0c5750 aliguori
static int parse_filter(const char *spec, struct USBAutoFilter *f)
1189 4b096fc9 aliguori
{
1190 5d0c5750 aliguori
    enum { BUS, DEV, VID, PID, DONE };
1191 5d0c5750 aliguori
    const char *p = spec;
1192 5d0c5750 aliguori
    int i;
1193 5d0c5750 aliguori
1194 5d0c5750 aliguori
    f->bus_num    = -1;
1195 5d0c5750 aliguori
    f->addr       = -1;
1196 5d0c5750 aliguori
    f->vendor_id  = -1;
1197 5d0c5750 aliguori
    f->product_id = -1;
1198 5d0c5750 aliguori
1199 5d0c5750 aliguori
    for (i = BUS; i < DONE; i++) {
1200 5d0c5750 aliguori
            p = strpbrk(p, ":.");
1201 5d0c5750 aliguori
            if (!p) break;
1202 5d0c5750 aliguori
        p++;
1203 5d0c5750 aliguori
 
1204 5d0c5750 aliguori
            if (*p == '*')
1205 5d0c5750 aliguori
            continue;
1206 5d0c5750 aliguori
1207 5d0c5750 aliguori
        switch(i) {
1208 5d0c5750 aliguori
        case BUS: f->bus_num = strtol(p, NULL, 10);    break;
1209 5d0c5750 aliguori
        case DEV: f->addr    = strtol(p, NULL, 10);    break;
1210 5d0c5750 aliguori
        case VID: f->vendor_id  = strtol(p, NULL, 16); break;
1211 5d0c5750 aliguori
        case PID: f->product_id = strtol(p, NULL, 16); break;
1212 5d0c5750 aliguori
        }
1213 5d0c5750 aliguori
    }
1214 5d0c5750 aliguori
1215 5d0c5750 aliguori
    if (i < DEV) {
1216 5d0c5750 aliguori
        fprintf(stderr, "husb: invalid auto filter spec %s\n", spec);
1217 5d0c5750 aliguori
        return -1;
1218 5d0c5750 aliguori
    }
1219 5d0c5750 aliguori
1220 5d0c5750 aliguori
    return 0;
1221 5d0c5750 aliguori
}
1222 5d0c5750 aliguori
1223 5d0c5750 aliguori
static int match_filter(const struct USBAutoFilter *f1, 
1224 5d0c5750 aliguori
                        const struct USBAutoFilter *f2)
1225 5d0c5750 aliguori
{
1226 5d0c5750 aliguori
    return f1->bus_num    == f2->bus_num &&
1227 5d0c5750 aliguori
           f1->addr       == f2->addr &&
1228 5d0c5750 aliguori
           f1->vendor_id  == f2->vendor_id &&
1229 5d0c5750 aliguori
           f1->product_id == f2->product_id;
1230 5d0c5750 aliguori
}
1231 5d0c5750 aliguori
1232 5d0c5750 aliguori
static int usb_host_auto_add(const char *spec)
1233 5d0c5750 aliguori
{
1234 5d0c5750 aliguori
    struct USBAutoFilter filter, *f;
1235 5d0c5750 aliguori
1236 5d0c5750 aliguori
    if (parse_filter(spec, &filter) < 0)
1237 5d0c5750 aliguori
        return -1;
1238 5d0c5750 aliguori
1239 5d0c5750 aliguori
    f = qemu_mallocz(sizeof(*f));
1240 4b096fc9 aliguori
    if (!f) {
1241 0d380648 aliguori
        fprintf(stderr, "husb: failed to allocate auto filter\n");
1242 5d0c5750 aliguori
        return -1;
1243 4b096fc9 aliguori
    }
1244 4b096fc9 aliguori
1245 5d0c5750 aliguori
    *f = filter; 
1246 4b096fc9 aliguori
1247 4b096fc9 aliguori
    if (!usb_auto_filter) {
1248 4b096fc9 aliguori
        /*
1249 4b096fc9 aliguori
         * First entry. Init and start the monitor.
1250 4b096fc9 aliguori
         * Right now we're using timer to check for new devices.
1251 4b096fc9 aliguori
         * If this turns out to be too expensive we can move that into a 
1252 4b096fc9 aliguori
         * separate thread.
1253 4b096fc9 aliguori
         */
1254 4b096fc9 aliguori
        usb_auto_timer = qemu_new_timer(rt_clock, usb_host_auto_timer, NULL);
1255 4b096fc9 aliguori
        if (!usb_auto_timer) {
1256 0d380648 aliguori
            fprintf(stderr, "husb: failed to allocate auto scan timer\n");
1257 4b096fc9 aliguori
            qemu_free(f);
1258 5d0c5750 aliguori
            return -1;
1259 4b096fc9 aliguori
        }
1260 4b096fc9 aliguori
1261 4b096fc9 aliguori
        /* Check for new devices every two seconds */
1262 4b096fc9 aliguori
        qemu_mod_timer(usb_auto_timer, qemu_get_clock(rt_clock) + 2000);
1263 4b096fc9 aliguori
    }
1264 4b096fc9 aliguori
1265 5d0c5750 aliguori
    dprintf("husb: added auto filter: bus_num %d addr %d vid %d pid %d\n",
1266 5d0c5750 aliguori
        f->bus_num, f->addr, f->vendor_id, f->product_id);
1267 4b096fc9 aliguori
1268 4b096fc9 aliguori
    f->next = usb_auto_filter;
1269 4b096fc9 aliguori
    usb_auto_filter = f;
1270 5d0c5750 aliguori
1271 5d0c5750 aliguori
    return 0;
1272 5d0c5750 aliguori
}
1273 5d0c5750 aliguori
1274 5d0c5750 aliguori
static int usb_host_auto_del(const char *spec)
1275 5d0c5750 aliguori
{
1276 5d0c5750 aliguori
    struct USBAutoFilter *pf = usb_auto_filter;
1277 5d0c5750 aliguori
    struct USBAutoFilter **prev = &usb_auto_filter;
1278 5d0c5750 aliguori
    struct USBAutoFilter filter;
1279 5d0c5750 aliguori
1280 5d0c5750 aliguori
    if (parse_filter(spec, &filter) < 0)
1281 5d0c5750 aliguori
        return -1;
1282 5d0c5750 aliguori
1283 5d0c5750 aliguori
    while (pf) {
1284 5d0c5750 aliguori
        if (match_filter(pf, &filter)) {
1285 5d0c5750 aliguori
            dprintf("husb: removed auto filter: bus_num %d addr %d vid %d pid %d\n",
1286 5d0c5750 aliguori
                     pf->bus_num, pf->addr, pf->vendor_id, pf->product_id);
1287 5d0c5750 aliguori
1288 5d0c5750 aliguori
            *prev = pf->next;
1289 5d0c5750 aliguori
1290 5d0c5750 aliguori
            if (!usb_auto_filter) {
1291 5d0c5750 aliguori
                /* No more filters. Stop scanning. */
1292 5d0c5750 aliguori
                qemu_del_timer(usb_auto_timer);
1293 5d0c5750 aliguori
                qemu_free_timer(usb_auto_timer);
1294 5d0c5750 aliguori
            }
1295 5d0c5750 aliguori
1296 5d0c5750 aliguori
            return 0;
1297 5d0c5750 aliguori
        }
1298 5d0c5750 aliguori
1299 5d0c5750 aliguori
        prev = &pf->next;
1300 5d0c5750 aliguori
        pf   = pf->next;
1301 5d0c5750 aliguori
    }
1302 5d0c5750 aliguori
1303 5d0c5750 aliguori
    return -1;
1304 4b096fc9 aliguori
}
1305 4b096fc9 aliguori
1306 a594cfbf bellard
typedef struct FindDeviceState {
1307 a594cfbf bellard
    int vendor_id;
1308 a594cfbf bellard
    int product_id;
1309 a594cfbf bellard
    int bus_num;
1310 a594cfbf bellard
    int addr;
1311 1f6e24e7 bellard
    char product_name[PRODUCT_NAME_SZ];
1312 a594cfbf bellard
} FindDeviceState;
1313 a594cfbf bellard
1314 5fafdf24 ths
static int usb_host_find_device_scan(void *opaque, int bus_num, int addr,
1315 a594cfbf bellard
                                     int class_id,
1316 5fafdf24 ths
                                     int vendor_id, int product_id,
1317 a594cfbf bellard
                                     const char *product_name, int speed)
1318 bb36d470 bellard
{
1319 a594cfbf bellard
    FindDeviceState *s = opaque;
1320 1f6e24e7 bellard
    if ((vendor_id == s->vendor_id &&
1321 1f6e24e7 bellard
        product_id == s->product_id) ||
1322 1f6e24e7 bellard
        (bus_num == s->bus_num &&
1323 1f6e24e7 bellard
        addr == s->addr)) {
1324 1f6e24e7 bellard
        pstrcpy(s->product_name, PRODUCT_NAME_SZ, product_name);
1325 a594cfbf bellard
        s->bus_num = bus_num;
1326 a594cfbf bellard
        s->addr = addr;
1327 a594cfbf bellard
        return 1;
1328 a594cfbf bellard
    } else {
1329 a594cfbf bellard
        return 0;
1330 a594cfbf bellard
    }
1331 a594cfbf bellard
}
1332 bb36d470 bellard
1333 5fafdf24 ths
/* the syntax is :
1334 5fafdf24 ths
   'bus.addr' (decimal numbers) or
1335 a594cfbf bellard
   'vendor_id:product_id' (hexa numbers) */
1336 5fafdf24 ths
static int usb_host_find_device(int *pbus_num, int *paddr,
1337 1f6e24e7 bellard
                                char *product_name, int product_name_size,
1338 a594cfbf bellard
                                const char *devname)
1339 a594cfbf bellard
{
1340 a594cfbf bellard
    const char *p;
1341 a594cfbf bellard
    int ret;
1342 a594cfbf bellard
    FindDeviceState fs;
1343 a594cfbf bellard
1344 a594cfbf bellard
    p = strchr(devname, '.');
1345 a594cfbf bellard
    if (p) {
1346 a594cfbf bellard
        *pbus_num = strtoul(devname, NULL, 0);
1347 a594cfbf bellard
        *paddr = strtoul(p + 1, NULL, 0);
1348 1f6e24e7 bellard
        fs.bus_num = *pbus_num;
1349 1f6e24e7 bellard
        fs.addr = *paddr;
1350 1f6e24e7 bellard
        ret = usb_host_scan(&fs, usb_host_find_device_scan);
1351 1f6e24e7 bellard
        if (ret)
1352 1f6e24e7 bellard
            pstrcpy(product_name, product_name_size, fs.product_name);
1353 a594cfbf bellard
        return 0;
1354 a594cfbf bellard
    }
1355 5d0c5750 aliguori
1356 a594cfbf bellard
    p = strchr(devname, ':');
1357 a594cfbf bellard
    if (p) {
1358 a594cfbf bellard
        fs.vendor_id = strtoul(devname, NULL, 16);
1359 a594cfbf bellard
        fs.product_id = strtoul(p + 1, NULL, 16);
1360 a594cfbf bellard
        ret = usb_host_scan(&fs, usb_host_find_device_scan);
1361 a594cfbf bellard
        if (ret) {
1362 a594cfbf bellard
            *pbus_num = fs.bus_num;
1363 a594cfbf bellard
            *paddr = fs.addr;
1364 1f6e24e7 bellard
            pstrcpy(product_name, product_name_size, fs.product_name);
1365 a594cfbf bellard
            return 0;
1366 bb36d470 bellard
        }
1367 bb36d470 bellard
    }
1368 a594cfbf bellard
    return -1;
1369 bb36d470 bellard
}
1370 bb36d470 bellard
1371 a594cfbf bellard
/**********************/
1372 a594cfbf bellard
/* USB host device info */
1373 a594cfbf bellard
1374 a594cfbf bellard
struct usb_class_info {
1375 a594cfbf bellard
    int class;
1376 a594cfbf bellard
    const char *class_name;
1377 a594cfbf bellard
};
1378 a594cfbf bellard
1379 a594cfbf bellard
static const struct usb_class_info usb_class_info[] = {
1380 a594cfbf bellard
    { USB_CLASS_AUDIO, "Audio"},
1381 a594cfbf bellard
    { USB_CLASS_COMM, "Communication"},
1382 a594cfbf bellard
    { USB_CLASS_HID, "HID"},
1383 a594cfbf bellard
    { USB_CLASS_HUB, "Hub" },
1384 a594cfbf bellard
    { USB_CLASS_PHYSICAL, "Physical" },
1385 a594cfbf bellard
    { USB_CLASS_PRINTER, "Printer" },
1386 a594cfbf bellard
    { USB_CLASS_MASS_STORAGE, "Storage" },
1387 a594cfbf bellard
    { USB_CLASS_CDC_DATA, "Data" },
1388 a594cfbf bellard
    { USB_CLASS_APP_SPEC, "Application Specific" },
1389 a594cfbf bellard
    { USB_CLASS_VENDOR_SPEC, "Vendor Specific" },
1390 a594cfbf bellard
    { USB_CLASS_STILL_IMAGE, "Still Image" },
1391 b9dc033c balrog
    { USB_CLASS_CSCID, "Smart Card" },
1392 a594cfbf bellard
    { USB_CLASS_CONTENT_SEC, "Content Security" },
1393 a594cfbf bellard
    { -1, NULL }
1394 a594cfbf bellard
};
1395 a594cfbf bellard
1396 a594cfbf bellard
static const char *usb_class_str(uint8_t class)
1397 bb36d470 bellard
{
1398 a594cfbf bellard
    const struct usb_class_info *p;
1399 a594cfbf bellard
    for(p = usb_class_info; p->class != -1; p++) {
1400 a594cfbf bellard
        if (p->class == class)
1401 a594cfbf bellard
            break;
1402 bb36d470 bellard
    }
1403 a594cfbf bellard
    return p->class_name;
1404 a594cfbf bellard
}
1405 a594cfbf bellard
1406 9596ebb7 pbrook
static void usb_info_device(int bus_num, int addr, int class_id,
1407 9596ebb7 pbrook
                            int vendor_id, int product_id,
1408 9596ebb7 pbrook
                            const char *product_name,
1409 9596ebb7 pbrook
                            int speed)
1410 a594cfbf bellard
{
1411 a594cfbf bellard
    const char *class_str, *speed_str;
1412 a594cfbf bellard
1413 a594cfbf bellard
    switch(speed) {
1414 5fafdf24 ths
    case USB_SPEED_LOW:
1415 5fafdf24 ths
        speed_str = "1.5";
1416 a594cfbf bellard
        break;
1417 5fafdf24 ths
    case USB_SPEED_FULL:
1418 5fafdf24 ths
        speed_str = "12";
1419 a594cfbf bellard
        break;
1420 5fafdf24 ths
    case USB_SPEED_HIGH:
1421 5fafdf24 ths
        speed_str = "480";
1422 a594cfbf bellard
        break;
1423 a594cfbf bellard
    default:
1424 5fafdf24 ths
        speed_str = "?";
1425 a594cfbf bellard
        break;
1426 a594cfbf bellard
    }
1427 a594cfbf bellard
1428 5fafdf24 ths
    term_printf("  Device %d.%d, speed %s Mb/s\n",
1429 a594cfbf bellard
                bus_num, addr, speed_str);
1430 a594cfbf bellard
    class_str = usb_class_str(class_id);
1431 5fafdf24 ths
    if (class_str)
1432 a594cfbf bellard
        term_printf("    %s:", class_str);
1433 a594cfbf bellard
    else
1434 a594cfbf bellard
        term_printf("    Class %02x:", class_id);
1435 a594cfbf bellard
    term_printf(" USB device %04x:%04x", vendor_id, product_id);
1436 a594cfbf bellard
    if (product_name[0] != '\0')
1437 a594cfbf bellard
        term_printf(", %s", product_name);
1438 a594cfbf bellard
    term_printf("\n");
1439 a594cfbf bellard
}
1440 a594cfbf bellard
1441 5fafdf24 ths
static int usb_host_info_device(void *opaque, int bus_num, int addr,
1442 a594cfbf bellard
                                int class_id,
1443 5fafdf24 ths
                                int vendor_id, int product_id,
1444 a594cfbf bellard
                                const char *product_name,
1445 a594cfbf bellard
                                int speed)
1446 a594cfbf bellard
{
1447 a594cfbf bellard
    usb_info_device(bus_num, addr, class_id, vendor_id, product_id,
1448 a594cfbf bellard
                    product_name, speed);
1449 a594cfbf bellard
    return 0;
1450 a594cfbf bellard
}
1451 a594cfbf bellard
1452 5d0c5750 aliguori
static void dec2str(int val, char *str)
1453 5d0c5750 aliguori
{
1454 5d0c5750 aliguori
    if (val == -1)
1455 5d0c5750 aliguori
        strcpy(str, "*");
1456 5d0c5750 aliguori
    else
1457 5d0c5750 aliguori
        sprintf(str, "%d", val); 
1458 5d0c5750 aliguori
}
1459 5d0c5750 aliguori
1460 5d0c5750 aliguori
static void hex2str(int val, char *str)
1461 5d0c5750 aliguori
{
1462 5d0c5750 aliguori
    if (val == -1)
1463 5d0c5750 aliguori
        strcpy(str, "*");
1464 5d0c5750 aliguori
    else
1465 5d0c5750 aliguori
        sprintf(str, "%x", val);
1466 5d0c5750 aliguori
}
1467 5d0c5750 aliguori
1468 a594cfbf bellard
void usb_host_info(void)
1469 a594cfbf bellard
{
1470 5d0c5750 aliguori
    struct USBAutoFilter *f;
1471 5d0c5750 aliguori
1472 a594cfbf bellard
    usb_host_scan(NULL, usb_host_info_device);
1473 5d0c5750 aliguori
1474 5d0c5750 aliguori
    if (usb_auto_filter)
1475 5d0c5750 aliguori
        term_printf("  Auto filters:\n");
1476 5d0c5750 aliguori
    for (f = usb_auto_filter; f; f = f->next) {
1477 5d0c5750 aliguori
        char bus[10], addr[10], vid[10], pid[10];
1478 5d0c5750 aliguori
        dec2str(f->bus_num, bus);
1479 5d0c5750 aliguori
        dec2str(f->addr, addr);
1480 5d0c5750 aliguori
        hex2str(f->vendor_id, vid);
1481 5d0c5750 aliguori
        hex2str(f->product_id, pid);
1482 5d0c5750 aliguori
            term_printf("    Device %s.%s ID %s:%s\n", bus, addr, vid, pid);
1483 5d0c5750 aliguori
    }
1484 bb36d470 bellard
}
1485 bb36d470 bellard
1486 bb36d470 bellard
#else
1487 bb36d470 bellard
1488 446ab128 aliguori
#include "hw/usb.h"
1489 446ab128 aliguori
1490 a594cfbf bellard
void usb_host_info(void)
1491 a594cfbf bellard
{
1492 a594cfbf bellard
    term_printf("USB host devices not supported\n");
1493 a594cfbf bellard
}
1494 a594cfbf bellard
1495 bb36d470 bellard
/* XXX: modify configure to compile the right host driver */
1496 a594cfbf bellard
USBDevice *usb_host_device_open(const char *devname)
1497 bb36d470 bellard
{
1498 bb36d470 bellard
    return NULL;
1499 bb36d470 bellard
}
1500 bb36d470 bellard
1501 5d0c5750 aliguori
int usb_host_device_close(const char *devname)
1502 5d0c5750 aliguori
{
1503 5d0c5750 aliguori
    return 0;
1504 5d0c5750 aliguori
}
1505 5d0c5750 aliguori
1506 bb36d470 bellard
#endif