1/**
2 * \brief this file contains functions for dealing the the EHCI specific
3 *        management of xfers
4 */
5
6/*
7 * Copyright (c) 2007-2013 ETH Zurich.
8 * All rights reserved.
9 *
10 * This file is distributed under the terms in the attached LICENSE file.
11 * If you do not find this file, copies can be found by writing to:
12 * ETH Zurich D-INFK, Haldeneggsteig 4, CH-8092 Zurich. Attn: Systems Group.
13 */
14
15#include <stdlib.h>
16#include <stdio.h>
17#include <string.h>
18#include <barrelfish/barrelfish.h>
19
20#include <usb/usb.h>
21
22#include <usb_controller.h>
23#include <usb_device.h>
24#include <usb_xfer.h>
25#include <usb_memory.h>
26
27#include "usb_ehci.h"
28#include "usb_ehci_xfer.h"
29#include "usb_ehci_memory.h"
30#include "usb_ehci_queue.h"
31
32
33/**
34 * \brief this function sets up an usb_xfer structure according to the parameters
35 *
36 * \param param the setup parameters for the xfer to set up
37 *
38 * NOTE: the xfer is also supplied with the setup parameters
39 */
40void usb_ehci_xfer_setup(struct usb_xfer_setup_params *param)
41{
42    USB_DEBUG_TR_ENTER;
43
44    /* get the xfer to set up */
45    struct usb_xfer *xfer = param->curr_xfer;
46
47    /* variables for counting how many queue elements we have to allocate */
48    uint32_t num_qtd = 0;
49    uint32_t num_qh = 0;
50    uint32_t num_sitd = 0;
51    uint32_t num_itd = 0;
52
53    /* settig some standard values */
54    param->hc_max_packet_size = 0x400;
55    param->hc_max_packet_count = 1;
56    param->hc_max_frame_size = USB_EHCI_QTD_MAX_BYTES;
57
58    /*
59     * calculate the number of needed descriptors
60     */
61    switch (param->type) {
62        case USB_TYPE_CTRL:
63            /*
64             *  Control Transfer:
65             *      1 QH
66             *      x qTD (depending on the data phase)
67             */
68            param->num_pages = 5;
69            usb_xfer_setup_struct(param);
70            num_qh = 1;
71            num_qtd = ((2 * xfer->num_frames) + 1 + /* status phase */
72            (xfer->max_data_length / xfer->max_hc_frame_size));
73            break;
74
75        case USB_TYPE_BULK:
76            /*
77             *  Bulk Transfer
78             *      1 QH
79             *      x qTD (depending on the data phase)
80             */
81            param->num_pages = 5;
82            usb_xfer_setup_struct(param);
83            num_qh = 1;
84            num_qtd = ((2 * xfer->num_frames)
85                    + (xfer->max_data_length / xfer->max_hc_frame_size));
86            break;
87
88        case USB_TYPE_ISOC:
89            /*
90             * Isochronus Transfers
91             *      x itd or sitd (depending on the size or the speed)
92             */
93            if (xfer->device->speed == USB_SPEED_HIGH) {
94                param->hc_max_frame_size = 0xC00;
95                param->hc_max_packet_count = 3;
96                param->num_pages = 7;
97
98                usb_xfer_setup_struct(param);
99
100                num_itd = ((xfer->num_frames + 7) / 8) << xfer->frame_shift;
101
102            } else {
103                param->num_pages = 2;
104                param->hc_max_packet_size = 0x3FF;
105                param->hc_max_frame_size = 0x3FF;
106
107                usb_xfer_setup_struct(param);
108
109                num_sitd = xfer->num_frames;
110            }
111            break;
112
113        case USB_TYPE_INTR:
114            switch (param->speed) {
115                /*
116                 * Interrupt Transfers
117                 *     1 QH
118                 *     x qTD depending on the data stage
119                 */
120                case USB_SPEED_HIGH:
121                    param->num_pages = 7;
122                    param->hc_max_packet_count = 3;
123                    break;
124                case USB_SPEED_FULL:
125                    param->num_pages = 2;
126                    /* FS bytes per HS frame */
127                    param->hc_max_packet_size = 188;
128                    break;
129                default:
130                    param->num_pages = 2;
131                    /* FS bytes per HS frame / 8 */
132                    param->hc_max_packet_size = (188 / 8);
133                    break;
134            }
135            usb_xfer_setup_struct(param);
136            num_qh = 1;
137            num_qtd = ((2 * xfer->num_frames)
138                    + (xfer->max_data_length / xfer->max_hc_frame_size));
139            break;
140        default:
141            usb_xfer_setup_struct(param);
142            param->hc_max_frame_size = 0x400;
143            break;
144    }
145
146    uint8_t alloc_dma_set;
147
148    USB_DEBUG_XFER_HC("usb_ehci_xfer_setup() Start Allocating queue...\n");
149
150    /*
151     * allocate the number of queue elements as determined above
152     */
153    do {
154        alloc_dma_set = 0;
155
156        if (param->err != USB_ERR_OK) {
157            debug_printf("Error while setting up usb transfer \n");
158            return;
159        }
160
161        void *obj_last = NULL;
162        uint32_t td_alloc;
163
164        /* isochronus transfer descriptors */
165        USB_DEBUG_XFER_HC("Allocating %u iTDs...\n", num_itd);
166        for (td_alloc = 0; td_alloc < num_itd; td_alloc++) {
167            usb_ehci_itd_t *itd = usb_ehci_itd_alloc();
168
169            if (itd == NULL) {
170                USB_DEBUG("ERROR: Failed to allocate iTD descriptor");
171                itd = obj_last;
172                while (itd != NULL) {
173                    usb_ehci_itd_free(itd);
174                    itd = itd->obj_next;
175                }
176                param->err = USB_ERR_NOMEM;
177                break;
178            }
179
180            itd->obj_next = obj_last;
181
182            obj_last = itd;
183        }
184
185        /* split isochronus transfer descriptors */
186        USB_DEBUG_XFER_HC("Allocating %u siTDs...\n", num_sitd);
187        for (td_alloc = 0; td_alloc < num_sitd; td_alloc++) {
188            usb_ehci_sitd_t *sitd = usb_ehci_sitd_alloc();
189
190            if (sitd == NULL) {
191                USB_DEBUG("ERROR: Failed to allocate iTD descriptor");
192                sitd = obj_last;
193                while (sitd != NULL) {
194                    usb_ehci_sitd_free(sitd);
195                    sitd = sitd->obj_next;
196                }
197                param->err = USB_ERR_NOMEM;
198                break;
199            }
200
201            sitd->obj_next = obj_last;
202
203            obj_last = sitd;
204        }
205
206        /* queue element transfer descriptors */
207        USB_DEBUG_XFER_HC("Allocating %u qTDs...\n", num_qtd);
208        for (td_alloc = 0; td_alloc < num_qtd; td_alloc++) {
209            usb_ehci_qtd_t *qtd = usb_ehci_qtd_alloc();
210
211            if (qtd == NULL) {
212                USB_DEBUG("ERROR: Failed to allocate qTD descriptor");
213                qtd = obj_last;
214                while (qtd != NULL) {
215                    usb_ehci_qtd_free(qtd);
216                    qtd = qtd->obj_next;
217                }
218                param->err = USB_ERR_NOMEM;
219                break;
220            }
221            qtd->obj_next = obj_last;
222
223            obj_last = qtd;
224        }
225
226        /* set the transfer descriptor start field in the xfer */
227        xfer->hcd_td_start[xfer->flags_internal.curr_dma_set] = obj_last;
228
229        obj_last = NULL;
230
231        /* allocate the queue heads */
232        USB_DEBUG_XFER_HC("usb_ehci_xfer_setup() Allocating %u QHs...\n", num_qh);
233        for (td_alloc = 0; td_alloc < num_qh; td_alloc++) {
234            usb_ehci_qh_t *qh = usb_ehci_qh_alloc();
235            if (qh == NULL) {
236                USB_DEBUG("ERROR: Failed to allocate iTD descriptor");
237                qh = obj_last;
238                while (qh != NULL) {
239                    usb_ehci_qh_free(qh);
240                    qh = qh->obj_next;
241                }
242                param->err = USB_ERR_NOMEM;
243                break;
244            }
245            qh->obj_next = obj_last;
246            obj_last = qh;
247        }
248
249        /* set the queue head start field */
250        xfer->hcd_qh_start[xfer->flags_internal.curr_dma_set] = obj_last;
251
252        if (!xfer->flags_internal.curr_dma_set) {
253            xfer->flags_internal.curr_dma_set = 1;
254            alloc_dma_set = 1;
255        }
256    } while (alloc_dma_set);
257
258    USB_DEBUG_TR_RETURN;
259}
260
261
262/**
263 * \brief this function frees up the resources when a transfer is unsetup
264 *
265 * \param xfer the xfer to un setup
266 */
267void usb_ehci_xfer_unsetup(struct usb_xfer *xfer)
268{
269    /*
270     * TODO: Free up resources
271     */
272    switch(xfer->type) {
273        case USB_TYPE_CTRL:
274        case USB_TYPE_INTR:
275        case USB_TYPE_BULK:
276            /* free the qtd with the allocated frame buffers */
277            /* free the qh */
278            break;
279        case USB_TYPE_ISOC:
280            assert("!NYI: isochronus transfers");
281            break;
282    }
283    return;
284}
285
286/**
287 * \brief this function handles the removal of the xfer from their correspondin
288 *        queues on the host controller
289 *
290 * \param xfer the xfer to remove from the queues
291 * \param error the outcome of the transfer
292 */
293void usb_ehci_xfer_remove(struct usb_xfer *xfer, usb_error_t error)
294{
295    USB_DEBUG_TR_ENTER;
296
297    // get the host controller of this transfer
298    usb_ehci_hc_t *hc = (usb_ehci_hc_t *) xfer->host_controller->hc_control;
299
300    switch (xfer->type) {
301        case USB_TYPE_BULK:
302        case USB_TYPE_CTRL:
303            /* remove from the async queue */
304            usb_ehci_deq_qh(
305                    xfer->hcd_qh_start[xfer->flags_internal.curr_dma_set],
306                    hc->qh_async_last);
307            break;
308        case USB_TYPE_INTR:
309            /* remove from the host controller interrupt queue */
310            usb_ehci_deq_qh(
311                    xfer->hcd_qh_start[xfer->flags_internal.curr_dma_set],
312                    hc->qh_intr_last[xfer->intr_qh_pos]);
313            break;
314
315        case USB_TYPE_ISOC:
316            /* isochronus transfers need special handling here */
317            if (xfer->hcd_td_first && xfer->hcd_td_last) {
318                switch (xfer->device->speed) {
319                    case USB_SPEED_HIGH:
320                        usb_ehci_xfer_hs_isoc_done(xfer);
321                    case USB_SPEED_FULL:
322                    case USB_SPEED_LOW:
323                        usb_ehci_xfer_fs_isoc_done(xfer);
324                    default:
325                        debug_printf("WARNING: Unknown speed\n");
326                        return;
327                }
328                xfer->hcd_td_first = NULL;
329                xfer->hcd_td_last = NULL;
330            }
331            break;
332        default:
333            USB_DEBUG("ERROR: Invalid transfer type");
334            USB_DEBUG_TR_RETURN;
335            return;
336            break;
337    }
338
339    usb_xfer_done(xfer, error);
340    USB_DEBUG_TR_RETURN;
341}
342
343/**
344 * this structure contains the setup parameters for setting up the queue
345 * element transfer descriptors (qTD) of an transfer
346 */
347struct usb_ehci_qtd_setup_param {
348    usb_ehci_hc_t *hc;              ///< the host controller
349    usb_ehci_qtd_t *td;             ///< the current qtd
350    usb_ehci_qtd_t *td_next;        ///< pointer tot he next qtd
351    usb_ehci_qtd_token_t qtd_token; ///< the qtd token flags
352    uint32_t length_avg;            ///< the average length
353    uint32_t length;                ///< the length of data for this qutd
354    uint16_t max_frame_size;        ///< the maximum frame size of the hc
355    uint8_t shortpkt;               ///< flag to tell if we have a short packet
356    uint8_t auto_data_toggle;       ///< flag to set the data togle bit
357    uint8_t setup_alt_next;         ///< flag indicating to set up the alt next
358    uint8_t last_frame;             ///< flag indicating if it is the last frame
359    struct usb_dma_page *pages;     ///< pointer to a set of dma pages
360    uint16_t num_pages;             ///< the number of dma pages that are needed
361};
362
363/**
364 * \brief   setting up the queue element transfer descriptors for an
365 *          USB transfer
366 *
367 * \param   setup   the setup parameters for the qtd
368 */
369static void usb_ehci_xfer_qtd_setup(struct usb_ehci_qtd_setup_param *setup)
370{
371    USB_DEBUG_TR_ENTER;
372
373    /* pointers to the terminated queue head */
374    usb_paddr_t terminate = setup->hc->qh_terminate->qh_self;
375    usb_paddr_t qtd_alt_next = setup->hc->qh_terminate->qh_self;
376
377    /* variables for tracking the length */
378
379    uint32_t length_avg = 0;
380    uint32_t length_old = setup->length;
381
382    usb_ehci_qtd_t *td;
383    usb_ehci_qtd_t *td_next;
384    usb_ehci_qtd_t *td_alt_next;
385
386    uint8_t shortpkt_old = setup->shortpkt;
387
388    /* first we are precomputing, then we fill in the structs */
389    uint8_t precompute = 1;
390
391    do {
392        td = setup->td;
393        td_next = setup->td_next;
394
395        while (1) {
396            if (setup->length == 0) {
397
398                if (setup->shortpkt) {
399                    /* the short packet */
400                    break;
401                }
402
403                /* zero length packet, this one has to be sent last */
404                setup->shortpkt = 1;
405                length_avg = 0;
406            } else {
407
408                /* we have some data to process */
409                length_avg = setup->length_avg;
410
411                if (setup->length < length_avg) {
412                    /*
413                     * handle the case when the lenght of this packet is
414                     * smaller than the average packet length, so update
415                     * the average length and if it is smaller than the
416                     * max_frame_size, indicate a short packet
417                     */
418                    if (setup->length % setup->max_frame_size) {
419                        setup->shortpkt = 1;
420                    }
421                    length_avg = setup->length;
422                }
423
424            }
425
426            assert(td_next != NULL);
427
428            /* iterate to the next qTD */
429            td = td_next;
430            td_next = td->obj_next;
431
432            if (precompute) {
433                /*
434                 * we are in the precomputing phase, so update remaining
435                 * length and continue
436                 */
437                setup->length -= length_avg;
438                continue;
439            }
440
441            /* we are not precomputing anymore so fill out the qTD */
442            td->qtd_token = setup->qtd_token;
443            // TODO: TEST... td->qtd_token.ioc = 1;
444            td->qtd_token.bytes = length_avg;
445
446            memset(td->qtd_bp, 0, sizeof(td->qtd_bp));
447            if (length_avg == 0) {
448                if (setup->auto_data_toggle == 0) {
449                    /* update the data toggle for the last, zero length packet */
450                    setup->qtd_token.data_toggle = 1;
451                }
452                td->len = 0;
453                td->qtd_bp[0].address = 0;
454                td->qtd_bp[1].address = 0;
455                /* XXX: NO 64 bit support at the moment ! */
456            } else {
457                if (setup->auto_data_toggle == 0) {
458                    /* update data toggle */
459                    if (((length_avg + setup->max_frame_size - 1)
460                            / setup->max_frame_size) & 1) {
461                        setup->qtd_token.data_toggle = 1;
462                    }
463                }
464                /* set the length of this qTD */
465                td->len = length_avg;
466
467                /* update the remaining length to process */
468                setup->length -= length_avg;
469
470                uint32_t buf_offset = 0;
471
472
473                uint8_t pages_count = 0;
474
475                /* fill in the buffer pointers */
476                while (length_avg > USB_EHCI_BUFFER_SIZE) {
477
478                    length_avg -= USB_EHCI_BUFFER_SIZE;
479                    buf_offset += USB_EHCI_BUFFER_SIZE;
480                    td->qtd_bp[pages_count].address = (setup->pages->phys_addr
481                            + buf_offset) & (~0xFFF);
482
483                    assert(!((setup->pages->phys_addr + buf_offset) & (0xFFF)));
484
485                    pages_count++;
486                }
487
488                /* the last remainder < USB_EHCI_BUFFER_SIZE */
489                buf_offset += length_avg;
490                td->qtd_bp[pages_count].address = (setup->pages->phys_addr
491                        + buf_offset) & (~0xFFF);
492            }
493
494            if (td_next) {
495                td->qtd_next = td_next->qtd_self;
496            }
497
498            td->qtd_alt_next = qtd_alt_next;
499            td->alt_next = td_alt_next;
500        }
501
502        if (precompute) {
503            precompute = 0;
504
505            qtd_alt_next = terminate;
506
507            /* this was the last frame, so we have no alternative poiters */
508            if (setup->last_frame) {
509                td->alt_next = NULL;
510            } else {
511                td_alt_next = td_next;
512                if (setup->setup_alt_next) {
513                    qtd_alt_next = td_next->qtd_self;
514                }
515            }
516
517            setup->shortpkt = shortpkt_old;
518            setup->length = length_old;
519        } else {
520            /* break the loop */
521            break;
522        }
523
524    } while (!precompute);
525
526    setup->td = td;
527    setup->td_next = td_next;
528
529    USB_DEBUG_TR_RETURN;
530}
531
532
533/**
534 * \brief this function sets up the standard queue chains for an xfer
535 *
536 * \param xfer the transfer to set up
537 * \param qh_last the last queue head in the queue
538 */
539void usb_ehci_xfer_standard_setup(struct usb_xfer *xfer,
540        usb_ehci_qh_t **qh_last)
541{
542    USB_DEBUG_TR_ENTER;
543
544    usb_ehci_qh_t *qh;
545
546    /*
547     * there are two different queues that are associated with each transfer
548     * every time we start the new one, the
549     */
550    xfer->flags_internal.curr_dma_set ^= 1;
551
552    usb_ehci_qtd_t *td = xfer->hcd_td_start[xfer->flags_internal.curr_dma_set];
553
554    assert(td != NULL);
555
556    xfer->hcd_td_first = td;
557    xfer->hcd_td_cache = td;
558
559    /*
560     * initialize some fields of the setup parameters
561     */
562    struct usb_ehci_qtd_setup_param setup = {
563        .length_avg = xfer->max_hc_frame_size,
564        .max_frame_size = xfer->max_frame_size,
565        .hc = (usb_ehci_hc_t *) xfer->host_controller->hc_control,
566        .td_next = td,
567        .td = NULL,
568        .setup_alt_next = xfer->flags_internal.short_frames_ok,
569    };
570
571    /* set the data toggle for control tansfers or normal transfers */
572    if (xfer->flags_internal.ctrl_xfer) {
573        if (xfer->endpoint->data_toggle) {
574            setup.qtd_token.data_toggle = 1;
575        }
576        setup.auto_data_toggle = 0;
577    } else {
578        setup.auto_data_toggle = 1;
579    }
580
581    /*
582     * set the number of retries to 3
583     */
584    if ((xfer->device->parent_hs_hub != NULL)
585            || (xfer->device->device_address != 0)) {
586        setup.qtd_token.err_count = 3;
587    }
588
589    uint32_t frames = 0;
590    /*
591     * prepend a setup message if it is a control transfer and
592     * we need to send headers
593     */
594    if (xfer->flags_internal.ctrl_xfer) {
595        if (xfer->flags_internal.ctrl_header) {
596
597            xfer->endpoint->data_toggle = 0;
598            memset(&setup.qtd_token, 0, sizeof(setup.qtd_token));
599            setup.qtd_token.err_count = 3;
600            setup.qtd_token.status = USB_EHCI_QTD_STATUS_ACTIVE;
601            setup.qtd_token.pid = USB_EHCI_QTD_PID_SETUP;
602            setup.qtd_token.data_toggle = 0;
603
604            setup.length = xfer->frame_lengths[0];
605            setup.shortpkt = setup.length ? 1 : 0;
606            setup.pages = xfer->frame_buffers[0];
607
608            /*
609             * we have just one frame, this means we just have a setup phase
610             * but no data or status stage.
611             */
612            if (xfer->num_frames == 1) {
613                if (xfer->flags_internal.ctrl_active) {
614                    setup.last_frame = 1;
615                    setup.setup_alt_next = 0;
616                }
617            }
618
619            usb_ehci_xfer_qtd_setup(&setup);
620        }
621        frames = 1;
622    }
623
624    /*
625     * setup the remaining frames
626     */
627    while (frames < xfer->num_frames) {
628        setup.length = xfer->frame_lengths[frames];
629        setup.pages = xfer->frame_buffers[frames];
630        frames++;
631
632        if (frames == xfer->num_frames) {
633            if (xfer->flags_internal.ctrl_xfer) {
634                if (xfer->flags_internal.ctrl_active) {
635                    setup.last_frame = 1;
636                    setup.setup_alt_next = 0;
637                }
638            } else {
639                setup.last_frame = 1;
640                setup.setup_alt_next = 0;
641            }
642        }
643
644        memset(&setup.qtd_token, 0, sizeof(setup.qtd_token));
645        setup.qtd_token.err_count = 3;
646        setup.qtd_token.data_toggle = 1;
647
648        /* we have to send a short packet if length = 0 */
649        if (setup.length == 0) {
650            setup.shortpkt = 0;
651        } else {
652            setup.shortpkt = (xfer->flags.short_xfer_forced) ? 0 : 1;
653        }
654
655        setup.qtd_token.status = USB_EHCI_QTD_STATUS_ACTIVE;
656        if (xfer->ed_direction == USB_ENDPOINT_DIRECTION_IN) {
657            setup.qtd_token.pid = USB_EHCI_QTD_PID_IN;
658        } else {
659            setup.qtd_token.pid = USB_EHCI_QTD_PID_OUT;
660        }
661
662        usb_ehci_xfer_qtd_setup(&setup);
663    }
664
665    /*
666     * we have to append a status stage, if the xfer is a control transfer
667     * and the xfer is not active
668     */
669    if (xfer->flags_internal.ctrl_xfer && !xfer->flags_internal.ctrl_active) {
670
671        memset(&setup.qtd_token, 0, sizeof(setup.qtd_token));
672        setup.qtd_token.err_count = 3;
673        setup.qtd_token.data_toggle = 1;
674        setup.qtd_token.status = USB_EHCI_QTD_STATUS_ACTIVE;
675        if (xfer->ed_direction == USB_ENDPOINT_DIRECTION_IN) {
676            setup.qtd_token.pid = USB_EHCI_QTD_PID_OUT;
677        } else {
678            setup.qtd_token.pid = USB_EHCI_QTD_PID_IN;
679        }
680        setup.length = 0;
681        setup.shortpkt = 0;
682        setup.last_frame = 1;
683        setup.setup_alt_next = 0;
684        setup.pages = NULL;
685
686        usb_ehci_xfer_qtd_setup(&setup);
687    }
688
689    /* all the qTDs have ben setup now. so we can update the QH */
690
691    td = setup.td;
692
693    /* set the links to terminate for the last TD */
694    td->qtd_next = USB_EHCI_LINK_TERMINATE;
695    td->qtd_alt_next = USB_EHCI_LINK_TERMINATE;
696
697    /* Last qtD rises interrupt */
698    td->qtd_token.ioc = 1;
699
700    xfer->hcd_td_last = td;
701
702    /* get the qh */
703    qh = xfer->hcd_qh_start[xfer->flags_internal.curr_dma_set];
704
705    qh->qh_curr_qtd = 0;
706    qh->qh_next_qtd = 0;
707    qh->qh_alt_next_qtd = 0;
708    memset(&qh->qh_status, 0, sizeof(usb_ehci_qh_status_t));
709    memset(qh->bp_list, 0, sizeof(qh->bp_list));
710
711    qh->qh_ep.device_address = xfer->device_address;
712    qh->qh_ep.inactive  = 0;
713    qh->qh_ep.ep_number = xfer->endpoint_number;
714    qh->qh_ep.max_packet_size = xfer->max_packet_size;
715
716    switch (xfer->device->speed) {
717        case USB_SPEED_HIGH:
718            qh->qh_ep.ep_speed = USB_EHCI_QH_SPEED_HIGH;
719            if (xfer->type != USB_TYPE_INTR) {
720                qh->qh_ep.nak_count_reload = 8;
721            }
722            break;
723        case USB_SPEED_FULL:
724            qh->qh_ep.ep_speed = USB_EHCI_QH_SPEED_FULL;
725            if (xfer->type == USB_TYPE_CTRL) {
726                qh->qh_ep.is_control_ep = 1;
727            }
728            if (xfer->type != USB_TYPE_INTR) {
729                qh->qh_ep.nak_count_reload = 1;
730            }
731            break;
732        case USB_SPEED_LOW:
733            qh->qh_ep.ep_speed = USB_EHCI_QH_SPEED_LOW;
734            if (xfer->type == USB_TYPE_CTRL) {
735                qh->qh_ep.is_control_ep = 1;
736            }
737            if (xfer->type != USB_TYPE_INTR) {
738                qh->qh_ep.nak_count_reload = 1;
739            }
740            break;
741        default:
742            assert(!"ERROR: WRING SPEED\n");
743            break;
744    }
745
746    if (setup.auto_data_toggle == 0) {
747        qh->qh_ep.data_toggle_ctrl = 1;
748    }
749
750    qh->qh_ep.complete_mask = xfer->endpoint->hs_cmask;
751    qh->qh_ep.irq_mask = xfer->endpoint->hs_smask;
752    qh->qh_ep.mult = xfer->max_packet_count & 0x3;
753    qh->qh_ep.hub_addr = xfer->device->hs_hub_address;
754    qh->qh_ep.port_number = xfer->device->hs_hub_port_number;
755
756    qh->qh_curr_qtd = 0;
757
758    memset(&qh->qh_status, 0, sizeof(qh->qh_status));
759    if (setup.auto_data_toggle && xfer->endpoint->data_toggle) {
760        qh->qh_status.data_togglet = 1;
761    } else {
762        qh->qh_status.data_togglet = 0;
763    }
764
765    td = xfer->hcd_td_first;
766
767    assert(!(td->qtd_self & 0x1F));
768
769    qh->qh_next_qtd = td->qtd_self;
770    qh->qh_alt_next_qtd = USB_EHCI_LINK_TERMINATE;
771
772    if (xfer->device->flags.self_suspended == 0) {
773        usb_ehci_enq_qh(qh, *qh_last);
774    }
775
776    USB_DEBUG_TR_RETURN;
777}
778
779/**
780 * \brief this function handles the completition of FS isochronus transfers
781 */
782void usb_ehci_xfer_fs_isoc_done(struct usb_xfer *xfer)
783{
784    assert(!"NYI: Full speed isochronous done handling!");
785}
786
787/**
788 * \brief this function handles the completition of HS isochronus transfers
789 */
790void usb_ehci_xfer_hs_isoc_done(struct usb_xfer *xfer)
791{
792    assert(!"NYI: High speed isochronous done handling!");
793}
794
795/**
796 * \brief this function updates the data toggle bit of the xfer endpoint
797 *
798 * \param xfer the transfer
799 * \param actual_length the current length of the xfer
800 * \param xfer_length   the total bytes to transfer
801 */
802static void usb_ehci_update_dt(struct usb_xfer *xfer, uint16_t actual_length,
803        uint16_t xfer_length)
804{
805    uint8_t dt = (actual_length / xfer->max_packet_size) & 0x1;
806    uint16_t remaining = actual_length % xfer->max_packet_size;
807
808    if (remaining > 0) {
809        dt ^= 1;
810    } else if (actual_length != xfer_length) {
811        dt ^= 1;
812    } else if (xfer_length == 0) {
813        dt ^= 1;
814    }
815
816    xfer->endpoint->data_toggle = dt;
817}
818
819/**
820 * \brief   this function processes the frames of an usb xfer and resets the
821 *          frame length and checks if the transfer was sucessful
822 *
823 * \param xfer the xfer to check
824 *
825 * \return USB_ERR_OK when the transfer is successful
826 *         USB_ERR_STALLED when there was an error condition
827 */
828static usb_error_t usb_ehci_xfer_done_process_frames(struct usb_xfer *xfer)
829{
830    USB_DEBUG_TR_ENTER;
831
832    if (xfer == NULL) {
833        USB_DEBUG("WARNING: xfer is NULL.\n");
834        return (USB_ERR_OK);
835    }
836
837    usb_ehci_qtd_t *qtd = xfer->hcd_td_first;
838    usb_ehci_qtd_t *qtd_alt_next = qtd->alt_next;
839
840    qtd = xfer->hcd_td_cache;
841
842    /*
843     * update the frame length
844     */
845    if (xfer->actual_frames != xfer->num_frames) {
846        xfer->frame_lengths[xfer->actual_frames] = 0;
847    }
848
849    uint16_t actual_length;
850    uint8_t status;
851    while (1) {
852        actual_length = qtd->qtd_token.bytes;
853        status = qtd->qtd_token.status;
854
855        if (actual_length > qtd->len) {
856            USB_DEBUG("WARNING: Invalid status length. Halting EP\n");
857            status |= USB_EHCI_QTD_STATUS_HALTED;
858        } else {
859            xfer->frame_lengths[xfer->actual_frames] += qtd->len
860                    - actual_length;
861            usb_ehci_update_dt(xfer, qtd->len - actual_length, qtd->len);
862        }
863
864        /*
865         * last transfer
866         *  - the current qtd equal to the last td pointer of the xfer
867         *  - set the qtd to NULL and stop processing
868         */
869        if (((void *) qtd) == xfer->hcd_td_last) {
870            qtd = NULL;
871            break;
872        }
873
874        /*
875         * check for error conditions, i.e. the endpoint is halted
876         *  - set the qtd to NULL and stop processing
877         */
878        if (status & USB_EHCI_QTD_STATUS_HALTED) {
879            qtd = NULL;
880            break;
881        }
882
883        /*
884         * check for short transfers
885         *  - if they are ok, then follow the alternative next pointer
886         *  - else we are done
887         */
888        if (actual_length > 0) {
889            if (xfer->flags_internal.short_frames_ok) {
890                qtd->qtd_alt_next;
891            } else {
892                qtd = NULL;
893            }
894            break;
895        }
896        qtd = qtd->obj_next;
897
898        /*
899         * this frame is complete
900         */
901        if (qtd->alt_next != qtd_alt_next) {
902            break;
903        }
904    }
905
906    /* update the transfer cache used to signal processing */
907    xfer->hcd_td_cache = qtd;
908
909    if (status & USB_EHCI_QTD_STATUS_HALTED) {
910        while (qtd) {
911            USB_DEBUG_XFER_HC(
912                    "QTD Status: %x, errorcount = %u\n", qtd->qtd_token.status, qtd->qtd_token.err_count);
913            qtd = qtd->obj_next;
914        }
915        USB_DEBUG_XFER_HC("NOTICE: status = %x\n", status);
916
917        USB_DEBUG_TR_RETURN;
918
919        return (USB_ERR_STALLED);
920    } else {
921
922        USB_DEBUG_TR_RETURN;
923        return (USB_ERR_OK);
924    }
925}
926
927/**
928 * \brief   handles the competition of non-isochronus transfers
929 *
930 * \param   xfer the usb transfer to be removed
931 */
932void usb_ehci_xfer_done(struct usb_xfer *xfer)
933{
934    USB_DEBUG_TR_ENTER;
935    usb_error_t err = USB_ERR_OK;
936
937    /*
938     * iterate over all queue transfer descriptors
939     */
940    xfer->hcd_td_cache = xfer->hcd_td_first;
941
942    /* CASE 1: control transfers */
943    if (xfer->flags_internal.ctrl_xfer) {
944
945        if (xfer->flags_internal.ctrl_header) {
946            /* the header was not sent */
947            USB_DEBUG_XFER_HC("usb_ehci_xfer_done: xfer->flags_internal.ctrl_header\n");
948            err = usb_ehci_xfer_done_process_frames(xfer);
949        }
950        /* control transfers have one frame max per transfer */
951        xfer->actual_frames = 1;
952
953        if (xfer->hcd_td_cache == NULL) {
954            /* remove the xfer */
955            USB_DEBUG_XFER_HC("usb_ehci_xfer_done: xfer->hcd_td_cache == NULL\n");
956            usb_ehci_xfer_remove(xfer, err);
957            return;
958        }
959    }
960
961    /* loop over the xfer till we get actual frames == num frames */
962    while (xfer->actual_frames < xfer->num_frames) {
963        err = usb_ehci_xfer_done_process_frames(xfer);
964
965        xfer->actual_frames++;
966
967        if (xfer->hcd_td_cache == NULL) {
968            USB_DEBUG_XFER_HC("usb_ehci_xfer_done: xfer->hcd_td_cache == NULL loop\n");
969            usb_ehci_xfer_remove(xfer, err);
970            return;
971        }
972    }
973
974    /* the control transfer has not started yet, remove it */
975    if (xfer->flags_internal.ctrl_xfer && !xfer->flags_internal.ctrl_active) {
976        err = usb_ehci_xfer_done_process_frames(xfer);
977    }
978
979    /* remove the xfer from the list */
980    usb_ehci_xfer_remove(xfer, err);
981
982    USB_DEBUG_TR_RETURN;
983}
984
985/*
986 * \brief   checks if the transfer is finished
987 *
988 * \param xfer  the transfer to check for completition
989 *
990 * \return 0:    the transfer is not finihsed
991 *         Else: the the transfer is finished
992 */
993uint8_t usb_ehci_xfer_is_finished(struct usb_xfer *xfer)
994{
995    USB_DEBUG_TR_ENTER;
996
997    assert(xfer != NULL);
998
999    if (xfer->type == USB_TYPE_ISOC) {
1000        /*
1001         * TODO Handling of isochronus transfers
1002         */
1003        if (xfer->device->speed == USB_SPEED_HIGH) {
1004            assert(!"NYI: handling of high speed isochr transfers");
1005        } else {
1006            assert(!"NYI: handling of full speed isochr transfers");
1007        }
1008        return (0);
1009    }
1010
1011    /*
1012     * non isochronus transfer
1013     */
1014    usb_ehci_qtd_t *qtd = ((xfer->hcd_td_cache != NULL) ?
1015                                xfer->hcd_td_cache : xfer->hcd_td_first);
1016
1017    usb_ehci_qh_t *qh = xfer->hcd_qh_start[xfer->flags_internal.curr_dma_set];
1018
1019    if (qtd == NULL) {
1020        return (0);
1021    }
1022
1023    assert(qtd != NULL);
1024    assert(qh != NULL);
1025
1026    uint8_t status = qh->qh_status.status;
1027
1028    /*
1029     * check if the status is still pending
1030     */
1031    if (status & USB_EHCI_QTD_STATUS_ACTIVE) {
1032        USB_DEBUG_XFER_HC("NOTICE: transfer still active..\n");
1033        USB_DEBUG_TR_RETURN;
1034        return (0);
1035    }
1036
1037    /*
1038     * check if there is still an active qtd in this qh
1039     * this indicats that the transfer is not done
1040     */
1041    while (1) {
1042        status = qtd->qtd_token.status;
1043
1044        if (status & USB_EHCI_QTD_STATUS_ACTIVE) {
1045            xfer->hcd_td_cache = qtd;
1046            USB_DEBUG_XFER_HC("NOTICE: transfer still active..\n");
1047            USB_DEBUG_TR_RETURN;
1048            return (0);
1049        }
1050
1051        /*
1052         * the last transfer descriptor is not active, this makes
1053         * the whole transfer done
1054         */
1055        if (((void *) qtd) == xfer->hcd_td_last) {
1056            break;
1057        }
1058
1059        /*
1060         * the transfer is halted, this indicates an error
1061         * and implies the transfer is done
1062         */
1063        if (status & USB_EHCI_QTD_STATUS_HALTED) {
1064            break;
1065        }
1066
1067        /*
1068         * a short packet indicates that the transfer is done
1069         * iff there is no alternative transfer
1070         *
1071         * follow the alternate transfer
1072         */
1073        if (qtd->qtd_token.bytes) {
1074            if (xfer->flags_internal.short_frames_ok) {
1075                if (qtd->alt_next) {
1076                    qtd = qtd->alt_next;
1077                    continue;
1078                }
1079                break;
1080            }
1081        }
1082
1083        qtd = qtd->obj_next;
1084    }
1085    USB_DEBUG_XFER_HC("NOTICE: transfer done..\n");
1086
1087    xfer->flags_internal.done = 1;
1088    xfer->flags_internal.transferring = 0;
1089
1090    usb_ehci_xfer_done(xfer);
1091
1092    USB_DEBUG_TR_RETURN;
1093    return (1);
1094}
1095
1096