Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/usbhost/src/hcd.c

    r20eaa82 rf527f58  
    4444#include "hcd.h"
    4545
     46/** Calls ep_add_hook upon endpoint registration.
     47 * @param ep Endpoint to be registered.
     48 * @param arg hcd_t in disguise.
     49 * @return Error code.
     50 */
     51static int register_helper(endpoint_t *ep, void *arg)
     52{
     53        hcd_t *hcd = arg;
     54        assert(ep);
     55        assert(hcd);
     56        if (hcd->ops.ep_add_hook)
     57                return hcd->ops.ep_add_hook(hcd, ep);
     58        return EOK;
     59}
     60
     61/** Calls ep_remove_hook upon endpoint removal.
     62 * @param ep Endpoint to be unregistered.
     63 * @param arg hcd_t in disguise.
     64 */
     65static void unregister_helper(endpoint_t *ep, void *arg)
     66{
     67        hcd_t *hcd = arg;
     68        assert(ep);
     69        assert(hcd);
     70        if (hcd->ops.ep_remove_hook)
     71                hcd->ops.ep_remove_hook(hcd, ep);
     72}
     73
     74/** Calls ep_remove_hook upon endpoint removal. Prints warning.
     75 *  * @param ep Endpoint to be unregistered.
     76 *   * @param arg hcd_t in disguise.
     77 *    */
     78static void unregister_helper_warn(endpoint_t *ep, void *arg)
     79{
     80        assert(ep);
     81        usb_log_warning("Endpoint %d:%d %s was left behind, removing.\n",
     82            ep->address, ep->endpoint, usb_str_direction(ep->direction));
     83        unregister_helper(ep, arg);
     84}
     85
    4686
    4787/** Initialize hcd_t structure.
     
    5393 * @param bw_count Bandwidth compute function, passed to endpoint manager.
    5494 */
    55 void hcd_init(hcd_t *hcd) {
    56         assert(hcd);
    57 
    58         hcd_set_implementation(hcd, NULL, NULL, NULL);
     95void hcd_init(hcd_t *hcd, usb_speed_t max_speed, size_t bandwidth,
     96    bw_count_func_t bw_count)
     97{
     98        assert(hcd);
     99        usb_bus_init(&hcd->bus, bandwidth, bw_count, max_speed);
     100
     101        hcd_set_implementation(hcd, NULL, NULL);
    59102}
    60103
     
    63106        assert(hcd);
    64107        usb_address_t address = 0;
    65         const int ret = bus_request_address(hcd->bus, &address, false, speed);
     108        const int ret = usb_bus_request_address(
     109            &hcd->bus, &address, false, speed);
    66110        if (ret != EOK)
    67111                return ret;
    68112        return address;
    69113}
     114
     115int hcd_release_address(hcd_t *hcd, usb_address_t address)
     116{
     117        assert(hcd);
     118        return usb_bus_remove_address(&hcd->bus, address,
     119            unregister_helper_warn, hcd);
     120}
     121
     122int hcd_reserve_default_address(hcd_t *hcd, usb_speed_t speed)
     123{
     124        assert(hcd);
     125        usb_address_t address = 0;
     126        return usb_bus_request_address(&hcd->bus, &address, true, speed);
     127}
     128
     129int hcd_add_ep(hcd_t *hcd, usb_target_t target, usb_direction_t dir,
     130    usb_transfer_type_t type, size_t max_packet_size, unsigned packets,
     131    size_t size, usb_address_t tt_address, unsigned tt_port)
     132{
     133        assert(hcd);
     134        return usb_bus_add_ep(&hcd->bus, target.address,
     135            target.endpoint, dir, type, max_packet_size, packets, size,
     136            register_helper, hcd, tt_address, tt_port);
     137}
     138
     139int hcd_remove_ep(hcd_t *hcd, usb_target_t target, usb_direction_t dir)
     140{
     141        assert(hcd);
     142        return usb_bus_remove_ep(&hcd->bus, target.address,
     143            target.endpoint, dir, unregister_helper, hcd);
     144}
     145
    70146
    71147typedef struct {
     
    83159                usb_log_debug2("Reseting toggle on %d:%d.\n",
    84160                    toggle->target.address, toggle->target.endpoint);
    85                 bus_reset_toggle(toggle->hcd->bus,
     161                usb_bus_reset_toggle(&toggle->hcd->bus,
    86162                    toggle->target, toggle->target.endpoint == 0);
    87163        }
     
    109185        assert(hcd);
    110186
    111         endpoint_t *ep = bus_find_endpoint(hcd->bus, target, direction);
     187        endpoint_t *ep = usb_bus_find_ep(&hcd->bus,
     188            target.address, target.endpoint, direction);
    112189        if (ep == NULL) {
    113190                usb_log_error("Endpoint(%d:%d) not registered for %s.\n",
     
    119196            name, target.address, target.endpoint, size, ep->max_packet_size);
    120197
    121         const size_t bw = bus_count_bw(ep, size);
     198        const size_t bw = bandwidth_count_usb11(
     199            ep->speed, ep->transfer_type, size, ep->max_packet_size);
    122200        /* Check if we have enough bandwidth reserved */
    123201        if (ep->bandwidth < bw) {
    124202                usb_log_error("Endpoint(%d:%d) %s needs %zu bw "
    125203                    "but only %zu is reserved.\n",
    126                     ep->target.address, ep->target.endpoint, name, bw, ep->bandwidth);
     204                    ep->address, ep->endpoint, name, bw, ep->bandwidth);
    127205                return ENOSPC;
    128206        }
     
    170248
    171249typedef struct {
    172         fibril_mutex_t done_mtx;
    173         fibril_condvar_t done_cv;
    174         unsigned done;
     250        volatile unsigned done;
    175251        int ret;
    176252        size_t size;
     
    182258        assert(d);
    183259        d->ret = ret;
     260        d->done = 1;
    184261        d->size = size;
    185         fibril_mutex_lock(&d->done_mtx);
    186         d->done = 1;
    187         fibril_condvar_broadcast(&d->done_cv);
    188         fibril_mutex_unlock(&d->done_mtx);
    189262}
    190263
     
    194267        assert(data);
    195268        d->ret = ret;
    196         fibril_mutex_lock(&d->done_mtx);
    197269        d->done = 1;
    198         fibril_condvar_broadcast(&d->done_cv);
    199         fibril_mutex_unlock(&d->done_mtx);
    200270}
    201271
     
    207277        assert(hcd);
    208278        sync_data_t sd = { .done = 0, .ret = EBUSY, .size = size };
    209         fibril_mutex_initialize(&sd.done_mtx);
    210         fibril_condvar_initialize(&sd.done_cv);
    211279
    212280        const int ret = hcd_send_batch(hcd, target, dir, data, size, setup_data,
     
    216284                return ret;
    217285
    218         fibril_mutex_lock(&sd.done_mtx);
    219         while (!sd.done)
    220                 fibril_condvar_wait(&sd.done_cv, &sd.done_mtx);
    221         fibril_mutex_unlock(&sd.done_mtx);
     286        while (!sd.done) {
     287                async_usleep(1000);
     288        }
    222289
    223290        if (sd.ret == EOK)
Note: See TracChangeset for help on using the changeset viewer.