Ignore:
File:
1 edited

Legend:

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

    rbdc8ab1 r30a4301  
    3333 */
    3434#include <errno.h>
    35 #include <str_error.h>
    36 
    37 #include <usb/usb.h>
     35
    3836#include <usb/debug.h>
    3937
     
    4745static int batch_schedule(batch_t *instance);
    4846
    49 static void batch_control(
    50     batch_t *instance, int data_stage, int status_stage);
    5147static void batch_call_in(batch_t *instance);
    5248static void batch_call_out(batch_t *instance);
     
    5551
    5652
    57 batch_t * batch_get(ddf_fun_t *fun, usb_target_t target,
     53batch_t * batch_get(device_t *dev, usb_target_t target,
    5854    usb_transfer_type_t transfer_type, size_t max_packet_size,
    59     usb_speed_t speed, char *buffer, size_t size,
     55    dev_speed_t speed, char *buffer, size_t size,
    6056    char* setup_buffer, size_t setup_size,
    6157    usbhc_iface_transfer_in_callback_t func_in,
     
    9692        instance->transport_buffer =
    9793           (size > 0) ? malloc32(transport_size) : NULL;
    98 
    9994        if ((size > 0) && (instance->transport_buffer == NULL)) {
    10095                usb_log_error("Failed to allocate device accessible buffer.\n");
     
    133128        instance->buffer_size = size;
    134129        instance->setup_size = setup_size;
    135         instance->fun = fun;
     130        instance->dev = dev;
    136131        instance->arg = arg;
    137132        instance->speed = speed;
    138133
    139134        queue_head_element_td(instance->qh, addr_to_phys(instance->tds));
    140         usb_log_debug("Batch(%p) %d:%d memory structures ready.\n",
    141             instance, target.address, target.endpoint);
    142135        return instance;
    143136}
     
    146139{
    147140        assert(instance);
    148         usb_log_debug2("Batch(%p) checking %d packet(s) for completion.\n",
     141        usb_log_debug("Checking(%p) %d packet for completion.\n",
    149142            instance, instance->packets);
    150143        instance->transfered_size = 0;
     
    158151                        if (i > 0)
    159152                                instance->transfered_size -= instance->setup_size;
    160                         usb_log_debug("Batch(%p) found error TD(%d):%x.\n",
    161                           instance, i, instance->tds[i].status);
    162153                        return true;
    163154                }
     
    165156                    transfer_descriptor_actual_size(&instance->tds[i]);
    166157        }
     158        /* This is just an ugly trick to support the old API */
    167159        instance->transfered_size -= instance->setup_size;
    168160        return true;
     
    172164{
    173165        assert(instance);
     166
    174167        /* we are data out, we are supposed to provide data */
    175168        memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size);
    176         batch_control(instance, USB_PID_OUT, USB_PID_IN);
     169
     170        int toggle = 0;
     171        /* setup stage */
     172        transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
     173            instance->setup_size, toggle, false, instance->target,
     174            USB_PID_SETUP, instance->setup_buffer, &instance->tds[1]);
     175
     176        /* data stage */
     177        size_t i = 1;
     178        for (;i < instance->packets - 1; ++i) {
     179                char *data =
     180                    instance->transport_buffer + ((i - 1) * instance->max_packet_size);
     181                toggle = 1 - toggle;
     182
     183                transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
     184                    instance->max_packet_size, toggle++, false, instance->target,
     185                    USB_PID_OUT, data, &instance->tds[i + 1]);
     186        }
     187
     188        /* status stage */
     189        i = instance->packets - 1;
     190        transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
     191            0, 1, false, instance->target, USB_PID_IN, NULL, NULL);
     192
     193        instance->tds[i].status |= TD_STATUS_COMPLETE_INTERRUPT_FLAG;
     194
    177195        instance->next_step = batch_call_out_and_dispose;
    178         usb_log_debug("Batch(%p) CONTROL WRITE initialized.\n", instance);
    179196        batch_schedule(instance);
    180197}
     
    183200{
    184201        assert(instance);
    185         batch_control(instance, USB_PID_IN, USB_PID_OUT);
     202
     203        int toggle = 0;
     204        /* setup stage */
     205        transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
     206            instance->setup_size, toggle, false, instance->target,
     207            USB_PID_SETUP, instance->setup_buffer, &instance->tds[1]);
     208
     209        /* data stage */
     210        size_t i = 1;
     211        for (;i < instance->packets - 1; ++i) {
     212                char *data =
     213                    instance->transport_buffer + ((i - 1) * instance->max_packet_size);
     214                toggle = 1 - toggle;
     215
     216                transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
     217                    instance->max_packet_size, toggle, false, instance->target,
     218                    USB_PID_IN, data, &instance->tds[i + 1]);
     219        }
     220
     221        /* status stage */
     222        i = instance->packets - 1;
     223        transfer_descriptor_init(&instance->tds[i], DEFAULT_ERROR_COUNT,
     224            0, 1, false, instance->target, USB_PID_OUT, NULL, NULL);
     225
     226        instance->tds[i].status |= TD_STATUS_COMPLETE_INTERRUPT_FLAG;
     227
    186228        instance->next_step = batch_call_in_and_dispose;
    187         usb_log_debug("Batch(%p) CONTROL READ initialized.\n", instance);
    188229        batch_schedule(instance);
    189230}
     
    193234        assert(instance);
    194235
    195         const bool low_speed = instance->speed == USB_SPEED_LOW;
    196236        int toggle = 1;
    197237        size_t i = 0;
     
    204244
    205245                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);
     246                    instance->max_packet_size, toggle, false, instance->target,
     247                    USB_PID_IN, data, next);
    208248        }
    209249
     
    211251
    212252        instance->next_step = batch_call_in_and_dispose;
    213         usb_log_debug("Batch(%p) INTERRUPT IN initialized.\n", instance);
    214253        batch_schedule(instance);
    215254}
     
    218257{
    219258        assert(instance);
     259
    220260        memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size);
    221261
    222         const bool low_speed = instance->speed == USB_SPEED_LOW;
    223262        int toggle = 1;
    224263        size_t i = 0;
     
    231270
    232271                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);
     272                    instance->max_packet_size, toggle++, false, instance->target,
     273                    USB_PID_OUT, data, next);
    235274        }
    236275
     
    238277
    239278        instance->next_step = batch_call_out_and_dispose;
    240         usb_log_debug("Batch(%p) INTERRUPT OUT initialized.\n", instance);
    241         batch_schedule(instance);
    242 }
    243 /*----------------------------------------------------------------------------*/
    244 static void batch_control(
    245     batch_t *instance, int data_stage, int status_stage)
    246 {
    247         assert(instance);
    248 
    249         const bool low_speed = instance->speed == USB_SPEED_LOW;
    250         int toggle = 0;
    251         /* setup stage */
    252         transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
    253             instance->setup_size, toggle, false, low_speed, instance->target,
    254             USB_PID_SETUP, instance->setup_buffer, &instance->tds[1]);
    255 
    256         /* data stage */
    257         size_t packet = 1;
    258         size_t remain_size = instance->buffer_size;
    259         while (remain_size > 0) {
    260                 char *data =
    261                     instance->transport_buffer + instance->buffer_size
    262                     - remain_size;
    263 
    264                 toggle = 1 - toggle;
    265 
    266                 const size_t packet_size =
    267                     (instance->max_packet_size > remain_size) ?
    268                     remain_size : instance->max_packet_size;
    269 
    270                 transfer_descriptor_init(&instance->tds[packet],
    271                     DEFAULT_ERROR_COUNT, packet_size, toggle, false, low_speed,
    272                     instance->target, data_stage, data,
    273                     &instance->tds[packet + 1]);
    274 
    275                 ++packet;
    276                 assert(packet < instance->packets);
    277                 assert(packet_size <= remain_size);
    278                 remain_size -= packet_size;
    279         }
    280 
    281         /* status stage */
    282         assert(packet == instance->packets - 1);
    283         transfer_descriptor_init(&instance->tds[packet], DEFAULT_ERROR_COUNT,
    284             0, 1, false, low_speed, instance->target, status_stage, NULL, NULL);
    285 
    286 
    287         instance->tds[packet].status |= TD_STATUS_COMPLETE_INTERRUPT_FLAG;
    288         usb_log_debug2("Control last TD status: %x.\n",
    289             instance->tds[packet].status);
     279        batch_schedule(instance);
    290280}
    291281/*----------------------------------------------------------------------------*/
     
    298288
    299289        int err = instance->error;
    300         usb_log_debug("Batch(%p) callback IN(type:%d): %s(%d), %zu.\n",
    301             instance, instance->transfer_type, str_error(err), err,
    302             instance->transfered_size);
    303 
    304         instance->callback_in(instance->fun,
     290        usb_log_info("Callback IN(%d): %d, %zu.\n", instance->transfer_type,
     291            err, instance->transfered_size);
     292
     293        instance->callback_in(instance->dev,
    305294            err, instance->transfered_size,
    306295            instance->arg);
     
    313302
    314303        int err = instance->error;
    315         usb_log_debug("Batch(%p) callback OUT(type:%d): %s(%d).\n",
    316             instance, instance->transfer_type, str_error(err), err);
    317         instance->callback_out(instance->fun,
     304        usb_log_info("Callback OUT(%d): %d.\n", instance->transfer_type, err);
     305        instance->callback_out(instance->dev,
    318306            err, instance->arg);
    319307}
     
    323311        assert(instance);
    324312        batch_call_in(instance);
    325         usb_log_debug("Batch(%p) disposing.\n", instance);
     313        usb_log_debug("Disposing batch: %p.\n", instance);
    326314        free32(instance->tds);
    327315        free32(instance->qh);
     
    335323        assert(instance);
    336324        batch_call_out(instance);
    337         usb_log_debug("Batch(%p) disposing.\n", instance);
     325        usb_log_debug("Disposing batch: %p.\n", instance);
    338326        free32(instance->tds);
    339327        free32(instance->qh);
     
    346334{
    347335        assert(instance);
    348         uhci_t *hc = fun_to_uhci(instance->fun);
     336        uhci_t *hc = dev_to_uhci(instance->dev);
    349337        assert(hc);
    350338        return uhci_schedule(hc, instance);
     339}
     340/*----------------------------------------------------------------------------*/
     341/* DEPRECATED FUNCTIONS NEEDED BY THE OLD API */
     342void batch_control_setup_old(batch_t *instance)
     343{
     344        assert(instance);
     345        instance->packets = 1;
     346
     347        /* setup stage */
     348        transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
     349            instance->setup_size, 0, false, instance->target,
     350            USB_PID_SETUP, instance->setup_buffer, NULL);
     351
     352        instance->next_step = batch_call_out_and_dispose;
     353        batch_schedule(instance);
     354}
     355/*----------------------------------------------------------------------------*/
     356void batch_control_write_data_old(batch_t *instance)
     357{
     358        assert(instance);
     359        instance->packets -= 2;
     360        batch_interrupt_out(instance);
     361}
     362/*----------------------------------------------------------------------------*/
     363void batch_control_read_data_old(batch_t *instance)
     364{
     365        assert(instance);
     366        instance->packets -= 2;
     367        batch_interrupt_in(instance);
     368}
     369/*----------------------------------------------------------------------------*/
     370void batch_control_write_status_old(batch_t *instance)
     371{
     372        assert(instance);
     373        instance->packets = 1;
     374        transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
     375            0, 1, false, instance->target, USB_PID_IN, NULL, NULL);
     376        instance->next_step = batch_call_in_and_dispose;
     377        batch_schedule(instance);
     378}
     379/*----------------------------------------------------------------------------*/
     380void batch_control_read_status_old(batch_t *instance)
     381{
     382        assert(instance);
     383        instance->packets = 1;
     384        transfer_descriptor_init(instance->tds, DEFAULT_ERROR_COUNT,
     385            0, 1, false, instance->target, USB_PID_OUT, NULL, NULL);
     386        instance->next_step = batch_call_out_and_dispose;
     387        batch_schedule(instance);
    351388}
    352389/**
Note: See TracChangeset for help on using the changeset viewer.