Ignore:
Timestamp:
2011-10-16T19:33:47Z (13 years ago)
Author:
Jan Vesely <jano.vesely@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
1f131fb9
Parents:
721d4b6e (diff), f8dfb40 (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 OHCI related changes and improvements.

Rework some routines and use asserts to verify that the device follows OHCI specs.
Add explanatory comments.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/drv/bus/usb/ohci/hw_struct/endpoint_descriptor.h

    r721d4b6e r98fb010  
    4545#include "completion_codes.h"
    4646
     47/**
     48 * OHCI Endpoint Descriptor representation.
     49 *
     50 * See OHCI spec. Chapter 4.2, page 16 (pdf page 30) for details */
    4751typedef struct ed {
     52        /**
     53         * Status field.
     54         *
     55         * See table 4-1, p. 17 OHCI spec (pdf page 31).
     56         */
    4857        volatile uint32_t status;
    4958#define ED_STATUS_FA_MASK (0x7f)   /* USB device address   */
     
    5160#define ED_STATUS_EN_MASK (0xf)    /* USB endpoint address */
    5261#define ED_STATUS_EN_SHIFT (7)
    53 #define ED_STATUS_D_MASK (0x3)     /* direction */
     62#define ED_STATUS_D_MASK (0x3)     /* Direction */
    5463#define ED_STATUS_D_SHIFT (11)
    5564#define ED_STATUS_D_OUT (0x1)
    5665#define ED_STATUS_D_IN (0x2)
    57 #define ED_STATUS_D_TRANSFER (0x3)
     66#define ED_STATUS_D_TD (0x3) /* Direction is specified by TD */
    5867
    59 #define ED_STATUS_S_FLAG (1 << 13) /* speed flag: 1 = low */
    60 #define ED_STATUS_K_FLAG (1 << 14) /* skip flag (no not execute this ED) */
    61 #define ED_STATUS_F_FLAG (1 << 15) /* format: 1 = isochronous*/
    62 #define ED_STATUS_MPS_MASK (0x3ff) /* max_packet_size*/
     68#define ED_STATUS_S_FLAG (1 << 13) /* Speed flag: 1 = low */
     69#define ED_STATUS_K_FLAG (1 << 14) /* Skip flag (no not execute this ED) */
     70#define ED_STATUS_F_FLAG (1 << 15) /* Format: 1 = isochronous */
     71#define ED_STATUS_MPS_MASK (0x3ff) /* Maximum packet size */
    6372#define ED_STATUS_MPS_SHIFT (16)
    6473
     74        /**
     75         * Pointer to the last TD.
     76         *
     77         * OHCI hw never changes this field and uses it only for a reference.
     78         */
    6579        volatile uint32_t td_tail;
    6680#define ED_TDTAIL_PTR_MASK (0xfffffff0)
    6781#define ED_TDTAIL_PTR_SHIFT (0)
    6882
     83        /**
     84         * Pointer to the first TD.
     85         *
     86         * Driver should not change this field if the ED is active.
     87         * This field is updated by OHCI hw and points to the next TD
     88         * to be executed.
     89         */
    6990        volatile uint32_t td_head;
    7091#define ED_TDHEAD_PTR_MASK (0xfffffff0)
     
    7596#define ED_TDHEAD_HALTED_FLAG (0x1)
    7697
     98        /**
     99         * Pointer to the next ED.
     100         *
     101         * Driver should not change this field on active EDs.
     102         */
    77103        volatile uint32_t next;
    78104#define ED_NEXT_PTR_MASK (0xfffffff0)
     
    80106} __attribute__((packed)) ed_t;
    81107
    82 void ed_init(ed_t *instance, endpoint_t *ep);
     108void ed_init(ed_t *instance, const endpoint_t *ep, const td_t *td);
    83109
    84 static inline void ed_set_td(ed_t *instance, td_t *td)
     110/**
     111 * Check for SKIP or HALTED flag being set.
     112 * @param instance ED
     113 * @return true if either SKIP or HALTED flag is set, false otherwise.
     114 */
     115static inline bool ed_inactive(const ed_t *instance)
    85116{
    86117        assert(instance);
    87         uintptr_t pa = addr_to_phys(td);
    88         instance->td_head =
    89             ((pa & ED_TDHEAD_PTR_MASK)
    90             | (instance->td_head & ~ED_TDHEAD_PTR_MASK));
     118        return (instance->td_head & ED_TDHEAD_HALTED_FLAG)
     119            || (instance->status & ED_STATUS_K_FLAG);
     120}
     121
     122/**
     123 * Check whether this ED contains TD to be executed.
     124 * @param instance ED
     125 * @return true if there are pending TDs, false otherwise.
     126 */
     127static inline bool ed_transfer_pending(const ed_t *instance)
     128{
     129        assert(instance);
     130        return (instance->td_head & ED_TDHEAD_PTR_MASK)
     131            != (instance->td_tail & ED_TDTAIL_PTR_MASK);
     132}
     133
     134/**
     135 * Set the last element of TD list
     136 * @param instance ED
     137 * @param instance TD to set as the last item.
     138 */
     139static inline void ed_set_tail_td(ed_t *instance, const td_t *td)
     140{
     141        assert(instance);
     142        const uintptr_t pa = addr_to_phys(td);
    91143        instance->td_tail = pa & ED_TDTAIL_PTR_MASK;
    92144}
    93145
    94 static inline void ed_set_end_td(ed_t *instance, td_t *td)
    95 {
    96         assert(instance);
    97         uintptr_t pa = addr_to_phys(td);
    98         instance->td_tail = pa & ED_TDTAIL_PTR_MASK;
    99 }
    100 
    101 static inline void ed_append_ed(ed_t *instance, ed_t *next)
     146/**
     147 * Set next ED in ED chain.
     148 * @param instance ED to modify
     149 * @param next ED to append
     150 */
     151static inline void ed_append_ed(ed_t *instance, const ed_t *next)
    102152{
    103153        assert(instance);
    104154        assert(next);
    105         uint32_t pa = addr_to_phys(next);
     155        const uint32_t pa = addr_to_phys(next);
    106156        assert((pa & ED_NEXT_PTR_MASK) << ED_NEXT_PTR_SHIFT == pa);
    107157        instance->next = pa;
    108158}
    109159
    110 static inline int ed_toggle_get(ed_t *instance)
     160/**
     161 * Get toggle bit value stored in this ED
     162 * @param instance ED
     163 * @return Toggle bit value
     164 */
     165static inline int ed_toggle_get(const ed_t *instance)
    111166{
    112167        assert(instance);
     
    114169}
    115170
    116 static inline void ed_toggle_set(ed_t *instance, int toggle)
     171/**
     172 * Set toggle bit value stored in this ED
     173 * @param instance ED
     174 * @param toggle Toggle bit value
     175 */
     176static inline void ed_toggle_set(ed_t *instance, bool toggle)
    117177{
    118178        assert(instance);
    119         assert(toggle == 0 || toggle == 1);
    120         if (toggle == 1) {
     179        if (toggle) {
    121180                instance->td_head |= ED_TDHEAD_TOGGLE_CARRY;
    122181        } else {
    123                 /* clear halted flag when reseting toggle */
     182                /* Clear halted flag when reseting toggle TODO: Why? */
    124183                instance->td_head &= ~ED_TDHEAD_TOGGLE_CARRY;
    125184                instance->td_head &= ~ED_TDHEAD_HALTED_FLAG;
Note: See TracChangeset for help on using the changeset viewer.