1 /***********************license start***************
2 * Copyright (c) 2003-2008 Cavium Networks (support@cavium.com). All rights
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions are
10 * * Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
13 * * Redistributions in binary form must reproduce the above
14 * copyright notice, this list of conditions and the following
15 * disclaimer in the documentation and/or other materials provided
16 * with the distribution.
18 * * Neither the name of Cavium Networks nor the names of
19 * its contributors may be used to endorse or promote products
20 * derived from this software without specific prior written
23 * TO THE MAXIMUM EXTENT PERMITTED BY LAW, THE SOFTWARE IS PROVIDED "AS IS"
24 * AND WITH ALL FAULTS AND CAVIUM NETWORKS MAKES NO PROMISES, REPRESENTATIONS
25 * OR WARRANTIES, EITHER EXPRESS, IMPLIED, STATUTORY, OR OTHERWISE, WITH
26 * RESPECT TO THE SOFTWARE, INCLUDING ITS CONDITION, ITS CONFORMITY TO ANY
27 * REPRESENTATION OR DESCRIPTION, OR THE EXISTENCE OF ANY LATENT OR PATENT
28 * DEFECTS, AND CAVIUM SPECIFICALLY DISCLAIMS ALL IMPLIED (IF ANY) WARRANTIES
29 * OF TITLE, MERCHANTABILITY, NONINFRINGEMENT, FITNESS FOR A PARTICULAR
30 * PURPOSE, LACK OF VIRUSES, ACCURACY OR COMPLETENESS, QUIET ENJOYMENT, QUIET
31 * POSSESSION OR CORRESPONDENCE TO DESCRIPTION. THE ENTIRE RISK ARISING OUT
32 * OF USE OR PERFORMANCE OF THE SOFTWARE LIES WITH YOU.
35 * For any questions regarding licensing please contact marketing@caviumnetworks.com
37 ***********************license end**************************************/
42 * "cvmx-usb.c" defines a set of low level USB functions to help
43 * developers create Octeon USB drivers for various operating
44 * systems. These functions provide a generic API to the Octeon
45 * USB blocks, hiding the internal hardware specific
48 * <hr>$Revision: 32636 $<hr>
51 #include "cvmx-sysinfo.h"
53 #include "cvmx-helper.h"
54 #include "cvmx-helper-board.h"
55 #include "cvmx-csr-db.h"
56 #include "cvmx-swap.h"
58 #define MAX_RETRIES 3 /* Maximum number of times to retry failed transactions */
59 #define MAX_PIPES 32 /* Maximum number of pipes that can be open at once */
60 #define MAX_TRANSACTIONS 256 /* Maximum number of outstanding transactions across all pipes */
61 #define MAX_CHANNELS 8 /* Maximum number of hardware channels supported by the USB block */
62 #define MAX_USB_ADDRESS 127 /* The highest valid USB device address */
63 #define MAX_USB_ENDPOINT 15 /* The highest valid USB endpoint number */
64 #define MAX_USB_HUB_PORT 15 /* The highest valid port number on a hub */
65 #define ALLOW_CSR_DECODES 0 /* CSR decoding when CVMX_USB_INITIALIZE_FLAGS_DEBUG_CSRS is set
66 enlarges the code a lot. This define overrides the ability to do CSR
67 decoding since it isn't necessary 99% of the time. Change this to a
68 one if you need CSR decoding */
70 /* These defines disable the normal read and write csr. This is so I can add
71 extra debug stuff to the usb specific version and I won't use the normal
73 #define cvmx_read_csr use_cvmx_usb_read_csr64_instead_of_cvmx_read_csr
74 #define cvmx_write_csr use_cvmx_usb_write_csr64_instead_of_cvmx_write_csr
78 __CVMX_USB_TRANSACTION_FLAGS_IN_USE = 1<<16,
79 } cvmx_usb_transaction_flags_t;
82 * Logical transactions may take numerous low level
83 * transactions, especially when splits are concerned. This
84 * enum represents all of the possible stages a transaction can
85 * be in. Note that split completes are always even. This is so
86 * the NAK handler can backup to the previous low level
87 * transaction with a simple clearing of bit 0.
91 CVMX_USB_STAGE_NON_CONTROL,
92 CVMX_USB_STAGE_NON_CONTROL_SPLIT_COMPLETE,
94 CVMX_USB_STAGE_SETUP_SPLIT_COMPLETE,
96 CVMX_USB_STAGE_DATA_SPLIT_COMPLETE,
97 CVMX_USB_STAGE_STATUS,
98 CVMX_USB_STAGE_STATUS_SPLIT_COMPLETE,
102 * This structure describes each pending USB transaction
103 * regardless of type. These are linked together to form a list
104 * of pending requests for a pipe.
106 typedef struct cvmx_usb_transaction
108 struct cvmx_usb_transaction *prev; /**< Transaction before this one in the pipe */
109 struct cvmx_usb_transaction *next; /**< Transaction after this one in the pipe */
110 cvmx_usb_transfer_t type; /**< Type of transaction, duplicated of the pipe */
111 cvmx_usb_transaction_flags_t flags; /**< State flags for this transaction */
112 uint64_t buffer; /**< User's physical buffer address to read/write */
113 int buffer_length; /**< Size of the user's buffer in bytes */
114 uint64_t control_header; /**< For control transactions, physical address of the 8 byte standard header */
115 int iso_start_frame; /**< For ISO transactions, the starting frame number */
116 int iso_number_packets; /**< For ISO transactions, the number of packets in the request */
117 cvmx_usb_iso_packet_t *iso_packets; /**< For ISO transactions, the sub packets in the request */
121 int actual_bytes; /**< Actual bytes transfer for this transaction */
122 cvmx_usb_stage_t stage; /**< For control transactions, the current stage */
123 cvmx_usb_callback_func_t callback; /**< User's callback function when complete */
124 void *callback_data; /**< User's data */
125 } cvmx_usb_transaction_t;
128 * A pipe represents a virtual connection between Octeon and some
129 * USB device. It contains a list of pending request to the device.
131 typedef struct cvmx_usb_pipe
133 struct cvmx_usb_pipe *prev; /**< Pipe before this one in the list */
134 struct cvmx_usb_pipe *next; /**< Pipe after this one in the list */
135 cvmx_usb_transaction_t *head; /**< The first pending transaction */
136 cvmx_usb_transaction_t *tail; /**< The last pending transaction */
137 uint64_t interval; /**< For periodic pipes, the interval between packets in cycles */
138 uint64_t next_tx_cycle; /**< The next cycle this pipe is allowed to transmit on */
139 cvmx_usb_pipe_flags_t flags; /**< State flags for this pipe */
140 cvmx_usb_speed_t device_speed; /**< Speed of device connected to this pipe */
141 cvmx_usb_transfer_t transfer_type; /**< Type of transaction supported by this pipe */
142 cvmx_usb_direction_t transfer_dir; /**< IN or OUT. Ignored for Control */
143 int multi_count; /**< Max packet in a row for the device */
144 uint16_t max_packet; /**< The device's maximum packet size in bytes */
145 uint8_t device_addr; /**< USB device address at other end of pipe */
146 uint8_t endpoint_num; /**< USB endpoint number at other end of pipe */
147 uint8_t hub_device_addr; /**< Hub address this device is connected to */
148 uint8_t hub_port; /**< Hub port this device is connected to */
149 uint8_t pid_toggle; /**< This toggles between 0/1 on every packet send to track the data pid needed */
150 uint8_t channel; /**< Hardware DMA channel for this pipe */
151 int8_t split_sc_frame; /**< The low order bits of the frame number the split complete should be sent on */
156 cvmx_usb_pipe_t *head; /**< Head of the list, or NULL if empty */
157 cvmx_usb_pipe_t *tail; /**< Tail if the list, or NULL if empty */
158 } cvmx_usb_pipe_list_t;
161 * The state of the USB block is stored in this structure
165 int init_flags; /**< Flags passed to initialize */
166 int index; /**< Which USB block this is for */
167 int idle_hardware_channels; /**< Bit set for every idle hardware channel */
168 int active_transactions; /**< Number of active transactions across all pipes */
169 cvmx_usbcx_hprt_t usbcx_hprt; /**< Stored port status so we don't need to read a CSR to determine splits */
170 cvmx_usb_pipe_t *pipe_for_channel[MAX_CHANNELS]; /**< Map channels to pipes */
171 cvmx_usb_transaction_t *free_transaction_head; /**< List of free transactions head */
172 cvmx_usb_transaction_t *free_transaction_tail; /**< List of free transactions tail */
173 cvmx_usb_pipe_t pipe[MAX_PIPES]; /**< Storage for pipes */
174 cvmx_usb_transaction_t transaction[MAX_TRANSACTIONS]; /**< Storage for transactions */
175 cvmx_usb_callback_func_t callback[__CVMX_USB_CALLBACK_END]; /**< User global callbacks */
176 void *callback_data[__CVMX_USB_CALLBACK_END]; /**< User data for each callback */
177 int indent; /**< Used by debug output to indent functions */
178 cvmx_usb_port_status_t port_status; /**< Last port status used for change notification */
179 cvmx_usb_pipe_list_t free_pipes; /**< List of all pipes that are currently closed */
180 cvmx_usb_pipe_list_t idle_pipes; /**< List of open pipes that have no transactions */
181 cvmx_usb_pipe_list_t active_pipes[4]; /**< Active pipes indexed by transfer type */
182 } cvmx_usb_internal_state_t;
184 /* This macro logs out whenever a function is called if debugging is on */
185 #define CVMX_USB_LOG_CALLED() \
186 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CALLS)) \
187 cvmx_dprintf("%*s%s: called\n", 2*usb->indent++, "", __FUNCTION__);
189 /* This macro logs out each function parameter if debugging is on */
190 #define CVMX_USB_LOG_PARAM(format, param) \
191 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CALLS)) \
192 cvmx_dprintf("%*s%s: param %s = " format "\n", 2*usb->indent, "", __FUNCTION__, #param, param);
194 /* This macro logs out when a function returns a value */
195 #define CVMX_USB_RETURN(v) \
198 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CALLS)) \
199 cvmx_dprintf("%*s%s: returned %s(%d)\n", 2*--usb->indent, "", __FUNCTION__, #v, r); \
203 /* This macro logs out when a function doesn't return a value */
204 #define CVMX_USB_RETURN_NOTHING() \
206 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CALLS)) \
207 cvmx_dprintf("%*s%s: returned\n", 2*--usb->indent, "", __FUNCTION__); \
211 /* This macro spins on a field waiting for it to reach a value */
212 #define CVMX_WAIT_FOR_FIELD32(address, type, field, op, value, timeout_usec)\
215 uint64_t done = cvmx_get_cycle() + (uint64_t)timeout_usec * \
216 cvmx_sysinfo_get()->cpu_clock_hz / 1000000; \
220 c.u32 = __cvmx_usb_read_csr32(usb, address); \
221 if (c.s.field op (value)) { \
224 } else if (cvmx_get_cycle() > done) { \
233 /* This macro logically sets a single field in a CSR. It does the sequence
234 read, modify, and write */
235 #define USB_SET_FIELD32(address, type, field, value)\
238 c.u32 = __cvmx_usb_read_csr32(usb, address);\
240 __cvmx_usb_write_csr32(usb, address, c.u32);\
246 * Read a USB 32bit CSR. It performs the necessary address swizzle
247 * for 32bit CSRs and logs the value in a readable format if
250 * @param usb USB block this access is for
251 * @param address 64bit address to read
253 * @return Result of the read
255 static inline uint32_t __cvmx_usb_read_csr32(cvmx_usb_internal_state_t *usb,
258 uint32_t result = cvmx_read64_uint32(address ^ 4);
259 #if ALLOW_CSR_DECODES
260 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CSRS))
262 cvmx_dprintf("Read: ");
263 cvmx_csr_db_decode(cvmx_get_proc_id(), address, result);
272 * Write a USB 32bit CSR. It performs the necessary address
273 * swizzle for 32bit CSRs and logs the value in a readable format
274 * if debugging is on.
276 * @param usb USB block this access is for
277 * @param address 64bit address to write
278 * @param value Value to write
280 static inline void __cvmx_usb_write_csr32(cvmx_usb_internal_state_t *usb,
281 uint64_t address, uint32_t value)
283 #if ALLOW_CSR_DECODES
284 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CSRS))
286 cvmx_dprintf("Write: ");
287 cvmx_csr_db_decode(cvmx_get_proc_id(), address, value);
290 cvmx_write64_uint32(address ^ 4, value);
296 * Read a USB 64bit CSR. It logs the value in a readable format if
299 * @param usb USB block this access is for
300 * @param address 64bit address to read
302 * @return Result of the read
304 static inline uint64_t __cvmx_usb_read_csr64(cvmx_usb_internal_state_t *usb,
307 uint64_t result = cvmx_read64_uint64(address);
308 #if ALLOW_CSR_DECODES
309 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CSRS))
311 cvmx_dprintf("Read: ");
312 cvmx_csr_db_decode(cvmx_get_proc_id(), address, result);
321 * Write a USB 64bit CSR. It logs the value in a readable format
322 * if debugging is on.
324 * @param usb USB block this access is for
325 * @param address 64bit address to write
326 * @param value Value to write
328 static inline void __cvmx_usb_write_csr64(cvmx_usb_internal_state_t *usb,
329 uint64_t address, uint64_t value)
331 #if ALLOW_CSR_DECODES
332 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CSRS))
334 cvmx_dprintf("Write: ");
335 cvmx_csr_db_decode(cvmx_get_proc_id(), address, value);
338 cvmx_write64_uint64(address, value);
344 * Uitility function to convert complete codes into strings
346 * @param complete_code
349 * @return Human readable string
351 static const char *__cvmx_usb_complete_to_string(cvmx_usb_complete_t complete_code)
353 switch (complete_code)
355 case CVMX_USB_COMPLETE_SUCCESS: return "SUCCESS";
356 case CVMX_USB_COMPLETE_SHORT: return "SHORT";
357 case CVMX_USB_COMPLETE_CANCEL: return "CANCEL";
358 case CVMX_USB_COMPLETE_ERROR: return "ERROR";
359 case CVMX_USB_COMPLETE_STALL: return "STALL";
360 case CVMX_USB_COMPLETE_XACTERR: return "XACTERR";
361 case CVMX_USB_COMPLETE_DATATGLERR: return "DATATGLERR";
362 case CVMX_USB_COMPLETE_BABBLEERR: return "BABBLEERR";
363 case CVMX_USB_COMPLETE_FRAMEERR: return "FRAMEERR";
365 return "Update __cvmx_usb_complete_to_string";
371 * Return non zero if this pipe connects to a non HIGH speed
372 * device through a high speed hub.
374 * @param usb USB block this access is for
375 * @param pipe Pipe to check
377 * @return Non zero if we need to do split transactions
379 static inline int __cvmx_usb_pipe_needs_split(cvmx_usb_internal_state_t *usb, cvmx_usb_pipe_t *pipe)
381 return ((pipe->device_speed != CVMX_USB_SPEED_HIGH) && (usb->usbcx_hprt.s.prtspd == CVMX_USB_SPEED_HIGH));
387 * Trivial utility function to return the correct PID for a pipe
389 * @param pipe pipe to check
391 * @return PID for pipe
393 static inline int __cvmx_usb_get_data_pid(cvmx_usb_pipe_t *pipe)
395 if (pipe->pid_toggle)
396 return 2; /* Data1 */
398 return 0; /* Data0 */
403 * Return the number of USB ports supported by this Octeon
404 * chip. If the chip doesn't support USB, or is not supported
405 * by this API, a zero will be returned. Most Octeon chips
406 * support one usb port, but some support two ports.
407 * cvmx_usb_initialize() must be called on independent
408 * cvmx_usb_state_t structures.
410 * This utilizes cvmx_helper_board_usb_get_num_ports()
411 * to get any board specific variatons.
413 * @return Number of port, zero if usb isn't supported
415 int cvmx_usb_get_num_ports(void)
419 if (OCTEON_IS_MODEL(OCTEON_CN52XX))
421 else if (OCTEON_IS_MODEL(OCTEON_CN31XX))
422 arch_ports = 0; /* This chip has USB but it doesn't support DMA */
423 else if (OCTEON_IS_MODEL(OCTEON_CN38XX) || OCTEON_IS_MODEL(OCTEON_CN58XX))
428 return __cvmx_helper_board_usb_get_num_ports(arch_ports);
434 * Allocate a usb transaction for use
436 * @param usb USB device state populated by
437 * cvmx_usb_initialize().
439 * @return Transaction or NULL
441 static inline cvmx_usb_transaction_t *__cvmx_usb_alloc_transaction(cvmx_usb_internal_state_t *usb)
443 cvmx_usb_transaction_t *t;
444 t = usb->free_transaction_head;
447 usb->free_transaction_head = t->next;
448 if (!usb->free_transaction_head)
449 usb->free_transaction_tail = NULL;
451 else if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
452 cvmx_dprintf("%s: Failed to allocate a transaction\n", __FUNCTION__);
455 memset(t, 0, sizeof(*t));
456 t->flags = __CVMX_USB_TRANSACTION_FLAGS_IN_USE;
464 * Free a usb transaction
466 * @param usb USB device state populated by
467 * cvmx_usb_initialize().
469 * Transaction to free
471 static inline void __cvmx_usb_free_transaction(cvmx_usb_internal_state_t *usb,
472 cvmx_usb_transaction_t *transaction)
474 transaction->flags = 0;
475 transaction->prev = NULL;
476 transaction->next = NULL;
477 if (usb->free_transaction_tail)
478 usb->free_transaction_tail->next = transaction;
480 usb->free_transaction_head = transaction;
481 usb->free_transaction_tail = transaction;
487 * Add a pipe to the tail of a list
488 * @param list List to add pipe to
489 * @param pipe Pipe to add
491 static inline void __cvmx_usb_append_pipe(cvmx_usb_pipe_list_t *list, cvmx_usb_pipe_t *pipe)
494 pipe->prev = list->tail;
496 list->tail->next = pipe;
505 * Remove a pipe from a list
506 * @param list List to remove pipe from
507 * @param pipe Pipe to remove
509 static inline void __cvmx_usb_remove_pipe(cvmx_usb_pipe_list_t *list, cvmx_usb_pipe_t *pipe)
511 if (list->head == pipe)
513 list->head = pipe->next;
516 list->head->prev = NULL;
520 else if (list->tail == pipe)
522 list->tail = pipe->prev;
523 list->tail->next = NULL;
528 pipe->prev->next = pipe->next;
529 pipe->next->prev = pipe->prev;
538 * Perfrom USB device mode initialization after a reset completes.
539 * This should be called after USBC0/1_GINTSTS[USBRESET] and
540 * coresponds to section 22.6.1.1, "Initialization on USB Reset",
543 * @param usb USB device state populated by
544 * cvmx_usb_initialize().
546 * @return CVMX_USB_SUCCESS or a negative error code defined in
549 static cvmx_usb_status_t __cvmx_usb_device_reset_complete(cvmx_usb_internal_state_t *usb)
551 cvmx_usbcx_ghwcfg3_t usbcx_ghwcfg3;
554 CVMX_USB_LOG_CALLED();
555 CVMX_USB_LOG_PARAM("%p", usb);
557 /* 1. Set USBC0/1_DOEPCTLn[SNAK] = 1 (for all OUT endpoints, n = 0-4). */
560 USB_SET_FIELD32(CVMX_USBCX_DOEPCTLX(i, usb->index),
561 cvmx_usbcx_doepctlx_t, snak, 1);
564 /* 2. Unmask the following interrupt bits:
565 USBC0/1_DAINTMSK[INEPMSK] = 1 (control 0 IN endpoint)
566 USBC0/1_DAINTMSK[OUTEPMSK] = 1 (control 0 OUT endpoint)
567 USBC0/1_DOEPMSK[SETUPMSK] = 1
568 USBC0/1_DOEPMSK[XFERCOMPLMSK] = 1
569 USBC0/1_DIEPMSK[XFERCOMPLMSK] = 1
570 USBC0/1_DIEPMSK[TIMEOUTMSK] = 1 */
571 USB_SET_FIELD32(CVMX_USBCX_DAINTMSK(usb->index), cvmx_usbcx_daintmsk_t,
573 USB_SET_FIELD32(CVMX_USBCX_DAINTMSK(usb->index), cvmx_usbcx_daintmsk_t,
575 USB_SET_FIELD32(CVMX_USBCX_DOEPMSK(usb->index), cvmx_usbcx_doepmsk_t,
577 USB_SET_FIELD32(CVMX_USBCX_DOEPMSK(usb->index), cvmx_usbcx_doepmsk_t,
579 USB_SET_FIELD32(CVMX_USBCX_DIEPMSK(usb->index), cvmx_usbcx_diepmsk_t,
581 USB_SET_FIELD32(CVMX_USBCX_DIEPMSK(usb->index), cvmx_usbcx_diepmsk_t,
584 /* 3. To transmit or receive data, the device must initialize more
585 registers as specified in Section 22.6.1.7 */
588 /* 4. Set up the data FIFO RAM for each of the FIFOs:
589 Program USBC0/1_GRXFSIZ to be able to receive control OUT data and
590 SETUP data. This must equal at least one maximum packet size of
591 control endpoint 0 + 2 Dwords (for the status of the control OUT
592 data packet) + 10 Dwords (for SETUP packets).
593 Program USBC0/1_GNPTXFSIZ to be able to transmit control IN data. This
594 must equal at least one maximum packet size of control endpoint 0. */
596 /* Read the HWCFG3 register so we know how much space is in the FIFO */
597 usbcx_ghwcfg3.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_GHWCFG3(usb->index));
600 cvmx_usbcx_gnptxfsiz_t gnptxfsiz;
601 int fifo_space = usbcx_ghwcfg3.s.dfifodepth;
604 /* Start at the top of the FIFO and assign space for each periodic
608 cvmx_usbcx_dptxfsizx_t siz;
609 siz.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_DPTXFSIZX(i, usb->index));
610 fifo_space -= siz.s.dptxfsize;
611 siz.s.dptxfstaddr = fifo_space;
612 __cvmx_usb_write_csr32(usb, CVMX_USBCX_DPTXFSIZX(i, usb->index), siz.u32);
615 /* Assign half the leftover space to the non periodic tx fifo */
616 gnptxfsiz.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_GNPTXFSIZ(usb->index));
617 gnptxfsiz.s.nptxfdep = fifo_space / 2;
618 fifo_space -= gnptxfsiz.s.nptxfdep;
619 gnptxfsiz.s.nptxfstaddr = fifo_space;
620 __cvmx_usb_write_csr32(usb, CVMX_USBCX_GNPTXFSIZ(usb->index), gnptxfsiz.u32);
622 /* Assign the remain space to the RX fifo */
623 USB_SET_FIELD32(CVMX_USBCX_GRXFSIZ(usb->index), cvmx_usbcx_grxfsiz_t,
627 /* 5. Program the following fields in the endpoint-specific registers for
628 control OUT endpoint 0 to receive a SETUP packet
629 USBC0/1_DOEPTSIZ0[SUPCNT] = 0x3 (to receive up to three back-to-back
631 In DMA mode, USBC0/1_DOEPDMA0 register with a memory address to
632 store any SETUP packets received */
633 USB_SET_FIELD32(CVMX_USBCX_DOEPTSIZX(0, usb->index),
634 cvmx_usbcx_doeptsizx_t, mc, 3);
637 /* At this point, all initialization required to receive SETUP packets is
640 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
645 * Initialize a USB port for use. This must be called before any
646 * other access to the Octeon USB port is made. The port starts
647 * off in the disabled state.
649 * @param state Pointer to an empty cvmx_usb_state_t structure
650 * that will be populated by the initialize call.
651 * This structure is then passed to all other USB
653 * @param usb_port_number
654 * Which Octeon USB port to initialize.
655 * @param flags Flags to control hardware initialization. See
656 * cvmx_usb_initialize_flags_t for the flag
657 * definitions. Some flags are mandatory.
659 * @return CVMX_USB_SUCCESS or a negative error code defined in
662 cvmx_usb_status_t cvmx_usb_initialize(cvmx_usb_state_t *state,
664 cvmx_usb_initialize_flags_t flags)
666 cvmx_usbnx_clk_ctl_t usbn_clk_ctl;
667 cvmx_usbnx_usbp_ctl_status_t usbn_usbp_ctl_status;
668 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
670 usb->init_flags = flags;
671 CVMX_USB_LOG_CALLED();
672 CVMX_USB_LOG_PARAM("%p", state);
673 CVMX_USB_LOG_PARAM("%d", usb_port_number);
674 CVMX_USB_LOG_PARAM("0x%x", flags);
676 /* Make sure that state is large enough to store the internal state */
677 if (sizeof(*state) < sizeof(*usb))
678 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
679 /* At first allow 0-1 for the usb port number */
680 if ((usb_port_number < 0) || (usb_port_number > 1))
681 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
682 /* For all chips except 52XX there is only one port */
683 if (!OCTEON_IS_MODEL(OCTEON_CN52XX) && (usb_port_number > 0))
684 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
685 /* Try to determine clock type automatically */
686 if ((flags & (CVMX_USB_INITIALIZE_FLAGS_CLOCK_XO_XI |
687 CVMX_USB_INITIALIZE_FLAGS_CLOCK_XO_GND)) == 0)
689 if (__cvmx_helper_board_usb_get_clock_type() == USB_CLOCK_TYPE_CRYSTAL_12)
690 flags |= CVMX_USB_INITIALIZE_FLAGS_CLOCK_XO_XI; /* Only 12 MHZ crystals are supported */
692 flags |= CVMX_USB_INITIALIZE_FLAGS_CLOCK_XO_GND;
695 if (flags & CVMX_USB_INITIALIZE_FLAGS_CLOCK_XO_GND)
697 /* Check for auto ref clock frequency */
698 if (!(flags & CVMX_USB_INITIALIZE_FLAGS_CLOCK_MHZ_MASK))
699 switch (__cvmx_helper_board_usb_get_clock_type())
701 case USB_CLOCK_TYPE_REF_12:
702 flags |= CVMX_USB_INITIALIZE_FLAGS_CLOCK_12MHZ;
704 case USB_CLOCK_TYPE_REF_24:
705 flags |= CVMX_USB_INITIALIZE_FLAGS_CLOCK_24MHZ;
707 case USB_CLOCK_TYPE_REF_48:
708 flags |= CVMX_USB_INITIALIZE_FLAGS_CLOCK_48MHZ;
711 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
716 memset(usb, 0, sizeof(usb));
717 usb->init_flags = flags;
719 /* Initialize the USB state structure */
722 usb->index = usb_port_number;
724 /* Initialize the transaction double linked list */
725 usb->free_transaction_head = NULL;
726 usb->free_transaction_tail = NULL;
727 for (i=0; i<MAX_TRANSACTIONS; i++)
728 __cvmx_usb_free_transaction(usb, usb->transaction + i);
729 for (i=0; i<MAX_PIPES; i++)
730 __cvmx_usb_append_pipe(&usb->free_pipes, usb->pipe + i);
733 /* Power On Reset and PHY Initialization */
735 /* 1. Wait for DCOK to assert (nothing to do) */
736 /* 2a. Write USBN0/1_CLK_CTL[POR] = 1 and
737 USBN0/1_CLK_CTL[HRST,PRST,HCLK_RST] = 0 */
738 usbn_clk_ctl.u64 = __cvmx_usb_read_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index));
739 usbn_clk_ctl.s.por = 1;
740 usbn_clk_ctl.s.hrst = 0;
741 usbn_clk_ctl.s.prst = 0;
742 usbn_clk_ctl.s.hclk_rst = 0;
743 usbn_clk_ctl.s.enable = 0;
744 /* 2b. Select the USB reference clock/crystal parameters by writing
745 appropriate values to USBN0/1_CLK_CTL[P_C_SEL, P_RTYPE, P_COM_ON] */
746 if (usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_CLOCK_XO_GND)
748 /* The USB port uses 12/24/48MHz 2.5V board clock
749 source at USB_XO. USB_XI should be tied to GND.
750 Most Octeon evaluation boards require this setting */
751 if (OCTEON_IS_MODEL(OCTEON_CN3XXX))
753 usbn_clk_ctl.cn31xx.p_rclk = 1; /* From CN31XX,CN30XX manual */
754 usbn_clk_ctl.cn31xx.p_xenbn = 0;
756 else if (OCTEON_IS_MODEL(OCTEON_CN56XX) || OCTEON_IS_MODEL(OCTEON_CN50XX))
757 usbn_clk_ctl.cn56xx.p_rtype = 2; /* From CN56XX,CN50XX manual */
759 usbn_clk_ctl.cn52xx.p_rtype = 1; /* From CN52XX manual */
761 switch (flags & CVMX_USB_INITIALIZE_FLAGS_CLOCK_MHZ_MASK)
763 case CVMX_USB_INITIALIZE_FLAGS_CLOCK_12MHZ:
764 usbn_clk_ctl.s.p_c_sel = 0;
766 case CVMX_USB_INITIALIZE_FLAGS_CLOCK_24MHZ:
767 usbn_clk_ctl.s.p_c_sel = 1;
769 case CVMX_USB_INITIALIZE_FLAGS_CLOCK_48MHZ:
770 usbn_clk_ctl.s.p_c_sel = 2;
776 /* The USB port uses a 12MHz crystal as clock source
777 at USB_XO and USB_XI */
778 if (OCTEON_IS_MODEL(OCTEON_CN3XXX))
780 usbn_clk_ctl.cn31xx.p_rclk = 1; /* From CN31XX,CN30XX manual */
781 usbn_clk_ctl.cn31xx.p_xenbn = 1;
783 else if (OCTEON_IS_MODEL(OCTEON_CN56XX) || OCTEON_IS_MODEL(OCTEON_CN50XX))
784 usbn_clk_ctl.cn56xx.p_rtype = 0; /* From CN56XX,CN50XX manual */
786 usbn_clk_ctl.cn52xx.p_rtype = 0; /* From CN52XX manual */
788 usbn_clk_ctl.s.p_c_sel = 0;
790 /* 2c. Select the HCLK via writing USBN0/1_CLK_CTL[DIVIDE, DIVIDE2] and
791 setting USBN0/1_CLK_CTL[ENABLE] = 1. Divide the core clock down such
792 that USB is as close as possible to 125Mhz */
794 int divisor = (cvmx_sysinfo_get()->cpu_clock_hz+125000000-1)/125000000;
795 if (divisor < 4) /* Lower than 4 doesn't seem to work properly */
797 usbn_clk_ctl.s.divide = divisor;
798 usbn_clk_ctl.s.divide2 = 0;
800 __cvmx_usb_write_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index),
802 /* 2d. Write USBN0/1_CLK_CTL[HCLK_RST] = 1 */
803 usbn_clk_ctl.s.hclk_rst = 1;
804 __cvmx_usb_write_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index),
806 /* 2e. Wait 64 core-clock cycles for HCLK to stabilize */
808 /* 3. Program the power-on reset field in the USBN clock-control register:
809 USBN_CLK_CTL[POR] = 0 */
810 usbn_clk_ctl.s.por = 0;
811 __cvmx_usb_write_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index),
813 /* 4. Wait 1 ms for PHY clock to start */
814 cvmx_wait_usec(1000);
815 /* 5. Program the Reset input from automatic test equipment field in the
816 USBP control and status register: USBN_USBP_CTL_STATUS[ATE_RESET] = 1 */
817 usbn_usbp_ctl_status.u64 = __cvmx_usb_read_csr64(usb, CVMX_USBNX_USBP_CTL_STATUS(usb->index));
818 usbn_usbp_ctl_status.s.ate_reset = 1;
819 __cvmx_usb_write_csr64(usb, CVMX_USBNX_USBP_CTL_STATUS(usb->index),
820 usbn_usbp_ctl_status.u64);
821 /* 6. Wait 10 cycles */
823 /* 7. Clear ATE_RESET field in the USBN clock-control register:
824 USBN_USBP_CTL_STATUS[ATE_RESET] = 0 */
825 usbn_usbp_ctl_status.s.ate_reset = 0;
826 __cvmx_usb_write_csr64(usb, CVMX_USBNX_USBP_CTL_STATUS(usb->index),
827 usbn_usbp_ctl_status.u64);
828 /* 8. Program the PHY reset field in the USBN clock-control register:
829 USBN_CLK_CTL[PRST] = 1 */
830 usbn_clk_ctl.s.prst = 1;
831 __cvmx_usb_write_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index),
833 /* 9. Program the USBP control and status register to select host or
834 device mode. USBN_USBP_CTL_STATUS[HST_MODE] = 0 for host, = 1 for
836 if (usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE)
838 usbn_usbp_ctl_status.s.hst_mode = 1;
839 usbn_usbp_ctl_status.s.dm_pulld = 0;
840 usbn_usbp_ctl_status.s.dp_pulld = 0;
844 usbn_usbp_ctl_status.s.hst_mode = 0;
846 __cvmx_usb_write_csr64(usb, CVMX_USBNX_USBP_CTL_STATUS(usb->index),
847 usbn_usbp_ctl_status.u64);
850 /* 11. Program the hreset_n field in the USBN clock-control register:
851 USBN_CLK_CTL[HRST] = 1 */
852 usbn_clk_ctl.s.hrst = 1;
853 __cvmx_usb_write_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index),
855 /* 12. Proceed to USB core initialization */
856 usbn_clk_ctl.s.enable = 1;
857 __cvmx_usb_write_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index),
861 /* USB Core Initialization */
863 /* 1. Read USBC_GHWCFG1, USBC_GHWCFG2, USBC_GHWCFG3, USBC_GHWCFG4 to
864 determine USB core configuration parameters. */
866 /* 2. Program the following fields in the global AHB configuration
867 register (USBC_GAHBCFG)
868 DMA mode, USBC_GAHBCFG[DMAEn]: 1 = DMA mode, 0 = slave mode
869 Burst length, USBC_GAHBCFG[HBSTLEN] = 0
870 Nonperiodic TxFIFO empty level (slave mode only),
871 USBC_GAHBCFG[NPTXFEMPLVL]
872 Periodic TxFIFO empty level (slave mode only),
873 USBC_GAHBCFG[PTXFEMPLVL]
874 Global interrupt mask, USBC_GAHBCFG[GLBLINTRMSK] = 1 */
876 cvmx_usbcx_gahbcfg_t usbcx_gahbcfg;
877 usbcx_gahbcfg.u32 = 0;
878 usbcx_gahbcfg.s.dmaen = !OCTEON_IS_MODEL(OCTEON_CN31XX);
879 /* If we are using DMA, start off with 8 idle channels. Without
880 DMA we emulate a single channel */
881 if (usbcx_gahbcfg.s.dmaen)
882 usb->idle_hardware_channels = 0xff;
884 usb->idle_hardware_channels = 0x1;
885 usbcx_gahbcfg.s.hbstlen = 0;
886 usbcx_gahbcfg.s.nptxfemplvl = 1;
887 usbcx_gahbcfg.s.ptxfemplvl = 1;
888 usbcx_gahbcfg.s.glblintrmsk = 1;
889 __cvmx_usb_write_csr32(usb, CVMX_USBCX_GAHBCFG(usb->index),
892 /* 3. Program the following fields in USBC_GUSBCFG register.
893 HS/FS timeout calibration, USBC_GUSBCFG[TOUTCAL] = 0
894 ULPI DDR select, USBC_GUSBCFG[DDRSEL] = 0
895 USB turnaround time, USBC_GUSBCFG[USBTRDTIM] = 0x5
896 PHY low-power clock select, USBC_GUSBCFG[PHYLPWRCLKSEL] = 0 */
898 cvmx_usbcx_gusbcfg_t usbcx_gusbcfg;
899 usbcx_gusbcfg.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_GUSBCFG(usb->index));
900 usbcx_gusbcfg.s.toutcal = 0;
901 usbcx_gusbcfg.s.ddrsel = 0;
902 usbcx_gusbcfg.s.usbtrdtim = 0x5;
903 usbcx_gusbcfg.s.phylpwrclksel = 0;
904 __cvmx_usb_write_csr32(usb, CVMX_USBCX_GUSBCFG(usb->index),
907 /* 4. The software must unmask the following bits in the USBC_GINTMSK
909 OTG interrupt mask, USBC_GINTMSK[OTGINTMSK] = 1
910 Mode mismatch interrupt mask, USBC_GINTMSK[MODEMISMSK] = 1 */
912 cvmx_usbcx_gintmsk_t usbcx_gintmsk;
913 cvmx_usbcx_hcintmskx_t usbc_hcintmsk;
914 cvmx_usbcx_haintmsk_t usbc_haintmsk;
917 usbcx_gintmsk.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_GINTMSK(usb->index));
918 usbcx_gintmsk.s.otgintmsk = 1;
919 usbcx_gintmsk.s.modemismsk = 1;
920 usbcx_gintmsk.s.hchintmsk = 1;
921 usbcx_gintmsk.s.sofmsk = 0;
922 __cvmx_usb_write_csr32(usb, CVMX_USBCX_GINTMSK(usb->index),
925 /* Enable the channel halt interrupt */
926 usbc_hcintmsk.u32 = 0;
927 usbc_hcintmsk.s.chhltdmsk = 1;
928 for (channel=0; channel<8; channel++)
929 if (usb->idle_hardware_channels & (1<<channel))
930 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCINTMSKX(channel, usb->index), usbc_hcintmsk.u32);
932 /* Enable the channel interrupt to propagate */
933 usbc_haintmsk.u32 = 0;
934 usbc_haintmsk.s.haintmsk = usb->idle_hardware_channels;
935 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HAINTMSK(usb->index), usbc_haintmsk.u32);
938 if ((usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE) == 0)
940 /* Host Port Initialization */
941 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
942 cvmx_dprintf("%s: USB%d is in host mode\n", __FUNCTION__, usb->index);
944 /* 1. Program the host-port interrupt-mask field to unmask,
945 USBC_GINTMSK[PRTINT] = 1 */
946 USB_SET_FIELD32(CVMX_USBCX_GINTMSK(usb->index), cvmx_usbcx_gintmsk_t,
948 USB_SET_FIELD32(CVMX_USBCX_GINTMSK(usb->index), cvmx_usbcx_gintmsk_t,
950 /* 2. Program the USBC_HCFG register to select full-speed host or
953 cvmx_usbcx_hcfg_t usbcx_hcfg;
954 usbcx_hcfg.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HCFG(usb->index));
955 usbcx_hcfg.s.fslssupp = 0;
956 usbcx_hcfg.s.fslspclksel = 0;
957 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCFG(usb->index), usbcx_hcfg.u32);
959 /* 3. Program the port power bit to drive VBUS on the USB,
960 USBC_HPRT[PRTPWR] = 1 */
961 USB_SET_FIELD32(CVMX_USBCX_HPRT(usb->index), cvmx_usbcx_hprt_t, prtpwr, 1);
963 /* Steps 4-15 from the manual are done later in the port enable */
967 /* Device Port Initialization */
968 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
969 cvmx_dprintf("%s: USB%d is in device mode\n", __FUNCTION__, usb->index);
971 /* 1. Program the following fields in the USBC0/1_DCFG register:
972 Device speed, USBC0/1_DCFG[DEVSPD] = 0 (high speed)
973 Non-zero-length status OUT handshake, USBC0/1_DCFG[NZSTSOUTHSHK]=0
974 Periodic frame interval (if periodic endpoints are supported),
975 USBC0/1_DCFG[PERFRINT] = 1 */
976 USB_SET_FIELD32(CVMX_USBCX_DCFG(usb->index), cvmx_usbcx_dcfg_t,
978 USB_SET_FIELD32(CVMX_USBCX_DCFG(usb->index), cvmx_usbcx_dcfg_t,
980 USB_SET_FIELD32(CVMX_USBCX_DCFG(usb->index), cvmx_usbcx_dcfg_t,
983 /* 2. Program the USBC0/1_GINTMSK register to unmask the following
985 USB Reset, USBC0/1_GINTMSK[USBRSTMSK] = 1
986 Enumeration done, USBC0/1_GINTMSK[ENUMDONEMSK] = 1
987 SOF, USBC0/1_GINTMSK[SOFMSK] = 1 */
988 USB_SET_FIELD32(CVMX_USBCX_GINTMSK(usb->index), cvmx_usbcx_gintmsk_t,
990 USB_SET_FIELD32(CVMX_USBCX_GINTMSK(usb->index), cvmx_usbcx_gintmsk_t,
992 USB_SET_FIELD32(CVMX_USBCX_GINTMSK(usb->index), cvmx_usbcx_gintmsk_t,
995 /* 3. Wait for the USBC0/1_GINTSTS[USBRESET] interrupt, which
996 indicates a reset has been detected on the USB and lasts for
997 about 10 ms. On receiving this interrupt, the application must
998 perform the steps listed in Section 22.6.1.1, "Initialization on
1000 /* Handled in cvmx_poll() usbc_gintsts.s.usbrst processing */
1002 /* 4. Wait for the USBC0/1_GINTSTS[ENUMERATIONDONE] interrupt, which
1003 indicates the end of reset on the USB. On receiving this interrupt,
1004 the application must read the USBC0/1_DSTS register to determine
1005 the enumeration speed and perform the steps listed in Section
1006 22.6.1.2, "Initialization on Enumeration Completion". */
1007 /* Handled in cvmx_poll() usbc_gintsts.s.enumdone processing */
1010 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
1015 * Shutdown a USB port after a call to cvmx_usb_initialize().
1016 * The port should be disabled with all pipes closed when this
1017 * function is called.
1019 * @param state USB device state populated by
1020 * cvmx_usb_initialize().
1022 * @return CVMX_USB_SUCCESS or a negative error code defined in
1023 * cvmx_usb_status_t.
1025 cvmx_usb_status_t cvmx_usb_shutdown(cvmx_usb_state_t *state)
1027 cvmx_usbnx_clk_ctl_t usbn_clk_ctl;
1028 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
1030 CVMX_USB_LOG_CALLED();
1031 CVMX_USB_LOG_PARAM("%p", state);
1033 /* Make sure all pipes are closed */
1034 if (usb->idle_pipes.head ||
1035 usb->active_pipes[CVMX_USB_TRANSFER_ISOCHRONOUS].head ||
1036 usb->active_pipes[CVMX_USB_TRANSFER_INTERRUPT].head ||
1037 usb->active_pipes[CVMX_USB_TRANSFER_CONTROL].head ||
1038 usb->active_pipes[CVMX_USB_TRANSFER_BULK].head)
1039 CVMX_USB_RETURN(CVMX_USB_BUSY);
1041 /* Disable the clocks and put them in power on reset */
1042 usbn_clk_ctl.u64 = __cvmx_usb_read_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index));
1043 usbn_clk_ctl.s.enable = 1;
1044 usbn_clk_ctl.s.por = 1;
1045 usbn_clk_ctl.s.hclk_rst = 1;
1046 usbn_clk_ctl.s.prst = 0;
1047 usbn_clk_ctl.s.hrst = 0;
1048 __cvmx_usb_write_csr64(usb, CVMX_USBNX_CLK_CTL(usb->index),
1050 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
1055 * Enable a USB port. After this call succeeds, the USB port is
1056 * online and servicing requests.
1058 * @param state USB device state populated by
1059 * cvmx_usb_initialize().
1061 * @return CVMX_USB_SUCCESS or a negative error code defined in
1062 * cvmx_usb_status_t.
1064 cvmx_usb_status_t cvmx_usb_enable(cvmx_usb_state_t *state)
1066 cvmx_usbcx_ghwcfg3_t usbcx_ghwcfg3;
1067 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
1069 CVMX_USB_LOG_CALLED();
1070 CVMX_USB_LOG_PARAM("%p", state);
1071 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
1072 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
1074 usb->usbcx_hprt.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HPRT(usb->index));
1076 /* If the port is already enabled the just return. We don't need to do
1078 if (usb->usbcx_hprt.s.prtena)
1079 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
1081 /* If there is nothing plugged into the port then fail immediately */
1082 if (!usb->usbcx_hprt.s.prtconnsts)
1084 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
1085 cvmx_dprintf("%s: USB%d Nothing plugged into the port\n", __FUNCTION__, usb->index);
1086 CVMX_USB_RETURN(CVMX_USB_TIMEOUT);
1089 /* Program the port reset bit to start the reset process */
1090 USB_SET_FIELD32(CVMX_USBCX_HPRT(usb->index), cvmx_usbcx_hprt_t, prtrst, 1);
1092 /* Wait at least 50ms (high speed), or 10ms (full speed) for the reset
1093 process to complete. */
1094 cvmx_wait_usec(50000);
1096 /* Program the port reset bit to 0, USBC_HPRT[PRTRST] = 0 */
1097 USB_SET_FIELD32(CVMX_USBCX_HPRT(usb->index), cvmx_usbcx_hprt_t, prtrst, 0);
1099 /* Wait for the USBC_HPRT[PRTENA]. */
1100 if (CVMX_WAIT_FOR_FIELD32(CVMX_USBCX_HPRT(usb->index), cvmx_usbcx_hprt_t,
1101 prtena, ==, 1, 100000))
1103 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
1104 cvmx_dprintf("%s: Timeout waiting for the port to finish reset\n",
1106 CVMX_USB_RETURN(CVMX_USB_TIMEOUT);
1109 /* Read the port speed field to get the enumerated speed, USBC_HPRT[PRTSPD]. */
1110 usb->usbcx_hprt.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HPRT(usb->index));
1111 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
1112 cvmx_dprintf("%s: USB%d is in %s speed mode\n", __FUNCTION__, usb->index,
1113 (usb->usbcx_hprt.s.prtspd == CVMX_USB_SPEED_HIGH) ? "high" :
1114 (usb->usbcx_hprt.s.prtspd == CVMX_USB_SPEED_FULL) ? "full" :
1117 usbcx_ghwcfg3.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_GHWCFG3(usb->index));
1119 /* 13. Program the USBC_GRXFSIZ register to select the size of the receive
1121 USB_SET_FIELD32(CVMX_USBCX_GRXFSIZ(usb->index), cvmx_usbcx_grxfsiz_t,
1122 rxfdep, usbcx_ghwcfg3.s.dfifodepth / 4);
1123 /* 14. Program the USBC_GNPTXFSIZ register to select the size and the
1124 start address of the non- periodic transmit FIFO for nonperiodic
1125 transactions (50%). */
1127 cvmx_usbcx_gnptxfsiz_t siz;
1128 siz.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_GNPTXFSIZ(usb->index));
1129 siz.s.nptxfdep = usbcx_ghwcfg3.s.dfifodepth / 2;
1130 siz.s.nptxfstaddr = usbcx_ghwcfg3.s.dfifodepth / 4;
1131 __cvmx_usb_write_csr32(usb, CVMX_USBCX_GNPTXFSIZ(usb->index), siz.u32);
1133 /* 15. Program the USBC_HPTXFSIZ register to select the size and start
1134 address of the periodic transmit FIFO for periodic transactions (25%). */
1136 cvmx_usbcx_hptxfsiz_t siz;
1137 siz.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HPTXFSIZ(usb->index));
1138 siz.s.ptxfsize = usbcx_ghwcfg3.s.dfifodepth / 4;
1139 siz.s.ptxfstaddr = 3 * usbcx_ghwcfg3.s.dfifodepth / 4;
1140 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HPTXFSIZ(usb->index), siz.u32);
1142 /* Flush all FIFOs */
1143 USB_SET_FIELD32(CVMX_USBCX_GRSTCTL(usb->index), cvmx_usbcx_grstctl_t, txfnum, 0x10);
1144 USB_SET_FIELD32(CVMX_USBCX_GRSTCTL(usb->index), cvmx_usbcx_grstctl_t, txfflsh, 1);
1145 CVMX_WAIT_FOR_FIELD32(CVMX_USBCX_GRSTCTL(usb->index), cvmx_usbcx_grstctl_t,
1146 txfflsh, ==, 0, 100);
1147 USB_SET_FIELD32(CVMX_USBCX_GRSTCTL(usb->index), cvmx_usbcx_grstctl_t, rxfflsh, 1);
1148 CVMX_WAIT_FOR_FIELD32(CVMX_USBCX_GRSTCTL(usb->index), cvmx_usbcx_grstctl_t,
1149 rxfflsh, ==, 0, 100);
1151 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
1156 * Disable a USB port. After this call the USB port will not
1157 * generate data transfers and will not generate events.
1158 * Transactions in process will fail and call their
1159 * associated callbacks.
1161 * @param state USB device state populated by
1162 * cvmx_usb_initialize().
1164 * @return CVMX_USB_SUCCESS or a negative error code defined in
1165 * cvmx_usb_status_t.
1167 cvmx_usb_status_t cvmx_usb_disable(cvmx_usb_state_t *state)
1169 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
1171 CVMX_USB_LOG_CALLED();
1172 CVMX_USB_LOG_PARAM("%p", state);
1173 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
1174 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
1176 /* Disable the port */
1177 USB_SET_FIELD32(CVMX_USBCX_HPRT(usb->index), cvmx_usbcx_hprt_t, prtena, 1);
1178 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
1183 * Get the current state of the USB port. Use this call to
1184 * determine if the usb port has anything connected, is enabled,
1185 * or has some sort of error condition. The return value of this
1186 * call has "changed" bits to signal of the value of some fields
1187 * have changed between calls. These "changed" fields are based
1188 * on the last call to cvmx_usb_set_status(). In order to clear
1189 * them, you must update the status through cvmx_usb_set_status().
1191 * @param state USB device state populated by
1192 * cvmx_usb_initialize().
1194 * @return Port status information
1196 cvmx_usb_port_status_t cvmx_usb_get_status(cvmx_usb_state_t *state)
1198 cvmx_usbcx_hprt_t usbc_hprt;
1199 cvmx_usb_port_status_t result;
1200 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
1202 memset(&result, 0, sizeof(result));
1204 CVMX_USB_LOG_CALLED();
1205 CVMX_USB_LOG_PARAM("%p", state);
1207 usbc_hprt.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HPRT(usb->index));
1208 result.port_enabled = usbc_hprt.s.prtena;
1209 result.port_over_current = usbc_hprt.s.prtovrcurract;
1210 result.port_powered = usbc_hprt.s.prtpwr;
1211 result.port_speed = usbc_hprt.s.prtspd;
1212 result.connected = usbc_hprt.s.prtconnsts;
1213 result.connect_change = (result.connected != usb->port_status.connected);
1215 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CALLS))
1216 cvmx_dprintf("%*s%s: returned port enabled=%d, over_current=%d, powered=%d, speed=%d, connected=%d, connect_change=%d\n",
1217 2*(--usb->indent), "", __FUNCTION__,
1218 result.port_enabled,
1219 result.port_over_current,
1220 result.port_powered,
1223 result.connect_change);
1229 * Set the current state of the USB port. The status is used as
1230 * a reference for the "changed" bits returned by
1231 * cvmx_usb_get_status(). Other than serving as a reference, the
1232 * status passed to this function is not used. No fields can be
1233 * changed through this call.
1235 * @param state USB device state populated by
1236 * cvmx_usb_initialize().
1237 * @param port_status
1238 * Port status to set, most like returned by cvmx_usb_get_status()
1240 void cvmx_usb_set_status(cvmx_usb_state_t *state, cvmx_usb_port_status_t port_status)
1242 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
1243 CVMX_USB_LOG_CALLED();
1244 CVMX_USB_LOG_PARAM("%p", state);
1245 usb->port_status = port_status;
1246 CVMX_USB_RETURN_NOTHING();
1252 * Convert a USB transaction into a handle
1254 * @param usb USB device state populated by
1255 * cvmx_usb_initialize().
1256 * @param transaction
1257 * Transaction to get handle for
1261 static inline int __cvmx_usb_get_submit_handle(cvmx_usb_internal_state_t *usb,
1262 cvmx_usb_transaction_t *transaction)
1264 return ((unsigned long)transaction - (unsigned long)usb->transaction) /
1265 sizeof(*transaction);
1271 * Convert a USB pipe into a handle
1273 * @param usb USB device state populated by
1274 * cvmx_usb_initialize().
1275 * @param pipe Pipe to get handle for
1279 static inline int __cvmx_usb_get_pipe_handle(cvmx_usb_internal_state_t *usb,
1280 cvmx_usb_pipe_t *pipe)
1282 return ((unsigned long)pipe - (unsigned long)usb->pipe) / sizeof(*pipe);
1287 * Open a virtual pipe between the host and a USB device. A pipe
1288 * must be opened before data can be transferred between a device
1291 * @param state USB device state populated by
1292 * cvmx_usb_initialize().
1293 * @param flags Optional pipe flags defined in
1294 * cvmx_usb_pipe_flags_t.
1295 * @param device_addr
1296 * USB device address to open the pipe to
1298 * @param endpoint_num
1299 * USB endpoint number to open the pipe to
1301 * @param device_speed
1302 * The speed of the device the pipe is going
1303 * to. This must match the device's speed,
1304 * which may be different than the port speed.
1305 * @param max_packet The maximum packet length the device can
1306 * transmit/receive (low speed=0-8, full
1307 * speed=0-1023, high speed=0-1024). This value
1308 * comes from the stadnard endpoint descriptor
1309 * field wMaxPacketSize bits <10:0>.
1310 * @param transfer_type
1311 * The type of transfer this pipe is for.
1312 * @param transfer_dir
1313 * The direction the pipe is in. This is not
1314 * used for control pipes.
1315 * @param interval For ISOCHRONOUS and INTERRUPT transfers,
1316 * this is how often the transfer is scheduled
1317 * for. All other transfers should specify
1318 * zero. The units are in frames (8000/sec at
1319 * high speed, 1000/sec for full speed).
1320 * @param multi_count
1321 * For high speed devices, this is the maximum
1322 * allowed number of packet per microframe.
1323 * Specify zero for non high speed devices. This
1324 * value comes from the stadnard endpoint descriptor
1325 * field wMaxPacketSize bits <12:11>.
1326 * @param hub_device_addr
1327 * Hub device address this device is connected
1328 * to. Devices connected directly to Octeon
1329 * use zero. This is only used when the device
1330 * is full/low speed behind a high speed hub.
1331 * The address will be of the high speed hub,
1332 * not and full speed hubs after it.
1333 * @param hub_port Which port on the hub the device is
1334 * connected. Use zero for devices connected
1335 * directly to Octeon. Like hub_device_addr,
1336 * this is only used for full/low speed
1337 * devices behind a high speed hub.
1339 * @return A non negative value is a pipe handle. Negative
1340 * values are failure codes from cvmx_usb_status_t.
1342 int cvmx_usb_open_pipe(cvmx_usb_state_t *state, cvmx_usb_pipe_flags_t flags,
1343 int device_addr, int endpoint_num,
1344 cvmx_usb_speed_t device_speed, int max_packet,
1345 cvmx_usb_transfer_t transfer_type,
1346 cvmx_usb_direction_t transfer_dir, int interval,
1347 int multi_count, int hub_device_addr, int hub_port)
1349 cvmx_usb_pipe_t *pipe;
1350 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
1352 CVMX_USB_LOG_CALLED();
1353 CVMX_USB_LOG_PARAM("%p", state);
1354 CVMX_USB_LOG_PARAM("0x%x", flags);
1355 CVMX_USB_LOG_PARAM("%d", device_addr);
1356 CVMX_USB_LOG_PARAM("%d", endpoint_num);
1357 CVMX_USB_LOG_PARAM("%d", device_speed);
1358 CVMX_USB_LOG_PARAM("%d", max_packet);
1359 CVMX_USB_LOG_PARAM("%d", transfer_type);
1360 CVMX_USB_LOG_PARAM("%d", transfer_dir);
1361 CVMX_USB_LOG_PARAM("%d", interval);
1362 CVMX_USB_LOG_PARAM("%d", multi_count);
1363 CVMX_USB_LOG_PARAM("%d", hub_device_addr);
1364 CVMX_USB_LOG_PARAM("%d", hub_port);
1366 if (cvmx_unlikely((device_addr < 0) || (device_addr > MAX_USB_ADDRESS)))
1367 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1368 if (cvmx_unlikely((endpoint_num < 0) || (endpoint_num > MAX_USB_ENDPOINT)))
1369 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1370 if (cvmx_unlikely(device_speed > CVMX_USB_SPEED_LOW))
1371 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1372 if (cvmx_unlikely((max_packet <= 0) || (max_packet > 1024)))
1373 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1374 if (cvmx_unlikely(transfer_type > CVMX_USB_TRANSFER_INTERRUPT))
1375 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1376 if (cvmx_unlikely((transfer_dir != CVMX_USB_DIRECTION_OUT) &&
1377 (transfer_dir != CVMX_USB_DIRECTION_IN)))
1378 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1379 if (cvmx_unlikely(interval < 0))
1380 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1381 if (cvmx_unlikely((transfer_type == CVMX_USB_TRANSFER_CONTROL) && interval))
1382 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1383 if (cvmx_unlikely(multi_count < 0))
1384 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1385 if (cvmx_unlikely((device_speed != CVMX_USB_SPEED_HIGH) &&
1386 (multi_count != 0)))
1387 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1388 if (cvmx_unlikely((hub_device_addr < 0) || (hub_device_addr > MAX_USB_ADDRESS)))
1389 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1390 if (cvmx_unlikely((hub_port < 0) || (hub_port > MAX_USB_HUB_PORT)))
1391 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
1392 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
1393 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
1395 /* Find a free pipe */
1396 pipe = usb->free_pipes.head;
1398 CVMX_USB_RETURN(CVMX_USB_NO_MEMORY);
1399 __cvmx_usb_remove_pipe(&usb->free_pipes, pipe);
1400 pipe->flags = flags | __CVMX_USB_PIPE_FLAGS_OPEN;
1401 if ((device_speed == CVMX_USB_SPEED_HIGH) &&
1402 (transfer_dir == CVMX_USB_DIRECTION_OUT) &&
1403 (transfer_type == CVMX_USB_TRANSFER_BULK))
1404 pipe->flags |= __CVMX_USB_PIPE_FLAGS_NEED_PING;
1405 pipe->device_addr = device_addr;
1406 pipe->endpoint_num = endpoint_num;
1407 pipe->device_speed = device_speed;
1408 pipe->max_packet = max_packet;
1409 pipe->transfer_type = transfer_type;
1410 pipe->transfer_dir = transfer_dir;
1411 /* All pipes use interval to rate limit NAK processing. Force an interval
1412 if one wasn't supplied */
1415 if (device_speed == CVMX_USB_SPEED_HIGH)
1416 pipe->interval = (uint64_t)interval * cvmx_sysinfo_get()->cpu_clock_hz / 8000;
1418 pipe->interval = (uint64_t)interval * cvmx_sysinfo_get()->cpu_clock_hz / 1000;
1419 pipe->multi_count = multi_count;
1420 pipe->hub_device_addr = hub_device_addr;
1421 pipe->hub_port = hub_port;
1422 pipe->pid_toggle = 0;
1423 pipe->next_tx_cycle = cvmx_read64_uint64(CVMX_IPD_CLK_COUNT) + pipe->interval;
1424 pipe->split_sc_frame = -1;
1425 __cvmx_usb_append_pipe(&usb->idle_pipes, pipe);
1427 /* We don't need to tell the hardware about this pipe yet since
1428 it doesn't have any submitted requests */
1430 CVMX_USB_RETURN(__cvmx_usb_get_pipe_handle(usb, pipe));
1436 * Perform channel specific setup for Control transactions. All
1437 * the generic stuff will already have been done in
1438 * __cvmx_usb_start_channel()
1440 * @param usb USB device state populated by
1441 * cvmx_usb_initialize().
1442 * @param channel Channel to setup
1443 * @param pipe Pipe for control transaction
1445 static void __cvmx_usb_start_channel_control(cvmx_usb_internal_state_t *usb,
1447 cvmx_usb_pipe_t *pipe)
1449 cvmx_usb_transaction_t *transaction = pipe->head;
1450 cvmx_usb_control_header_t *header = cvmx_phys_to_ptr(transaction->control_header);
1451 int bytes_to_transfer = transaction->buffer_length - transaction->actual_bytes;
1452 cvmx_usbcx_hctsizx_t usbc_hctsiz;
1454 CVMX_USB_LOG_CALLED();
1455 CVMX_USB_LOG_PARAM("%p", usb);
1456 CVMX_USB_LOG_PARAM("%d", channel);
1457 CVMX_USB_LOG_PARAM("%p", pipe);
1459 usbc_hctsiz.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HCTSIZX(channel, usb->index));
1461 switch (transaction->stage)
1463 case CVMX_USB_STAGE_NON_CONTROL:
1464 case CVMX_USB_STAGE_NON_CONTROL_SPLIT_COMPLETE:
1465 cvmx_dprintf("%s: ERROR - Non control stage\n", __FUNCTION__);
1467 case CVMX_USB_STAGE_SETUP:
1468 usbc_hctsiz.s.pid = 3; /* Setup */
1469 usbc_hctsiz.s.xfersize = sizeof(*header);
1470 /* All Control operations start with a setup going OUT */
1471 USB_SET_FIELD32(CVMX_USBCX_HCCHARX(channel, usb->index), cvmx_usbcx_hccharx_t, epdir, CVMX_USB_DIRECTION_OUT);
1472 /* Setup send the control header instead of the buffer data. The
1473 buffer data will be used in the next stage */
1474 __cvmx_usb_write_csr64(usb, CVMX_USBNX_DMA0_OUTB_CHN0(usb->index) + channel*8, transaction->control_header);
1476 case CVMX_USB_STAGE_SETUP_SPLIT_COMPLETE:
1477 usbc_hctsiz.s.pid = 3; /* Setup */
1478 usbc_hctsiz.s.xfersize = 0;
1479 /* All Control operations start with a setup going OUT */
1480 USB_SET_FIELD32(CVMX_USBCX_HCCHARX(channel, usb->index), cvmx_usbcx_hccharx_t, epdir, CVMX_USB_DIRECTION_OUT);
1481 USB_SET_FIELD32(CVMX_USBCX_HCSPLTX(channel, usb->index), cvmx_usbcx_hcspltx_t, compsplt, 1);
1483 case CVMX_USB_STAGE_DATA:
1484 usbc_hctsiz.s.pid = __cvmx_usb_get_data_pid(pipe);
1485 if (__cvmx_usb_pipe_needs_split(usb, pipe))
1487 usbc_hctsiz.s.xfersize = (header->s.request_type & 0x80) ? 0 : bytes_to_transfer;
1488 if (usbc_hctsiz.s.xfersize > pipe->max_packet)
1489 usbc_hctsiz.s.xfersize = pipe->max_packet;
1492 usbc_hctsiz.s.xfersize = bytes_to_transfer;
1493 USB_SET_FIELD32(CVMX_USBCX_HCCHARX(channel, usb->index),
1494 cvmx_usbcx_hccharx_t, epdir,
1495 ((header->s.request_type & 0x80) ?
1496 CVMX_USB_DIRECTION_IN :
1497 CVMX_USB_DIRECTION_OUT));
1499 case CVMX_USB_STAGE_DATA_SPLIT_COMPLETE:
1500 usbc_hctsiz.s.pid = __cvmx_usb_get_data_pid(pipe);
1501 usbc_hctsiz.s.xfersize = (header->s.request_type & 0x80) ? bytes_to_transfer : 0;
1502 USB_SET_FIELD32(CVMX_USBCX_HCCHARX(channel, usb->index),
1503 cvmx_usbcx_hccharx_t, epdir,
1504 ((header->s.request_type & 0x80) ?
1505 CVMX_USB_DIRECTION_IN :
1506 CVMX_USB_DIRECTION_OUT));
1507 USB_SET_FIELD32(CVMX_USBCX_HCSPLTX(channel, usb->index), cvmx_usbcx_hcspltx_t, compsplt, 1);
1509 case CVMX_USB_STAGE_STATUS:
1510 usbc_hctsiz.s.pid = __cvmx_usb_get_data_pid(pipe);
1511 usbc_hctsiz.s.xfersize = 0;
1512 USB_SET_FIELD32(CVMX_USBCX_HCCHARX(channel, usb->index), cvmx_usbcx_hccharx_t, epdir,
1513 ((header->s.request_type & 0x80) ?
1514 CVMX_USB_DIRECTION_OUT :
1515 CVMX_USB_DIRECTION_IN));
1517 case CVMX_USB_STAGE_STATUS_SPLIT_COMPLETE:
1518 usbc_hctsiz.s.pid = __cvmx_usb_get_data_pid(pipe);
1519 usbc_hctsiz.s.xfersize = 0;
1520 USB_SET_FIELD32(CVMX_USBCX_HCCHARX(channel, usb->index), cvmx_usbcx_hccharx_t, epdir,
1521 ((header->s.request_type & 0x80) ?
1522 CVMX_USB_DIRECTION_OUT :
1523 CVMX_USB_DIRECTION_IN));
1524 USB_SET_FIELD32(CVMX_USBCX_HCSPLTX(channel, usb->index), cvmx_usbcx_hcspltx_t, compsplt, 1);
1528 /* Set the number of packets needed for this transfer */
1529 usbc_hctsiz.s.pktcnt = (usbc_hctsiz.s.xfersize + pipe->max_packet - 1) / pipe->max_packet;
1530 if (!usbc_hctsiz.s.pktcnt)
1531 usbc_hctsiz.s.pktcnt = 1;
1533 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCTSIZX(channel, usb->index), usbc_hctsiz.u32);
1534 CVMX_USB_RETURN_NOTHING();
1540 * Start a channel to perform the pipe's head transaction
1542 * @param usb USB device state populated by
1543 * cvmx_usb_initialize().
1544 * @param channel Channel to setup
1545 * @param pipe Pipe to start
1547 static void __cvmx_usb_start_channel(cvmx_usb_internal_state_t *usb,
1549 cvmx_usb_pipe_t *pipe)
1551 cvmx_usb_transaction_t *transaction = pipe->head;
1552 cvmx_usbcx_hfnum_t usbc_hfnum;
1554 CVMX_USB_LOG_CALLED();
1555 CVMX_USB_LOG_PARAM("%p", usb);
1556 CVMX_USB_LOG_PARAM("%d", channel);
1557 CVMX_USB_LOG_PARAM("%p", pipe);
1559 if (cvmx_unlikely((usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_TRANSFERS) ||
1560 (pipe->flags & CVMX_USB_PIPE_FLAGS_DEBUG_TRANSFERS)))
1561 cvmx_dprintf("%s: Channel %d started. Pipe %d transaction %d stage %d\n",
1562 __FUNCTION__, channel, __cvmx_usb_get_pipe_handle(usb, pipe),
1563 __cvmx_usb_get_submit_handle(usb, transaction),
1564 transaction->stage);
1566 /* Make sure all writes to the DMA region get flushed */
1569 /* Read the current frame number for use with split, INTERRUPT, and ISO
1571 usbc_hfnum.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HFNUM(usb->index));
1573 /* Attach the channel to the pipe */
1574 usb->pipe_for_channel[channel] = pipe;
1575 pipe->channel = channel;
1576 pipe->flags |= __CVMX_USB_PIPE_FLAGS_SCHEDULED;
1578 /* Mark this channel as in use */
1579 usb->idle_hardware_channels &= ~(1<<channel);
1581 /* Enable the channel interrupt bits */
1583 cvmx_usbcx_hcintx_t usbc_hcint;
1585 /* Clear all channel status bits */
1586 usbc_hcint.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HCINTX(channel, usb->index));
1587 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCINTX(channel, usb->index), usbc_hcint.u32);
1590 /* Setup the locations the DMA engines use */
1592 uint64_t dma_address = transaction->buffer + transaction->actual_bytes;
1593 if (transaction->type == CVMX_USB_TRANSFER_ISOCHRONOUS)
1594 dma_address = transaction->buffer + transaction->iso_packets[0].offset + transaction->actual_bytes;
1595 __cvmx_usb_write_csr64(usb, CVMX_USBNX_DMA0_OUTB_CHN0(usb->index) + channel*8, dma_address);
1596 __cvmx_usb_write_csr64(usb, CVMX_USBNX_DMA0_INB_CHN0(usb->index) + channel*8, dma_address);
1599 /* Setup both the size of the transfer and the SPLIT characteristics */
1601 cvmx_usbcx_hcspltx_t usbc_hcsplt = {.u32 = 0};
1602 cvmx_usbcx_hctsizx_t usbc_hctsiz = {.u32 = 0};
1603 int bytes_to_transfer = transaction->buffer_length - transaction->actual_bytes;
1605 /* ISOCHRONOUS transactions store each individual transfer size in the
1606 packet structure, not the global buffer_length */
1607 if (transaction->type == CVMX_USB_TRANSFER_ISOCHRONOUS)
1608 bytes_to_transfer = transaction->iso_packets[0].length - transaction->actual_bytes;
1610 /* We need to do split transactions when we are talking to non high
1611 speed devices that are behind a high speed hub */
1612 if (__cvmx_usb_pipe_needs_split(usb, pipe))
1614 /* On the start split phase (stage is even) record the frame number we
1615 will need to send the split complete. We only store the lower two bits
1616 since the time ahead can only be two frames */
1617 if ((transaction->stage&1) == 0)
1619 if (transaction->type == CVMX_USB_TRANSFER_BULK)
1620 pipe->split_sc_frame = (usbc_hfnum.s.frnum + 1) & 0x7f;
1622 pipe->split_sc_frame = (usbc_hfnum.s.frnum + 2) & 0x7f;
1625 pipe->split_sc_frame = -1;
1627 usbc_hcsplt.s.spltena = 1;
1628 usbc_hcsplt.s.hubaddr = pipe->hub_device_addr;
1629 usbc_hcsplt.s.prtaddr = pipe->hub_port;
1630 usbc_hcsplt.s.compsplt = (transaction->stage == CVMX_USB_STAGE_NON_CONTROL_SPLIT_COMPLETE);
1632 /* SPLIT transactions can only ever transmit one data packet so
1633 limit the transfer size to the max packet size */
1634 if (bytes_to_transfer > pipe->max_packet)
1635 bytes_to_transfer = pipe->max_packet;
1637 /* ISOCHRONOUS OUT splits are unique in that they limit
1638 data transfers to 188 byte chunks representing the
1639 begin/middle/end of the data or all */
1640 if (!usbc_hcsplt.s.compsplt &&
1641 (pipe->transfer_dir == CVMX_USB_DIRECTION_OUT) &&
1642 (pipe->transfer_type == CVMX_USB_TRANSFER_ISOCHRONOUS))
1644 /* See if we've started this tranfer and sent data */
1645 if (transaction->actual_bytes == 0)
1647 /* Nothing sent yet, this is either a begin or the
1649 if (bytes_to_transfer <= 188)
1650 usbc_hcsplt.s.xactpos = 3; /* Entire payload in one go */
1652 usbc_hcsplt.s.xactpos = 2; /* First part of payload */
1656 /* Continuing the previous data, we must either be
1657 in the middle or at the end */
1658 if (bytes_to_transfer <= 188)
1659 usbc_hcsplt.s.xactpos = 1; /* End of payload */
1661 usbc_hcsplt.s.xactpos = 0; /* Middle of payload */
1663 /* Again, the transfer size is limited to 188 bytes */
1664 if (bytes_to_transfer > 188)
1665 bytes_to_transfer = 188;
1669 usbc_hctsiz.s.xfersize = bytes_to_transfer;
1670 usbc_hctsiz.s.pktcnt = (bytes_to_transfer + pipe->max_packet - 1) / pipe->max_packet;
1671 if (!usbc_hctsiz.s.pktcnt)
1672 usbc_hctsiz.s.pktcnt = 1;
1674 /* Update the DATA0/DATA1 toggle */
1675 usbc_hctsiz.s.pid = __cvmx_usb_get_data_pid(pipe);
1676 /* High speed pipes may need a hardware ping before they start */
1677 if (pipe->flags & __CVMX_USB_PIPE_FLAGS_NEED_PING)
1678 usbc_hctsiz.s.dopng = 1;
1680 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCSPLTX(channel, usb->index), usbc_hcsplt.u32);
1681 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCTSIZX(channel, usb->index), usbc_hctsiz.u32);
1684 /* Setup the Host Channel Characteristics Register */
1686 cvmx_usbcx_hccharx_t usbc_hcchar = {.u32 = 0};
1688 /* Make all transfers start on the next frame and not this one. This
1689 way the time we spend processing doesn't affect USB timing */
1690 usbc_hcchar.s.oddfrm = !(usbc_hfnum.s.frnum&1);
1692 /* Set the number of back to back packets allowed by this endpoint.
1693 Split transactions interpret "ec" as the number of immediate
1694 retries of failure. These retries happen too quickly, so we
1695 disable these entirely for splits */
1696 if (__cvmx_usb_pipe_needs_split(usb, pipe))
1697 usbc_hcchar.s.ec = 1;
1698 else if (pipe->multi_count < 1)
1699 usbc_hcchar.s.ec = 1;
1700 else if (pipe->multi_count > 3)
1701 usbc_hcchar.s.ec = 3;
1703 usbc_hcchar.s.ec = pipe->multi_count;
1705 /* Set the rest of the endpoint specific settings */
1706 usbc_hcchar.s.devaddr = pipe->device_addr;
1707 usbc_hcchar.s.eptype = transaction->type;
1708 usbc_hcchar.s.lspddev = (pipe->device_speed == CVMX_USB_SPEED_LOW);
1709 usbc_hcchar.s.epdir = pipe->transfer_dir;
1710 usbc_hcchar.s.epnum = pipe->endpoint_num;
1711 usbc_hcchar.s.mps = pipe->max_packet;
1712 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCCHARX(channel, usb->index), usbc_hcchar.u32);
1715 /* Do transaction type specific fixups as needed */
1716 switch (transaction->type)
1718 case CVMX_USB_TRANSFER_CONTROL:
1719 __cvmx_usb_start_channel_control(usb, channel, pipe);
1721 case CVMX_USB_TRANSFER_BULK:
1722 case CVMX_USB_TRANSFER_INTERRUPT:
1724 case CVMX_USB_TRANSFER_ISOCHRONOUS:
1725 if (!__cvmx_usb_pipe_needs_split(usb, pipe))
1727 /* ISO transactions require differnet PIDs depending on direction
1728 and how many packets are needed */
1729 if (pipe->transfer_dir == CVMX_USB_DIRECTION_OUT)
1731 if (pipe->multi_count < 2) /* Need DATA0 */
1732 USB_SET_FIELD32(CVMX_USBCX_HCTSIZX(channel, usb->index), cvmx_usbcx_hctsizx_t, pid, 0);
1733 else /* Need MDATA */
1734 USB_SET_FIELD32(CVMX_USBCX_HCTSIZX(channel, usb->index), cvmx_usbcx_hctsizx_t, pid, 3);
1740 cvmx_usbcx_hctsizx_t usbc_hctsiz = {.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HCTSIZX(channel, usb->index))};
1741 transaction->xfersize = usbc_hctsiz.s.xfersize;
1742 transaction->pktcnt = usbc_hctsiz.s.pktcnt;
1744 USB_SET_FIELD32(CVMX_USBCX_HCCHARX(channel, usb->index), cvmx_usbcx_hccharx_t, chena, 1);
1745 CVMX_USB_RETURN_NOTHING();
1751 * Find a pipe that is ready to be scheduled to hardware.
1753 * @param list Pipe list to search
1754 * @param usbc_hfnum Current USB frame number
1755 * @param current_cycle
1756 * Cycle counter to use as a time reference.
1758 * @return Pipe or NULL if none are ready
1760 static cvmx_usb_pipe_t *__cvmx_usb_find_ready_pipe(cvmx_usb_pipe_list_t *list, cvmx_usbcx_hfnum_t usbc_hfnum, uint64_t current_cycle)
1762 cvmx_usb_pipe_t *pipe = list->head;
1765 if (!(pipe->flags & __CVMX_USB_PIPE_FLAGS_SCHEDULED) && pipe->head &&
1766 (pipe->next_tx_cycle <= current_cycle) &&
1767 ((pipe->split_sc_frame == -1) || ((((int)usbc_hfnum.s.frnum - (int)pipe->split_sc_frame) & 0x7f) < 0x40)))
1769 CVMX_PREFETCH(pipe, 128);
1770 CVMX_PREFETCH(pipe->head, 0);
1781 * Called whenever a pipe might need to be scheduled to the
1784 * @param usb USB device state populated by
1785 * cvmx_usb_initialize().
1786 * @param is_sof True if this schedule was called on a SOF interrupt.
1788 static void __cvmx_usb_schedule(cvmx_usb_internal_state_t *usb, int is_sof)
1791 cvmx_usb_pipe_t *pipe;
1792 cvmx_usbcx_hfnum_t usbc_hfnum;
1793 uint64_t current_cycle = cvmx_read64_uint64(CVMX_IPD_CLK_COUNT);
1795 CVMX_USB_LOG_CALLED();
1796 CVMX_USB_LOG_PARAM("%p", usb);
1798 usbc_hfnum.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HFNUM(usb->index));
1800 while (usb->idle_hardware_channels)
1802 /* Find an idle channel */
1803 CVMX_CLZ(channel, usb->idle_hardware_channels);
1804 channel = 31 - channel;
1805 if (cvmx_unlikely(channel > 7))
1807 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
1808 cvmx_dprintf("%s: Idle hardware channels has a channel higher than 7. This is wrong\n", __FUNCTION__);
1812 /* Find a pipe needing service */
1816 /* Only process periodic pipes on SOF interrupts. This way we are
1817 sure that the periodic data is sent in the beginning of the
1819 pipe = __cvmx_usb_find_ready_pipe(usb->active_pipes + CVMX_USB_TRANSFER_ISOCHRONOUS, usbc_hfnum, current_cycle);
1820 if (cvmx_likely(!pipe))
1821 pipe = __cvmx_usb_find_ready_pipe(usb->active_pipes + CVMX_USB_TRANSFER_INTERRUPT, usbc_hfnum, current_cycle);
1823 if (cvmx_likely(!pipe))
1825 pipe = __cvmx_usb_find_ready_pipe(usb->active_pipes + CVMX_USB_TRANSFER_CONTROL, usbc_hfnum, current_cycle);
1826 if (cvmx_likely(!pipe))
1827 pipe = __cvmx_usb_find_ready_pipe(usb->active_pipes + CVMX_USB_TRANSFER_BULK, usbc_hfnum, current_cycle);
1832 CVMX_USB_LOG_PARAM("%d", channel);
1833 CVMX_USB_LOG_PARAM("%p", pipe);
1835 if (cvmx_unlikely((usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_TRANSFERS) ||
1836 (pipe->flags & CVMX_USB_PIPE_FLAGS_DEBUG_TRANSFERS)))
1838 cvmx_usb_transaction_t *transaction = pipe->head;
1839 const cvmx_usb_control_header_t *header = (transaction->control_header) ? cvmx_phys_to_ptr(transaction->control_header) : NULL;
1840 const char *dir = (pipe->transfer_dir == CVMX_USB_DIRECTION_IN) ? "IN" : "OUT";
1842 switch (pipe->transfer_type)
1844 case CVMX_USB_TRANSFER_CONTROL:
1846 dir = (header->s.request_type & 0x80) ? "IN" : "OUT";
1848 case CVMX_USB_TRANSFER_ISOCHRONOUS:
1849 type = "ISOCHRONOUS";
1851 case CVMX_USB_TRANSFER_BULK:
1854 default: /* CVMX_USB_TRANSFER_INTERRUPT */
1858 cvmx_dprintf("%s: Starting pipe %d, transaction %d on channel %d. %s %s len=%d header=0x%llx\n",
1859 __FUNCTION__, __cvmx_usb_get_pipe_handle(usb, pipe),
1860 __cvmx_usb_get_submit_handle(usb, transaction),
1862 transaction->buffer_length,
1863 (header) ? (unsigned long long)header->u64 : 0ull);
1865 __cvmx_usb_start_channel(usb, channel, pipe);
1867 CVMX_USB_RETURN_NOTHING();
1873 * Call a user's callback for a specific reason.
1875 * @param usb USB device state populated by
1876 * cvmx_usb_initialize().
1877 * @param pipe Pipe the callback is for or NULL
1878 * @param transaction
1879 * Transaction the callback is for or NULL
1880 * @param reason Reason this callback is being called
1881 * @param complete_code
1882 * Completion code for the transaction, if any
1884 static void __cvmx_usb_perform_callback(cvmx_usb_internal_state_t *usb,
1885 cvmx_usb_pipe_t *pipe,
1886 cvmx_usb_transaction_t *transaction,
1887 cvmx_usb_callback_t reason,
1888 cvmx_usb_complete_t complete_code)
1890 cvmx_usb_callback_func_t callback = usb->callback[reason];
1891 void *user_data = usb->callback_data[reason];
1892 int submit_handle = -1;
1893 int pipe_handle = -1;
1894 int bytes_transferred = 0;
1897 pipe_handle = __cvmx_usb_get_pipe_handle(usb, pipe);
1901 submit_handle = __cvmx_usb_get_submit_handle(usb, transaction);
1902 bytes_transferred = transaction->actual_bytes;
1903 /* Transactions are allowed to override the default callback */
1904 if ((reason == CVMX_USB_CALLBACK_TRANSFER_COMPLETE) && transaction->callback)
1906 callback = transaction->callback;
1907 user_data = transaction->callback_data;
1914 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CALLBACKS))
1915 cvmx_dprintf("%*s%s: calling callback %p(usb=%p, complete_code=%s, "
1916 "pipe_handle=%d, submit_handle=%d, bytes_transferred=%d, user_data=%p);\n",
1917 2*usb->indent, "", __FUNCTION__, callback, usb,
1918 __cvmx_usb_complete_to_string(complete_code),
1919 pipe_handle, submit_handle, bytes_transferred, user_data);
1921 callback((cvmx_usb_state_t *)usb, reason, complete_code, pipe_handle, submit_handle,
1922 bytes_transferred, user_data);
1924 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_CALLBACKS))
1925 cvmx_dprintf("%*s%s: callback %p complete\n", 2*usb->indent, "",
1926 __FUNCTION__, callback);
1932 * Signal the completion of a transaction and free it. The
1933 * transaction will be removed from the pipe transaction list.
1935 * @param usb USB device state populated by
1936 * cvmx_usb_initialize().
1937 * @param pipe Pipe the transaction is on
1938 * @param transaction
1939 * Transaction that completed
1940 * @param complete_code
1943 static void __cvmx_usb_perform_complete(cvmx_usb_internal_state_t * usb,
1944 cvmx_usb_pipe_t *pipe,
1945 cvmx_usb_transaction_t *transaction,
1946 cvmx_usb_complete_t complete_code)
1948 CVMX_USB_LOG_CALLED();
1949 CVMX_USB_LOG_PARAM("%p", usb);
1950 CVMX_USB_LOG_PARAM("%p", pipe);
1951 CVMX_USB_LOG_PARAM("%p", transaction);
1952 CVMX_USB_LOG_PARAM("%d", complete_code);
1954 /* Isochronous transactions need extra processing as they might not be done
1955 after a single data transfer */
1956 if (cvmx_unlikely(transaction->type == CVMX_USB_TRANSFER_ISOCHRONOUS))
1958 /* Update the number of bytes transfered in this ISO packet */
1959 transaction->iso_packets[0].length = transaction->actual_bytes;
1960 transaction->iso_packets[0].status = complete_code;
1962 /* If there are more ISOs pending and we suceeded, schedule the next
1964 if ((transaction->iso_number_packets > 1) && (complete_code == CVMX_USB_COMPLETE_SUCCESS))
1966 transaction->actual_bytes = 0; /* No bytes transfered for this packet as of yet */
1967 transaction->iso_number_packets--; /* One less ISO waiting to transfer */
1968 transaction->iso_packets++; /* Increment to the next location in our packet array */
1969 transaction->stage = CVMX_USB_STAGE_NON_CONTROL;
1974 /* Remove the transaction from the pipe list */
1975 if (transaction->next)
1976 transaction->next->prev = transaction->prev;
1978 pipe->tail = transaction->prev;
1979 if (transaction->prev)
1980 transaction->prev->next = transaction->next;
1982 pipe->head = transaction->next;
1985 __cvmx_usb_remove_pipe(usb->active_pipes + pipe->transfer_type, pipe);
1986 __cvmx_usb_append_pipe(&usb->idle_pipes, pipe);
1989 __cvmx_usb_perform_callback(usb, pipe, transaction,
1990 CVMX_USB_CALLBACK_TRANSFER_COMPLETE,
1992 __cvmx_usb_free_transaction(usb, transaction);
1993 /* Disable SOF interrupts if we don't have any pending transactions */
1994 usb->active_transactions--;
1995 if (usb->active_transactions == 0)
1996 USB_SET_FIELD32(CVMX_USBCX_GINTMSK(usb->index), cvmx_usbcx_gintmsk_t, sofmsk, 0);
1998 CVMX_USB_RETURN_NOTHING();
2004 * Submit a usb transaction to a pipe. Called for all types
2008 * @param pipe_handle
2009 * Which pipe to submit to. Will be validated in this function.
2010 * @param type Transaction type
2011 * @param flags Flags for the transaction
2012 * @param buffer User buffer for the transaction
2013 * @param buffer_length
2014 * User buffer's length in bytes
2015 * @param control_header
2016 * For control transactions, the 8 byte standard header
2017 * @param iso_start_frame
2018 * For ISO transactiosn, the start frame
2019 * @param iso_number_packets
2020 * For ISO, the number of packet in the transaction.
2021 * @param iso_packets
2022 * A description of each ISO packet
2023 * @param callback User callback to call when the transaction completes
2024 * @param user_data User's data for the callback
2026 * @return Submit handle or negative on failure. Matches the result
2027 * in the external API.
2029 static int __cvmx_usb_submit_transaction(cvmx_usb_internal_state_t *usb,
2031 cvmx_usb_transfer_t type,
2035 uint64_t control_header,
2036 int iso_start_frame,
2037 int iso_number_packets,
2038 cvmx_usb_iso_packet_t *iso_packets,
2039 cvmx_usb_callback_func_t callback,
2043 cvmx_usb_transaction_t *transaction;
2044 cvmx_usb_pipe_t *pipe = usb->pipe + pipe_handle;
2046 CVMX_USB_LOG_CALLED();
2047 if (cvmx_unlikely((pipe_handle < 0) || (pipe_handle >= MAX_PIPES)))
2048 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2049 /* Fail if the pipe isn't open */
2050 if (cvmx_unlikely((pipe->flags & __CVMX_USB_PIPE_FLAGS_OPEN) == 0))
2051 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2052 if (cvmx_unlikely(pipe->transfer_type != type))
2053 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2055 transaction = __cvmx_usb_alloc_transaction(usb);
2056 if (cvmx_unlikely(!transaction))
2057 CVMX_USB_RETURN(CVMX_USB_NO_MEMORY);
2059 /* Enable SOF interrupts now that we have pending transactions */
2060 if (usb->active_transactions == 0)
2061 USB_SET_FIELD32(CVMX_USBCX_GINTMSK(usb->index), cvmx_usbcx_gintmsk_t, sofmsk, 1);
2062 usb->active_transactions++;
2064 transaction->type = type;
2065 transaction->flags |= flags;
2066 transaction->buffer = buffer;
2067 transaction->buffer_length = buffer_length;
2068 transaction->control_header = control_header;
2069 transaction->iso_start_frame = iso_start_frame; // FIXME: This is not used, implement it
2070 transaction->iso_number_packets = iso_number_packets;
2071 transaction->iso_packets = iso_packets;
2072 transaction->callback = callback;
2073 transaction->callback_data = user_data;
2074 if (transaction->type == CVMX_USB_TRANSFER_CONTROL)
2075 transaction->stage = CVMX_USB_STAGE_SETUP;
2077 transaction->stage = CVMX_USB_STAGE_NON_CONTROL;
2079 transaction->next = NULL;
2082 transaction->prev = pipe->tail;
2083 transaction->prev->next = transaction;
2087 transaction->prev = NULL;
2088 pipe->head = transaction;
2089 __cvmx_usb_remove_pipe(&usb->idle_pipes, pipe);
2090 __cvmx_usb_append_pipe(usb->active_pipes + pipe->transfer_type, pipe);
2092 pipe->tail = transaction;
2094 submit_handle = __cvmx_usb_get_submit_handle(usb, transaction);
2096 /* We may need to schedule the pipe if this was the head of the pipe */
2097 if (!transaction->prev)
2098 __cvmx_usb_schedule(usb, 0);
2100 CVMX_USB_RETURN(submit_handle);
2105 * Call to submit a USB Bulk transfer to a pipe.
2107 * @param state USB device state populated by
2108 * cvmx_usb_initialize().
2109 * @param pipe_handle
2110 * Handle to the pipe for the transfer.
2111 * @param buffer Physical address of the data buffer in
2112 * memory. Note that this is NOT A POINTER, but
2113 * the full 64bit physical address of the
2114 * buffer. This may be zero if buffer_length is
2116 * @param buffer_length
2117 * Length of buffer in bytes.
2118 * @param callback Function to call when this transaction
2119 * completes. If the return value of this
2120 * function isn't an error, then this function
2121 * is guaranteed to be called when the
2122 * transaction completes. If this parameter is
2123 * NULL, then the generic callback registered
2124 * through cvmx_usb_register_callback is
2125 * called. If both are NULL, then there is no
2126 * way to know when a transaction completes.
2127 * @param user_data User supplied data returned when the
2128 * callback is called. This is only used if
2129 * callback in not NULL.
2131 * @return A submitted transaction handle or negative on
2132 * failure. Negative values are failure codes from
2133 * cvmx_usb_status_t.
2135 int cvmx_usb_submit_bulk(cvmx_usb_state_t *state, int pipe_handle,
2136 uint64_t buffer, int buffer_length,
2137 cvmx_usb_callback_func_t callback,
2141 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2143 CVMX_USB_LOG_CALLED();
2144 CVMX_USB_LOG_PARAM("%p", state);
2145 CVMX_USB_LOG_PARAM("%d", pipe_handle);
2146 CVMX_USB_LOG_PARAM("0x%llx", (unsigned long long)buffer);
2147 CVMX_USB_LOG_PARAM("%d", buffer_length);
2149 /* Pipe handle checking is done later in a common place */
2150 if (cvmx_unlikely(!buffer))
2151 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2152 if (cvmx_unlikely(buffer_length < 0))
2153 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2154 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
2155 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
2157 submit_handle = __cvmx_usb_submit_transaction(usb, pipe_handle,
2158 CVMX_USB_TRANSFER_BULK,
2162 0, /* control_header */
2163 0, /* iso_start_frame */
2164 0, /* iso_number_packets */
2165 NULL, /* iso_packets */
2168 CVMX_USB_RETURN(submit_handle);
2173 * Call to submit a USB Interrupt transfer to a pipe.
2175 * @param state USB device state populated by
2176 * cvmx_usb_initialize().
2177 * @param pipe_handle
2178 * Handle to the pipe for the transfer.
2179 * @param buffer Physical address of the data buffer in
2180 * memory. Note that this is NOT A POINTER, but
2181 * the full 64bit physical address of the
2182 * buffer. This may be zero if buffer_length is
2184 * @param buffer_length
2185 * Length of buffer in bytes.
2186 * @param callback Function to call when this transaction
2187 * completes. If the return value of this
2188 * function isn't an error, then this function
2189 * is guaranteed to be called when the
2190 * transaction completes. If this parameter is
2191 * NULL, then the generic callback registered
2192 * through cvmx_usb_register_callback is
2193 * called. If both are NULL, then there is no
2194 * way to know when a transaction completes.
2195 * @param user_data User supplied data returned when the
2196 * callback is called. This is only used if
2197 * callback in not NULL.
2199 * @return A submitted transaction handle or negative on
2200 * failure. Negative values are failure codes from
2201 * cvmx_usb_status_t.
2203 int cvmx_usb_submit_interrupt(cvmx_usb_state_t *state, int pipe_handle,
2204 uint64_t buffer, int buffer_length,
2205 cvmx_usb_callback_func_t callback,
2209 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2211 CVMX_USB_LOG_CALLED();
2212 CVMX_USB_LOG_PARAM("%p", state);
2213 CVMX_USB_LOG_PARAM("%d", pipe_handle);
2214 CVMX_USB_LOG_PARAM("0x%llx", (unsigned long long)buffer);
2215 CVMX_USB_LOG_PARAM("%d", buffer_length);
2217 /* Pipe handle checking is done later in a common place */
2218 if (cvmx_unlikely(!buffer))
2219 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2220 if (cvmx_unlikely(buffer_length < 0))
2221 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2222 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
2223 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
2225 submit_handle = __cvmx_usb_submit_transaction(usb, pipe_handle,
2226 CVMX_USB_TRANSFER_INTERRUPT,
2230 0, /* control_header */
2231 0, /* iso_start_frame */
2232 0, /* iso_number_packets */
2233 NULL, /* iso_packets */
2236 CVMX_USB_RETURN(submit_handle);
2241 * Call to submit a USB Control transfer to a pipe.
2243 * @param state USB device state populated by
2244 * cvmx_usb_initialize().
2245 * @param pipe_handle
2246 * Handle to the pipe for the transfer.
2247 * @param control_header
2248 * USB 8 byte control header physical address.
2249 * Note that this is NOT A POINTER, but the
2250 * full 64bit physical address of the buffer.
2251 * @param buffer Physical address of the data buffer in
2252 * memory. Note that this is NOT A POINTER, but
2253 * the full 64bit physical address of the
2254 * buffer. This may be zero if buffer_length is
2256 * @param buffer_length
2257 * Length of buffer in bytes.
2258 * @param callback Function to call when this transaction
2259 * completes. If the return value of this
2260 * function isn't an error, then this function
2261 * is guaranteed to be called when the
2262 * transaction completes. If this parameter is
2263 * NULL, then the generic callback registered
2264 * through cvmx_usb_register_callback is
2265 * called. If both are NULL, then there is no
2266 * way to know when a transaction completes.
2267 * @param user_data User supplied data returned when the
2268 * callback is called. This is only used if
2269 * callback in not NULL.
2271 * @return A submitted transaction handle or negative on
2272 * failure. Negative values are failure codes from
2273 * cvmx_usb_status_t.
2275 int cvmx_usb_submit_control(cvmx_usb_state_t *state, int pipe_handle,
2276 uint64_t control_header,
2277 uint64_t buffer, int buffer_length,
2278 cvmx_usb_callback_func_t callback,
2282 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2283 cvmx_usb_control_header_t *header = cvmx_phys_to_ptr(control_header);
2285 CVMX_USB_LOG_CALLED();
2286 CVMX_USB_LOG_PARAM("%p", state);
2287 CVMX_USB_LOG_PARAM("%d", pipe_handle);
2288 CVMX_USB_LOG_PARAM("0x%llx", (unsigned long long)control_header);
2289 CVMX_USB_LOG_PARAM("0x%llx", (unsigned long long)buffer);
2290 CVMX_USB_LOG_PARAM("%d", buffer_length);
2292 /* Pipe handle checking is done later in a common place */
2293 if (cvmx_unlikely(!control_header))
2294 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2295 /* Some drivers send a buffer with a zero length. God only knows why */
2296 if (cvmx_unlikely(buffer && (buffer_length < 0)))
2297 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2298 if (cvmx_unlikely(!buffer && (buffer_length != 0)))
2299 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2300 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
2301 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
2302 if ((header->s.request_type & 0x80) == 0)
2303 buffer_length = cvmx_le16_to_cpu(header->s.length);
2305 submit_handle = __cvmx_usb_submit_transaction(usb, pipe_handle,
2306 CVMX_USB_TRANSFER_CONTROL,
2311 0, /* iso_start_frame */
2312 0, /* iso_number_packets */
2313 NULL, /* iso_packets */
2316 CVMX_USB_RETURN(submit_handle);
2321 * Call to submit a USB Isochronous transfer to a pipe.
2323 * @param state USB device state populated by
2324 * cvmx_usb_initialize().
2325 * @param pipe_handle
2326 * Handle to the pipe for the transfer.
2327 * @param start_frame
2328 * Number of frames into the future to schedule
2330 * @param flags Flags to control the transfer. See
2331 * cvmx_usb_isochronous_flags_t for the flag
2333 * @param number_packets
2334 * Number of sequential packets to transfer.
2335 * "packets" is a pointer to an array of this
2336 * many packet structures.
2337 * @param packets Description of each transfer packet as
2338 * defined by cvmx_usb_iso_packet_t. The array
2339 * pointed to here must stay valid until the
2340 * complete callback is called.
2341 * @param buffer Physical address of the data buffer in
2342 * memory. Note that this is NOT A POINTER, but
2343 * the full 64bit physical address of the
2344 * buffer. This may be zero if buffer_length is
2346 * @param buffer_length
2347 * Length of buffer in bytes.
2348 * @param callback Function to call when this transaction
2349 * completes. If the return value of this
2350 * function isn't an error, then this function
2351 * is guaranteed to be called when the
2352 * transaction completes. If this parameter is
2353 * NULL, then the generic callback registered
2354 * through cvmx_usb_register_callback is
2355 * called. If both are NULL, then there is no
2356 * way to know when a transaction completes.
2357 * @param user_data User supplied data returned when the
2358 * callback is called. This is only used if
2359 * callback in not NULL.
2361 * @return A submitted transaction handle or negative on
2362 * failure. Negative values are failure codes from
2363 * cvmx_usb_status_t.
2365 int cvmx_usb_submit_isochronous(cvmx_usb_state_t *state, int pipe_handle,
2366 int start_frame, int flags,
2368 cvmx_usb_iso_packet_t packets[],
2369 uint64_t buffer, int buffer_length,
2370 cvmx_usb_callback_func_t callback,
2374 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2376 CVMX_USB_LOG_CALLED();
2377 CVMX_USB_LOG_PARAM("%p", state);
2378 CVMX_USB_LOG_PARAM("%d", pipe_handle);
2379 CVMX_USB_LOG_PARAM("%d", start_frame);
2380 CVMX_USB_LOG_PARAM("0x%x", flags);
2381 CVMX_USB_LOG_PARAM("%d", number_packets);
2382 CVMX_USB_LOG_PARAM("%p", packets);
2383 CVMX_USB_LOG_PARAM("0x%llx", (unsigned long long)buffer);
2384 CVMX_USB_LOG_PARAM("%d", buffer_length);
2386 /* Pipe handle checking is done later in a common place */
2387 if (cvmx_unlikely(start_frame < 0))
2388 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2389 if (cvmx_unlikely(flags & ~(CVMX_USB_ISOCHRONOUS_FLAGS_ALLOW_SHORT | CVMX_USB_ISOCHRONOUS_FLAGS_ASAP)))
2390 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2391 if (cvmx_unlikely(number_packets < 1))
2392 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2393 if (cvmx_unlikely(!packets))
2394 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2395 if (cvmx_unlikely(!buffer))
2396 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2397 if (cvmx_unlikely(buffer_length < 0))
2398 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2399 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
2400 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
2402 submit_handle = __cvmx_usb_submit_transaction(usb, pipe_handle,
2403 CVMX_USB_TRANSFER_ISOCHRONOUS,
2407 0, /* control_header */
2413 CVMX_USB_RETURN(submit_handle);
2418 * Cancel one outstanding request in a pipe. Canceling a request
2419 * can fail if the transaction has already completed before cancel
2420 * is called. Even after a successful cancel call, it may take
2421 * a frame or two for the cvmx_usb_poll() function to call the
2422 * associated callback.
2424 * @param state USB device state populated by
2425 * cvmx_usb_initialize().
2426 * @param pipe_handle
2427 * Pipe handle to cancel requests in.
2428 * @param submit_handle
2429 * Handle to transaction to cancel, returned by the submit function.
2431 * @return CVMX_USB_SUCCESS or a negative error code defined in
2432 * cvmx_usb_status_t.
2434 cvmx_usb_status_t cvmx_usb_cancel(cvmx_usb_state_t *state, int pipe_handle,
2437 cvmx_usb_transaction_t *transaction;
2438 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2439 cvmx_usb_pipe_t *pipe = usb->pipe + pipe_handle;
2441 CVMX_USB_LOG_CALLED();
2442 CVMX_USB_LOG_PARAM("%p", state);
2443 CVMX_USB_LOG_PARAM("%d", pipe_handle);
2444 CVMX_USB_LOG_PARAM("%d", submit_handle);
2446 if (cvmx_unlikely((pipe_handle < 0) || (pipe_handle >= MAX_PIPES)))
2447 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2448 if (cvmx_unlikely((submit_handle < 0) || (submit_handle >= MAX_TRANSACTIONS)))
2449 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2450 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
2451 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
2453 /* Fail if the pipe isn't open */
2454 if (cvmx_unlikely((pipe->flags & __CVMX_USB_PIPE_FLAGS_OPEN) == 0))
2455 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2457 transaction = usb->transaction + submit_handle;
2459 /* Fail if this transaction already completed */
2460 if (cvmx_unlikely((transaction->flags & __CVMX_USB_TRANSACTION_FLAGS_IN_USE) == 0))
2461 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2463 /* If the transaction is the HEAD of the queue and scheduled. We need to
2465 if ((pipe->head == transaction) &&
2466 (pipe->flags & __CVMX_USB_PIPE_FLAGS_SCHEDULED))
2468 cvmx_usbcx_hccharx_t usbc_hcchar;
2470 usb->pipe_for_channel[pipe->channel] = NULL;
2471 pipe->flags &= ~__CVMX_USB_PIPE_FLAGS_SCHEDULED;
2475 usbc_hcchar.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HCCHARX(pipe->channel, usb->index));
2476 /* If the channel isn't enabled then the transaction already completed */
2477 if (usbc_hcchar.s.chena)
2479 usbc_hcchar.s.chdis = 1;
2480 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCCHARX(pipe->channel, usb->index), usbc_hcchar.u32);
2483 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_CANCEL);
2484 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
2489 * Cancel all outstanding requests in a pipe. Logically all this
2490 * does is call cvmx_usb_cancel() in a loop.
2492 * @param state USB device state populated by
2493 * cvmx_usb_initialize().
2494 * @param pipe_handle
2495 * Pipe handle to cancel requests in.
2497 * @return CVMX_USB_SUCCESS or a negative error code defined in
2498 * cvmx_usb_status_t.
2500 cvmx_usb_status_t cvmx_usb_cancel_all(cvmx_usb_state_t *state, int pipe_handle)
2502 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2503 cvmx_usb_pipe_t *pipe = usb->pipe + pipe_handle;
2505 CVMX_USB_LOG_CALLED();
2506 CVMX_USB_LOG_PARAM("%p", state);
2507 CVMX_USB_LOG_PARAM("%d", pipe_handle);
2508 if (cvmx_unlikely((pipe_handle < 0) || (pipe_handle >= MAX_PIPES)))
2509 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2510 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
2511 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
2513 /* Fail if the pipe isn't open */
2514 if (cvmx_unlikely((pipe->flags & __CVMX_USB_PIPE_FLAGS_OPEN) == 0))
2515 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2517 /* Simply loop through and attempt to cancel each transaction */
2520 cvmx_usb_status_t result = cvmx_usb_cancel(state, pipe_handle,
2521 __cvmx_usb_get_submit_handle(usb, pipe->head));
2522 if (cvmx_unlikely(result != CVMX_USB_SUCCESS))
2523 CVMX_USB_RETURN(result);
2525 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
2530 * Close a pipe created with cvmx_usb_open_pipe().
2532 * @param state USB device state populated by
2533 * cvmx_usb_initialize().
2534 * @param pipe_handle
2535 * Pipe handle to close.
2537 * @return CVMX_USB_SUCCESS or a negative error code defined in
2538 * cvmx_usb_status_t. CVMX_USB_BUSY is returned if the
2539 * pipe has outstanding transfers.
2541 cvmx_usb_status_t cvmx_usb_close_pipe(cvmx_usb_state_t *state, int pipe_handle)
2543 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2544 cvmx_usb_pipe_t *pipe = usb->pipe + pipe_handle;
2546 CVMX_USB_LOG_CALLED();
2547 CVMX_USB_LOG_PARAM("%p", state);
2548 CVMX_USB_LOG_PARAM("%d", pipe_handle);
2549 if (cvmx_unlikely((pipe_handle < 0) || (pipe_handle >= MAX_PIPES)))
2550 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2551 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
2552 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
2554 /* Fail if the pipe isn't open */
2555 if (cvmx_unlikely((pipe->flags & __CVMX_USB_PIPE_FLAGS_OPEN) == 0))
2556 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2558 /* Fail if the pipe has pending transactions */
2559 if (cvmx_unlikely(pipe->head))
2560 CVMX_USB_RETURN(CVMX_USB_BUSY);
2563 __cvmx_usb_remove_pipe(&usb->idle_pipes, pipe);
2564 __cvmx_usb_append_pipe(&usb->free_pipes, pipe);
2566 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
2571 * Register a function to be called when various USB events occur.
2573 * @param state USB device state populated by
2574 * cvmx_usb_initialize().
2575 * @param reason Which event to register for.
2576 * @param callback Function to call when the event occurs.
2577 * @param user_data User data parameter to the function.
2579 * @return CVMX_USB_SUCCESS or a negative error code defined in
2580 * cvmx_usb_status_t.
2582 cvmx_usb_status_t cvmx_usb_register_callback(cvmx_usb_state_t *state,
2583 cvmx_usb_callback_t reason,
2584 cvmx_usb_callback_func_t callback,
2587 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2589 CVMX_USB_LOG_CALLED();
2590 CVMX_USB_LOG_PARAM("%p", state);
2591 CVMX_USB_LOG_PARAM("%d", reason);
2592 CVMX_USB_LOG_PARAM("%p", callback);
2593 CVMX_USB_LOG_PARAM("%p", user_data);
2594 if (cvmx_unlikely(reason >= __CVMX_USB_CALLBACK_END))
2595 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2596 if (cvmx_unlikely(!callback))
2597 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
2599 usb->callback[reason] = callback;
2600 usb->callback_data[reason] = user_data;
2602 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
2607 * Get the current USB protocol level frame number. The frame
2608 * number is always in the range of 0-0x7ff.
2610 * @param state USB device state populated by
2611 * cvmx_usb_initialize().
2613 * @return USB frame number
2615 int cvmx_usb_get_frame_number(cvmx_usb_state_t *state)
2618 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
2620 CVMX_USB_LOG_CALLED();
2621 CVMX_USB_LOG_PARAM("%p", state);
2623 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE))
2625 cvmx_usbcx_dsts_t usbc_dsts;
2626 usbc_dsts.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_DSTS(usb->index));
2627 frame_number = usbc_dsts.s.soffn;
2631 cvmx_usbcx_hfnum_t usbc_hfnum;
2632 usbc_hfnum.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HFNUM(usb->index));
2633 frame_number = usbc_hfnum.s.frnum;
2636 CVMX_USB_RETURN(frame_number);
2642 * Poll a channel for status
2644 * @param usb USB device
2645 * @param channel Channel to poll
2647 * @return Zero on success
2649 static int __cvmx_usb_poll_channel(cvmx_usb_internal_state_t *usb, int channel)
2651 cvmx_usbcx_hcintx_t usbc_hcint;
2652 cvmx_usbcx_hctsizx_t usbc_hctsiz;
2653 cvmx_usbcx_hccharx_t usbc_hcchar;
2654 cvmx_usb_pipe_t *pipe;
2655 cvmx_usb_transaction_t *transaction;
2656 int bytes_this_transfer;
2657 int bytes_in_last_packet;
2658 int packets_processed;
2659 int buffer_space_left;
2660 CVMX_USB_LOG_CALLED();
2661 CVMX_USB_LOG_PARAM("%p", usb);
2662 CVMX_USB_LOG_PARAM("%d", channel);
2664 /* Read the interrupt status bits for the channel */
2665 usbc_hcint.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HCINTX(channel, usb->index));
2667 /* We ignore any interrupts where the channel hasn't halted yet. These
2668 should be impossible since we don't enable any interrupts except for
2670 if (!usbc_hcint.s.chhltd)
2673 /* Now that the channel has halted, clear all status bits before
2674 processing. This way we don't have any race conditions caused by the
2675 channel starting up and finishing before we clear the bits */
2676 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HCINTX(channel, usb->index), usbc_hcint.u32);
2677 //cvmx_csr_db_decode(cvmx_get_proc_id(), CVMX_USBCX_HCINTX(channel, usb->index), usbc_hcint.u32);
2679 usb->idle_hardware_channels |= (1<<channel);
2681 /* Make sure this channel is tied to a valid pipe */
2682 pipe = usb->pipe_for_channel[channel];
2683 CVMX_PREFETCH(pipe, 0);
2684 CVMX_PREFETCH(pipe, 128);
2687 transaction = pipe->head;
2688 CVMX_PREFETCH0(transaction);
2690 /* Disconnect this pipe from the HW channel. Later the schedule function will
2691 figure out which pipe needs to go */
2692 usb->pipe_for_channel[channel] = NULL;
2693 pipe->flags &= ~__CVMX_USB_PIPE_FLAGS_SCHEDULED;
2695 /* Read the channel config info so we can figure out how much data
2697 usbc_hcchar.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HCCHARX(channel, usb->index));
2698 usbc_hctsiz.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HCTSIZX(channel, usb->index));
2700 /* Calculating the number of bytes successfully transfered is dependent on
2701 the transfer direction */
2702 packets_processed = transaction->pktcnt - usbc_hctsiz.s.pktcnt;
2703 if (usbc_hcchar.s.epdir)
2705 /* IN transactions are easy. For every byte received the hardware
2706 decrements xfersize. All we need to do is subtract the current
2707 value of xfersize from its starting value and we know how many
2708 bytes were written to the buffer */
2709 bytes_this_transfer = transaction->xfersize - usbc_hctsiz.s.xfersize;
2713 /* OUT transaction don't decrement xfersize. Instead pktcnt is
2714 decremented on every successful packet send. The hardware does
2715 this when it receives an ACK, or NYET. If it doesn't
2716 receive one of these responses pktcnt doesn't change */
2717 bytes_this_transfer = packets_processed * usbc_hcchar.s.mps;
2718 /* The last packet may not be a full transfer if we didn't have
2720 if (bytes_this_transfer > transaction->xfersize)
2721 bytes_this_transfer = transaction->xfersize;
2723 /* Figure out how many bytes were in the last packet of the transfer */
2724 if (packets_processed)
2725 bytes_in_last_packet = bytes_this_transfer - (packets_processed-1) * usbc_hcchar.s.mps;
2727 bytes_in_last_packet = bytes_this_transfer;
2729 /* As a special case, setup transactions output the setup header, not
2730 the user's data. For this reason we don't count setup data as bytes
2732 if ((transaction->stage == CVMX_USB_STAGE_SETUP) ||
2733 (transaction->stage == CVMX_USB_STAGE_SETUP_SPLIT_COMPLETE))
2734 bytes_this_transfer = 0;
2736 /* Optional debug output */
2737 if (cvmx_unlikely((usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_TRANSFERS) ||
2738 (pipe->flags & CVMX_USB_PIPE_FLAGS_DEBUG_TRANSFERS)))
2739 cvmx_dprintf("%s: Channel %d halted. Pipe %d transaction %d stage %d bytes=%d\n",
2740 __FUNCTION__, channel,
2741 __cvmx_usb_get_pipe_handle(usb, pipe),
2742 __cvmx_usb_get_submit_handle(usb, transaction),
2743 transaction->stage, bytes_this_transfer);
2745 /* Add the bytes transfered to the running total. It is important that
2746 bytes_this_transfer doesn't count any data that needs to be
2748 transaction->actual_bytes += bytes_this_transfer;
2749 if (transaction->type == CVMX_USB_TRANSFER_ISOCHRONOUS)
2750 buffer_space_left = transaction->iso_packets[0].length - transaction->actual_bytes;
2752 buffer_space_left = transaction->buffer_length - transaction->actual_bytes;
2754 /* We need to remember the PID toggle state for the next transaction. The
2755 hardware already updated it for the next transaction */
2756 pipe->pid_toggle = !(usbc_hctsiz.s.pid == 0);
2758 /* For high speed bulk out, assume the next transaction will need to do a
2759 ping before proceeding. If this isn't true the ACK processing below
2760 will clear this flag */
2761 if ((pipe->device_speed == CVMX_USB_SPEED_HIGH) &&
2762 (pipe->transfer_type == CVMX_USB_TRANSFER_BULK) &&
2763 (pipe->transfer_dir == CVMX_USB_DIRECTION_OUT))
2764 pipe->flags |= __CVMX_USB_PIPE_FLAGS_NEED_PING;
2766 if (usbc_hcint.s.stall)
2768 /* STALL as a response means this transaction cannot be completed
2769 because the device can't process transactions. Tell the user. Any
2770 data that was transfered will be counted on the actual bytes
2772 pipe->pid_toggle = 0;
2773 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_STALL);
2775 else if (0 && usbc_hcint.s.xfercompl)
2777 /* XferCompl is only useful in non DMA mode */
2779 else if (usbc_hcint.s.xacterr)
2781 /* We know at least one packet worked if we get a ACK or NAK. Reset the retry counter */
2782 if (usbc_hcint.s.nak || usbc_hcint.s.ack)
2783 transaction->retries = 0;
2784 transaction->retries++;
2785 if (transaction->retries > MAX_RETRIES)
2787 /* XactErr as a response means the device signaled something wrong with
2788 the transfer. For example, PID toggle errors cause these */
2789 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_XACTERR);
2793 /* Rewind to the beginning of the transaction by anding off the
2794 split complete bit */
2795 transaction->stage &= ~1;
2796 pipe->split_sc_frame = -1;
2797 pipe->next_tx_cycle = cvmx_read64_uint64(CVMX_IPD_CLK_COUNT) + pipe->interval;
2800 else if (0 && usbc_hcint.s.datatglerr)
2802 /* The hardware automatically handles Data Toggle Errors for us */
2804 else if (usbc_hcint.s.bblerr)
2806 /* Babble Error (BblErr) */
2807 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_BABBLEERR);
2809 else if (usbc_hcint.s.frmovrun)
2811 /* Frame Overrun (FrmOvrun) */
2812 /* Rewind to the beginning of the transaction by anding off the
2813 split complete bit */
2814 transaction->stage &= ~1;
2815 pipe->split_sc_frame = -1;
2817 else if (usbc_hcint.s.nyet)
2819 /* NYET as a response is only allowed in three cases: as a response to
2820 a ping, as a response to a split transaction, and as a response to
2821 a bulk out. The ping case is handled by hardware, so we only have
2822 splits and bulk out */
2823 if (!__cvmx_usb_pipe_needs_split(usb, pipe))
2825 transaction->retries = 0;
2826 /* If there is more data to go then we need to try again. Otherwise
2827 this transaction is complete */
2828 if ((buffer_space_left == 0) || (bytes_in_last_packet < pipe->max_packet))
2829 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_SUCCESS);
2833 /* Split transactions retry the split complete 4 times then rewind
2834 to the start split and do the entire transactions again */
2835 transaction->retries++;
2836 if ((transaction->retries & 0x3) == 0)
2838 /* Rewind to the beginning of the transaction by anding off the
2839 split complete bit */
2840 transaction->stage &= ~1;
2841 pipe->split_sc_frame = -1;
2845 else if (usbc_hcint.s.ack)
2847 transaction->retries = 0;
2848 /* The ACK bit can only be checked after the other error bits. This is
2849 because a multi packet transfer may succeed in a number of packets
2850 and then get a different response on the last packet. In this case
2851 both ACK and the last response bit will be set. If none of the
2852 other response bits is set, then the last packet must have been an
2855 /* Since we got an ACK, we know we don't need to do a ping on this
2857 pipe->flags &= ~__CVMX_USB_PIPE_FLAGS_NEED_PING;
2859 switch (transaction->type)
2861 case CVMX_USB_TRANSFER_CONTROL:
2862 switch (transaction->stage)
2864 case CVMX_USB_STAGE_NON_CONTROL:
2865 case CVMX_USB_STAGE_NON_CONTROL_SPLIT_COMPLETE:
2866 /* This should be impossible */
2867 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_ERROR);
2869 case CVMX_USB_STAGE_SETUP:
2870 pipe->pid_toggle = 1;
2871 if (__cvmx_usb_pipe_needs_split(usb, pipe))
2872 transaction->stage = CVMX_USB_STAGE_SETUP_SPLIT_COMPLETE;
2875 cvmx_usb_control_header_t *header = cvmx_phys_to_ptr(transaction->control_header);
2876 if (header->s.length)
2877 transaction->stage = CVMX_USB_STAGE_DATA;
2879 transaction->stage = CVMX_USB_STAGE_STATUS;
2882 case CVMX_USB_STAGE_SETUP_SPLIT_COMPLETE:
2884 cvmx_usb_control_header_t *header = cvmx_phys_to_ptr(transaction->control_header);
2885 if (header->s.length)
2886 transaction->stage = CVMX_USB_STAGE_DATA;
2888 transaction->stage = CVMX_USB_STAGE_STATUS;
2891 case CVMX_USB_STAGE_DATA:
2892 if (__cvmx_usb_pipe_needs_split(usb, pipe))
2893 transaction->stage = CVMX_USB_STAGE_DATA_SPLIT_COMPLETE;
2894 else if ((buffer_space_left == 0) || (bytes_in_last_packet < pipe->max_packet))
2896 pipe->pid_toggle = 1;
2897 transaction->stage = CVMX_USB_STAGE_STATUS;
2900 case CVMX_USB_STAGE_DATA_SPLIT_COMPLETE:
2901 if ((buffer_space_left == 0) || (bytes_in_last_packet < pipe->max_packet))
2903 pipe->pid_toggle = 1;
2904 transaction->stage = CVMX_USB_STAGE_STATUS;
2908 transaction->stage = CVMX_USB_STAGE_DATA;
2911 case CVMX_USB_STAGE_STATUS:
2912 if (__cvmx_usb_pipe_needs_split(usb, pipe))
2913 transaction->stage = CVMX_USB_STAGE_STATUS_SPLIT_COMPLETE;
2915 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_SUCCESS);
2917 case CVMX_USB_STAGE_STATUS_SPLIT_COMPLETE:
2918 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_SUCCESS);
2922 case CVMX_USB_TRANSFER_BULK:
2923 case CVMX_USB_TRANSFER_INTERRUPT:
2924 /* The only time a bulk transfer isn't complete when
2925 it finishes with an ACK is during a split transaction. For
2926 splits we need to continue the transfer if more data is
2928 if (__cvmx_usb_pipe_needs_split(usb, pipe))
2930 if (transaction->stage == CVMX_USB_STAGE_NON_CONTROL)
2931 transaction->stage = CVMX_USB_STAGE_NON_CONTROL_SPLIT_COMPLETE;
2934 if (buffer_space_left && (bytes_in_last_packet == pipe->max_packet))
2935 transaction->stage = CVMX_USB_STAGE_NON_CONTROL;
2938 if (transaction->type == CVMX_USB_TRANSFER_INTERRUPT)
2939 pipe->next_tx_cycle += pipe->interval;
2940 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_SUCCESS);
2946 if ((pipe->device_speed == CVMX_USB_SPEED_HIGH) &&
2947 (pipe->transfer_type == CVMX_USB_TRANSFER_BULK) &&
2948 (pipe->transfer_dir == CVMX_USB_DIRECTION_OUT) &&
2950 pipe->flags |= __CVMX_USB_PIPE_FLAGS_NEED_PING;
2951 if (!buffer_space_left || (bytes_in_last_packet < pipe->max_packet))
2953 if (transaction->type == CVMX_USB_TRANSFER_INTERRUPT)
2954 pipe->next_tx_cycle += pipe->interval;
2955 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_SUCCESS);
2959 case CVMX_USB_TRANSFER_ISOCHRONOUS:
2960 if (__cvmx_usb_pipe_needs_split(usb, pipe))
2962 /* ISOCHRONOUS OUT splits don't require a complete split stage.
2963 Instead they use a sequence of begin OUT splits to transfer
2964 the data 188 bytes at a time. Once the transfer is complete,
2965 the pipe sleeps until the next schedule interval */
2966 if (pipe->transfer_dir == CVMX_USB_DIRECTION_OUT)
2968 pipe->next_tx_cycle += pipe->interval;
2969 /* If no space left or this wasn't a max size packet then
2970 this transfer is complete. Otherwise start it again
2971 to send the next 188 bytes */
2972 if (!buffer_space_left || (bytes_this_transfer < 188))
2973 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_SUCCESS);
2977 if (transaction->stage == CVMX_USB_STAGE_NON_CONTROL_SPLIT_COMPLETE)
2979 /* We are in the incomming data phase. Keep getting
2980 data until we run out of space or get a small
2982 if ((buffer_space_left == 0) || (bytes_in_last_packet < pipe->max_packet))
2984 pipe->next_tx_cycle += pipe->interval;
2985 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_SUCCESS);
2989 transaction->stage = CVMX_USB_STAGE_NON_CONTROL_SPLIT_COMPLETE;
2994 pipe->next_tx_cycle += pipe->interval;
2995 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_SUCCESS);
3000 else if (usbc_hcint.s.nak)
3002 uint64_t ipd_clk_count;
3003 /* NAK as a response means the device couldn't accept the transaction,
3004 but it should be retried in the future. Rewind to the beginning of
3005 the transaction by anding off the split complete bit. Retry in the
3007 transaction->retries = 0;
3008 transaction->stage &= ~1;
3009 pipe->next_tx_cycle += pipe->interval;
3010 ipd_clk_count = cvmx_read64_uint64(CVMX_IPD_CLK_COUNT);
3011 if (pipe->next_tx_cycle < ipd_clk_count)
3012 pipe->next_tx_cycle = ipd_clk_count + pipe->interval;
3016 /* We get channel halted interrupts with no result bits sets when the
3017 cable is unplugged */
3018 __cvmx_usb_perform_complete(usb, pipe, transaction, CVMX_USB_COMPLETE_ERROR);
3025 * Poll a device mode endpoint for status
3027 * @param usb USB device state populated by
3028 * cvmx_usb_initialize().
3029 * @param endpoint_num
3032 * @return Zero on success
3034 static int __cvmx_usb_poll_endpoint(cvmx_usb_internal_state_t *usb, int endpoint_num)
3036 cvmx_usbcx_diepintx_t usbc_diepint;
3037 cvmx_usbcx_doepintx_t usbc_doepint;
3039 CVMX_USB_LOG_CALLED();
3040 CVMX_USB_LOG_PARAM("%p", usb);
3041 CVMX_USB_LOG_PARAM("%d", endpoint_num);
3043 usbc_diepint.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_DIEPINTX(endpoint_num, usb->index));
3044 __cvmx_usb_write_csr32(usb, CVMX_USBCX_DIEPINTX(endpoint_num, usb->index), usbc_diepint.u32);
3045 //cvmx_csr_db_decode(cvmx_get_proc_id(), CVMX_USBCX_DIEPINTX(endpoint_num, usb->index), usbc_diepint.u32);
3046 if (usbc_diepint.s.inepnakeff)
3048 /* IN Endpoint NAK Effective (INEPNakEff)
3049 Applies to periodic IN endpoints only.
3050 Indicates that the IN endpoint NAK bit set by the application has
3051 taken effect in the core. This bit can be cleared when the
3052 application clears the IN endpoint NAK by writing to
3054 This interrupt indicates that the core has sampled the NAK bit
3055 set (either by the application or by the core).
3056 This interrupt does not necessarily mean that a NAK handshake
3057 is sent on the USB. A STALL bit takes priority over a NAK bit. */
3060 if (usbc_diepint.s.intknepmis)
3062 /* IN Token Received with EP Mismatch (INTknEPMis)
3063 Applies to non-periodic IN endpoints only.
3064 Indicates that the data in the top of the non-periodic TxFIFO
3065 belongs to an endpoint other than the one for which the IN
3066 token was received. This interrupt is asserted on the endpoint
3067 for which the IN token was received. */
3068 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
3069 cvmx_dprintf("%s: Endpoint %d mismatch\n", __FUNCTION__, endpoint_num);
3071 if (usbc_diepint.s.intkntxfemp)
3073 /* IN Token Received When TxFIFO is Empty (INTknTXFEmp)
3074 Applies only to non-periodic IN endpoints.
3075 Indicates that an IN token was received when the associated
3076 TxFIFO (periodic/non-periodic) was empty. This interrupt is
3077 asserted on the endpoint for which the IN token was received. */
3078 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
3079 cvmx_dprintf("%s: Received IN token on endpoint %d without data\n", __FUNCTION__, endpoint_num);
3081 if (usbc_diepint.s.timeout)
3083 /* Timeout Condition (TimeOUT)
3084 Applies to non-isochronous IN endpoints only.
3085 Indicates that the core has detected a timeout condition on the
3086 USB for the last IN token on this endpoint. */
3087 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
3088 cvmx_dprintf("%s: Received timeout on endpoint %d\n", __FUNCTION__, endpoint_num);
3090 if (usbc_diepint.s.ahberr)
3092 /* AHB Error (AHBErr)
3093 This is generated only in Internal DMA mode when there is an
3094 AHB error during an AHB read/write. The application can read
3095 the corresponding endpoint DMA address register to get the
3097 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
3098 cvmx_dprintf("%s: AHB error on endpoint %d\n", __FUNCTION__, endpoint_num);
3100 if (usbc_diepint.s.epdisbld)
3102 /* Endpoint Disabled Interrupt (EPDisbld)
3103 This bit indicates that the endpoint is disabled per the
3104 application's request. */
3107 if (usbc_diepint.s.xfercompl)
3109 /* Transfer Completed Interrupt (XferCompl)
3110 Indicates that the programmed transfer is complete on the AHB
3111 as well as on the USB, for this endpoint. */
3112 __cvmx_usb_perform_callback(usb, usb->pipe + endpoint_num, NULL,
3113 CVMX_USB_CALLBACK_TRANSFER_COMPLETE,
3114 CVMX_USB_COMPLETE_SUCCESS);
3117 usbc_doepint.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_DOEPINTX(endpoint_num, usb->index));
3118 __cvmx_usb_write_csr32(usb, CVMX_USBCX_DOEPINTX(endpoint_num, usb->index), usbc_doepint.u32);
3119 //cvmx_csr_db_decode(cvmx_get_proc_id(), CVMX_USBCX_DOEPINTX(endpoint_num, usb->index), usbc_doepint.u32);
3120 if (usbc_doepint.s.outtknepdis)
3122 /* OUT Token Received When Endpoint Disabled (OUTTknEPdis)
3123 Applies only to control OUT endpoints.
3124 Indicates that an OUT token was received when the endpoint
3125 was not yet enabled. This interrupt is asserted on the endpoint
3126 for which the OUT token was received. */
3127 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
3128 cvmx_dprintf("%s: Received OUT token on disabled endpoint %d\n", __FUNCTION__, endpoint_num);
3130 if (usbc_doepint.s.setup)
3132 /* SETUP Phase Done (SetUp)
3133 Applies to control OUT endpoints only.
3134 Indicates that the SETUP phase for the control endpoint is
3135 complete and no more back-to-back SETUP packets were
3136 received for the current control transfer. On this interrupt, the
3137 application can decode the received SETUP data packet. */
3138 __cvmx_usb_perform_callback(usb, usb->pipe + endpoint_num, NULL,
3139 CVMX_USB_CALLBACK_DEVICE_SETUP,
3140 CVMX_USB_COMPLETE_SUCCESS);
3142 if (usbc_doepint.s.ahberr)
3144 /* AHB Error (AHBErr)
3145 This is generated only in Internal DMA mode when there is an
3146 AHB error during an AHB read/write. The application can read
3147 the corresponding endpoint DMA address register to get the
3149 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
3150 cvmx_dprintf("%s: AHB error on endpoint %d\n", __FUNCTION__, endpoint_num);
3152 if (usbc_doepint.s.epdisbld)
3154 /* Endpoint Disabled Interrupt (EPDisbld)
3155 This bit indicates that the endpoint is disabled per the
3156 application's request. */
3159 if (usbc_doepint.s.xfercompl)
3161 /* Transfer Completed Interrupt (XferCompl)
3162 Indicates that the programmed transfer is complete on the AHB
3163 as well as on the USB, for this endpoint. */
3164 __cvmx_usb_perform_callback(usb, usb->pipe + endpoint_num, NULL,
3165 CVMX_USB_CALLBACK_TRANSFER_COMPLETE,
3166 CVMX_USB_COMPLETE_SUCCESS);
3174 * Poll the device mode endpoints for status
3176 * @param usb USB device state populated by
3177 * cvmx_usb_initialize().
3179 * @return Zero on success
3181 static int __cvmx_usb_poll_endpoints(cvmx_usb_internal_state_t *usb)
3183 cvmx_usbcx_daint_t usbc_daint;
3184 int active_endpoints;
3186 CVMX_USB_LOG_CALLED();
3187 CVMX_USB_LOG_PARAM("%p", usb);
3189 usbc_daint.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_DAINT(usb->index));
3190 active_endpoints = usbc_daint.s.inepint | usbc_daint.s.outepint;
3192 while (active_endpoints)
3195 CVMX_CLZ(endpoint, active_endpoints);
3196 endpoint = 31 - endpoint;
3197 __cvmx_usb_poll_endpoint(usb, endpoint);
3198 active_endpoints ^= 1<<endpoint;
3206 * Poll the USB block for status and call all needed callback
3207 * handlers. This function is meant to be called in the interrupt
3208 * handler for the USB controller. It can also be called
3209 * periodically in a loop for non-interrupt based operation.
3211 * @param state USB device state populated by
3212 * cvmx_usb_initialize().
3214 * @return CVMX_USB_SUCCESS or a negative error code defined in
3215 * cvmx_usb_status_t.
3217 cvmx_usb_status_t cvmx_usb_poll(cvmx_usb_state_t *state)
3219 cvmx_usbcx_gintsts_t usbc_gintsts;
3220 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
3222 CVMX_PREFETCH(usb, 0);
3223 CVMX_PREFETCH(usb, 1*128);
3224 CVMX_PREFETCH(usb, 2*128);
3225 CVMX_PREFETCH(usb, 3*128);
3226 CVMX_PREFETCH(usb, 4*128);
3228 CVMX_USB_LOG_CALLED();
3229 CVMX_USB_LOG_PARAM("%p", state);
3231 /* Read the pending interrupts */
3232 usbc_gintsts.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_GINTSTS(usb->index));
3234 if (usbc_gintsts.s.wkupint)
3236 /* Resume/Remote Wakeup Detected Interrupt (WkUpInt)
3237 In Device mode, this interrupt is asserted when a resume is
3238 detected on the USB. In Host mode, this interrupt is asserted
3239 when a remote wakeup is detected on the USB. */
3240 /* Octeon doesn't support suspend / resume */
3242 if (usbc_gintsts.s.sessreqint)
3244 /* Session Request/New Session Detected Interrupt (SessReqInt)
3245 In Host mode, this interrupt is asserted when a session request
3246 is detected from the device. In Device mode, this interrupt is
3247 asserted when the utmiotg_bvalid signal goes high. */
3248 /* Octeon doesn't support OTG */
3250 if (usbc_gintsts.s.disconnint || usbc_gintsts.s.prtint)
3252 cvmx_usbcx_hprt_t usbc_hprt;
3253 /* Disconnect Detected Interrupt (DisconnInt)
3254 Asserted when a device disconnect is detected. */
3256 /* Host Port Interrupt (PrtInt)
3257 The core sets this bit to indicate a change in port status of one
3258 of the O2P USB core ports in Host mode. The application must
3259 read the Host Port Control and Status (HPRT) register to
3260 determine the exact event that caused this interrupt. The
3261 application must clear the appropriate status bit in the Host Port
3262 Control and Status register to clear this bit. */
3264 /* Call the user's port callback */
3265 __cvmx_usb_perform_callback(usb, NULL, NULL,
3266 CVMX_USB_CALLBACK_PORT_CHANGED,
3267 CVMX_USB_COMPLETE_SUCCESS);
3268 /* Clear the port change bits */
3269 usbc_hprt.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HPRT(usb->index));
3270 usbc_hprt.s.prtena = 0;
3271 __cvmx_usb_write_csr32(usb, CVMX_USBCX_HPRT(usb->index), usbc_hprt.u32);
3273 if (usbc_gintsts.s.conidstschng)
3275 /* Connector ID Status Change (ConIDStsChng)
3276 The core sets this bit when there is a change in connector ID
3278 /* The USB core currently doesn't support dynamically changing from
3279 host to device mode */
3281 if (usbc_gintsts.s.ptxfemp)
3283 /* Periodic TxFIFO Empty (PTxFEmp)
3284 Asserted when the Periodic Transmit FIFO is either half or
3285 completely empty and there is space for at least one entry to be
3286 written in the Periodic Request Queue. The half or completely
3287 empty status is determined by the Periodic TxFIFO Empty Level
3288 bit in the Core AHB Configuration register
3289 (GAHBCFG.PTxFEmpLvl). */
3290 /* In DMA mode we don't care */
3292 if (usbc_gintsts.s.hchint)
3294 /* Host Channels Interrupt (HChInt)
3295 The core sets this bit to indicate that an interrupt is pending on
3296 one of the channels of the core (in Host mode). The application
3297 must read the Host All Channels Interrupt (HAINT) register to
3298 determine the exact number of the channel on which the
3299 interrupt occurred, and then read the corresponding Host
3300 Channel-n Interrupt (HCINTn) register to determine the exact
3301 cause of the interrupt. The application must clear the
3302 appropriate status bit in the HCINTn register to clear this bit. */
3303 cvmx_usbcx_haint_t usbc_haint;
3304 usbc_haint.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_HAINT(usb->index));
3305 while (usbc_haint.u32)
3308 CVMX_CLZ(channel, usbc_haint.u32);
3309 channel = 31 - channel;
3310 __cvmx_usb_poll_channel(usb, channel);
3311 usbc_haint.u32 ^= 1<<channel;
3314 if (usbc_gintsts.s.fetsusp)
3316 /* Data Fetch Suspended (FetSusp)
3317 This interrupt is valid only in DMA mode. This interrupt indicates
3318 that the core has stopped fetching data for IN endpoints due to
3319 the unavailability of TxFIFO space or Request Queue space.
3320 This interrupt is used by the application for an endpoint
3321 mismatch algorithm. */
3324 if (usbc_gintsts.s.incomplp)
3326 /* Incomplete Periodic Transfer (incomplP)
3327 In Host mode, the core sets this interrupt bit when there are
3328 incomplete periodic transactions still pending which are
3329 scheduled for the current microframe.
3330 Incomplete Isochronous OUT Transfer (incompISOOUT)
3331 The Device mode, the core sets this interrupt to indicate that
3332 there is at least one isochronous OUT endpoint on which the
3333 transfer is not completed in the current microframe. This
3334 interrupt is asserted along with the End of Periodic Frame
3335 Interrupt (EOPF) bit in this register. */
3338 if (usbc_gintsts.s.incompisoin)
3340 /* Incomplete Isochronous IN Transfer (incompISOIN)
3341 The core sets this interrupt to indicate that there is at least one
3342 isochronous IN endpoint on which the transfer is not completed
3343 in the current microframe. This interrupt is asserted along with
3344 the End of Periodic Frame Interrupt (EOPF) bit in this register. */
3347 if (usbc_gintsts.s.oepint)
3349 /* OUT Endpoints Interrupt (OEPInt)
3350 The core sets this bit to indicate that an interrupt is pending on
3351 one of the OUT endpoints of the core (in Device mode). The
3352 application must read the Device All Endpoints Interrupt
3353 (DAINT) register to determine the exact number of the OUT
3354 endpoint on which the interrupt occurred, and then read the
3355 corresponding Device OUT Endpoint-n Interrupt (DOEPINTn)
3356 register to determine the exact cause of the interrupt. The
3357 application must clear the appropriate status bit in the
3358 corresponding DOEPINTn register to clear this bit. */
3359 __cvmx_usb_poll_endpoints(usb);
3361 if (usbc_gintsts.s.iepint)
3363 /* IN Endpoints Interrupt (IEPInt)
3364 The core sets this bit to indicate that an interrupt is pending on
3365 one of the IN endpoints of the core (in Device mode). The
3366 application must read the Device All Endpoints Interrupt
3367 (DAINT) register to determine the exact number of the IN
3368 endpoint on which the interrupt occurred, and then read the
3369 corresponding Device IN Endpoint-n Interrupt (DIEPINTn)
3370 register to determine the exact cause of the interrupt. The
3371 application must clear the appropriate status bit in the
3372 corresponding DIEPINTn register to clear this bit. */
3373 __cvmx_usb_poll_endpoints(usb);
3375 if (usbc_gintsts.s.epmis)
3377 /* Endpoint Mismatch Interrupt (EPMis)
3378 Indicates that an IN token has been received for a non-periodic
3379 endpoint, but the data for another endpoint is present in the top
3380 of the Non-Periodic Transmit FIFO and the IN endpoint
3381 mismatch count programmed by the application has expired. */
3384 if (usbc_gintsts.s.eopf)
3386 /* End of Periodic Frame Interrupt (EOPF)
3387 Indicates that the period specified in the Periodic Frame Interval
3388 field of the Device Configuration register (DCFG.PerFrInt) has
3389 been reached in the current microframe. */
3392 if (usbc_gintsts.s.isooutdrop)
3394 /* Isochronous OUT Packet Dropped Interrupt (ISOOutDrop)
3395 The core sets this bit when it fails to write an isochronous OUT
3396 packet into the RxFIFO because the RxFIFO doesn't have
3397 enough space to accommodate a maximum packet size packet
3398 for the isochronous OUT endpoint. */
3401 if (usbc_gintsts.s.enumdone)
3403 /* Enumeration Done (EnumDone)
3404 The core sets this bit to indicate that speed enumeration is
3405 complete. The application must read the Device Status (DSTS)
3406 register to obtain the enumerated speed. */
3407 if (usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE)
3409 cvmx_usbcx_dsts_t usbc_dsts;
3410 usbc_dsts.u32 = __cvmx_usb_read_csr32(usb, CVMX_USBCX_DSTS(usb->index));
3411 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
3412 cvmx_dprintf("%s: USB%d Enumeration complete with %s speed\n",
3413 __FUNCTION__, usb->index,
3414 (usbc_dsts.s.enumspd == CVMX_USB_SPEED_HIGH) ? "high" :
3415 (usbc_dsts.s.enumspd == CVMX_USB_SPEED_FULL) ? "full" :
3417 USB_SET_FIELD32(CVMX_USBCX_DIEPCTLX(0, usb->index),
3418 cvmx_usbcx_diepctlx_t, mps,
3419 (usbc_dsts.s.enumspd == CVMX_USB_SPEED_LOW) ? 3 : 0);
3420 USB_SET_FIELD32(CVMX_USBCX_DOEPCTLX(0, usb->index),
3421 cvmx_usbcx_doepctlx_t, epena, 1);
3424 if (usbc_gintsts.s.usbrst)
3426 /* USB Reset (USBRst)
3427 The core sets this bit to indicate that a reset is
3428 detected on the USB. */
3429 if (usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE)
3431 if (cvmx_unlikely(usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEBUG_INFO))
3432 cvmx_dprintf("%s: USB%d Reset complete\n", __FUNCTION__, usb->index);
3433 __cvmx_usb_device_reset_complete(usb);
3436 if (usbc_gintsts.s.nptxfemp)
3438 /* Non-Periodic TxFIFO Empty (NPTxFEmp)
3439 This interrupt is asserted when the Non-Periodic TxFIFO is
3440 either half or completely empty, and there is space for at least
3441 one entry to be written to the Non-Periodic Transmit Request
3442 Queue. The half or completely empty status is determined by
3443 the Non-Periodic TxFIFO Empty Level bit in the Core AHB
3444 Configuration register (GAHBCFG.NPTxFEmpLvl). */
3445 /* In DMA mode this is handled by hardware */
3447 if (usbc_gintsts.s.rxflvl)
3449 /* RxFIFO Non-Empty (RxFLvl)
3450 Indicates that there is at least one packet pending to be read
3452 /* In DMA mode this is handled by hardware */
3454 if (usbc_gintsts.s.sof)
3456 /* Start of (micro)Frame (Sof)
3457 In Host mode, the core sets this bit to indicate that an SOF
3458 (FS), micro-SOF (HS), or Keep-Alive (LS) is transmitted on the
3459 USB. The application must write a 1 to this bit to clear the
3461 In Device mode, in the core sets this bit to indicate that an SOF
3462 token has been received on the USB. The application can read
3463 the Device Status register to get the current (micro)frame
3464 number. This interrupt is seen only when the core is operating
3465 at either HS or FS. */
3467 if (usbc_gintsts.s.otgint)
3469 /* OTG Interrupt (OTGInt)
3470 The core sets this bit to indicate an OTG protocol event. The
3471 application must read the OTG Interrupt Status (GOTGINT)
3472 register to determine the exact event that caused this interrupt.
3473 The application must clear the appropriate status bit in the
3474 GOTGINT register to clear this bit. */
3475 /* Octeon doesn't support OTG, so ignore */
3477 if (usbc_gintsts.s.modemis)
3479 /* Mode Mismatch Interrupt (ModeMis)
3480 The core sets this bit when the application is trying to access:
3481 * A Host mode register, when the core is operating in Device
3483 * A Device mode register, when the core is operating in Host
3485 The register access is completed on the AHB with an OKAY
3486 response, but is ignored by the core internally and doesn't
3487 affect the operation of the core. */
3488 /* Ignored for now */
3491 __cvmx_usb_schedule(usb, usbc_gintsts.s.sof);
3493 /* Clear the interrupts now that we know about them */
3494 __cvmx_usb_write_csr32(usb, CVMX_USBCX_GINTSTS(usb->index), usbc_gintsts.u32);
3496 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
3501 * Enable an endpoint for use in device mode. After this call
3502 * transactions will be allowed over the endpoint. This must be
3503 * called after every usb reset.
3505 * @param state USB device state populated by
3506 * cvmx_usb_initialize().
3507 * @param endpoint_num
3508 * The endpoint number to enable (0-4)
3509 * @param transfer_type
3510 * USB transfer type of this endpoint
3511 * @param transfer_dir
3512 * Direction of transfer relative to Octeon
3513 * @param max_packet_size
3514 * Maximum packet size support by this endpoint
3515 * @param buffer Buffer to send/receive
3516 * @param buffer_length
3517 * Length of the buffer in bytes
3519 * @return CVMX_USB_SUCCESS or a negative error code defined in
3520 * cvmx_usb_status_t.
3522 cvmx_usb_status_t cvmx_usb_device_enable_endpoint(cvmx_usb_state_t *state,
3524 cvmx_usb_transfer_t transfer_type,
3525 cvmx_usb_direction_t transfer_dir,
3526 int max_packet_size,
3530 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
3532 CVMX_USB_LOG_CALLED();
3533 CVMX_USB_LOG_PARAM("%p", state);
3534 CVMX_USB_LOG_PARAM("%d", endpoint_num);
3535 CVMX_USB_LOG_PARAM("%d", transfer_type);
3536 CVMX_USB_LOG_PARAM("%d", transfer_dir);
3537 CVMX_USB_LOG_PARAM("%d", max_packet_size);
3538 CVMX_USB_LOG_PARAM("0x%llx", (unsigned long long)buffer);
3539 CVMX_USB_LOG_PARAM("%d", buffer_length);
3541 if (cvmx_unlikely((endpoint_num < 0) || (endpoint_num > 4)))
3542 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
3543 if (cvmx_unlikely(transfer_type > CVMX_USB_TRANSFER_INTERRUPT))
3544 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
3545 if (cvmx_unlikely((transfer_dir != CVMX_USB_DIRECTION_OUT) &&
3546 (transfer_dir != CVMX_USB_DIRECTION_IN)))
3547 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
3548 if (cvmx_unlikely((max_packet_size < 0) || (max_packet_size > 512)))
3549 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
3550 if (cvmx_unlikely(!buffer))
3551 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
3552 if (cvmx_unlikely(buffer_length < 0))
3553 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
3554 if (cvmx_unlikely((usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE) == 0))
3555 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
3557 if (transfer_dir == CVMX_USB_DIRECTION_IN)
3559 cvmx_usbcx_doepctlx_t usbc_doepctl;
3560 cvmx_usbcx_doeptsizx_t usbc_doeptsiz;
3562 /* Setup the locations the DMA engines use */
3563 __cvmx_usb_write_csr64(usb, CVMX_USBNX_DMA0_INB_CHN0(usb->index) + endpoint_num*8, buffer);
3564 usbc_doeptsiz.u32 = 0;
3565 usbc_doeptsiz.s.mc = 1; // FIXME
3566 usbc_doeptsiz.s.pktcnt = (buffer_length + max_packet_size - 1) / max_packet_size;
3567 if (usbc_doeptsiz.s.pktcnt == 0)
3568 usbc_doeptsiz.s.pktcnt = 1;
3569 usbc_doeptsiz.s.xfersize = buffer_length;
3570 __cvmx_usb_write_csr32(usb, CVMX_USBCX_DOEPTSIZX(endpoint_num, usb->index), usbc_doeptsiz.u32);
3572 usbc_doepctl.u32 = 0;
3573 usbc_doepctl.s.epena = 1;
3574 usbc_doepctl.s.setd1pid = 0; // FIXME
3575 usbc_doepctl.s.setd0pid = 0; // FIXME
3576 usbc_doepctl.s.cnak = 1;
3577 usbc_doepctl.s.eptype = transfer_type;
3578 usbc_doepctl.s.usbactep = 1;
3579 usbc_doepctl.s.mps = max_packet_size;
3580 __cvmx_usb_write_csr32(usb, CVMX_USBCX_DOEPCTLX(endpoint_num, usb->index), usbc_doepctl.u32);
3584 cvmx_usbcx_diepctlx_t usbc_diepctl;
3585 cvmx_usbcx_dieptsizx_t usbc_dieptsiz;
3587 /* Setup the locations the DMA engines use */
3588 __cvmx_usb_write_csr64(usb, CVMX_USBNX_DMA0_OUTB_CHN0(usb->index) + endpoint_num*8, buffer);
3589 usbc_dieptsiz.u32 = 0;
3590 usbc_dieptsiz.s.mc = 1; // FIXME
3591 usbc_dieptsiz.s.pktcnt = (buffer_length + max_packet_size - 1) / max_packet_size;
3592 if (usbc_dieptsiz.s.pktcnt == 0)
3593 usbc_dieptsiz.s.pktcnt = 1;
3594 usbc_dieptsiz.s.xfersize = buffer_length;
3595 __cvmx_usb_write_csr32(usb, CVMX_USBCX_DIEPTSIZX(endpoint_num, usb->index), usbc_dieptsiz.u32);
3597 usbc_diepctl.u32 = 0;
3598 usbc_diepctl.s.epena = 1;
3599 usbc_diepctl.s.setd1pid = 0; // FIXME
3600 usbc_diepctl.s.setd0pid = 0; // FIXME
3601 usbc_diepctl.s.cnak = 1;
3602 if ((transfer_type == CVMX_USB_TRANSFER_INTERRUPT) ||
3603 (transfer_type == CVMX_USB_TRANSFER_ISOCHRONOUS))
3604 usbc_diepctl.s.txfnum = endpoint_num; // FIXME
3606 usbc_diepctl.s.txfnum = 0;
3607 usbc_diepctl.s.eptype = transfer_type;
3608 usbc_diepctl.s.usbactep = 1;
3609 usbc_diepctl.s.nextep = endpoint_num - 1; // FIXME
3610 usbc_diepctl.s.mps = max_packet_size;
3611 __cvmx_usb_write_csr32(usb, CVMX_USBCX_DIEPCTLX(endpoint_num, usb->index), usbc_diepctl.u32);
3614 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
3619 * Disable an endpoint in device mode.
3621 * @param state USB device state populated by
3622 * cvmx_usb_initialize().
3623 * @param endpoint_num
3624 * The endpoint number to disable (0-4)
3626 * @return CVMX_USB_SUCCESS or a negative error code defined in
3627 * cvmx_usb_status_t.
3629 cvmx_usb_status_t cvmx_usb_device_disable_endpoint(cvmx_usb_state_t *state,
3632 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
3634 CVMX_USB_LOG_CALLED();
3635 CVMX_USB_LOG_PARAM("%p", state);
3636 CVMX_USB_LOG_PARAM("%d", endpoint_num);
3638 if (cvmx_unlikely((endpoint_num < 0) || (endpoint_num > 4)))
3639 CVMX_USB_RETURN(CVMX_USB_INVALID_PARAM);
3640 if (cvmx_unlikely((usb->init_flags & CVMX_USB_INITIALIZE_FLAGS_DEVICE_MODE) == 0))
3641 CVMX_USB_RETURN(CVMX_USB_INCORRECT_MODE);
3643 USB_SET_FIELD32(CVMX_USBCX_DOEPCTLX(endpoint_num, usb->index),
3644 cvmx_usbcx_doepctlx_t, epdis, 1);
3645 USB_SET_FIELD32(CVMX_USBCX_DIEPCTLX(endpoint_num, usb->index),
3646 cvmx_usbcx_diepctlx_t, epdis, 1);
3648 CVMX_USB_RETURN(CVMX_USB_SUCCESS);
3651 extern void cvmx_usb_set_toggle(cvmx_usb_state_t *state, int endpoint_num, int toggle)
3653 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
3654 cvmx_usb_pipe_t *pipe = usb->pipe + endpoint_num;
3656 pipe->pid_toggle = !!toggle;
3659 extern int cvmx_usb_get_toggle(cvmx_usb_state_t *state, int endpoint_num)
3661 cvmx_usb_internal_state_t *usb = (cvmx_usb_internal_state_t*)state;
3662 cvmx_usb_pipe_t *pipe = usb->pipe + endpoint_num;
3664 if (pipe->pid_toggle)