Changeset 0e06a14 in mainline


Ignore:
Timestamp:
2011-03-04T23:15:27Z (13 years ago)
Author:
Jan Vesely <jano.vesely@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
80fdffe, c5b93dc
Parents:
f5246b6
Message:

Adds support for bulk transfers

Unifies data transfer initialization

Location:
uspace/drv/uhci-hcd
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • uspace/drv/uhci-hcd/batch.c

    rf5246b6 r0e06a14  
    4949static void batch_control(
    5050    batch_t *instance, int data_stage, int status_stage);
     51static void batch_data(batch_t *instance, int pid);
    5152static void batch_call_in(batch_t *instance);
    5253static void batch_call_out(batch_t *instance);
     
    192193{
    193194        assert(instance);
    194 
     195        batch_data(instance, USB_PID_IN);
     196        instance->next_step = batch_call_in_and_dispose;
     197        usb_log_debug("Batch(%p) INTERRUPT IN initialized.\n", instance);
     198        batch_schedule(instance);
     199}
     200/*----------------------------------------------------------------------------*/
     201void batch_interrupt_out(batch_t *instance)
     202{
     203        assert(instance);
     204        memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size);
     205        batch_data(instance, USB_PID_OUT);
     206        instance->next_step = batch_call_out_and_dispose;
     207        usb_log_debug("Batch(%p) INTERRUPT OUT initialized.\n", instance);
     208        batch_schedule(instance);
     209}
     210/*----------------------------------------------------------------------------*/
     211void batch_bulk_in(batch_t *instance)
     212{
     213        assert(instance);
     214        batch_data(instance, USB_PID_IN);
     215        instance->next_step = batch_call_in_and_dispose;
     216        usb_log_debug("Batch(%p) BULK IN initialized.\n", instance);
     217        batch_schedule(instance);
     218}
     219/*----------------------------------------------------------------------------*/
     220void batch_bulk_out(batch_t *instance)
     221{
     222        assert(instance);
     223        memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size);
     224        batch_data(instance, USB_PID_OUT);
     225        instance->next_step = batch_call_out_and_dispose;
     226        usb_log_debug("Batch(%p) BULK OUT initialized.\n", instance);
     227        batch_schedule(instance);
     228}
     229/*----------------------------------------------------------------------------*/
     230static void batch_data(batch_t *instance, int pid)
     231{
     232        assert(instance);
    195233        const bool low_speed = instance->speed == USB_SPEED_LOW;
    196234        int toggle = 1;
    197         size_t i = 0;
    198         for (;i < instance->packets; ++i) {
     235
     236        size_t packet = 0;
     237        size_t remain_size = instance->buffer_size;
     238        while (remain_size > 0) {
    199239                char *data =
    200                     instance->transport_buffer + (i  * instance->max_packet_size);
    201                 transfer_descriptor_t *next = (i + 1) < instance->packets ?
    202                     &instance->tds[i + 1] : NULL;
     240                    instance->transport_buffer + instance->buffer_size
     241                    - remain_size;
     242
    203243                toggle = 1 - toggle;
    204244
    205                 transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
    206                     instance->max_packet_size, toggle, false, low_speed,
    207                     instance->target, USB_PID_IN, data, next);
    208         }
    209 
    210         instance->tds[i - 1].status |= TD_STATUS_COMPLETE_INTERRUPT_FLAG;
    211 
    212         instance->next_step = batch_call_in_and_dispose;
    213         usb_log_debug("Batch(%p) INTERRUPT IN initialized.\n", instance);
    214         batch_schedule(instance);
    215 }
    216 /*----------------------------------------------------------------------------*/
    217 void batch_interrupt_out(batch_t *instance)
    218 {
    219         assert(instance);
    220         memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size);
    221 
    222         const bool low_speed = instance->speed == USB_SPEED_LOW;
    223         int toggle = 1;
    224         size_t i = 0;
    225         for (;i < instance->packets; ++i) {
    226                 char *data =
    227                     instance->transport_buffer + (i  * instance->max_packet_size);
    228                 transfer_descriptor_t *next = (i + 1) < instance->packets ?
    229                     &instance->tds[i + 1] : NULL;
    230                 toggle = 1 - toggle;
    231 
    232                 transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
    233                     instance->max_packet_size, toggle++, false, low_speed,
    234                     instance->target, USB_PID_OUT, data, next);
    235         }
    236 
    237         instance->tds[i - 1].status |= TD_STATUS_COMPLETE_INTERRUPT_FLAG;
    238 
    239         instance->next_step = batch_call_out_and_dispose;
    240         usb_log_debug("Batch(%p) INTERRUPT OUT initialized.\n", instance);
    241         batch_schedule(instance);
     245                const size_t packet_size =
     246                    (instance->max_packet_size > remain_size) ?
     247                    remain_size : instance->max_packet_size;
     248
     249                transfer_descriptor_init(&instance->tds[packet],
     250                    DEFAULT_ERROR_COUNT, packet_size, toggle, false, low_speed,
     251                    instance->target, pid, data,
     252                    &instance->tds[packet + 1]);
     253
     254                ++packet;
     255                assert(packet <= instance->packets);
     256                assert(packet_size <= remain_size);
     257                remain_size -= packet_size;
     258        }
     259
     260        instance->tds[packet - 1].status |= TD_STATUS_COMPLETE_INTERRUPT_FLAG;
     261        instance->tds[packet - 1].next = 0 | LINK_POINTER_TERMINATE_FLAG;
    242262}
    243263/*----------------------------------------------------------------------------*/
  • uspace/drv/uhci-hcd/batch.h

    rf5246b6 r0e06a14  
    8686void batch_interrupt_out(batch_t *instance);
    8787
    88 /* DEPRECATED FUNCTIONS NEEDED BY THE OLD API */
    89 void batch_control_setup_old(batch_t *instance);
     88void batch_bulk_in(batch_t *instance);
    9089
    91 void batch_control_write_data_old(batch_t *instance);
    92 
    93 void batch_control_read_data_old(batch_t *instance);
    94 
    95 void batch_control_write_status_old(batch_t *instance);
    96 
    97 void batch_control_read_status_old(batch_t *instance);
     90void batch_bulk_out(batch_t *instance);
    9891#endif
    9992/**
  • uspace/drv/uhci-hcd/iface.c

    rf5246b6 r0e06a14  
    140140}
    141141/*----------------------------------------------------------------------------*/
     142static int bulk_out(ddf_fun_t *fun, usb_target_t target,
     143    size_t max_packet_size, void *data, size_t size,
     144    usbhc_iface_transfer_out_callback_t callback, void *arg)
     145{
     146        assert(fun);
     147        uhci_t *hc = fun_to_uhci(fun);
     148        assert(hc);
     149        usb_speed_t speed = device_keeper_speed(&hc->device_manager, target.address);
     150
     151        usb_log_debug("Bulk OUT %d:%d %zu(%zu).\n",
     152            target.address, target.endpoint, size, max_packet_size);
     153
     154        batch_t *batch = batch_get(fun, target, USB_TRANSFER_BULK,
     155            max_packet_size, speed, data, size, NULL, 0, NULL, callback, arg);
     156        if (!batch)
     157                return ENOMEM;
     158        batch_bulk_out(batch);
     159        return EOK;
     160}
     161/*----------------------------------------------------------------------------*/
     162static int bulk_in(ddf_fun_t *fun, usb_target_t target,
     163    size_t max_packet_size, void *data, size_t size,
     164    usbhc_iface_transfer_in_callback_t callback, void *arg)
     165{
     166        assert(fun);
     167        uhci_t *hc = fun_to_uhci(fun);
     168        assert(hc);
     169        usb_speed_t speed = device_keeper_speed(&hc->device_manager, target.address);
     170        usb_log_debug("Bulk IN %d:%d %zu(%zu).\n",
     171            target.address, target.endpoint, size, max_packet_size);
     172
     173        batch_t *batch = batch_get(fun, target, USB_TRANSFER_BULK,
     174            max_packet_size, speed, data, size, NULL, 0, callback, NULL, arg);
     175        if (!batch)
     176                return ENOMEM;
     177        batch_bulk_in(batch);
     178        return EOK;
     179}
     180/*----------------------------------------------------------------------------*/
    142181static int control_write(ddf_fun_t *fun, usb_target_t target,
    143182    size_t max_packet_size,
     
    181220        return EOK;
    182221}
    183 
    184 
    185222/*----------------------------------------------------------------------------*/
    186223usbhc_iface_t uhci_iface = {
     
    194231        .interrupt_in = interrupt_in,
    195232
     233        .bulk_in = bulk_in,
     234        .bulk_out = bulk_out,
     235
    196236        .control_read = control_read,
    197237        .control_write = control_write,
Note: See TracChangeset for help on using the changeset viewer.