Changeset 50ba203 in mainline


Ignore:
Timestamp:
2011-02-20T15:46:48Z (13 years ago)
Author:
Matus Dekanek <smekideki@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
6bb83c7
Parents:
d81ef61c (diff), 0c00dac (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

merge with usb/development

Location:
uspace
Files:
7 added
6 deleted
48 edited
2 moved

Legend:

Unmodified
Added
Removed
  • uspace/app/tester/adt/usbaddrkeep.c

    rd81ef61c r50ba203  
    2929#include <stdio.h>
    3030#include <stdlib.h>
    31 #include <usb/hcd.h>
     31#include <usb/addrkeep.h>
    3232#include <errno.h>
    3333#include "../tester.h"
  • uspace/app/usbinfo/info.c

    rd81ef61c r50ba203  
    3939#include <usb/usbdrv.h>
    4040#include <usb/pipes.h>
     41#include <usb/recognise.h>
    4142#include <usb/request.h>
    4243#include "usbinfo.h"
     
    4748        usb_device_connection_t wire;
    4849        usb_endpoint_pipe_t ctrl_pipe;
    49         ctrl_pipe.hc_phone = -1;
    50 
    51         int hc_phone = devman_device_connect(hc_handle, 0);
    52         if (hc_phone < 0) {
    53                 fprintf(stderr,
    54                     NAME ": failed to connect to host controller (%zu): %s.\n",
    55                         (size_t) hc_handle, str_error(hc_phone));
    56                 return hc_phone;
    57         }
    58 
    59         /*
    60          * Dump information about possible match ids.
    61          */
    62         match_id_list_t match_id_list;
    63         init_match_ids(&match_id_list);
    64         rc = usb_drv_create_device_match_ids(hc_phone, &match_id_list, address);
    65         if (rc != EOK) {
    66                 fprintf(stderr,
    67                     NAME ": failed to fetch match ids of the device: %s.\n",
    68                     str_error(rc));
    69                 goto leave;
    70         }
    71         dump_match_ids(&match_id_list);
    7250
    7351        /*
     
    9573                goto leave;
    9674        }
     75
     76        /*
     77         * Dump information about possible match ids.
     78         */
     79        match_id_list_t match_id_list;
     80        init_match_ids(&match_id_list);
     81        rc = usb_device_create_match_ids(&ctrl_pipe, &match_id_list);
     82        if (rc != EOK) {
     83                fprintf(stderr,
     84                    NAME ": failed to fetch match ids of the device: %s.\n",
     85                    str_error(rc));
     86                goto leave;
     87        }
     88        dump_match_ids(&match_id_list);
    9789
    9890        /*
     
    141133leave:
    142134        /* Ignoring errors here. */
    143         async_hangup(hc_phone);
    144135        usb_endpoint_pipe_end_session(&ctrl_pipe);
    145136
  • uspace/app/usbinfo/main.c

    rd81ef61c r50ba203  
    8181{
    8282        int rc;
     83
     84        if (str_cmp(path, "uhci") == 0) {
     85                path = "/hw/pci0/00:01.2";
     86        }
    8387
    8488        devman_handle_t handle;
  • uspace/app/virtusbkbd/kbdconfig.c

    rd81ef61c r50ba203  
    6161        .endpoint_count = 1,
    6262        .interface_class = USB_CLASS_HID,
    63         .interface_subclass = 0,
     63        .interface_subclass = USB_HID_SUBCLASS_BOOT,
    6464        .interface_protocol = USB_HID_PROTOCOL_KEYBOARD,
    6565        .str_interface = 0
  • uspace/drv/uhci-hcd/Makefile

    rd81ef61c r50ba203  
    4040        uhci_struct/transfer_descriptor.c \
    4141        pci.c \
    42         tracker.c
     42        batch.c
    4343
    4444include $(USPACE_PREFIX)/Makefile.common
  • uspace/drv/uhci-hcd/batch.h

    rd81ef61c r50ba203  
    3232 * @brief UHCI driver
    3333 */
    34 #ifndef DRV_UHCI_TRACKER_H
    35 #define DRV_UHCI_TRACKER_H
     34#ifndef DRV_UHCI_BATCH_H
     35#define DRV_UHCI_BATCH_H
    3636
    3737#include <adt/list.h>
     
    4141
    4242#include "uhci_struct/transfer_descriptor.h"
     43#include "uhci_struct/queue_head.h"
    4344
    4445typedef enum {
     
    4748} dev_speed_t;
    4849
    49 typedef struct tracker
     50typedef struct batch
    5051{
    5152        link_t link;
     53        dev_speed_t speed;
    5254        usb_target_t target;
    5355        usb_transfer_type_t transfer_type;
     
    5759        };
    5860        void *arg;
     61        char *transport_buffer;
     62        char *setup_buffer;
     63        size_t setup_size;
    5964        char *buffer;
    60         char *packet;
    6165        size_t buffer_size;
    6266        size_t max_packet_size;
    63         size_t packet_size;
    64         size_t buffer_offset;
    65         dev_speed_t speed;
     67        size_t packets;
     68        size_t transfered_size;
     69        int error;
    6670        device_t *dev;
    67         transfer_descriptor_t *td;
    68         void (*next_step)(struct tracker*);
    69         unsigned toggle:1;
    70 } tracker_t;
     71        queue_head_t *qh;
     72        transfer_descriptor_t *tds;
     73        void (*next_step)(struct batch*);
     74} batch_t;
    7175
    72 
    73 tracker_t * tracker_get(device_t *dev, usb_target_t target,
     76batch_t * batch_get(device_t *dev, usb_target_t target,
    7477    usb_transfer_type_t transfer_type, size_t max_packet_size,
    7578    dev_speed_t speed, char *buffer, size_t size,
     79                char *setup_buffer, size_t setup_size,
    7680    usbhc_iface_transfer_in_callback_t func_in,
    7781    usbhc_iface_transfer_out_callback_t func_out, void *arg);
    7882
    79 void tracker_control_write(
    80     tracker_t *instance, char* setup_buffer, size_t setup_size);
     83bool batch_is_complete(batch_t *instance);
    8184
    82 void tracker_control_read(
    83     tracker_t *instance, char* setup_buffer, size_t setup_size);
     85void batch_control_write(batch_t *instance);
    8486
    85 void tracker_interrupt_in(tracker_t *instance);
     87void batch_control_read(batch_t *instance);
    8688
    87 void tracker_interrupt_out(tracker_t *instance);
     89void batch_interrupt_in(batch_t *instance);
     90
     91void batch_interrupt_out(batch_t *instance);
    8892
    8993/* DEPRECATED FUNCTIONS NEEDED BY THE OLD API */
    90 void tracker_control_setup_old(tracker_t *instance);
     94void batch_control_setup_old(batch_t *instance);
    9195
    92 void tracker_control_write_data_old(tracker_t *instance);
     96void batch_control_write_data_old(batch_t *instance);
    9397
    94 void tracker_control_read_data_old(tracker_t *instance);
     98void batch_control_read_data_old(batch_t *instance);
    9599
    96 void tracker_control_write_status_old(tracker_t *instance);
     100void batch_control_write_status_old(batch_t *instance);
    97101
    98 void tracker_control_read_status_old(tracker_t *instance);
     102void batch_control_read_status_old(batch_t *instance);
    99103#endif
    100104/**
  • uspace/drv/uhci-hcd/iface.c

    rd81ef61c r50ba203  
    5454}
    5555/*----------------------------------------------------------------------------*/
    56 static int reserve_default_address(device_t *dev)
     56static int reserve_default_address(device_t *dev, bool full_speed)
    5757{
    5858        assert(dev);
     
    7272}
    7373/*----------------------------------------------------------------------------*/
    74 static int request_address(device_t *dev, usb_address_t *address)
     74static int request_address(device_t *dev, bool full_speed,
     75    usb_address_t *address)
    7576{
    7677        assert(dev);
     
    103104/*----------------------------------------------------------------------------*/
    104105static int interrupt_out(device_t *dev, usb_target_t target,
    105     void *data, size_t size,
    106     usbhc_iface_transfer_out_callback_t callback, void *arg)
     106    size_t max_packet_size,
     107    void *data, size_t size,
     108    usbhc_iface_transfer_out_callback_t callback, void *arg)
     109{
     110        dev_speed_t speed = FULL_SPEED;
     111
     112        batch_t *batch = batch_get(dev, target, USB_TRANSFER_INTERRUPT,
     113            max_packet_size, speed, data, size, NULL, 0, NULL, callback, arg);
     114        if (!batch)
     115                return ENOMEM;
     116        batch_interrupt_out(batch);
     117        return EOK;
     118}
     119/*----------------------------------------------------------------------------*/
     120static int interrupt_in(device_t *dev, usb_target_t target,
     121    size_t max_packet_size,
     122    void *data, size_t size,
     123    usbhc_iface_transfer_in_callback_t callback, void *arg)
     124{
     125        dev_speed_t speed = FULL_SPEED;
     126
     127        batch_t *batch = batch_get(dev, target, USB_TRANSFER_INTERRUPT,
     128            max_packet_size, speed, data, size, NULL, 0, callback, NULL, arg);
     129        if (!batch)
     130                return ENOMEM;
     131        batch_interrupt_in(batch);
     132        return EOK;
     133}
     134/*----------------------------------------------------------------------------*/
     135static int control_write(device_t *dev, usb_target_t target,
     136    size_t max_packet_size,
     137    void *setup_data, size_t setup_size, void *data, size_t size,
     138    usbhc_iface_transfer_out_callback_t callback, void *arg)
     139{
     140        dev_speed_t speed = FULL_SPEED;
     141
     142        batch_t *batch = batch_get(dev, target, USB_TRANSFER_CONTROL,
     143            max_packet_size, speed, data, size, setup_data, setup_size,
     144            NULL, callback, arg);
     145        if (!batch)
     146                return ENOMEM;
     147        batch_control_write(batch);
     148        return EOK;
     149}
     150/*----------------------------------------------------------------------------*/
     151static int control_read(device_t *dev, usb_target_t target,
     152    size_t max_packet_size,
     153    void *setup_data, size_t setup_size, void *data, size_t size,
     154    usbhc_iface_transfer_in_callback_t callback, void *arg)
     155{
     156        dev_speed_t speed = FULL_SPEED;
     157
     158        batch_t *batch = batch_get(dev, target, USB_TRANSFER_CONTROL,
     159            max_packet_size, speed, data, size, setup_data, setup_size, callback,
     160            NULL, arg);
     161        if (!batch)
     162                return ENOMEM;
     163        batch_control_read(batch);
     164        return EOK;
     165}
     166/*----------------------------------------------------------------------------*/
     167static int control_write_setup(device_t *dev, usb_target_t target,
     168    size_t max_packet_size,
     169    void *data, size_t size,
     170    usbhc_iface_transfer_out_callback_t callback, void *arg)
     171{
     172        dev_speed_t speed = FULL_SPEED;
     173
     174        usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
     175        batch_t *batch = batch_get(dev, target, USB_TRANSFER_CONTROL,
     176            max_packet_size, speed, NULL, 0, data, size, NULL, callback, arg);
     177        if (!batch)
     178                return ENOMEM;
     179        batch_control_setup_old(batch);
     180        return EOK;
     181}
     182/*----------------------------------------------------------------------------*/
     183static int control_write_data(device_t *dev, usb_target_t target,
     184    size_t max_packet_size,
     185    void *data, size_t size,
     186    usbhc_iface_transfer_out_callback_t callback, void *arg)
     187{
     188        dev_speed_t speed = FULL_SPEED;
     189
     190        usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
     191        batch_t *batch = batch_get(dev, target, USB_TRANSFER_CONTROL,
     192            max_packet_size, speed, data, size, NULL, 0, NULL, callback, arg);
     193        if (!batch)
     194                return ENOMEM;
     195        batch_control_write_data_old(batch);
     196        return EOK;
     197}
     198/*----------------------------------------------------------------------------*/
     199static int control_write_status(device_t *dev, usb_target_t target,
     200    usbhc_iface_transfer_in_callback_t callback, void *arg)
    107201{
    108202        size_t max_packet_size = 8;
    109203        dev_speed_t speed = FULL_SPEED;
    110204
    111         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_INTERRUPT,
    112             max_packet_size, speed, data, size, NULL, callback, arg);
    113         if (!tracker)
    114                 return ENOMEM;
    115         tracker_interrupt_out(tracker);
    116         return EOK;
    117 }
    118 /*----------------------------------------------------------------------------*/
    119 static int interrupt_in(device_t *dev, usb_target_t target,
    120     void *data, size_t size,
    121     usbhc_iface_transfer_in_callback_t callback, void *arg)
    122 {
    123         size_t max_packet_size = 4;
    124         dev_speed_t speed = FULL_SPEED;
    125 
    126         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_INTERRUPT,
    127             max_packet_size, speed, data, size, callback, NULL, arg);
    128         if (!tracker)
    129                 return ENOMEM;
    130         tracker_interrupt_in(tracker);
    131         return EOK;
    132 }
    133 /*----------------------------------------------------------------------------*/
    134 static int control_write(device_t *dev, usb_target_t target,
    135     void *setup_data, size_t setup_size, void *data, size_t size,
     205        usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
     206        batch_t *batch = batch_get(dev, target, USB_TRANSFER_CONTROL,
     207            max_packet_size, speed, NULL, 0, NULL, 0, callback, NULL, arg);
     208        if (!batch)
     209                return ENOMEM;
     210        batch_control_write_status_old(batch);
     211        return EOK;
     212}
     213/*----------------------------------------------------------------------------*/
     214static int control_read_setup(device_t *dev, usb_target_t target,
     215    size_t max_packet_size,
     216    void *data, size_t size,
     217    usbhc_iface_transfer_out_callback_t callback, void *arg)
     218{
     219        dev_speed_t speed = FULL_SPEED;
     220
     221        usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
     222        batch_t *batch = batch_get(dev, target, USB_TRANSFER_CONTROL,
     223            max_packet_size, speed, NULL, 0, data, size, NULL, callback, arg);
     224        if (!batch)
     225                return ENOMEM;
     226        batch_control_setup_old(batch);
     227        return EOK;
     228}
     229/*----------------------------------------------------------------------------*/
     230static int control_read_data(device_t *dev, usb_target_t target,
     231    size_t max_packet_size,
     232    void *data, size_t size,
     233    usbhc_iface_transfer_in_callback_t callback, void *arg)
     234{
     235        dev_speed_t speed = FULL_SPEED;
     236
     237        usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
     238        batch_t *batch = batch_get(dev, target, USB_TRANSFER_CONTROL,
     239            max_packet_size, speed, data, size, NULL, 0, callback, NULL, arg);
     240        if (!batch)
     241                return ENOMEM;
     242        batch_control_read_data_old(batch);
     243        return EOK;
     244}
     245/*----------------------------------------------------------------------------*/
     246static int control_read_status(device_t *dev, usb_target_t target,
    136247    usbhc_iface_transfer_out_callback_t callback, void *arg)
    137248{
     
    139250        dev_speed_t speed = FULL_SPEED;
    140251
    141         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
    142             max_packet_size, speed, data, size, NULL, callback, arg);
    143         if (!tracker)
    144                 return ENOMEM;
    145         tracker_control_write(tracker, setup_data, setup_size);
    146         return EOK;
    147 }
    148 /*----------------------------------------------------------------------------*/
    149 static int control_read(device_t *dev, usb_target_t target,
    150     void *setup_data, size_t setup_size, void *data, size_t size,
    151     usbhc_iface_transfer_in_callback_t callback, void *arg)
    152 {
    153         size_t max_packet_size = 8;
    154         dev_speed_t speed = FULL_SPEED;
    155 
    156         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
    157             max_packet_size, speed, data, size, callback, NULL, arg);
    158         if (!tracker)
    159                 return ENOMEM;
    160         tracker_control_read(tracker, setup_data, setup_size);
    161         return EOK;
    162 }
    163 /*----------------------------------------------------------------------------*/
    164 static int control_write_setup(device_t *dev, usb_target_t target,
    165     void *data, size_t size,
    166     usbhc_iface_transfer_out_callback_t callback, void *arg)
    167 {
    168         usb_log_warning("Using deprecated API control write setup.\n");
    169         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
    170             8, FULL_SPEED, data, size, NULL, callback, arg);
    171         if (!tracker)
    172                 return ENOMEM;
    173         tracker_control_setup_old(tracker);
    174         return EOK;
    175 }
    176 /*----------------------------------------------------------------------------*/
    177 static int control_write_data(device_t *dev, usb_target_t target,
    178     void *data, size_t size,
    179     usbhc_iface_transfer_out_callback_t callback, void *arg)
    180 {
    181         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
    182             size, FULL_SPEED, data, size, NULL, callback, arg);
    183         if (!tracker)
    184                 return ENOMEM;
    185         tracker_control_write_data_old(tracker);
    186         return EOK;
    187 }
    188 /*----------------------------------------------------------------------------*/
    189 static int control_write_status(device_t *dev, usb_target_t target,
    190     usbhc_iface_transfer_in_callback_t callback, void *arg)
    191 {
    192         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
    193             0, FULL_SPEED, NULL, 0, callback, NULL, arg);
    194         if (!tracker)
    195                 return ENOMEM;
    196         tracker_control_write_status_old(tracker);
    197         return EOK;
    198 }
    199 /*----------------------------------------------------------------------------*/
    200 static int control_read_setup(device_t *dev, usb_target_t target,
    201     void *data, size_t size,
    202     usbhc_iface_transfer_out_callback_t callback, void *arg)
    203 {
    204         usb_log_warning("Using deprecated API control read setup.\n");
    205         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
    206             8, FULL_SPEED, data, size, NULL, callback, arg);
    207         if (!tracker)
    208                 return ENOMEM;
    209         tracker_control_setup_old(tracker);
    210         return EOK;
    211 }
    212 /*----------------------------------------------------------------------------*/
    213 static int control_read_data(device_t *dev, usb_target_t target,
    214     void *data, size_t size,
    215     usbhc_iface_transfer_in_callback_t callback, void *arg)
    216 {
    217         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
    218             size, FULL_SPEED, data, size, callback, NULL, arg);
    219         if (!tracker)
    220                 return ENOMEM;
    221         tracker_control_read_data_old(tracker);
    222         return EOK;
    223 }
    224 /*----------------------------------------------------------------------------*/
    225 static int control_read_status(device_t *dev, usb_target_t target,
    226     usbhc_iface_transfer_out_callback_t callback, void *arg)
    227 {
    228         tracker_t *tracker = tracker_get(dev, target, USB_TRANSFER_CONTROL,
    229             0, FULL_SPEED, NULL, 0, NULL, callback, arg);
    230         if (!tracker)
    231                 return ENOMEM;
    232         tracker_control_read_status_old(tracker);
     252        usb_log_warning("Using deprecated API %s.\n", __FUNCTION__);
     253        batch_t *batch = batch_get(dev, target, USB_TRANSFER_CONTROL,
     254            max_packet_size, speed, NULL, 0, NULL, 0, NULL, callback, arg);
     255        if (!batch)
     256                return ENOMEM;
     257        batch_control_read_status_old(batch);
    233258        return EOK;
    234259}
  • uspace/drv/uhci-hcd/root_hub.c

    rd81ef61c r50ba203  
    3535#include <errno.h>
    3636#include <stdio.h>
    37 
    3837#include <usb_iface.h>
    39 
    4038#include <usb/debug.h>
    4139
    4240#include "root_hub.h"
     41
     42extern device_ops_t child_ops;
    4343/*----------------------------------------------------------------------------*/
    44 static int usb_iface_get_hc_handle(device_t *dev, devman_handle_t *handle)
    45 {
    46   assert(dev);
    47   assert(dev->parent != NULL);
    48 
    49   device_t *parent = dev->parent;
    50 
    51   if (parent->ops && parent->ops->interfaces[USB_DEV_IFACE]) {
    52     usb_iface_t *usb_iface
    53         = (usb_iface_t *) parent->ops->interfaces[USB_DEV_IFACE];
    54     assert(usb_iface != NULL);
    55     if (usb_iface->get_hc_handle) {
    56       int rc = usb_iface->get_hc_handle(parent, handle);
    57       return rc;
    58     }
    59   }
    60 
    61   return ENOTSUP;
    62 }
    63 /*----------------------------------------------------------------------------*/
    64 static usb_iface_t usb_iface = {
    65   .get_hc_handle = usb_iface_get_hc_handle
    66 };
    67 
    68 static device_ops_t rh_ops = {
    69         .interfaces[USB_DEV_IFACE] = &usb_iface
    70 };
    71 
    7244int setup_root_hub(device_t **device, device_t *hc)
    7345{
     
    10880        hub->name = name;
    10981        hub->parent = hc;
    110         hub->ops = &rh_ops;
     82        hub->ops = &child_ops;
    11183
    11284        *device = hub;
  • uspace/drv/uhci-hcd/transfer_list.c

    rd81ef61c r50ba203  
    5151
    5252        queue_head_init(instance->queue_head);
     53        list_initialize(&instance->batch_list);
     54        fibril_mutex_initialize(&instance->guard);
    5355        return EOK;
    5456}
     
    5860        assert(instance);
    5961        assert(next);
    60         instance->next = next;
    6162        if (!instance->queue_head)
    6263                return;
    63         queue_head_add_next(instance->queue_head, next->queue_head_pa);
     64        queue_head_append_qh(instance->queue_head, next->queue_head_pa);
     65        instance->queue_head->element = instance->queue_head->next_queue;
    6466}
    6567/*----------------------------------------------------------------------------*/
    66 void transfer_list_add_tracker(transfer_list_t *instance, tracker_t *tracker)
     68void transfer_list_add_batch(transfer_list_t *instance, batch_t *batch)
    6769{
    6870        assert(instance);
    69         assert(tracker);
     71        assert(batch);
    7072
    71         uint32_t pa = (uintptr_t)addr_to_phys(tracker->td);
     73        uint32_t pa = (uintptr_t)addr_to_phys(batch->qh);
    7274        assert((pa & LINK_POINTER_ADDRESS_MASK) == pa);
     75        pa |= LINK_POINTER_QUEUE_HEAD_FLAG;
    7376
     77        batch->qh->next_queue = instance->queue_head->next_queue;
    7478
    75         if (instance->queue_head->element & LINK_POINTER_TERMINATE_FLAG) {
    76                 usb_log_debug2("Adding td(%X:%X) to queue %s first.\n",
    77                         tracker->td->status, tracker->td->device, instance->name);
     79        fibril_mutex_lock(&instance->guard);
     80
     81        if (instance->queue_head->element == instance->queue_head->next_queue) {
    7882                /* there is nothing scheduled */
    79                 instance->last_tracker = tracker;
     83                list_append(&batch->link, &instance->batch_list);
    8084                instance->queue_head->element = pa;
    81                 usb_log_debug2("Added td(%X:%X) to queue %s first.\n",
    82                         tracker->td->status, tracker->td->device, instance->name);
     85                usb_log_debug2("Added batch(%p) to queue %s first.\n",
     86                        batch, instance->name);
     87                fibril_mutex_unlock(&instance->guard);
    8388                return;
    8489        }
    85         usb_log_debug2("Adding td(%X:%X) to queue %s last.%p\n",
    86             tracker->td->status, tracker->td->device, instance->name,
    87             instance->last_tracker);
    88         /* now we can be sure that last_tracker is a valid pointer */
    89         instance->last_tracker->td->next = pa;
    90         instance->last_tracker = tracker;
     90        /* now we can be sure that there is someting scheduled */
     91        assert(!list_empty(&instance->batch_list));
     92        batch_t *first = list_get_instance(
     93                  instance->batch_list.next, batch_t, link);
     94        batch_t *last = list_get_instance(
     95            instance->batch_list.prev, batch_t, link);
     96        queue_head_append_qh(last->qh, pa);
     97        list_append(&batch->link, &instance->batch_list);
     98        usb_log_debug2("Added batch(%p) to queue %s last, first is %p.\n",
     99                batch, instance->name, first );
     100        fibril_mutex_unlock(&instance->guard);
     101}
     102/*----------------------------------------------------------------------------*/
     103static void transfer_list_remove_batch(
     104    transfer_list_t *instance, batch_t *batch)
     105{
     106        assert(instance);
     107        assert(batch);
     108        assert(instance->queue_head);
     109        assert(batch->qh);
    91110
    92         usb_log_debug2("Added td(%X:%X) to queue %s last.\n",
    93                 tracker->td->status, tracker->td->device, instance->name);
     111        /* I'm the first one here */
     112        if (batch->link.prev == &instance->batch_list) {
     113                usb_log_debug("Removing tracer %p was first, next element %x.\n",
     114                        batch, batch->qh->next_queue);
     115                instance->queue_head->element = batch->qh->next_queue;
     116        } else {
     117                usb_log_debug("Removing tracer %p was NOT first, next element %x.\n",
     118                        batch, batch->qh->next_queue);
     119                batch_t *prev = list_get_instance(batch->link.prev, batch_t, link);
     120                prev->qh->next_queue = batch->qh->next_queue;
     121        }
     122        list_remove(&batch->link);
     123}
     124/*----------------------------------------------------------------------------*/
     125void transfer_list_check(transfer_list_t *instance)
     126{
     127        assert(instance);
     128        fibril_mutex_lock(&instance->guard);
     129        link_t *current = instance->batch_list.next;
     130        while (current != &instance->batch_list) {
     131                link_t *next = current->next;
     132                batch_t *batch = list_get_instance(current, batch_t, link);
    94133
    95         /* check again, may be use atomic compare and swap */
    96         if (instance->queue_head->element & LINK_POINTER_TERMINATE_FLAG) {
    97                 instance->queue_head->element = pa;
    98                 usb_log_debug2("Added td(%X:%X) to queue first2 %s.\n",
    99                         tracker->td->status, tracker->td->device, instance->name);
     134                if (batch_is_complete(batch)) {
     135                        transfer_list_remove_batch(instance, batch);
     136                        batch->next_step(batch);
     137                }
     138                current = next;
    100139        }
     140        fibril_mutex_unlock(&instance->guard);
    101141}
    102142/**
  • uspace/drv/uhci-hcd/transfer_list.h

    rd81ef61c r50ba203  
    3535#define DRV_UHCI_TRANSFER_LIST_H
    3636
     37#include <fibril_synch.h>
     38
    3739#include "uhci_struct/queue_head.h"
    38 #include "tracker.h"
     40
     41#include "batch.h"
    3942
    4043typedef struct transfer_list
    4144{
    42         tracker_t *last_tracker;
    43 
     45        fibril_mutex_t guard;
    4446        queue_head_t *queue_head;
    4547        uint32_t queue_head_pa;
    4648        struct transfer_list *next;
    4749        const char *name;
     50        link_t batch_list;
    4851} transfer_list_t;
    4952
     
    5760        queue_head_dispose(instance->queue_head);
    5861}
     62void transfer_list_check(transfer_list_t *instance);
    5963
    60 
    61 void transfer_list_add_tracker(transfer_list_t *instance, tracker_t *tracker);
    62 
     64void transfer_list_add_batch(transfer_list_t *instance, batch_t *batch);
    6365#endif
    6466/**
  • uspace/drv/uhci-hcd/uhci.c

    rd81ef61c r50ba203  
    8989        pio_write_32(&instance->registers->flbaseadd, (uint32_t)pa);
    9090
    91         list_initialize(&instance->tracker_list);
    92         fibril_mutex_initialize(&instance->tracker_list_mutex);
     91        list_initialize(&instance->batch_list);
     92        fibril_mutex_initialize(&instance->batch_list_mutex);
    9393
    9494        instance->cleaner = fibril_create(uhci_clean_finished, instance);
     
    152152}
    153153/*----------------------------------------------------------------------------*/
    154 int uhci_schedule(uhci_t *instance, tracker_t *tracker)
    155 {
    156         assert(instance);
    157         assert(tracker);
    158         const int low_speed = (tracker->speed == LOW_SPEED);
     154int uhci_schedule(uhci_t *instance, batch_t *batch)
     155{
     156        assert(instance);
     157        assert(batch);
     158        const int low_speed = (batch->speed == LOW_SPEED);
    159159        if (!allowed_usb_packet(
    160             low_speed, tracker->transfer_type, tracker->packet_size)) {
     160            low_speed, batch->transfer_type, batch->max_packet_size)) {
    161161                usb_log_warning("Invalid USB packet specified %s SPEED %d %zu.\n",
    162                           low_speed ? "LOW" : "FULL" , tracker->transfer_type,
    163                     tracker->packet_size);
     162                          low_speed ? "LOW" : "FULL" , batch->transfer_type,
     163                    batch->max_packet_size);
    164164                return ENOTSUP;
    165165        }
    166166        /* TODO: check available bandwith here */
    167167
    168         usb_log_debug2("Scheduler(%d) acquiring tracker list mutex.\n",
    169             fibril_get_id());
    170         fibril_mutex_lock(&instance->tracker_list_mutex);
    171         usb_log_debug2("Scheduler(%d) acquired tracker list mutex.\n",
    172             fibril_get_id());
    173 
    174168        transfer_list_t *list =
    175             instance->transfers[low_speed][tracker->transfer_type];
     169            instance->transfers[low_speed][batch->transfer_type];
    176170        assert(list);
    177         transfer_list_add_tracker(list, tracker);
    178         list_append(&tracker->link, &instance->tracker_list);
    179 
    180         usb_log_debug2("Scheduler(%d) releasing tracker list mutex.\n",
    181             fibril_get_id());
    182         fibril_mutex_unlock(&instance->tracker_list_mutex);
    183         usb_log_debug2("Scheduler(%d) released tracker list mutex.\n",
    184             fibril_get_id());
     171        transfer_list_add_batch(list, batch);
    185172
    186173        return EOK;
     
    194181
    195182        while(1) {
    196                 LIST_INITIALIZE(done_trackers);
    197                 /* tracker iteration */
    198 
    199                 usb_log_debug2("Cleaner(%d) acquiring tracker list mutex.\n",
    200                     fibril_get_id());
    201                 fibril_mutex_lock(&instance->tracker_list_mutex);
    202                 usb_log_debug2("Cleaner(%d) acquired tracker list mutex.\n",
    203                     fibril_get_id());
    204 
    205                 link_t *current = instance->tracker_list.next;
    206                 while (current != &instance->tracker_list)
    207                 {
    208 
    209                         link_t *next = current->next;
    210                         tracker_t *tracker = list_get_instance(current, tracker_t, link);
    211 
    212                         assert(current == &tracker->link);
    213                         assert(tracker);
    214                         assert(tracker->next_step);
    215                         assert(tracker->td);
    216 
    217                         if (!transfer_descriptor_is_active(tracker->td)) {
    218                                 usb_log_info("Found inactive tracker with status: %x:%x.\n",
    219                                     tracker->td->status, tracker->td->device);
    220                                 list_remove(current);
    221                                 list_append(current, &done_trackers);
    222                         }
    223                         current = next;
    224                 }
    225 
    226                 usb_log_debug2("Cleaner(%d) releasing tracker list mutex.\n",
    227                     fibril_get_id());
    228                 fibril_mutex_unlock(&instance->tracker_list_mutex);
    229                 usb_log_debug2("Cleaner(%d) released tracker list mutex.\n",
    230                     fibril_get_id());
    231 
    232                 while (!list_empty(&done_trackers)) {
    233                         tracker_t *tracker = list_get_instance(
    234                           done_trackers.next, tracker_t, link);
    235                         list_remove(&tracker->link);
    236                         tracker->next_step(tracker);
    237                 }
     183                transfer_list_check(&instance->transfers_interrupt);
     184                transfer_list_check(&instance->transfers_control_slow);
     185                transfer_list_check(&instance->transfers_control_full);
     186                transfer_list_check(&instance->transfers_bulk_full);
    238187                async_usleep(UHCI_CLEANER_TIMEOUT);
    239188        }
  • uspace/drv/uhci-hcd/uhci.h

    rd81ef61c r50ba203  
    4444
    4545#include "transfer_list.h"
    46 #include "tracker.h"
     46#include "batch.h"
    4747
    4848typedef struct uhci_regs {
     
    8181        link_pointer_t *frame_list;
    8282
    83         link_t tracker_list;
    84         fibril_mutex_t tracker_list_mutex;
     83        link_t batch_list;
     84        fibril_mutex_t batch_list_mutex;
    8585
    8686        transfer_list_t transfers_bulk_full;
     
    113113  void *arg );
    114114
    115 int uhci_schedule(uhci_t *instance, tracker_t *tracker);
     115int uhci_schedule(uhci_t *instance, batch_t *batch);
    116116
    117117static inline uhci_t * dev_to_uhci(device_t *dev)
  • uspace/drv/uhci-hcd/uhci_struct/queue_head.h

    rd81ef61c r50ba203  
    5555}
    5656
    57 static inline void queue_head_add_next(queue_head_t *instance, uint32_t next_queue_pa)
     57static inline void queue_head_append_qh(queue_head_t *instance, uint32_t pa)
    5858{
    59         if (next_queue_pa) {
    60                 instance->next_queue = (next_queue_pa & LINK_POINTER_ADDRESS_MASK)
    61                   | LINK_POINTER_QUEUE_HEAD_FLAG;
     59        if (pa) {
     60                instance->next_queue = (pa & LINK_POINTER_ADDRESS_MASK)
     61                    | LINK_POINTER_QUEUE_HEAD_FLAG;
    6262        }
    6363}
    6464
    65 static inline queue_head_t * queue_head_get()
    66         { return malloc32(sizeof(queue_head_t)); }
     65static inline void queue_head_element_qh(queue_head_t *instance, uint32_t pa)
     66{
     67        if (pa) {
     68                instance->next_queue = (pa & LINK_POINTER_ADDRESS_MASK)
     69                    | LINK_POINTER_QUEUE_HEAD_FLAG;
     70        }
     71}
     72
     73static inline void queue_head_element_td(queue_head_t *instance, uint32_t pa)
     74{
     75        if (pa) {
     76                instance->element = (pa & LINK_POINTER_ADDRESS_MASK);
     77        }
     78}
     79
     80static inline queue_head_t * queue_head_get() {
     81        queue_head_t *ret = malloc32(sizeof(queue_head_t));
     82        if (ret)
     83                queue_head_init(ret);
     84        return ret;
     85}
    6786
    6887static inline void queue_head_dispose(queue_head_t *head)
  • uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.c

    rd81ef61c r50ba203  
    4040void transfer_descriptor_init(transfer_descriptor_t *instance,
    4141    int error_count, size_t size, bool toggle, bool isochronous,
    42     usb_target_t target, int pid, void *buffer)
     42    usb_target_t target, int pid, void *buffer, transfer_descriptor_t *next)
    4343{
    4444        assert(instance);
    4545
    46         instance->next = 0 | LINK_POINTER_TERMINATE_FLAG;
     46        instance->next = 0
     47            | LINK_POINTER_VERTICAL_FLAG
     48            | ((next != NULL) ? addr_to_phys(next) : LINK_POINTER_TERMINATE_FLAG);
    4749
    4850        instance->status = 0
     
    8082#endif
    8183}
    82 
    83 static inline usb_transaction_outcome_t convert_outcome(uint32_t status)
    84 {
    85         /*TODO: refactor into something sane */
    86         /*TODO: add additional usb_errors to usb_outcome_t */
    87 
    88         if (status & TD_STATUS_ERROR_STALLED)
    89                 return USB_OUTCOME_CRCERROR;
    90 
    91         if (status & TD_STATUS_ERROR_BUFFER)
    92                 return USB_OUTCOME_CRCERROR;
    93 
    94         if (status & TD_STATUS_ERROR_BABBLE)
    95                 return USB_OUTCOME_BABBLE;
    96 
    97         if (status & TD_STATUS_ERROR_NAK)
    98                 return USB_OUTCOME_CRCERROR;
    99 
    100   if (status & TD_STATUS_ERROR_CRC)
    101                 return USB_OUTCOME_CRCERROR;
    102 
    103         if (status & TD_STATUS_ERROR_BIT_STUFF)
    104                 return USB_OUTCOME_CRCERROR;
    105 
    106 //      assert((((status >> TD_STATUS_ERROR_POS) & TD_STATUS_ERROR_MASK)
    107 //      | TD_STATUS_ERROR_RESERVED) == TD_STATUS_ERROR_RESERVED);
    108         return USB_OUTCOME_OK;
    109 }
    11084/*----------------------------------------------------------------------------*/
    11185int transfer_descriptor_status(transfer_descriptor_t *instance)
    11286{
    11387        assert(instance);
    114         if (convert_outcome(instance->status))
    115                 return EINVAL; //TODO: use sane error value here
     88
     89        if ((instance->status & TD_STATUS_ERROR_STALLED) != 0)
     90                return EIO;
     91
     92        if ((instance->status & TD_STATUS_ERROR_CRC) != 0)
     93                return EAGAIN;
     94
     95        if ((instance->status & TD_STATUS_ERROR_BUFFER) != 0)
     96                return EAGAIN;
     97
     98        if ((instance->status & TD_STATUS_ERROR_BABBLE) != 0)
     99                return EIO;
     100
     101        if ((instance->status & TD_STATUS_ERROR_NAK) != 0)
     102                return EAGAIN;
     103
     104        if ((instance->status & TD_STATUS_ERROR_BIT_STUFF) != 0)
     105                return EAGAIN;
     106
    116107        return EOK;
    117108}
  • uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.h

    rd81ef61c r50ba203  
    9393void transfer_descriptor_init(transfer_descriptor_t *instance,
    9494    int error_count, size_t size, bool toggle, bool isochronous,
    95     usb_target_t target, int pid, void *buffer);
     95    usb_target_t target, int pid, void *buffer, transfer_descriptor_t * next);
    9696
    9797int transfer_descriptor_status(transfer_descriptor_t *instance);
     98
     99static inline size_t transfer_descriptor_actual_size(
     100    transfer_descriptor_t *instance)
     101{
     102        assert(instance);
     103        return
     104            ((instance->status >> TD_STATUS_ACTLEN_POS) + 1) & TD_STATUS_ACTLEN_MASK;
     105}
    98106
    99107static inline bool transfer_descriptor_is_active(
  • uspace/drv/uhci-hcd/utils/malloc32.h

    rd81ef61c r50ba203  
    4545#define UHCI_REQUIRED_PAGE_SIZE 4096
    4646
    47 static inline void * addr_to_phys(void *addr)
     47static inline uintptr_t addr_to_phys(void *addr)
    4848{
    4949        uintptr_t result;
     
    5151
    5252        assert(ret == 0);
    53         return (void*)(result | ((uintptr_t)addr & 0xfff));
     53        return (result | ((uintptr_t)addr & 0xfff));
    5454}
    5555
  • uspace/drv/uhci-rhd/port.c

    rd81ef61c r50ba203  
    3333 */
    3434#include <errno.h>
     35#include <str_error.h>
    3536
    3637#include <usb/usb.h>    /* usb_address_t */
    37 #include <usb/usbdrv.h> /* usb_drv_*     */
     38#include <usb/usbdevice.h>
     39#include <usb/hub.h>
     40#include <usb/request.h>
    3841#include <usb/debug.h>
     42#include <usb/recognise.h>
    3943
    4044#include "port.h"
     
    5660        port->attached_device = 0;
    5761        port->rh = rh;
    58         port->hc_phone = parent_phone;
     62        int rc = usb_hc_connection_initialize_from_device(
     63            &port->hc_connection, rh);
     64        if (rc != EOK) {
     65                usb_log_error("Failed to initialize connection to HC.");
     66                return rc;
     67        }
    5968
    6069        port->checker = fibril_create(uhci_port_check, port);
     
    96105
    97106                if (port_status & STATUS_CONNECTED_CHANGED) {
     107                        int rc = usb_hc_connection_open(
     108                            &port_instance->hc_connection);
     109                        if (rc != EOK) {
     110                                usb_log_error("Failed to connect to HC.");
     111                                goto next;
     112                        }
     113
    98114                        if (port_status & STATUS_CONNECTED) {
    99115                                /* new device */
     
    102118                                uhci_port_remove_device(port_instance);
    103119                        }
     120
     121                        rc = usb_hc_connection_close(
     122                            &port_instance->hc_connection);
     123                        if (rc != EOK) {
     124                                usb_log_error("Failed to disconnect from HC.");
     125                                goto next;
     126                        }
    104127                }
     128        next:
    105129                async_usleep(port_instance->wait_period_usec);
    106130        }
     
    111135{
    112136        assert(port);
    113         assert(port->hc_phone);
     137        assert(usb_hc_connection_is_opened(&port->hc_connection));
    114138
    115139        usb_log_info("Adding new device on port %d.\n", port->number);
    116140
    117141        /* get address of the future device */
    118         const usb_address_t usb_address = usb_drv_request_address(port->hc_phone);
     142        const usb_address_t usb_address = usb_hc_request_address(
     143            &port->hc_connection, true);
    119144
    120145        if (usb_address <= 0) {
     
    126151
    127152        /* get default address */
    128         int ret = usb_drv_reserve_default_address(port->hc_phone);
     153        int ret = usb_hc_reserve_default_address(&port->hc_connection, true);
    129154        if (ret != EOK) {
    130155                usb_log_error("Failed to reserve default address on port %d.\n",
    131156                    port->number);
    132                 int ret2 =
    133                   usb_drv_release_address(port->hc_phone, usb_address);
     157                int ret2 = usb_hc_unregister_device(&port->hc_connection,
     158                    usb_address);
    134159                if (ret2 != EOK) {
    135160                        usb_log_fatal("Failed to return requested address on port %d.\n",
     
    172197        }
    173198
    174         /* assign address to device */
    175         ret = usb_drv_req_set_address(port->hc_phone, 0, usb_address);
     199        /*
     200         * Initialize connection to the device.
     201         */
     202        /* FIXME: check for errors. */
     203        usb_device_connection_t new_dev_connection;
     204        usb_endpoint_pipe_t new_dev_ctrl_pipe;
     205        usb_device_connection_initialize_on_default_address(
     206            &new_dev_connection, &port->hc_connection);
     207        usb_endpoint_pipe_initialize_default_control(&new_dev_ctrl_pipe,
     208            &new_dev_connection);
     209
     210        /*
     211         * Assign new address to the device. This function updates
     212         * the backing connection to still point to the same device.
     213         */
     214        /* FIXME: check for errors. */
     215        usb_endpoint_pipe_start_session(&new_dev_ctrl_pipe);
     216        ret = usb_request_set_address(&new_dev_ctrl_pipe, usb_address);
     217        usb_endpoint_pipe_end_session(&new_dev_ctrl_pipe);
    176218
    177219        if (ret != EOK) { /* address assigning went wrong */
    178220                usb_log_error("Failed(%d) to assign address to the device.\n", ret);
    179221                uhci_port_set_enabled(port, false);
    180                 int release = usb_drv_release_default_address(port->hc_phone);
     222                int release = usb_hc_release_default_address(&port->hc_connection);
    181223                if (release != EOK) {
    182224                        usb_log_error("Failed to release default address on port %d.\n",
     
    192234
    193235        /* release default address */
    194         ret = usb_drv_release_default_address(port->hc_phone);
     236        ret = usb_hc_release_default_address(&port->hc_connection);
    195237        if (ret != EOK) {
    196238                usb_log_error("Failed to release default address on port %d.\n",
     
    204246        assert(port->attached_device == 0);
    205247
    206         ret = usb_drv_register_child_in_devman(port->hc_phone, port->rh,
    207           usb_address, &port->attached_device);
     248        ret = usb_device_register_child_in_devman(new_dev_connection.address,
     249            new_dev_connection.hc_handle, port->rh, &port->attached_device);
    208250
    209251        if (ret != EOK) { /* something went wrong */
     
    215257                port->number, usb_address, port->attached_device);
    216258
    217         ret =
    218           usb_drv_bind_address(port->hc_phone, usb_address, port->attached_device);
     259        /*
     260         * Register the device in the host controller.
     261         */
     262        usb_hc_attached_device_t new_device = {
     263                .address = new_dev_connection.address,
     264                .handle = port->attached_device
     265        };
     266
     267        ret = usb_hc_register_device(&port->hc_connection, &new_device);
    219268        // TODO: proper error check here
    220269        assert(ret == EOK);
  • uspace/drv/uhci-rhd/port.h

    rd81ef61c r50ba203  
    3838#include <driver.h> /* device_t */
    3939#include <stdint.h>
     40#include <usb/usbdevice.h>
    4041
    4142#include "port_status.h"
     
    4647        unsigned number;
    4748        unsigned wait_period_usec;
    48         int hc_phone;
     49        usb_hc_connection_t hc_connection;
    4950        device_t *rh;
    5051        devman_handle_t attached_device;
  • uspace/drv/usbhid/hid.h

    rd81ef61c r50ba203  
    6969        device_t *device;
    7070        usb_hid_configuration_t *conf;
    71         usb_address_t address;
    7271        usb_hid_report_parser_t *parser;
    7372
    7473        usb_device_connection_t wire;
     74        usb_endpoint_pipe_t ctrl_pipe;
    7575        usb_endpoint_pipe_t poll_pipe;
    7676} usb_hid_dev_kbd_t;
  • uspace/drv/usbhid/main.c

    rd81ef61c r50ba203  
    4545#include <str_error.h>
    4646#include <fibril.h>
     47#include <usb/debug.h>
     48#include <usb/classes/classes.h>
    4749#include <usb/classes/hid.h>
    4850#include <usb/classes/hidparser.h>
    49 #include <usb/devreq.h>
     51#include <usb/request.h>
    5052#include <usb/descriptor.h>
    5153#include <io/console.h>
     
    6062
    6163#define GUESSED_POLL_ENDPOINT 1
     64
     65/** Keyboard polling endpoint description for boot protocol class. */
     66static usb_endpoint_description_t poll_endpoint_description = {
     67        .transfer_type = USB_TRANSFER_INTERRUPT,
     68        .direction = USB_DIRECTION_IN,
     69        .interface_class = USB_CLASS_HID,
     70        .interface_subclass = USB_HID_SUBCLASS_BOOT,
     71        .interface_protocol = USB_HID_PROTOCOL_KEYBOARD,
     72        .flags = 0
     73};
    6274
    6375static void default_connection_handler(device_t *, ipc_callid_t, ipc_call_t *);
     
    262274}
    263275
    264 # if 0
    265276/*
    266277 * Kbd functions
     
    281292               
    282293                // get the descriptor from the device
    283                 int rc = usb_drv_req_get_descriptor(kbd_dev->device->parent_phone,
    284                     kbd_dev->address, USB_REQUEST_TYPE_CLASS, USB_DESCTYPE_HID_REPORT,
    285                     0, i, kbd_dev->conf->interfaces[i].report_desc, length,
     294                int rc = usb_request_get_descriptor(&kbd_dev->ctrl_pipe,
     295                    USB_REQUEST_TYPE_CLASS, USB_DESCTYPE_HID_REPORT,
     296                    i, 0,
     297                    kbd_dev->conf->interfaces[i].report_desc, length,
    286298                    &actual_size);
    287299
     
    303315        usb_standard_configuration_descriptor_t config_desc;
    304316       
    305         int rc = usb_drv_req_get_bare_configuration_descriptor(
    306             kbd_dev->device->parent_phone, kbd_dev->address, 0, &config_desc);
     317        int rc;
     318        rc = usb_request_get_bare_configuration_descriptor(&kbd_dev->ctrl_pipe,
     319            0, &config_desc);
    307320       
    308321        if (rc != EOK) {
     
    318331        size_t transferred = 0;
    319332        // get full configuration descriptor
    320         rc = usb_drv_req_get_full_configuration_descriptor(
    321             kbd_dev->device->parent_phone, kbd_dev->address, 0, descriptors,
     333        rc = usb_request_get_full_configuration_descriptor(&kbd_dev->ctrl_pipe,
     334            0, descriptors,
    322335            config_desc.total_length, &transferred);
    323336       
     
    329342        }
    330343       
     344        /*
     345         * Initialize the interrupt in endpoint.
     346         */
     347        usb_endpoint_mapping_t endpoint_mapping[1] = {
     348                {
     349                        .pipe = &kbd_dev->poll_pipe,
     350                        .description = &poll_endpoint_description
     351                }
     352        };
     353        rc = usb_endpoint_pipe_initialize_from_configuration(
     354            endpoint_mapping, 1,
     355            descriptors, config_desc.total_length,
     356            &kbd_dev->wire);
     357        if (rc != EOK) {
     358                usb_log_error("Failed to initialize poll pipe: %s.\n",
     359                    str_error(rc));
     360                return rc;
     361        }
     362        if (!endpoint_mapping[0].present) {
     363                usb_log_warning("Not accepting device, " \
     364                    "not boot-protocol keyboard.\n");
     365                return EREFUSED;
     366        }
     367
     368
     369
     370
    331371        kbd_dev->conf = (usb_hid_configuration_t *)calloc(1,
    332372            sizeof(usb_hid_configuration_t));
     
    336376        }
    337377       
    338         rc = usbkbd_parse_descriptors(descriptors, transferred, kbd_dev->conf);
     378        /*rc = usbkbd_parse_descriptors(descriptors, transferred, kbd_dev->conf);
    339379        free(descriptors);
    340380        if (rc != EOK) {
     
    343383        }
    344384
    345         // get and report descriptors
     385        // get and report descriptors*/
    346386        rc = usbkbd_get_report_descriptor(kbd_dev);
    347387        if (rc != EOK) {
     
    360400     *    as the endpoint for polling
    361401         */
    362        
     402
    363403        return EOK;
    364404}
    365 #endif
     405
    366406static usb_hid_dev_kbd_t *usbkbd_init_device(device_t *dev)
    367407{
     408        int rc;
     409
    368410        usb_hid_dev_kbd_t *kbd_dev = (usb_hid_dev_kbd_t *)calloc(1,
    369411            sizeof(usb_hid_dev_kbd_t));
     
    376418        kbd_dev->device = dev;
    377419
    378         // get phone to my HC and save it as my parent's phone
    379         // TODO: maybe not a good idea if DDF will use parent_phone
    380         int rc = kbd_dev->device->parent_phone = usb_drv_hc_connect_auto(dev, 0);
    381         if (rc < 0) {
    382                 printf("Problem setting phone to HC.\n");
    383                 goto error_leave;
    384         }
    385 
    386         rc = kbd_dev->address = usb_drv_get_my_address(dev->parent_phone, dev);
    387         if (rc < 0) {
    388                 printf("Problem getting address of the device.\n");
    389                 goto error_leave;
    390         }
    391 
    392         // doesn't matter now that we have no address
    393 //      if (kbd_dev->address < 0) {
    394 //              fprintf(stderr, NAME ": No device address!\n");
    395 //              free(kbd_dev);
    396 //              return NULL;
    397 //      }
    398 
    399         /*
    400          * will need all descriptors:
    401          * 1) choose one configuration from configuration descriptors
    402          *    (set it to the device)
    403          * 2) set endpoints from endpoint descriptors
    404          */
    405 
    406 
    407         // TODO: get descriptors, parse descriptors and save endpoints
    408         //usbkbd_process_descriptors(kbd_dev);
    409         usb_drv_req_set_configuration(
    410           kbd_dev->device->parent_phone, kbd_dev->address, 1);
    411 
    412 
    413 
    414420        /*
    415421         * Initialize the backing connection to the host controller.
     
    425431         * Initialize device pipes.
    426432         */
    427         rc = usb_endpoint_pipe_initialize(&kbd_dev->poll_pipe, &kbd_dev->wire,
    428             GUESSED_POLL_ENDPOINT, USB_TRANSFER_INTERRUPT, USB_DIRECTION_IN);
    429         if (rc != EOK) {
    430                 printf("Failed to initialize interrupt in pipe: %s.\n",
     433        rc = usb_endpoint_pipe_initialize_default_control(&kbd_dev->ctrl_pipe,
     434            &kbd_dev->wire);
     435        if (rc != EOK) {
     436                printf("Failed to initialize default control pipe: %s.\n",
    431437                    str_error(rc));
    432438                goto error_leave;
    433439        }
    434440
     441        /*
     442         * will need all descriptors:
     443         * 1) choose one configuration from configuration descriptors
     444         *    (set it to the device)
     445         * 2) set endpoints from endpoint descriptors
     446         */
     447
     448        // TODO: get descriptors, parse descriptors and save endpoints
     449        usb_endpoint_pipe_start_session(&kbd_dev->ctrl_pipe);
     450        //usb_request_set_configuration(&kbd_dev->ctrl_pipe, 1);
     451        rc = usbkbd_process_descriptors(kbd_dev);
     452        usb_endpoint_pipe_end_session(&kbd_dev->ctrl_pipe);
     453        if (rc != EOK) {
     454                goto error_leave;
     455        }
    435456
    436457        return kbd_dev;
     
    590611int main(int argc, char *argv[])
    591612{
     613        usb_log_enable(USB_LOG_LEVEL_INFO, "usbhid");
    592614        return driver_main(&kbd_driver);
    593615}
  • uspace/drv/usbhub/usbhub.c

    rd81ef61c r50ba203  
    3636#include <bool.h>
    3737#include <errno.h>
     38#include <str_error.h>
    3839
    3940#include <usb_iface.h>
    4041#include <usb/usbdrv.h>
    4142#include <usb/descriptor.h>
     43#include <usb/recognise.h>
    4244#include <usb/devreq.h>
    4345#include <usb/request.h>
     
    7678        result->device = device;
    7779
     80<<<<<<< TREE
    7881        result->usb_device = usb_new(usb_hcd_attached_device_info_t);
    7982       
     83=======
     84
     85        dprintf(USB_LOG_LEVEL_DEBUG, "phone to hc = %d", hc);
     86        if (hc < 0) {
     87                return result;
     88        }
     89        //get some hub info
     90        usb_address_t addr = usb_drv_get_my_address(hc, device);
     91        dprintf(USB_LOG_LEVEL_DEBUG, "address of newly created hub = %d", addr);
     92        /*if(addr<0){
     93                //return result;
     94
     95        }*/
     96
     97        result->address = addr;
     98
     99>>>>>>> MERGE-SOURCE
    80100        // get hub descriptor
    81101
     
    148168        int port;
    149169        int opResult;
     170<<<<<<< TREE
    150171        //usb_target_t target;
    151172        //target.address = hub_info->usb_device->address;
    152173        //target.endpoint = 0;
     174=======
     175        usb_target_t target;
     176        target.address = hub_info->address;
     177        target.endpoint = 0;
     178>>>>>>> MERGE-SOURCE
    153179
    154180        //get configuration descriptor
     
    212238        dprintf(USB_LOG_LEVEL_INFO, "hub dev added");
    213239        dprintf(USB_LOG_LEVEL_DEBUG, "\taddress %d, has %d ports ",
    214                         hub_info->usb_device->address,
     240                        hub_info->address,
    215241                        hub_info->port_count);
    216242        dprintf(USB_LOG_LEVEL_DEBUG, "\tused configuration %d",config_descriptor.configuration_number);
     
    317343        }
    318344
     345        devman_handle_t hc_handle;
     346        opResult = usb_drv_find_hc(hub->device, &hc_handle);
     347        if (opResult != EOK) {
     348                usb_log_error("Failed to get handle of host controller: %s.\n",
     349                    str_error(opResult));
     350                return;
     351        }
     352
    319353        devman_handle_t child_handle;
    320         opResult = usb_drv_register_child_in_devman(hc, hub->device,
    321             new_device_address, &child_handle);
     354        opResult = usb_device_register_child_in_devman(new_device_address,
     355            hc_handle, hub->device, &child_handle);
    322356        if (opResult != EOK) {
    323357                dprintf(USB_LOG_LEVEL_ERROR, "could not start driver for new device");
     
    472506                /*
    473507                usb_target_t target;
    474                 target.address = hub_info->usb_device->address;
     508                target.address = hub_info->address;
    475509                target.endpoint = 1;/// \TODO get from endpoint descriptor
    476510                dprintf(USB_LOG_LEVEL_INFO, "checking changes for hub at addr %d",
     
    515549                        if (interrupt) {
    516550                                usb_hub_process_interrupt(
     551<<<<<<< TREE
    517552                                        hub_info, port);
     553=======
     554                                        hub_info, hc, port, hub_info->address);
     555>>>>>>> MERGE-SOURCE
    518556                        }
    519557                }
  • uspace/drv/usbhub/usbhub.h

    rd81ef61c r50ba203  
    3636#define DRV_USBHUB_USBHUB_H
    3737
     38#include <ipc/devman.h>
     39#include <usb/usb.h>
     40#include <driver.h>
     41
    3842#define NAME "usbhub"
    3943
     44<<<<<<< TREE
    4045#include "usb/hcdhubd.h"
    4146
    4247#include <usb/pipes.h>
    4348
     49=======
     50>>>>>>> MERGE-SOURCE
    4451/** basic information about device attached to hub */
    4552typedef struct{
     
    6269        /** attached device handles, for each port one */
    6370        usb_hub_attached_device_t * attached_devs;
    64         /** General usb device info. */
    65         usb_hcd_attached_device_info_t * usb_device;
     71        /** USB address of the hub. */
     72        usb_address_t address;
    6673        /** General device info*/
    6774        device_t * device;
     75<<<<<<< TREE
    6876        /** connection to hcd */
    6977        usb_device_connection_t connection;
     
    7179        usb_hub_endpoints_t endpoints;
    7280
     81=======
     82>>>>>>> MERGE-SOURCE
    7383} usb_hub_info_t;
    7484
  • uspace/drv/vhc/conn.h

    rd81ef61c r50ba203  
    3737
    3838#include <usb/usb.h>
    39 #include <usb/hcdhubd.h>
    4039#include <usbhc_iface.h>
    4140#include "vhcd.h"
     
    4443void connection_handler_host(sysarg_t);
    4544
    46 usb_hcd_transfer_ops_t vhc_transfer_ops;
    4745usbhc_iface_t vhc_iface;
    4846
  • uspace/drv/vhc/connhost.c

    rd81ef61c r50ba203  
    3636#include <errno.h>
    3737#include <usb/usb.h>
    38 #include <usb/hcd.h>
     38#include <usb/addrkeep.h>
    3939
    4040#include "vhcd.h"
     
    6464
    6565static void universal_callback(void *buffer, size_t size,
    66     usb_transaction_outcome_t outcome, void *arg)
     66    int outcome, void *arg)
    6767{
    6868        transfer_info_t *transfer = (transfer_info_t *) arg;
     
    107107
    108108static void control_abort_prematurely(control_transfer_info_t *transfer,
    109     size_t size, usb_transaction_outcome_t outcome)
     109    size_t size, int outcome)
    110110{
    111111        switch (transfer->direction) {
     
    127127
    128128static void control_callback_two(void *buffer, size_t size,
    129     usb_transaction_outcome_t outcome, void *arg)
     129    int outcome, void *arg)
    130130{
    131131        control_transfer_info_t *ctrl_transfer = (control_transfer_info_t *) arg;
    132132
    133         if (outcome != USB_OUTCOME_OK) {
     133        if (outcome != EOK) {
    134134                control_abort_prematurely(ctrl_transfer, outcome, size);
    135135                free(ctrl_transfer);
     
    165165
    166166static void control_callback_one(void *buffer, size_t size,
    167     usb_transaction_outcome_t outcome, void *arg)
     167    int outcome, void *arg)
    168168{
    169169        control_transfer_info_t *transfer = (control_transfer_info_t *) arg;
    170170
    171         if (outcome != USB_OUTCOME_OK) {
     171        if (outcome != EOK) {
    172172                control_abort_prematurely(transfer, outcome, size);
    173173                free(transfer);
     
    276276
    277277static int interrupt_out(device_t *dev, usb_target_t target,
     278    size_t max_packet_size,
    278279    void *data, size_t size,
    279280    usbhc_iface_transfer_out_callback_t callback, void *arg)
     
    285286
    286287static int interrupt_in(device_t *dev, usb_target_t target,
     288    size_t max_packet_size,
    287289    void *data, size_t size,
    288290    usbhc_iface_transfer_in_callback_t callback, void *arg)
     
    294296
    295297static int control_write_setup(device_t *dev, usb_target_t target,
     298    size_t max_packet_size,
    296299    void *data, size_t size,
    297300    usbhc_iface_transfer_out_callback_t callback, void *arg)
     
    303306
    304307static int control_write_data(device_t *dev, usb_target_t target,
     308    size_t max_packet_size,
    305309    void *data, size_t size,
    306310    usbhc_iface_transfer_out_callback_t callback, void *arg)
     
    320324
    321325static int control_write(device_t *dev, usb_target_t target,
     326    size_t max_packet_size,
    322327    void *setup_packet, size_t setup_packet_size,
    323328    void *data, size_t data_size,
     
    337342
    338343static int control_read_setup(device_t *dev, usb_target_t target,
     344    size_t max_packet_size,
    339345    void *data, size_t size,
    340346    usbhc_iface_transfer_out_callback_t callback, void *arg)
     
    346352
    347353static int control_read_data(device_t *dev, usb_target_t target,
     354    size_t max_packet_size,
    348355    void *data, size_t size,
    349356    usbhc_iface_transfer_in_callback_t callback, void *arg)
     
    363370
    364371static int control_read(device_t *dev, usb_target_t target,
     372    size_t max_packet_size,
    365373    void *setup_packet, size_t setup_packet_size,
    366374    void *data, size_t data_size,
     
    382390
    383391
    384 static int reserve_default_address(device_t *dev)
     392static int reserve_default_address(device_t *dev, bool ignored)
    385393{
    386394        usb_address_keeping_reserve_default(&addresses);
     
    394402}
    395403
    396 static int request_address(device_t *dev, usb_address_t *address)
     404static int request_address(device_t *dev, bool ignored, usb_address_t *address)
    397405{
    398406        usb_address_t addr = usb_address_keeping_request(&addresses);
  • uspace/drv/vhc/devices.c

    rd81ef61c r50ba203  
    112112 * @param transaction Transaction to be sent over the bus.
    113113 */
    114 usb_transaction_outcome_t virtdev_send_to_all(transaction_t *transaction)
     114int virtdev_send_to_all(transaction_t *transaction)
    115115{
    116116        /* For easier debugging. */
     
    126126                        assert(false && "unreachable branch in switch()");
    127127        }
    128         usb_transaction_outcome_t outcome = USB_OUTCOME_BABBLE;
     128        int outcome = EBADCHECKSUM;
    129129
    130130        link_t *pos;
     
    185185                 */
    186186                if (rc == EOK) {
    187                         outcome = USB_OUTCOME_OK;
     187                        outcome = EOK;
    188188                }
    189189        }
     
    221221                                break;
    222222                }
    223                 outcome = USB_OUTCOME_OK;
     223                outcome = EOK;
    224224        }
    225225       
  • uspace/drv/vhc/devices.h

    rd81ef61c r50ba203  
    5454virtdev_connection_t *virtdev_find(sysarg_t);
    5555void virtdev_destroy_device(virtdev_connection_t *);
    56 usb_transaction_outcome_t virtdev_send_to_all(transaction_t *);
     56int virtdev_send_to_all(transaction_t *);
    5757
    5858#endif
  • uspace/drv/vhc/hc.c

    rd81ef61c r50ba203  
    8989 */
    9090static void process_transaction_with_outcome(transaction_t * transaction,
    91     usb_transaction_outcome_t outcome)
     91    int outcome)
    9292{
    9393        usb_log_debug2("Transaction " TRANSACTION_FORMAT " done: %s.\n",
    9494            TRANSACTION_PRINTF(*transaction),
    95             usb_str_transaction_outcome(outcome));
     95            str_error(outcome));
    9696       
    9797        transaction->callback(transaction->buffer, transaction->actual_len,
     
    127127                    TRANSACTION_PRINTF(*transaction), ports);
    128128
    129                 usb_transaction_outcome_t outcome;
     129                int outcome;
    130130                outcome = virtdev_send_to_all(transaction);
    131131               
  • uspace/drv/vhc/hc.h

    rd81ef61c r50ba203  
    4747 */
    4848typedef void (*hc_transaction_done_callback_t)(void *buffer, size_t size,
    49     usb_transaction_outcome_t outcome, void *arg);
     49    int outcome, void *arg);
    5050
    5151/** Pending transaction details. */
  • uspace/drv/vhc/hub.c

    rd81ef61c r50ba203  
    4141#include <driver.h>
    4242#include <usb/usbdrv.h>
     43#include <usb/recognise.h>
    4344
    4445#include "hub.h"
     
    9394
    9495        devman_handle_t hub_handle;
    95         usb_drv_register_child_in_devman(hc, hc_dev, hub_address, &hub_handle);
     96        usb_device_register_child_in_devman(hub_address, hc_dev->handle,
     97            hc_dev, &hub_handle);
     98        //usb_drv_register_child_in_devman(hc, hc_dev, hub_address, &hub_handle);
    9699        usb_drv_bind_address(hc, hub_address, hub_handle);
    97100
  • uspace/lib/c/generic/async.c

    rd81ef61c r50ba203  
    15671567}
    15681568
     1569/** Start IPC_M_DATA_READ using the async framework.
     1570 *
     1571 * @param phoneid Phone that will be used to contact the receiving side.
     1572 * @param dst Address of the beginning of the destination buffer.
     1573 * @param size Size of the destination buffer (in bytes).
     1574 * @param dataptr Storage of call data (arg 2 holds actual data size).
     1575 * @return Hash of the sent message or 0 on error.
     1576 */
     1577aid_t async_data_read(int phoneid, void *dst, size_t size, ipc_call_t *dataptr)
     1578{
     1579        return async_send_2(phoneid, IPC_M_DATA_READ, (sysarg_t) dst,
     1580            (sysarg_t) size, dataptr);
     1581}
     1582
    15691583/** Wrapper for IPC_M_DATA_READ calls using the async framework.
    15701584 *
  • uspace/lib/c/generic/str_error.c

    rd81ef61c r50ba203  
    3333 */
    3434
     35#include <errno.h>
    3536#include <str_error.h>
    3637#include <stdio.h>
     
    6364static fibril_local char noerr[NOERR_LEN];
    6465
    65 const char *str_error(const int errno)
     66const char *str_error(const int e)
    6667{
    67         if ((errno <= 0) && (errno >= MIN_ERRNO))
    68                 return err_desc[-errno];
     68        if ((e <= 0) && (e >= MIN_ERRNO))
     69                return err_desc[-e];
    6970       
    70         snprintf(noerr, NOERR_LEN, "Unkown error code %d", errno);
     71        /* Ad hoc descriptions of error codes interesting for USB. */
     72        switch (e) {
     73                case EBADCHECKSUM:
     74                        return "Bad checksum";
     75                case EAGAIN:
     76                        return "Resource temporarily unavailable";
     77                default:
     78                        break;
     79        }
     80
     81        snprintf(noerr, NOERR_LEN, "Unkown error code %d", e);
    7182        return noerr;
    7283}
  • uspace/lib/c/include/async.h

    rd81ef61c r50ba203  
    340340            (arg4), (answer))
    341341
     342extern aid_t async_data_read(int, void *, size_t, ipc_call_t *);
    342343extern int async_data_read_start(int, void *, size_t);
    343344extern bool async_data_read_receive(ipc_callid_t *, size_t *);
  • uspace/lib/c/include/errno.h

    rd81ef61c r50ba203  
    5656#define EMLINK        (-266)
    5757
     58/** Bad checksum. */
     59#define EBADCHECKSUM  (-300)
     60
    5861/** An API function is called while another blocking function is in progress. */
    5962#define EINPROGRESS  (-10036)
  • uspace/lib/drv/generic/remote_usbhc.c

    rd81ef61c r50ba203  
    4040
    4141#define USB_MAX_PAYLOAD_SIZE 1020
     42#define HACK_MAX_PACKET_SIZE 8
     43#define HACK_MAX_PACKET_SIZE_INTERRUPT_IN 4
    4244
    4345static void remote_usbhc_get_address(device_t *, void *, ipc_callid_t, ipc_call_t *);
    44 static void remote_usbhc_get_buffer(device_t *, void *, ipc_callid_t, ipc_call_t *);
    4546static void remote_usbhc_interrupt_out(device_t *, void *, ipc_callid_t, ipc_call_t *);
    4647static void remote_usbhc_interrupt_in(device_t *, void *, ipc_callid_t, ipc_call_t *);
     
    6465        remote_usbhc_get_address,
    6566
    66         remote_usbhc_get_buffer,
    67 
    6867        remote_usbhc_reserve_default_address,
    6968        remote_usbhc_release_default_address,
     
    9897typedef struct {
    9998        ipc_callid_t caller;
     99        ipc_callid_t data_caller;
    100100        void *buffer;
    101101        void *setup_packet;
     
    127127
    128128        trans->caller = caller;
     129        trans->data_caller = 0;
    129130        trans->buffer = NULL;
    130131        trans->setup_packet = NULL;
     
    155156}
    156157
    157 void remote_usbhc_get_buffer(device_t *device, void *iface,
    158     ipc_callid_t callid, ipc_call_t *call)
    159 {
    160         sysarg_t buffer_hash = DEV_IPC_GET_ARG1(*call);
    161         async_transaction_t * trans = (async_transaction_t *)buffer_hash;
    162         if (trans == NULL) {
    163                 async_answer_0(callid, ENOENT);
    164                 return;
    165         }
    166         if (trans->buffer == NULL) {
    167                 async_answer_0(callid, EINVAL);
    168                 async_transaction_destroy(trans);
    169                 return;
    170         }
    171 
    172         ipc_callid_t cid;
    173         size_t accepted_size;
    174         if (!async_data_read_receive(&cid, &accepted_size)) {
    175                 async_answer_0(callid, EINVAL);
    176                 async_transaction_destroy(trans);
    177                 return;
    178         }
    179 
    180         if (accepted_size > trans->size) {
    181                 accepted_size = trans->size;
    182         }
    183         async_data_read_finalize(cid, trans->buffer, accepted_size);
    184 
    185         async_answer_1(callid, EOK, accepted_size);
    186 
    187         async_transaction_destroy(trans);
    188 }
    189 
    190158void remote_usbhc_reserve_default_address(device_t *device, void *iface,
    191159    ipc_callid_t callid, ipc_call_t *call)
     
    197165                return;
    198166        }
    199 
    200         int rc = usb_iface->reserve_default_address(device);
     167       
     168        bool full_speed = DEV_IPC_GET_ARG1(*call);
     169       
     170        int rc = usb_iface->reserve_default_address(device, full_speed);
    201171
    202172        async_answer_0(callid, rc);
     
    227197                return;
    228198        }
     199       
     200        bool full_speed = DEV_IPC_GET_ARG1(*call);
    229201
    230202        usb_address_t address;
    231         int rc = usb_iface->request_address(device, &address);
     203        int rc = usb_iface->request_address(device, full_speed, &address);
    232204        if (rc != EOK) {
    233205                async_answer_0(callid, rc);
     
    274246
    275247static void callback_out(device_t *device,
    276     usb_transaction_outcome_t outcome, void *arg)
     248    int outcome, void *arg)
    277249{
    278250        async_transaction_t *trans = (async_transaction_t *)arg;
     
    284256
    285257static void callback_in(device_t *device,
    286     usb_transaction_outcome_t outcome, size_t actual_size, void *arg)
     258    int outcome, size_t actual_size, void *arg)
    287259{
    288260        async_transaction_t *trans = (async_transaction_t *)arg;
    289261
    290         if (outcome != USB_OUTCOME_OK) {
     262        if (outcome != EOK) {
    291263                async_answer_0(trans->caller, outcome);
     264                if (trans->data_caller) {
     265                        async_answer_0(trans->data_caller, EINTR);
     266                }
    292267                async_transaction_destroy(trans);
    293268                return;
     
    295270
    296271        trans->size = actual_size;
    297         async_answer_1(trans->caller, USB_OUTCOME_OK, (sysarg_t)trans);
     272
     273        if (trans->data_caller) {
     274                async_data_read_finalize(trans->data_caller,
     275                    trans->buffer, actual_size);
     276        }
     277
     278        async_answer_0(trans->caller, EOK);
     279
     280        async_transaction_destroy(trans);
    298281}
    299282
     
    345328        trans->size = len;
    346329
    347         int rc = transfer_func(device, target, buffer, len,
     330        int rc = transfer_func(device, target, HACK_MAX_PACKET_SIZE,
     331            buffer, len,
    348332            callback_out, trans);
    349333
     
    376360        };
    377361
     362        ipc_callid_t data_callid;
     363        if (!async_data_read_receive(&data_callid, &len)) {
     364                async_answer_0(callid, EPARTY);
     365                return;
     366        }
     367
    378368        async_transaction_t *trans = async_transaction_create(callid);
    379369        if (trans == NULL) {
     
    381371                return;
    382372        }
     373        trans->data_caller = data_callid;
    383374        trans->buffer = malloc(len);
    384375        trans->size = len;
    385376
    386         int rc = transfer_func(device, target, trans->buffer, len,
     377        int rc = transfer_func(device, target, HACK_MAX_PACKET_SIZE_INTERRUPT_IN,
     378            trans->buffer, len,
    387379            callback_in, trans);
    388380
     
    556548                .endpoint = DEV_IPC_GET_ARG2(*call)
    557549        };
     550        size_t data_buffer_len = DEV_IPC_GET_ARG3(*call);
    558551
    559552        int rc;
     
    562555        void *data_buffer = NULL;
    563556        size_t setup_packet_len = 0;
    564         size_t data_buffer_len = 0;
    565557
    566558        rc = async_data_write_accept(&setup_packet, false,
     
    570562                return;
    571563        }
    572         rc = async_data_write_accept(&data_buffer, false,
    573             1, USB_MAX_PAYLOAD_SIZE, 0, &data_buffer_len);
    574         if (rc != EOK) {
    575                 async_answer_0(callid, rc);
    576                 free(setup_packet);
    577                 return;
     564
     565        if (data_buffer_len > 0) {
     566                rc = async_data_write_accept(&data_buffer, false,
     567                    1, USB_MAX_PAYLOAD_SIZE, 0, &data_buffer_len);
     568                if (rc != EOK) {
     569                        async_answer_0(callid, rc);
     570                        free(setup_packet);
     571                        return;
     572                }
    578573        }
    579574
     
    589584        trans->size = data_buffer_len;
    590585
    591         rc = usb_iface->control_write(device, target,
     586        rc = usb_iface->control_write(device, target, HACK_MAX_PACKET_SIZE,
    592587            setup_packet, setup_packet_len,
    593588            data_buffer, data_buffer_len,
     
    612607        }
    613608
    614         size_t data_len = DEV_IPC_GET_ARG3(*call);
    615609        usb_target_t target = {
    616610                .address = DEV_IPC_GET_ARG1(*call),
     
    622616        void *setup_packet = NULL;
    623617        size_t setup_packet_len = 0;
     618        size_t data_len = 0;
    624619
    625620        rc = async_data_write_accept(&setup_packet, false,
     
    627622        if (rc != EOK) {
    628623                async_answer_0(callid, rc);
     624                return;
     625        }
     626
     627        ipc_callid_t data_callid;
     628        if (!async_data_read_receive(&data_callid, &data_len)) {
     629                async_answer_0(callid, EPARTY);
     630                free(setup_packet);
    629631                return;
    630632        }
     
    636638                return;
    637639        }
     640        trans->data_caller = data_callid;
    638641        trans->setup_packet = setup_packet;
    639642        trans->size = data_len;
     
    645648        }
    646649
    647         rc = usb_iface->control_read(device, target,
     650        rc = usb_iface->control_read(device, target, HACK_MAX_PACKET_SIZE,
    648651            setup_packet, setup_packet_len,
    649652            trans->buffer, trans->size,
  • uspace/lib/drv/include/usbhc_iface.h

    rd81ef61c r50ba203  
    4040#include "driver.h"
    4141#include <usb/usb.h>
     42#include <bool.h>
    4243
    4344
     
    6667 *   - argument #2 is target endpoint
    6768 *   - argument #3 is buffer size
     69 * - this call is immediately followed by IPC data read (async version)
    6870 * - the call is not answered until the device returns some data (or until
    6971 *   error occurs)
    70  * - if the call is answered with EOK, first argument of the answer is buffer
    71  *   hash that could be used to retrieve the actual data
    7272 *
    7373 * Some special methods (NO-DATA transactions) do not send any data. These
    7474 * might behave as both OUT or IN transactions because communication parts
    7575 * where actual buffers are exchanged are omitted.
    76  *
    77  * The mentioned data retrieval can be done any time after receiving EOK
    78  * answer to IN method.
    79  * This retrieval is done using the IPC_M_USBHC_GET_BUFFER where
    80  * the first argument is buffer hash from call answer.
    81  * This call must be immediately followed by data read-in and after the
    82  * data are transferred, the initial call (IPC_M_USBHC_GET_BUFFER)
    83  * is answered. Each buffer can be retrieved only once.
    84  *
     76 **
    8577 * For all these methods, wrap functions exists. Important rule: functions
    8678 * for IN transactions have (as parameters) buffers where retrieved data
     
    10496        IPC_M_USBHC_GET_ADDRESS,
    10597
    106         /** Asks for data buffer.
    107          * See explanation at usb_iface_funcs_t.
    108          * This function does not have counter part in functional interface
    109          * as it is handled by the remote part itself.
    110          */
    111         IPC_M_USBHC_GET_BUFFER,
    112 
    11398
    11499        /** Reserve usage of default address.
     
    223208/** Callback for outgoing transfer. */
    224209typedef void (*usbhc_iface_transfer_out_callback_t)(device_t *,
    225     usb_transaction_outcome_t, void *);
     210    int, void *);
    226211
    227212/** Callback for incoming transfer. */
    228213typedef void (*usbhc_iface_transfer_in_callback_t)(device_t *,
    229     usb_transaction_outcome_t, size_t, void *);
     214    int, size_t, void *);
    230215
    231216
    232217/** Out transfer processing function prototype. */
    233 typedef int (*usbhc_iface_transfer_out_t)(device_t *, usb_target_t,
     218typedef int (*usbhc_iface_transfer_out_t)(device_t *, usb_target_t, size_t,
    234219    void *, size_t,
    235220    usbhc_iface_transfer_out_callback_t, void *);
    236221
    237 /** Setup transfer processing function prototype. */
     222/** Setup transfer processing function prototype. @deprecated */
    238223typedef usbhc_iface_transfer_out_t usbhc_iface_transfer_setup_t;
    239224
    240225/** In transfer processing function prototype. */
    241 typedef int (*usbhc_iface_transfer_in_t)(device_t *, usb_target_t,
     226typedef int (*usbhc_iface_transfer_in_t)(device_t *, usb_target_t, size_t,
    242227    void *, size_t,
    243228    usbhc_iface_transfer_in_callback_t, void *);
     
    247232        int (*tell_address)(device_t *, devman_handle_t, usb_address_t *);
    248233
    249         int (*reserve_default_address)(device_t *);
     234        int (*reserve_default_address)(device_t *, bool);
    250235        int (*release_default_address)(device_t *);
    251         int (*request_address)(device_t *, usb_address_t *);
     236        int (*request_address)(device_t *, bool, usb_address_t *);
    252237        int (*bind_address)(device_t *, usb_address_t, devman_handle_t);
    253238        int (*release_address)(device_t *, usb_address_t);
     
    267252
    268253        int (*control_write)(device_t *, usb_target_t,
     254            size_t,
    269255            void *, size_t, void *, size_t,
    270256            usbhc_iface_transfer_out_callback_t, void *);
    271257
    272258        int (*control_read)(device_t *, usb_target_t,
     259            size_t,
    273260            void *, size_t, void *, size_t,
    274261            usbhc_iface_transfer_in_callback_t, void *);
  • uspace/lib/usb/Makefile

    rd81ef61c r50ba203  
    3939        src/drvpsync.c \
    4040        src/dump.c \
    41         src/hcdhubd.c \
    42         src/hcdrv.c \
    4341        src/hidparser.c \
    44         src/localdrv.c \
     42        src/hub.c \
    4543        src/pipes.c \
     44        src/pipesinit.c \
     45        src/pipesio.c \
    4646        src/recognise.c \
    47         src/remotedrv.c \
    4847        src/request.c \
    4948        src/usb.c \
     49        src/usbdevice.c \
    5050        src/usbdrvreq.c \
    5151        src/usbdrv.c \
  • uspace/lib/usb/include/usb/addrkeep.h

    • Property mode changed from 120000 to 100644
    rd81ef61c r50ba203  
    1 hcd.h
     1/*
     2 * Copyright (c) 2010 Vojtech Horky
     3 * All rights reserved.
     4 *
     5 * Redistribution and use in source and binary forms, with or without
     6 * modification, are permitted provided that the following conditions
     7 * are met:
     8 *
     9 * - Redistributions of source code must retain the above copyright
     10 *   notice, this list of conditions and the following disclaimer.
     11 * - Redistributions in binary form must reproduce the above copyright
     12 *   notice, this list of conditions and the following disclaimer in the
     13 *   documentation and/or other materials provided with the distribution.
     14 * - The name of the author may not be used to endorse or promote products
     15 *   derived from this software without specific prior written permission.
     16 *
     17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
     18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
     19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
     20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
     21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
     22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
     26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     27 */
     28
     29/** @addtogroup libusb
     30 * @{
     31 */
     32/** @file
     33 * USB address keeping for host controller drivers.
     34 */
     35#ifndef LIBUSB_ADDRKEEP_H_
     36#define LIBUSB_ADDRKEEP_H_
     37
     38#include <usb/usb.h>
     39#include <fibril_synch.h>
     40#include <devman.h>
     41
     42/** Info about used address. */
     43typedef struct {
     44        /** Linked list member. */
     45        link_t link;
     46        /** Address. */
     47        usb_address_t address;
     48        /** Corresponding devman handle. */
     49        devman_handle_t devman_handle;
     50} usb_address_keeping_used_t;
     51
     52/** Structure for keeping track of free and used USB addresses. */
     53typedef struct {
     54        /** Head of list of used addresses. */
     55        link_t used_addresses;
     56        /** Upper bound for USB addresses. */
     57        usb_address_t max_address;
     58        /** Mutex protecting used address. */
     59        fibril_mutex_t used_addresses_guard;
     60        /** Condition variable for used addresses. */
     61        fibril_condvar_t used_addresses_condvar;
     62
     63        /** Condition variable mutex for default address. */
     64        fibril_mutex_t default_condvar_guard;
     65        /** Condition variable for default address. */
     66        fibril_condvar_t default_condvar;
     67        /** Whether is default address available. */
     68        bool default_available;
     69} usb_address_keeping_t;
     70
     71void usb_address_keeping_init(usb_address_keeping_t *, usb_address_t);
     72
     73void usb_address_keeping_reserve_default(usb_address_keeping_t *);
     74void usb_address_keeping_release_default(usb_address_keeping_t *);
     75
     76usb_address_t usb_address_keeping_request(usb_address_keeping_t *);
     77int usb_address_keeping_release(usb_address_keeping_t *, usb_address_t);
     78void usb_address_keeping_devman_bind(usb_address_keeping_t *, usb_address_t,
     79    devman_handle_t);
     80usb_address_t usb_address_keeping_find(usb_address_keeping_t *,
     81    devman_handle_t);
     82
     83#endif
     84/**
     85 * @}
     86 */
  • uspace/lib/usb/include/usb/classes/hid.h

    rd81ef61c r50ba203  
    5050        USB_HIDREQ_SET_PROTOCOL = 11
    5151} usb_hid_request_t;
     52
     53/** USB/HID subclass constants. */
     54typedef enum {
     55        USB_HID_SUBCLASS_NONE = 0,
     56        USB_HID_SUBCLASS_BOOT = 1
     57} usb_hid_subclass_t;
    5258
    5359/** USB/HID interface protocols. */
  • uspace/lib/usb/include/usb/classes/hub.h

    rd81ef61c r50ba203  
    3737
    3838#include <sys/types.h>
    39 #include <usb/hcdhubd.h>
    40 
    4139
    4240/** Hub class feature selector.
     
    8078    /**
    8179            D1...D0: Logical Power Switching Mode
    82             00: Ganged power switching (all ports power at
     80            00: Ganged power switching (all ports power at
    8381            once)
    8482            01: Individual port power switching
     
    9189            00: Global Over-current Protection. The hub
    9290            reports over-current as a summation of all
    93             ports current draw, without a breakdown of
     91            ports current draw, without a breakdown of
    9492            individual port over-current status.
    9593            01: Individual Port Over-current Protection. The
  • uspace/lib/usb/include/usb/hub.h

    rd81ef61c r50ba203  
    11/*
    2  * Copyright (c) 2010 Vojtech Horky
     2 * Copyright (c) 2011 Vojtech Horky
    33 * All rights reserved.
    44 *
     
    3131 */
    3232/** @file
    33  * @brief HC driver.
     33 * Functions needed by hub drivers.
    3434 */
    35 #ifndef LIBUSB_HCD_H_
    36 #define LIBUSB_HCD_H_
     35#ifndef LIBUSB_HUB_H_
     36#define LIBUSB_HUB_H_
    3737
    38 #include <usb/usb.h>
    39 #include <fibril_synch.h>
    40 #include <devman.h>
     38#include <sys/types.h>
     39#include <usb/usbdevice.h>
    4140
    42 /** Info about used address. */
     41/** Info about device attached to host controller.
     42 *
     43 * This structure exists only to keep the same signature of
     44 * usb_hc_register_device() when more properties of the device
     45 * would have to be passed to the host controller.
     46 */
    4347typedef struct {
    44         /** Linked list member. */
    45         link_t link;
    46         /** Address. */
     48        /** Device address. */
    4749        usb_address_t address;
    48         /** Corresponding devman handle. */
    49         devman_handle_t devman_handle;
    50 } usb_address_keeping_used_t;
     50        /** Devman handle of the device. */
     51        devman_handle_t handle;
     52} usb_hc_attached_device_t;
    5153
    52 /** Structure for keeping track of free and used USB addresses. */
    53 typedef struct {
    54         /** Head of list of used addresses. */
    55         link_t used_addresses;
    56         /** Upper bound for USB addresses. */
    57         usb_address_t max_address;
    58         /** Mutex protecting used address. */
    59         fibril_mutex_t used_addresses_guard;
    60         /** Condition variable for used addresses. */
    61         fibril_condvar_t used_addresses_condvar;
     54int usb_hc_reserve_default_address(usb_hc_connection_t *, bool);
     55int usb_hc_release_default_address(usb_hc_connection_t *);
    6256
    63         /** Condition variable mutex for default address. */
    64         fibril_mutex_t default_condvar_guard;
    65         /** Condition variable for default address. */
    66         fibril_condvar_t default_condvar;
    67         /** Whether is default address available. */
    68         bool default_available;
    69 } usb_address_keeping_t;
    70 
    71 void usb_address_keeping_init(usb_address_keeping_t *, usb_address_t);
    72 
    73 void usb_address_keeping_reserve_default(usb_address_keeping_t *);
    74 void usb_address_keeping_release_default(usb_address_keeping_t *);
    75 
    76 usb_address_t usb_address_keeping_request(usb_address_keeping_t *);
    77 int usb_address_keeping_release(usb_address_keeping_t *, usb_address_t);
    78 void usb_address_keeping_devman_bind(usb_address_keeping_t *, usb_address_t,
    79     devman_handle_t);
    80 usb_address_t usb_address_keeping_find(usb_address_keeping_t *,
    81     devman_handle_t);
     57usb_address_t usb_hc_request_address(usb_hc_connection_t *, bool);
     58int usb_hc_register_device(usb_hc_connection_t *,
     59    const usb_hc_attached_device_t *);
     60int usb_hc_unregister_device(usb_hc_connection_t *, usb_address_t);
    8261
    8362#endif
  • uspace/lib/usb/include/usb/pipes.h

    rd81ef61c r50ba203  
    3131 */
    3232/** @file
    33  * Communication between device drivers and host controller driver.
     33 * USB pipes representation.
    3434 */
    3535#ifndef LIBUSB_PIPES_H_
     
    3838#include <sys/types.h>
    3939#include <usb/usb.h>
     40#include <usb/usbdevice.h>
     41#include <usb/descriptor.h>
    4042#include <ipc/devman.h>
    4143#include <driver.h>
     
    7375        usb_direction_t direction;
    7476
     77        /** Maximum packet size for the endpoint. */
     78        size_t max_packet_size;
     79
    7580        /** Phone to the host controller.
    7681         * Negative when no session is active.
     
    8085
    8186
     87/** Description of endpoint characteristics. */
     88typedef struct {
     89        /** Transfer type (e.g. control or interrupt). */
     90        usb_transfer_type_t transfer_type;
     91        /** Transfer direction (to or from a device). */
     92        usb_direction_t direction;
     93        /** Interface class this endpoint belongs to (-1 for any). */
     94        int interface_class;
     95        /** Interface subclass this endpoint belongs to (-1 for any). */
     96        int interface_subclass;
     97        /** Interface protocol this endpoint belongs to (-1 for any). */
     98        int interface_protocol;
     99        /** Extra endpoint flags. */
     100        unsigned int flags;
     101} usb_endpoint_description_t;
     102
     103/** Mapping of endpoint pipes and endpoint descriptions. */
     104typedef struct {
     105        /** Endpoint pipe. */
     106        usb_endpoint_pipe_t *pipe;
     107        /** Endpoint description. */
     108        const usb_endpoint_description_t *description;
     109        /** Found descriptor fitting the description. */
     110        usb_standard_endpoint_descriptor_t *descriptor;
     111        /** Interface the endpoint belongs to. */
     112        usb_standard_interface_descriptor_t *interface;
     113        /** Whether the endpoint was actually found. */
     114        bool present;
     115} usb_endpoint_mapping_t;
     116
     117int usb_device_connection_initialize_on_default_address(
     118    usb_device_connection_t *, usb_hc_connection_t *);
    82119int usb_device_connection_initialize_from_device(usb_device_connection_t *,
    83120    device_t *);
     
    87124int usb_endpoint_pipe_initialize(usb_endpoint_pipe_t *,
    88125    usb_device_connection_t *,
    89     usb_endpoint_t, usb_transfer_type_t, usb_direction_t);
     126    usb_endpoint_t, usb_transfer_type_t, size_t, usb_direction_t);
    90127int usb_endpoint_pipe_initialize_default_control(usb_endpoint_pipe_t *,
    91128    usb_device_connection_t *);
     129int usb_endpoint_pipe_initialize_from_configuration(usb_endpoint_mapping_t *,
     130    size_t, uint8_t *, size_t, usb_device_connection_t *);
    92131
    93132
     
    103142    void *, size_t);
    104143
    105 
    106 
    107 int usb_endpoint_pipe_async_read(usb_endpoint_pipe_t *, void *, size_t,
    108     size_t *, usb_handle_t *);
    109 int usb_endpoint_pipe_async_write(usb_endpoint_pipe_t *, void *, size_t,
    110     usb_handle_t *);
    111 
    112 int usb_endpoint_pipe_async_control_read(usb_endpoint_pipe_t *, void *, size_t,
    113     void *, size_t, size_t *, usb_handle_t *);
    114 int usb_endpoint_pipe_async_control_write(usb_endpoint_pipe_t *, void *, size_t,
    115     void *, size_t, usb_handle_t *);
    116 
    117 int usb_endpoint_pipe_wait_for(usb_endpoint_pipe_t *, usb_handle_t);
    118 
    119144#endif
    120145/**
  • uspace/lib/usb/include/usb/usb.h

    rd81ef61c r50ba203  
    8383} usb_request_recipient_t;
    8484
    85 /** USB transaction outcome. */
    86 typedef enum {
    87         USB_OUTCOME_OK,
    88         USB_OUTCOME_CRCERROR,
    89         USB_OUTCOME_BABBLE
    90 } usb_transaction_outcome_t;
    91 
    92 const char * usb_str_transaction_outcome(usb_transaction_outcome_t o);
    93 
    9485/** USB address type.
    9586 * Negative values could be used to indicate error.
  • uspace/lib/usb/include/usb/usbdrv.h

    rd81ef61c r50ba203  
    106106    const void *, size_t);
    107107
    108 int usb_drv_create_device_match_ids(int, match_id_list_t *, usb_address_t);
    109 int usb_drv_register_child_in_devman(int, device_t *, usb_address_t,
    110     devman_handle_t *);
    111 
    112108
    113109#endif
  • uspace/lib/usb/src/addrkeep.c

    rd81ef61c r50ba203  
    3333 * @brief Address keeping.
    3434 */
    35 #include <usb/hcd.h>
     35#include <usb/addrkeep.h>
    3636#include <errno.h>
    3737#include <assert.h>
  • uspace/lib/usb/src/dump.c

    rd81ef61c r50ba203  
    147147        PRINTLINE("bDeviceProtocol = 0x%02x", d->device_protocol);
    148148        PRINTLINE("bMaxPacketSize0 = %d", d->max_packet_size);
    149         PRINTLINE("idVendor = %d", d->vendor_id);
    150         PRINTLINE("idProduct = %d", d->product_id);
     149        PRINTLINE("idVendor = 0x%04x", d->vendor_id);
     150        PRINTLINE("idProduct = 0x%04x", d->product_id);
    151151        PRINTLINE("bcdDevice = %d", d->device_version);
    152152        PRINTLINE("iManufacturer = %d", d->str_manufacturer);
  • uspace/lib/usb/src/pipes.c

    rd81ef61c r50ba203  
    3131 */
    3232/** @file
    33  * Communication between device drivers and host controller driver.
    34  *
    35  * Note on synchronousness of the operations: there is ABSOLUTELY NO
    36  * guarantee that a call to particular function will not trigger a fibril
    37  * switch.
    38  * The initialization functions may actually involve contacting some other
    39  * task, starting/ending a session might involve asynchronous IPC and since
    40  * the transfer functions uses IPC, asynchronous nature of them is obvious.
    41  * The pseudo synchronous versions for the transfers internally call the
    42  * asynchronous ones and so fibril switch is possible in them as well.
     33 * USB endpoint pipes miscellaneous functions.
    4334 */
    4435#include <usb/usb.h>
     
    4738#include <assert.h>
    4839#include <usb/usbdrv.h>
    49 
    50 #define _PREPARE_TARGET(varname, pipe) \
    51         usb_target_t varname = { \
    52                 .address = (pipe)->wire->address, \
    53                 .endpoint = (pipe)->endpoint_no \
    54         }
    5540
    5641/** Initialize connection to USB device.
     
    117102}
    118103
    119 /** Initialize USB endpoint pipe.
     104/** Initialize connection to USB device on default address.
    120105 *
    121  * @param pipe Endpoint pipe to be initialized.
    122  * @param connection Connection to the USB device backing this pipe (the wire).
    123  * @param endpoint_no Endpoint number (in USB 1.1 in range 0 to 15).
    124  * @param transfer_type Transfer type (e.g. interrupt or bulk).
    125  * @param direction Endpoint direction (in/out).
     106 * @param dev_connection Device connection structure to be initialized.
     107 * @param hc_connection Initialized connection to host controller.
    126108 * @return Error code.
    127109 */
    128 int usb_endpoint_pipe_initialize(usb_endpoint_pipe_t *pipe,
    129     usb_device_connection_t *connection, usb_endpoint_t endpoint_no,
    130     usb_transfer_type_t transfer_type, usb_direction_t direction)
     110int usb_device_connection_initialize_on_default_address(
     111    usb_device_connection_t *dev_connection,
     112    usb_hc_connection_t *hc_connection)
    131113{
    132         assert(pipe);
    133         assert(connection);
     114        assert(dev_connection);
    134115
    135         pipe->wire = connection;
    136         pipe->hc_phone = -1;
    137         pipe->endpoint_no = endpoint_no;
    138         pipe->transfer_type = transfer_type;
    139         pipe->direction = direction;
     116        if (hc_connection == NULL) {
     117                return EBADMEM;
     118        }
    140119
    141         return EOK;
    142 }
    143 
    144 
    145 /** Initialize USB endpoint pipe as the default zero control pipe.
    146  *
    147  * @param pipe Endpoint pipe to be initialized.
    148  * @param connection Connection to the USB device backing this pipe (the wire).
    149  * @return Error code.
    150  */
    151 int usb_endpoint_pipe_initialize_default_control(usb_endpoint_pipe_t *pipe,
    152     usb_device_connection_t *connection)
    153 {
    154         assert(pipe);
    155         assert(connection);
    156 
    157         int rc = usb_endpoint_pipe_initialize(pipe, connection,
    158             0, USB_TRANSFER_CONTROL, USB_DIRECTION_BOTH);
    159 
    160         return rc;
     120        return usb_device_connection_initialize(dev_connection,
     121            hc_connection->hc_handle, (usb_address_t) 0);
    161122}
    162123
     
    221182}
    222183
    223 
    224 /** Request a read (in) transfer on an endpoint pipe.
    225  *
    226  * @param[in] pipe Pipe used for the transfer.
    227  * @param[out] buffer Buffer where to store the data.
    228  * @param[in] size Size of the buffer (in bytes).
    229  * @param[out] size_transfered Number of bytes that were actually transfered.
    230  * @return Error code.
    231  */
    232 int usb_endpoint_pipe_read(usb_endpoint_pipe_t *pipe,
    233     void *buffer, size_t size, size_t *size_transfered)
    234 {
    235         assert(pipe);
    236 
    237         int rc;
    238         usb_handle_t handle;
    239 
    240         rc = usb_endpoint_pipe_async_read(pipe, buffer, size, size_transfered,
    241             &handle);
    242         if (rc != EOK) {
    243                 return rc;
    244         }
    245 
    246         rc = usb_endpoint_pipe_wait_for(pipe, handle);
    247         return rc;
    248 }
    249 
    250 /** Request a write (out) transfer on an endpoint pipe.
    251  *
    252  * @param[in] pipe Pipe used for the transfer.
    253  * @param[in] buffer Buffer with data to transfer.
    254  * @param[in] size Size of the buffer (in bytes).
    255  * @return Error code.
    256  */
    257 int usb_endpoint_pipe_write(usb_endpoint_pipe_t *pipe,
    258     void *buffer, size_t size)
    259 {
    260         assert(pipe);
    261 
    262         int rc;
    263         usb_handle_t handle;
    264 
    265         rc = usb_endpoint_pipe_async_write(pipe, buffer, size, &handle);
    266         if (rc != EOK) {
    267                 return rc;
    268         }
    269 
    270         rc = usb_endpoint_pipe_wait_for(pipe, handle);
    271         return rc;
    272 }
    273 
    274 
    275 /** Request a control read transfer on an endpoint pipe.
    276  *
    277  * This function encapsulates all three stages of a control transfer.
    278  *
    279  * @param[in] pipe Pipe used for the transfer.
    280  * @param[in] setup_buffer Buffer with the setup packet.
    281  * @param[in] setup_buffer_size Size of the setup packet (in bytes).
    282  * @param[out] data_buffer Buffer for incoming data.
    283  * @param[in] data_buffer_size Size of the buffer for incoming data (in bytes).
    284  * @param[out] data_transfered_size Number of bytes that were actually
    285  *                                  transfered during the DATA stage.
    286  * @return Error code.
    287  */
    288 int usb_endpoint_pipe_control_read(usb_endpoint_pipe_t *pipe,
    289     void *setup_buffer, size_t setup_buffer_size,
    290     void *data_buffer, size_t data_buffer_size, size_t *data_transfered_size)
    291 {
    292         assert(pipe);
    293 
    294         int rc;
    295         usb_handle_t handle;
    296 
    297         rc = usb_endpoint_pipe_async_control_read(pipe,
    298             setup_buffer, setup_buffer_size,
    299             data_buffer, data_buffer_size, data_transfered_size,
    300             &handle);
    301         if (rc != EOK) {
    302                 return rc;
    303         }
    304 
    305         rc = usb_endpoint_pipe_wait_for(pipe, handle);
    306         return rc;
    307 }
    308 
    309 
    310 /** Request a control write transfer on an endpoint pipe.
    311  *
    312  * This function encapsulates all three stages of a control transfer.
    313  *
    314  * @param[in] pipe Pipe used for the transfer.
    315  * @param[in] setup_buffer Buffer with the setup packet.
    316  * @param[in] setup_buffer_size Size of the setup packet (in bytes).
    317  * @param[in] data_buffer Buffer with data to be sent.
    318  * @param[in] data_buffer_size Size of the buffer with outgoing data (in bytes).
    319  * @return Error code.
    320  */
    321 int usb_endpoint_pipe_control_write(usb_endpoint_pipe_t *pipe,
    322     void *setup_buffer, size_t setup_buffer_size,
    323     void *data_buffer, size_t data_buffer_size)
    324 {
    325         assert(pipe);
    326 
    327         int rc;
    328         usb_handle_t handle;
    329 
    330         rc = usb_endpoint_pipe_async_control_write(pipe,
    331             setup_buffer, setup_buffer_size,
    332             data_buffer, data_buffer_size,
    333             &handle);
    334         if (rc != EOK) {
    335                 return rc;
    336         }
    337 
    338         rc = usb_endpoint_pipe_wait_for(pipe, handle);
    339         return rc;
    340 }
    341 
    342 
    343 /** Request a read (in) transfer on an endpoint pipe (asynchronous version).
    344  *
    345  * @param[in] pipe Pipe used for the transfer.
    346  * @param[out] buffer Buffer where to store the data.
    347  * @param[in] size Size of the buffer (in bytes).
    348  * @param[out] size_transfered Number of bytes that were actually transfered.
    349  * @param[out] handle Handle of the transfer.
    350  * @return Error code.
    351  */
    352 int usb_endpoint_pipe_async_read(usb_endpoint_pipe_t *pipe,
    353     void *buffer, size_t size, size_t *size_transfered,
    354     usb_handle_t *handle)
    355 {
    356         assert(pipe);
    357 
    358         if (pipe->hc_phone < 0) {
    359                 return EBADF;
    360         }
    361 
    362         if (pipe->direction != USB_DIRECTION_IN) {
    363                 return EBADF;
    364         }
    365 
    366         int rc;
    367         _PREPARE_TARGET(target, pipe);
    368 
    369         switch (pipe->transfer_type) {
    370                 case USB_TRANSFER_INTERRUPT:
    371                         rc = usb_drv_async_interrupt_in(pipe->hc_phone, target,
    372                             buffer, size, size_transfered, handle);
    373                         break;
    374                 case USB_TRANSFER_CONTROL:
    375                         rc = EBADF;
    376                         break;
    377                 default:
    378                         rc = ENOTSUP;
    379                         break;
    380         }
    381 
    382         return rc;
    383 }
    384 
    385 
    386 /** Request a write (out) transfer on an endpoint pipe (asynchronous version).
    387  *
    388  * @param[in] pipe Pipe used for the transfer.
    389  * @param[in] buffer Buffer with data to transfer.
    390  * @param[in] size Size of the buffer (in bytes).
    391  * @param[out] handle Handle of the transfer.
    392  * @return Error code.
    393  */
    394 int usb_endpoint_pipe_async_write(usb_endpoint_pipe_t *pipe,
    395     void *buffer, size_t size,
    396     usb_handle_t *handle)
    397 {
    398         assert(pipe);
    399 
    400         if (pipe->hc_phone < 0) {
    401                 return EBADF;
    402         }
    403 
    404         if (pipe->direction != USB_DIRECTION_OUT) {
    405                 return EBADF;
    406         }
    407 
    408         int rc;
    409         _PREPARE_TARGET(target, pipe);
    410 
    411         switch (pipe->transfer_type) {
    412                 case USB_TRANSFER_INTERRUPT:
    413                         rc = usb_drv_async_interrupt_out(pipe->hc_phone, target,
    414                             buffer, size, handle);
    415                         break;
    416                 case USB_TRANSFER_CONTROL:
    417                         rc = EBADF;
    418                         break;
    419                 default:
    420                         rc = ENOTSUP;
    421                         break;
    422         }
    423 
    424         return rc;
    425 }
    426 
    427 
    428 /** Request a control read transfer on an endpoint pipe (asynchronous version).
    429  *
    430  * This function encapsulates all three stages of a control transfer.
    431  *
    432  * @param[in] pipe Pipe used for the transfer.
    433  * @param[in] setup_buffer Buffer with the setup packet.
    434  * @param[in] setup_buffer_size Size of the setup packet (in bytes).
    435  * @param[out] data_buffer Buffer for incoming data.
    436  * @param[in] data_buffer_size Size of the buffer for incoming data (in bytes).
    437  * @param[out] data_transfered_size Number of bytes that were actually
    438  *                                  transfered during the DATA stage.
    439  * @param[out] handle Handle of the transfer.
    440  * @return Error code.
    441  */
    442 int usb_endpoint_pipe_async_control_read(usb_endpoint_pipe_t *pipe,
    443     void *setup_buffer, size_t setup_buffer_size,
    444     void *data_buffer, size_t data_buffer_size, size_t *data_transfered_size,
    445     usb_handle_t *handle)
    446 {
    447         assert(pipe);
    448 
    449         if (pipe->hc_phone < 0) {
    450                 return EBADF;
    451         }
    452 
    453         if ((pipe->direction != USB_DIRECTION_BOTH)
    454             || (pipe->transfer_type != USB_TRANSFER_CONTROL)) {
    455                 return EBADF;
    456         }
    457 
    458         int rc;
    459         _PREPARE_TARGET(target, pipe);
    460 
    461         rc = usb_drv_async_control_read(pipe->hc_phone, target,
    462             setup_buffer, setup_buffer_size,
    463             data_buffer, data_buffer_size, data_transfered_size,
    464             handle);
    465 
    466         return rc;
    467 }
    468 
    469 
    470 /** Request a control write transfer on an endpoint pipe (asynchronous version).
    471  *
    472  * This function encapsulates all three stages of a control transfer.
    473  *
    474  * @param[in] pipe Pipe used for the transfer.
    475  * @param[in] setup_buffer Buffer with the setup packet.
    476  * @param[in] setup_buffer_size Size of the setup packet (in bytes).
    477  * @param[in] data_buffer Buffer with data to be sent.
    478  * @param[in] data_buffer_size Size of the buffer with outgoing data (in bytes).
    479  * @param[out] handle Handle of the transfer.
    480  * @return Error code.
    481  */
    482 int usb_endpoint_pipe_async_control_write(usb_endpoint_pipe_t *pipe,
    483     void *setup_buffer, size_t setup_buffer_size,
    484     void *data_buffer, size_t data_buffer_size,
    485     usb_handle_t *handle)
    486 {
    487         assert(pipe);
    488 
    489         if (pipe->hc_phone < 0) {
    490                 return EBADF;
    491         }
    492 
    493         if ((pipe->direction != USB_DIRECTION_BOTH)
    494             || (pipe->transfer_type != USB_TRANSFER_CONTROL)) {
    495                 return EBADF;
    496         }
    497 
    498         int rc;
    499         _PREPARE_TARGET(target, pipe);
    500 
    501         rc = usb_drv_async_control_write(pipe->hc_phone, target,
    502             setup_buffer, setup_buffer_size,
    503             data_buffer, data_buffer_size,
    504             handle);
    505 
    506         return rc;
    507 }
    508 
    509 /** Wait for transfer completion.
    510  *
    511  * The function blocks the caller fibril until the transfer associated
    512  * with given @p handle is completed.
    513  *
    514  * @param[in] pipe Pipe the transfer executed on.
    515  * @param[in] handle Transfer handle.
    516  * @return Error code.
    517  */
    518 int usb_endpoint_pipe_wait_for(usb_endpoint_pipe_t *pipe, usb_handle_t handle)
    519 {
    520         return usb_drv_async_wait_for(handle);
    521 }
    522 
    523 
    524184/**
    525185 * @}
  • uspace/lib/usb/src/recognise.c

    rd81ef61c r50ba203  
    3636#include <usb_iface.h>
    3737#include <usb/usbdrv.h>
     38#include <usb/pipes.h>
     39#include <usb/recognise.h>
     40#include <usb/request.h>
    3841#include <usb/classes/classes.h>
    3942#include <stdio.h>
    4043#include <errno.h>
     44
     45static size_t device_name_index = 0;
     46static FIBRIL_MUTEX_INITIALIZE(device_name_index_mutex);
    4147
    4248/** Callback for getting host controller handle.
     
    7076};
    7177
    72 static device_ops_t child_ops = {
     78device_ops_t child_ops = {
    7379        .interfaces[USB_DEV_IFACE] = &usb_iface
    7480};
     
    155161                /* First, with release number. */
    156162                rc = usb_add_match_id(matches, 100,
    157                     "usb&vendor=%d&product=%d&release=" BCD_FMT,
     163                    "usb&vendor=0x%04x&product=0x%04x&release=" BCD_FMT,
    158164                    (int) device_descriptor->vendor_id,
    159165                    (int) device_descriptor->product_id,
     
    164170               
    165171                /* Next, without release number. */
    166                 rc = usb_add_match_id(matches, 90, "usb&vendor=%d&product=%d",
     172                rc = usb_add_match_id(matches, 90,
     173                    "usb&vendor=0x%04x&product=0x%04x",
    167174                    (int) device_descriptor->vendor_id,
    168175                    (int) device_descriptor->product_id);
     
    241248/** Add match ids based on configuration descriptor.
    242249 *
    243  * @param hc Open phone to host controller.
     250 * @param pipe Control pipe to the device.
    244251 * @param matches Match ids list to add matches to.
    245  * @param address USB address of the attached device.
    246252 * @param config_count Number of configurations the device has.
    247253 * @return Error code.
    248254 */
    249 static int usb_add_config_descriptor_match_ids(int hc,
    250     match_id_list_t *matches, usb_address_t address,
    251     int config_count)
     255static int usb_add_config_descriptor_match_ids(usb_endpoint_pipe_t *pipe,
     256    match_id_list_t *matches, int config_count)
    252257{
    253258        int final_rc = EOK;
     
    257262                int rc;
    258263                usb_standard_configuration_descriptor_t config_descriptor;
    259                 rc = usb_drv_req_get_bare_configuration_descriptor(hc,
    260                     address,  config_index, &config_descriptor);
     264                rc = usb_request_get_bare_configuration_descriptor(pipe,
     265                    config_index, &config_descriptor);
    261266                if (rc != EOK) {
    262267                        final_rc = rc;
     
    267272                void *full_config_descriptor
    268273                    = malloc(config_descriptor.total_length);
    269                 rc = usb_drv_req_get_full_configuration_descriptor(hc,
    270                     address, config_index,
     274                rc = usb_request_get_full_configuration_descriptor(pipe,
     275                    config_index,
    271276                    full_config_descriptor, config_descriptor.total_length,
    272277                    &full_config_descriptor_size);
     
    299304 * function exits with error.
    300305 *
    301  * @param hc Open phone to host controller.
     306 * @param ctrl_pipe Control pipe to given device (session must be already
     307 *      started).
    302308 * @param matches Initialized list of match ids.
    303  * @param address USB address of the attached device.
    304  * @return Error code.
    305  */
    306 int usb_drv_create_device_match_ids(int hc, match_id_list_t *matches,
    307     usb_address_t address)
     309 * @return Error code.
     310 */
     311int usb_device_create_match_ids(usb_endpoint_pipe_t *ctrl_pipe,
     312    match_id_list_t *matches)
    308313{
    309314        int rc;
    310        
    311315        /*
    312316         * Retrieve device descriptor and add matches from it.
     
    314318        usb_standard_device_descriptor_t device_descriptor;
    315319
    316         rc = usb_drv_req_get_device_descriptor(hc, address,
    317             &device_descriptor);
     320        rc = usb_request_get_device_descriptor(ctrl_pipe, &device_descriptor);
    318321        if (rc != EOK) {
    319322                return rc;
    320323        }
    321        
     324
    322325        rc = usb_drv_create_match_ids_from_device_descriptor(matches,
    323326            &device_descriptor);
     
    325328                return rc;
    326329        }
    327        
     330
    328331        /*
    329332         * Go through all configurations and add matches
    330333         * based on interface class.
    331334         */
    332         rc = usb_add_config_descriptor_match_ids(hc, matches,
    333             address, device_descriptor.configuration_count);
     335        rc = usb_add_config_descriptor_match_ids(ctrl_pipe, matches,
     336            device_descriptor.configuration_count);
    334337        if (rc != EOK) {
    335338                return rc;
     
    347350}
    348351
    349 
    350352/** Probe for device kind and register it in devman.
    351353 *
    352  * @param[in] hc Open phone to the host controller.
     354 * @param[in] address Address of the (unknown) attached device.
     355 * @param[in] hc_handle Handle of the host controller.
    353356 * @param[in] parent Parent device.
    354  * @param[in] address Address of the (unknown) attached device.
    355357 * @param[out] child_handle Handle of the child device.
    356358 * @return Error code.
    357359 */
    358 int usb_drv_register_child_in_devman(int hc, device_t *parent,
    359     usb_address_t address, devman_handle_t *child_handle)
    360 {
    361         static size_t device_name_index = 0;
    362         static FIBRIL_MUTEX_INITIALIZE(device_name_index_mutex);
    363 
     360int usb_device_register_child_in_devman(usb_address_t address,
     361    devman_handle_t hc_handle,
     362    device_t *parent, devman_handle_t *child_handle)
     363{
    364364        size_t this_device_name_index;
    365365
     
    369369        fibril_mutex_unlock(&device_name_index_mutex);
    370370
    371 
    372371        device_t *child = NULL;
    373372        char *child_name = NULL;
    374373        int rc;
     374        usb_device_connection_t dev_connection;
     375        usb_endpoint_pipe_t ctrl_pipe;
     376
     377        rc = usb_device_connection_initialize(&dev_connection, hc_handle, address);
     378        if (rc != EOK) {
     379                goto failure;
     380        }
     381
     382        rc = usb_endpoint_pipe_initialize_default_control(&ctrl_pipe,
     383            &dev_connection);
     384        if (rc != EOK) {
     385                goto failure;
     386        }
    375387
    376388        child = create_device();
     
    391403        child->name = child_name;
    392404        child->ops = &child_ops;
    393        
    394         rc = usb_drv_create_device_match_ids(hc, &child->match_ids, address);
     405
     406        rc = usb_endpoint_pipe_start_session(&ctrl_pipe);
     407        if (rc != EOK) {
     408                goto failure;
     409        }
     410
     411        rc = usb_device_create_match_ids(&ctrl_pipe, &child->match_ids);
     412        if (rc != EOK) {
     413                goto failure;
     414        }
     415
     416        rc = usb_endpoint_pipe_end_session(&ctrl_pipe);
    395417        if (rc != EOK) {
    396418                goto failure;
     
    405427                *child_handle = child->handle;
    406428        }
    407        
     429
    408430        return EOK;
    409431
     
    419441
    420442        return rc;
    421 
    422443}
    423444
  • uspace/lib/usb/src/usb.c

    rd81ef61c r50ba203  
    5454}
    5555
    56 /** String representation of USB transaction outcome. */
    57 const char * usb_str_transaction_outcome(usb_transaction_outcome_t o)
    58 {
    59         switch (o) {
    60                 case USB_OUTCOME_OK:
    61                         return "ok";
    62                 case USB_OUTCOME_CRCERROR:
    63                         return "CRC error";
    64                 case USB_OUTCOME_BABBLE:
    65                         return "babble";
    66                 default:
    67                         return "unknown";
    68         }
    69 }
    70 
    71 
    7256/**
    7357 * @}
  • uspace/lib/usb/src/usbdrv.c

    rd81ef61c r50ba203  
    4949        /** Storage for actual number of bytes transferred. */
    5050        size_t *size_transferred;
    51         /** Initial call replay data. */
     51        /** Initial call reply data. */
    5252        ipc_call_t reply;
    5353        /** Initial call identifier. */
    5454        aid_t request;
     55        /** Reply data for data read call. */
     56        ipc_call_t read_reply;
     57        /** Data read call identifier. */
     58        aid_t read_request;
    5559} transfer_info_t;
    5660
     
    140144
    141145        if (rc != EOK) {
    142                 printf("usb_drv_get_my_address over %d failed: %s\n", phone, str_error(rc));
    143146                return rc;
    144147        }
     
    250253        }
    251254
     255        transfer->read_request = 0;
    252256        transfer->size_transferred = NULL;
    253257        transfer->buffer = NULL;
     
    315319        }
    316320
     321        transfer->read_request = 0;
    317322        transfer->size_transferred = actual_size;
    318323        transfer->buffer = buffer;
     
    327332            &transfer->reply);
    328333
     334        if (buffer != NULL) {
     335                transfer->read_request = async_data_read(phone, buffer, size,
     336                    &transfer->read_reply);
     337        }
     338
    329339        *handle = (usb_handle_t) transfer;
    330340
     
    332342}
    333343
    334 /** Read buffer from HCD.
    335  *
    336  * @param phone Opened phone to HCD.
    337  * @param hash Buffer hash (obtained after completing IN transaction).
    338  * @param buffer Buffer where to store data data.
    339  * @param size Buffer size.
    340  * @param actual_size Storage where actual number of bytes transferred will
    341  *      be stored.
    342  * @return Error status.
    343  */
    344 static int read_buffer_in(int phone, sysarg_t hash,
    345     void *buffer, size_t size, size_t *actual_size)
    346 {
    347         ipc_call_t answer_data;
    348         sysarg_t answer_rc;
    349         aid_t req;
    350         int rc;
    351 
    352         req = async_send_2(phone,
    353             DEV_IFACE_ID(USBHC_DEV_IFACE),
    354             IPC_M_USBHC_GET_BUFFER,
    355             hash,
    356             &answer_data);
    357 
    358         rc = async_data_read_start(phone, buffer, size);
    359         if (rc != EOK) {
    360                 async_wait_for(req, NULL);
    361                 return EINVAL;
    362         }
    363 
    364         async_wait_for(req, &answer_rc);
    365         rc = (int)answer_rc;
    366 
    367         if (rc != EOK) {
    368                 return rc;
    369         }
    370 
    371         *actual_size = IPC_GET_ARG1(answer_data);
    372 
    373         return EOK;
    374 }
    375344
    376345/** Blocks caller until given USB transaction is finished.
     
    395364
    396365        sysarg_t answer_rc;
    397         async_wait_for(transfer->request, &answer_rc);
    398 
    399         if (answer_rc != EOK) {
    400                 rc = (int) answer_rc;
    401                 goto leave;
    402         }
    403366
    404367        /*
     
    406369         */
    407370        if ((transfer->buffer != NULL) && (transfer->size > 0)) {
    408                 /*
    409                  * The buffer hash identifies the data on the server
    410                  * side.
    411                  * We will use it when actually reading-in the data.
    412                  */
    413                 sysarg_t buffer_hash = IPC_GET_ARG1(transfer->reply);
    414                 if (buffer_hash == 0) {
    415                         rc = ENOENT;
     371                async_wait_for(transfer->read_request, &answer_rc);
     372
     373                if (answer_rc != EOK) {
     374                        rc = (int) answer_rc;
    416375                        goto leave;
    417376                }
    418377
    419                 size_t actual_size;
    420                 rc = read_buffer_in(transfer->phone, buffer_hash,
    421                     transfer->buffer, transfer->size, &actual_size);
    422 
    423                 if (rc != EOK) {
    424                         goto leave;
     378                if (transfer->size_transferred != NULL) {
     379                        *(transfer->size_transferred)
     380                            = IPC_GET_ARG2(transfer->read_reply);
    425381                }
    426 
    427                 if (transfer->size_transferred) {
    428                         *(transfer->size_transferred) = actual_size;
    429                 }
     382        }
     383
     384        async_wait_for(transfer->request, &answer_rc);
     385
     386        if (answer_rc != EOK) {
     387                rc = (int) answer_rc;
     388                goto leave;
    430389        }
    431390
     
    499458    void *setup_packet, size_t setup_packet_size,
    500459    void *buffer, size_t buffer_size,
     460    usb_handle_t *handle)
     461{
     462        // FIXME - check input parameters instead of asserting them
     463        assert(phone > 0);
     464        assert(setup_packet != NULL);
     465        assert(setup_packet_size > 0);
     466        assert(((buffer != NULL) && (buffer_size > 0))
     467            || ((buffer == NULL) && (buffer_size == 0)));
     468        assert(handle != NULL);
     469
     470        transfer_info_t *transfer
     471            = (transfer_info_t *) malloc(sizeof(transfer_info_t));
     472        if (transfer == NULL) {
     473                return ENOMEM;
     474        }
     475
     476        transfer->read_request = 0;
     477        transfer->size_transferred = NULL;
     478        transfer->buffer = NULL;
     479        transfer->size = 0;
     480        transfer->phone = phone;
     481
     482        int rc;
     483
     484        transfer->request = async_send_3(phone,
     485            DEV_IFACE_ID(USBHC_DEV_IFACE),
     486            IPC_M_USBHC_CONTROL_WRITE,
     487            target.address, target.endpoint,
     488            &transfer->reply);
     489
     490        rc = async_data_write_start(phone, setup_packet, setup_packet_size);
     491        if (rc != EOK) {
     492                async_wait_for(transfer->request, NULL);
     493                return rc;
     494        }
     495
     496        if (buffer_size > 0) {
     497                rc = async_data_write_start(phone, buffer, buffer_size);
     498                if (rc != EOK) {
     499                        async_wait_for(transfer->request, NULL);
     500                        return rc;
     501                }
     502        }
     503
     504        *handle = (usb_handle_t) transfer;
     505
     506        return EOK;
     507}
     508
     509/** Start control read transfer. */
     510int usb_drv_async_control_read_setup(int phone, usb_target_t target,
     511    void *buffer, size_t size,
     512    usb_handle_t *handle)
     513{
     514        return async_send_buffer(phone,
     515            IPC_M_USBHC_CONTROL_READ_SETUP,
     516            target,
     517            buffer, size,
     518            handle);
     519}
     520
     521/** Read data during control read transfer. */
     522int usb_drv_async_control_read_data(int phone, usb_target_t target,
     523    void *buffer, size_t size, size_t *actual_size,
     524    usb_handle_t *handle)
     525{
     526        return async_recv_buffer(phone,
     527            IPC_M_USBHC_CONTROL_READ_DATA,
     528            target,
     529            buffer, size, actual_size,
     530            handle);
     531}
     532
     533/** Finalize control read transfer. */
     534int usb_drv_async_control_read_status(int phone, usb_target_t target,
     535    usb_handle_t *handle)
     536{
     537        return async_send_buffer(phone,
     538            IPC_M_USBHC_CONTROL_READ_STATUS,
     539            target,
     540            NULL, 0,
     541            handle);
     542}
     543
     544/** Issue whole control read transfer. */
     545int usb_drv_async_control_read(int phone, usb_target_t target,
     546    void *setup_packet, size_t setup_packet_size,
     547    void *buffer, size_t buffer_size, size_t *actual_size,
    501548    usb_handle_t *handle)
    502549{
     
    515562        }
    516563
    517         transfer->size_transferred = NULL;
    518         transfer->buffer = NULL;
    519         transfer->size = 0;
    520         transfer->phone = phone;
    521 
    522         int rc;
    523 
    524         transfer->request = async_send_3(phone,
    525             DEV_IFACE_ID(USBHC_DEV_IFACE),
    526             IPC_M_USBHC_CONTROL_WRITE,
    527             target.address, target.endpoint,
    528             &transfer->reply);
    529 
    530         rc = async_data_write_start(phone, setup_packet, setup_packet_size);
    531         if (rc != EOK) {
    532                 async_wait_for(transfer->request, NULL);
    533                 return rc;
    534         }
    535 
    536         rc = async_data_write_start(phone, buffer, buffer_size);
    537         if (rc != EOK) {
    538                 async_wait_for(transfer->request, NULL);
    539                 return rc;
    540         }
    541 
    542         *handle = (usb_handle_t) transfer;
    543 
    544         return EOK;
    545 }
    546 
    547 /** Start control read transfer. */
    548 int usb_drv_async_control_read_setup(int phone, usb_target_t target,
    549     void *buffer, size_t size,
    550     usb_handle_t *handle)
    551 {
    552         return async_send_buffer(phone,
    553             IPC_M_USBHC_CONTROL_READ_SETUP,
    554             target,
    555             buffer, size,
    556             handle);
    557 }
    558 
    559 /** Read data during control read transfer. */
    560 int usb_drv_async_control_read_data(int phone, usb_target_t target,
    561     void *buffer, size_t size, size_t *actual_size,
    562     usb_handle_t *handle)
    563 {
    564         return async_recv_buffer(phone,
    565             IPC_M_USBHC_CONTROL_READ_DATA,
    566             target,
    567             buffer, size, actual_size,
    568             handle);
    569 }
    570 
    571 /** Finalize control read transfer. */
    572 int usb_drv_async_control_read_status(int phone, usb_target_t target,
    573     usb_handle_t *handle)
    574 {
    575         return async_send_buffer(phone,
    576             IPC_M_USBHC_CONTROL_READ_STATUS,
    577             target,
    578             NULL, 0,
    579             handle);
    580 }
    581 
    582 /** Issue whole control read transfer. */
    583 int usb_drv_async_control_read(int phone, usb_target_t target,
    584     void *setup_packet, size_t setup_packet_size,
    585     void *buffer, size_t buffer_size, size_t *actual_size,
    586     usb_handle_t *handle)
    587 {
    588         // FIXME - check input parameters instead of asserting them
    589         assert(phone > 0);
    590         assert(setup_packet != NULL);
    591         assert(setup_packet_size > 0);
    592         assert(buffer != NULL);
    593         assert(buffer_size > 0);
    594         assert(handle != NULL);
    595 
    596         transfer_info_t *transfer
    597             = (transfer_info_t *) malloc(sizeof(transfer_info_t));
    598         if (transfer == NULL) {
    599                 return ENOMEM;
    600         }
    601 
    602564        transfer->size_transferred = actual_size;
    603565        transfer->buffer = buffer;
     
    620582        }
    621583
     584        transfer->read_request = async_data_read(phone, buffer, buffer_size,
     585            &transfer->read_reply);
     586
    622587        *handle = (usb_handle_t) transfer;
    623588
  • uspace/lib/usbvirt/Makefile

    rd81ef61c r50ba203  
    3030LIBRARY = libusbvirt
    3131
    32 LIBS = $(LIBUSB_PREFIX)/libusb.a
    3332EXTRA_CFLAGS = -I$(LIBUSB_PREFIX)/include -Iinclude
    3433
Note: See TracChangeset for help on using the changeset viewer.