Merge branch 'next' of git://git.denx.de/u-boot-usb into next

- Assorted XHCI improvements
This commit is contained in:
Tom Rini 2020-10-01 14:52:56 -04:00
commit 7e373a1a6a
6 changed files with 97 additions and 117 deletions

View File

@ -236,8 +236,7 @@ static void xhci_link_segments(struct xhci_segment *prev,
*/
val = le32_to_cpu(prev->trbs[TRBS_PER_SEGMENT-1].link.control);
val &= ~TRB_TYPE_BITMASK;
val |= (TRB_LINK << TRB_TYPE_SHIFT);
val |= TRB_TYPE(TRB_LINK);
prev->trbs[TRBS_PER_SEGMENT-1].link.control = cpu_to_le32(val);
}
}
@ -826,25 +825,22 @@ void xhci_setup_addressable_virt_dev(struct xhci_ctrl *ctrl,
/* Step 4 - ring already allocated */
/* Step 5 */
ep0_ctx->ep_info2 = cpu_to_le32(CTRL_EP << EP_TYPE_SHIFT);
ep0_ctx->ep_info2 = cpu_to_le32(EP_TYPE(CTRL_EP));
debug("SPEED = %d\n", speed);
switch (speed) {
case USB_SPEED_SUPER:
ep0_ctx->ep_info2 |= cpu_to_le32(((512 & MAX_PACKET_MASK) <<
MAX_PACKET_SHIFT));
ep0_ctx->ep_info2 |= cpu_to_le32(MAX_PACKET(512));
debug("Setting Packet size = 512bytes\n");
break;
case USB_SPEED_HIGH:
/* USB core guesses at a 64-byte max packet first for FS devices */
case USB_SPEED_FULL:
ep0_ctx->ep_info2 |= cpu_to_le32(((64 & MAX_PACKET_MASK) <<
MAX_PACKET_SHIFT));
ep0_ctx->ep_info2 |= cpu_to_le32(MAX_PACKET(64));
debug("Setting Packet size = 64bytes\n");
break;
case USB_SPEED_LOW:
ep0_ctx->ep_info2 |= cpu_to_le32(((8 & MAX_PACKET_MASK) <<
MAX_PACKET_SHIFT));
ep0_ctx->ep_info2 |= cpu_to_le32(MAX_PACKET(8));
debug("Setting Packet size = 8bytes\n");
break;
default:
@ -853,9 +849,7 @@ void xhci_setup_addressable_virt_dev(struct xhci_ctrl *ctrl,
}
/* EP 0 can handle "burst" sizes of 1, so Max Burst Size field is 0 */
ep0_ctx->ep_info2 |=
cpu_to_le32(((0 & MAX_BURST_MASK) << MAX_BURST_SHIFT) |
((3 & ERROR_COUNT_MASK) << ERROR_COUNT_SHIFT));
ep0_ctx->ep_info2 |= cpu_to_le32(MAX_BURST(0) | ERROR_COUNT(3));
trb_64 = virt_to_phys(virt_dev->eps[0].ring->first_seg->trbs);
ep0_ctx->deq = cpu_to_le64(trb_64 | virt_dev->eps[0].ring->cycle_state);

View File

@ -258,6 +258,7 @@ static int xhci_mtk_probe(struct udevice *dev)
if (ret)
goto ssusb_init_err;
mtk->ctrl.quirks = XHCI_MTK_HOST;
hcor = (struct xhci_hcor *)((uintptr_t)mtk->hcd +
HC_LENGTH(xhci_readl(&mtk->hcd->cr_capbase)));

View File

@ -146,6 +146,7 @@ static int xhci_rcar_ofdata_to_platdata(struct udevice *dev)
}
static const struct udevice_id xhci_rcar_ids[] = {
{ .compatible = "renesas,rcar-gen3-xhci" },
{ .compatible = "renesas,xhci-r8a7795" },
{ .compatible = "renesas,xhci-r8a7796" },
{ .compatible = "renesas,xhci-r8a77965" },

View File

@ -298,55 +298,57 @@ void xhci_queue_command(struct xhci_ctrl *ctrl, u8 *ptr, u32 slot_id,
xhci_writel(&ctrl->dba->doorbell[0], DB_VALUE_HOST);
}
/**
* The TD size is the number of bytes remaining in the TD (including this TRB),
* right shifted by 10.
* It must fit in bits 21:17, so it can't be bigger than 31.
/*
* For xHCI 1.0 host controllers, TD size is the number of max packet sized
* packets remaining in the TD (*not* including this TRB).
*
* @param remainder remaining packets to be sent
* @return remainder if remainder is less than max else max
*/
static u32 xhci_td_remainder(unsigned int remainder)
{
u32 max = (1 << (21 - 17 + 1)) - 1;
if ((remainder >> 10) >= max)
return max << 17;
else
return (remainder >> 10) << 17;
}
/**
* Finds out the remanining packets to be sent
* Total TD packet count = total_packet_count =
* DIV_ROUND_UP(TD size in bytes / wMaxPacketSize)
*
* @param running_total total size sent so far
* Packets transferred up to and including this TRB = packets_transferred =
* rounddown(total bytes transferred including this TRB / wMaxPacketSize)
*
* TD size = total_packet_count - packets_transferred
*
* For xHCI 0.96 and older, TD size field should be the remaining bytes
* including this TRB, right shifted by 10
*
* For all hosts it must fit in bits 21:17, so it can't be bigger than 31.
* This is taken care of in the TRB_TD_SIZE() macro
*
* The last TRB in a TD must have the TD size set to zero.
*
* @param ctrl host controller data structure
* @param transferred total size sent so far
* @param trb_buff_len length of the TRB Buffer
* @param total_packet_count total packet count
* @param maxpacketsize max packet size of current pipe
* @param num_trbs_left number of TRBs left to be processed
* @return 0 if running_total or trb_buff_len is 0, else remainder
* @param td_total_len total packet count
* @param maxp max packet size of current pipe
* @param more_trbs_coming indicate last trb in TD
* @return remainder
*/
static u32 xhci_v1_0_td_remainder(int running_total,
int trb_buff_len,
unsigned int total_packet_count,
int maxpacketsize,
unsigned int num_trbs_left)
static u32 xhci_td_remainder(struct xhci_ctrl *ctrl, int transferred,
int trb_buff_len, unsigned int td_total_len,
int maxp, bool more_trbs_coming)
{
int packets_transferred;
u32 total_packet_count;
/* MTK xHCI 0.96 contains some features from 1.0 */
if (ctrl->hci_version < 0x100 && !(ctrl->quirks & XHCI_MTK_HOST))
return ((td_total_len - transferred) >> 10);
/* One TRB with a zero-length data packet. */
if (num_trbs_left == 0 || (running_total == 0 && trb_buff_len == 0))
if (!more_trbs_coming || (transferred == 0 && trb_buff_len == 0) ||
trb_buff_len == td_total_len)
return 0;
/*
* All the TRB queueing functions don't count the current TRB in
* running_total.
*/
packets_transferred = (running_total + trb_buff_len) / maxpacketsize;
/* for MTK xHCI 0.96, TD size include this TRB, but not in 1.x */
if ((ctrl->quirks & XHCI_MTK_HOST) && (ctrl->hci_version < 0x100))
trb_buff_len = 0;
if ((total_packet_count - packets_transferred) > 31)
return 31 << 17;
return (total_packet_count - packets_transferred) << 17;
total_packet_count = DIV_ROUND_UP(td_total_len, maxp);
/* Queueing functions don't count the current TRB into transferred */
return (total_packet_count - ((transferred + trb_buff_len) / maxp));
}
/**
@ -572,7 +574,7 @@ int xhci_bulk_tx(struct usb_device *udev, unsigned long pipe,
union xhci_trb *event;
int running_total, trb_buff_len;
unsigned int total_packet_count;
bool more_trbs_coming = true;
int maxpacketsize;
u64 addr;
int ret;
@ -636,8 +638,6 @@ int xhci_bulk_tx(struct usb_device *udev, unsigned long pipe,
running_total = 0;
maxpacketsize = usb_maxpacket(udev, pipe);
total_packet_count = DIV_ROUND_UP(length, maxpacketsize);
/* How much data is in the first TRB? */
/*
* How much data is (potentially) left before the 64KB boundary?
@ -672,34 +672,30 @@ int xhci_bulk_tx(struct usb_device *udev, unsigned long pipe,
* Chain all the TRBs together; clear the chain bit in the last
* TRB to indicate it's the last TRB in the chain.
*/
if (num_trbs > 1)
if (num_trbs > 1) {
field |= TRB_CHAIN;
else
} else {
field |= TRB_IOC;
more_trbs_coming = false;
}
/* Only set interrupt on short packet for IN endpoints */
if (usb_pipein(pipe))
field |= TRB_ISP;
/* Set the TRB length, TD size, and interrupter fields. */
if (HC_VERSION(xhci_readl(&ctrl->hccr->cr_capbase)) < 0x100)
remainder = xhci_td_remainder(length - running_total);
else
remainder = xhci_v1_0_td_remainder(running_total,
trb_buff_len,
total_packet_count,
maxpacketsize,
num_trbs - 1);
remainder = xhci_td_remainder(ctrl, running_total, trb_buff_len,
length, maxpacketsize,
more_trbs_coming);
length_field = ((trb_buff_len & TRB_LEN_MASK) |
remainder |
((0 & TRB_INTR_TARGET_MASK) <<
TRB_INTR_TARGET_SHIFT));
length_field = (TRB_LEN(trb_buff_len) |
TRB_TD_SIZE(remainder) |
TRB_INTR_TARGET(0));
trb_fields[0] = lower_32_bits(addr);
trb_fields[1] = upper_32_bits(addr);
trb_fields[2] = length_field;
trb_fields[3] = field | (TRB_NORMAL << TRB_TYPE_SHIFT);
trb_fields[3] = field | TRB_TYPE(TRB_NORMAL);
queue_trb(ctrl, ring, (num_trbs > 1), trb_fields);
@ -764,6 +760,7 @@ int xhci_ctrl_tx(struct usb_device *udev, unsigned long pipe,
struct xhci_virt_device *virt_dev = ctrl->devs[slot_id];
struct xhci_ring *ep_ring;
union xhci_trb *event;
u32 remainder;
debug("req=%u (%#x), type=%u (%#x), value=%u (%#x), index=%u\n",
req->request, req->request,
@ -825,17 +822,17 @@ int xhci_ctrl_tx(struct usb_device *udev, unsigned long pipe,
/* Queue setup TRB - see section 6.4.1.2.1 */
/* FIXME better way to translate setup_packet into two u32 fields? */
field = 0;
field |= TRB_IDT | (TRB_SETUP << TRB_TYPE_SHIFT);
field |= TRB_IDT | TRB_TYPE(TRB_SETUP);
if (start_cycle == 0)
field |= 0x1;
/* xHCI 1.0 6.4.1.2.1: Transfer Type field */
if (HC_VERSION(xhci_readl(&ctrl->hccr->cr_capbase)) >= 0x100) {
if (ctrl->hci_version >= 0x100 || ctrl->quirks & XHCI_MTK_HOST) {
if (length > 0) {
if (req->requesttype & USB_DIR_IN)
field |= (TRB_DATA_IN << TRB_TX_TYPE_SHIFT);
field |= TRB_TX_TYPE(TRB_DATA_IN);
else
field |= (TRB_DATA_OUT << TRB_TX_TYPE_SHIFT);
field |= TRB_TX_TYPE(TRB_DATA_OUT);
}
}
@ -851,8 +848,7 @@ int xhci_ctrl_tx(struct usb_device *udev, unsigned long pipe,
trb_fields[1] = le16_to_cpu(req->index) |
le16_to_cpu(req->length) << 16;
/* TRB_LEN | (TRB_INTR_TARGET) */
trb_fields[2] = (8 | ((0 & TRB_INTR_TARGET_MASK) <<
TRB_INTR_TARGET_SHIFT));
trb_fields[2] = (TRB_LEN(8) | TRB_INTR_TARGET(0));
/* Immediate data in pointer */
trb_fields[3] = field;
queue_trb(ctrl, ep_ring, true, trb_fields);
@ -862,16 +858,18 @@ int xhci_ctrl_tx(struct usb_device *udev, unsigned long pipe,
/* If there's data, queue data TRBs */
/* Only set interrupt on short packet for IN endpoints */
if (usb_pipein(pipe))
field = TRB_ISP | (TRB_DATA << TRB_TYPE_SHIFT);
field = TRB_ISP | TRB_TYPE(TRB_DATA);
else
field = (TRB_DATA << TRB_TYPE_SHIFT);
field = TRB_TYPE(TRB_DATA);
length_field = (length & TRB_LEN_MASK) | xhci_td_remainder(length) |
((0 & TRB_INTR_TARGET_MASK) << TRB_INTR_TARGET_SHIFT);
remainder = xhci_td_remainder(ctrl, 0, length, length,
usb_maxpacket(udev, pipe), true);
length_field = TRB_LEN(length) | TRB_TD_SIZE(remainder) |
TRB_INTR_TARGET(0);
debug("length_field = %d, length = %d,"
"xhci_td_remainder(length) = %d , TRB_INTR_TARGET(0) = %d\n",
length_field, (length & TRB_LEN_MASK),
xhci_td_remainder(length), 0);
length_field, TRB_LEN(length),
TRB_TD_SIZE(remainder), 0);
if (length > 0) {
if (req->requesttype & USB_DIR_IN)
@ -901,11 +899,10 @@ int xhci_ctrl_tx(struct usb_device *udev, unsigned long pipe,
trb_fields[0] = 0;
trb_fields[1] = 0;
trb_fields[2] = ((0 & TRB_INTR_TARGET_MASK) << TRB_INTR_TARGET_SHIFT);
trb_fields[2] = TRB_INTR_TARGET(0);
/* Event on completion */
trb_fields[3] = field | TRB_IOC |
(TRB_STATUS << TRB_TYPE_SHIFT) |
ep_ring->cycle_state;
TRB_TYPE(TRB_STATUS) | ep_ring->cycle_state;
queue_trb(ctrl, ep_ring, false, trb_fields);

View File

@ -33,6 +33,7 @@
#include <linux/bug.h>
#include <linux/delay.h>
#include <linux/errno.h>
#include <linux/iopoll.h>
#include <usb/xhci.h>
#ifndef CONFIG_USB_MAX_CONTROLLER_COUNT
@ -143,23 +144,19 @@ struct xhci_ctrl *xhci_get_ctrl(struct usb_device *udev)
* @param usec time to wait till
* @return 0 if handshake is success else < 0 on failure
*/
static int handshake(uint32_t volatile *ptr, uint32_t mask,
uint32_t done, int usec)
static int
handshake(uint32_t volatile *ptr, uint32_t mask, uint32_t done, int usec)
{
uint32_t result;
int ret;
do {
result = xhci_readl(ptr);
if (result == ~(uint32_t)0)
return -ENODEV;
result &= mask;
if (result == done)
return 0;
usec--;
udelay(1);
} while (usec > 0);
ret = readx_poll_sleep_timeout(xhci_readl, ptr, result,
(result & mask) == done || result == U32_MAX,
1, usec);
if (result == U32_MAX) /* card removed */
return -ENODEV;
return -ETIMEDOUT;
return ret;
}
/**
@ -618,8 +615,7 @@ static int xhci_set_configuration(struct usb_device *udev)
cpu_to_le32(EP_MAX_ESIT_PAYLOAD_HI(max_esit_payload) |
EP_INTERVAL(interval) | EP_MULT(mult));
ep_ctx[ep_index]->ep_info2 =
cpu_to_le32(ep_type << EP_TYPE_SHIFT);
ep_ctx[ep_index]->ep_info2 = cpu_to_le32(EP_TYPE(ep_type));
ep_ctx[ep_index]->ep_info2 |=
cpu_to_le32(MAX_PACKET
(get_unaligned(&endpt_desc->wMaxPacketSize)));
@ -650,7 +646,7 @@ static int xhci_set_configuration(struct usb_device *udev)
* are put into reserved DWs in Slot and Endpoint Contexts
* for synchronous endpoints.
*/
if (IS_ENABLED(CONFIG_USB_XHCI_MTK)) {
if (ctrl->quirks & XHCI_MTK_HOST) {
ep_ctx[ep_index]->reserved[0] =
cpu_to_le32(EP_BPKTS(1) | EP_BBM(1));
}
@ -832,8 +828,7 @@ int xhci_check_maxpacket(struct usb_device *udev)
ctrl->devs[slot_id]->out_ctx, ep_index);
in_ctx = ctrl->devs[slot_id]->in_ctx;
ep_ctx = xhci_get_ep_ctx(ctrl, in_ctx, ep_index);
ep_ctx->ep_info2 &= cpu_to_le32(~((0xffff & MAX_PACKET_MASK)
<< MAX_PACKET_SHIFT));
ep_ctx->ep_info2 &= cpu_to_le32(~MAX_PACKET(MAX_PACKET_MASK));
ep_ctx->ep_info2 |= cpu_to_le32(MAX_PACKET(max_packet_size));
/*
@ -1257,8 +1252,7 @@ static int xhci_lowlevel_init(struct xhci_ctrl *ctrl)
return -ENOMEM;
reg = xhci_readl(&hccr->cr_hcsparams1);
descriptor.hub.bNbrPorts = ((reg & HCS_MAX_PORTS_MASK) >>
HCS_MAX_PORTS_SHIFT);
descriptor.hub.bNbrPorts = HCS_MAX_PORTS(reg);
printf("Register %x NbrPorts %d\n", reg, descriptor.hub.bNbrPorts);
/* Port Indicators */
@ -1283,6 +1277,7 @@ static int xhci_lowlevel_init(struct xhci_ctrl *ctrl)
reg = HC_VERSION(xhci_readl(&hccr->cr_capbase));
printf("USB XHCI %x.%02x\n", reg >> 8, reg & 0xff);
ctrl->hci_version = reg;
return 0;
}

View File

@ -101,8 +101,6 @@ struct xhci_hccr {
/* bits 8:18, Max Interrupters */
#define HCS_MAX_INTRS(p) (((p) >> 8) & 0x7ff)
/* bits 24:31, Max Ports - max value is 0x7F = 127 ports */
#define HCS_MAX_PORTS_SHIFT 24
#define HCS_MAX_PORTS_MASK (0xff << HCS_MAX_PORTS_SHIFT)
#define HCS_MAX_PORTS(p) (((p) >> 24) & 0xff)
/* HCSPARAMS2 - hcs_params2 - bitmasks */
@ -634,11 +632,8 @@ struct xhci_ep_ctx {
*/
#define FORCE_EVENT (0x1)
#define ERROR_COUNT(p) (((p) & 0x3) << 1)
#define ERROR_COUNT_SHIFT (1)
#define ERROR_COUNT_MASK (0x3)
#define CTX_TO_EP_TYPE(p) (((p) >> 3) & 0x7)
#define EP_TYPE(p) ((p) << 3)
#define EP_TYPE_SHIFT (3)
#define ISOC_OUT_EP 1
#define BULK_OUT_EP 2
#define INT_OUT_EP 3
@ -649,13 +644,10 @@ struct xhci_ep_ctx {
/* bit 6 reserved */
/* bit 7 is Host Initiate Disable - for disabling stream selection */
#define MAX_BURST(p) (((p)&0xff) << 8)
#define MAX_BURST_MASK (0xff)
#define MAX_BURST_SHIFT (8)
#define CTX_TO_MAX_BURST(p) (((p) >> 8) & 0xff)
#define MAX_PACKET(p) (((p)&0xffff) << 16)
#define MAX_PACKET_MASK (0xffff)
#define MAX_PACKET_DECODED(p) (((p) >> 16) & 0xffff)
#define MAX_PACKET_SHIFT (16)
/* Get max packet size from ep desc. Bit 10..0 specify the max packet size.
* USB2.0 spec 9.6.6.
@ -849,10 +841,9 @@ struct xhci_event_cmd {
/* Normal TRB fields */
/* transfer_len bitmasks - bits 0:16 */
#define TRB_LEN(p) ((p) & 0x1ffff)
#define TRB_LEN_MASK (0x1ffff)
/* TD Size, packets remaining in this TD, bits 21:17 (5 bits, so max 31) */
#define TRB_TD_SIZE(p) (min((p), (u32)31) << 17)
/* Interrupter Target - which MSI-X vector to target the completion event at */
#define TRB_INTR_TARGET_SHIFT (22)
#define TRB_INTR_TARGET_MASK (0x3ff)
#define TRB_INTR_TARGET(p) (((p) & 0x3ff) << 22)
#define GET_INTR_TARGET(p) (((p) >> 22) & 0x3ff)
#define TRB_TBC(p) (((p) & 0x3) << 7)
@ -882,7 +873,6 @@ struct xhci_event_cmd {
/* Control transfer TRB specific fields */
#define TRB_DIR_IN (1<<16)
#define TRB_TX_TYPE(p) ((p) << 16)
#define TRB_TX_TYPE_SHIFT (16)
#define TRB_DATA_OUT 2
#define TRB_DATA_IN 3
@ -903,7 +893,6 @@ union xhci_trb {
/* TRB bit mask */
#define TRB_TYPE_BITMASK (0xfc00)
#define TRB_TYPE(p) ((p) << 10)
#define TRB_TYPE_SHIFT (10)
#define TRB_FIELD_TO_TYPE(p) (((p) & TRB_TYPE_BITMASK) >> 10)
/* TRB type IDs */
@ -1227,6 +1216,9 @@ struct xhci_ctrl {
struct xhci_scratchpad *scratchpad;
struct xhci_virt_device *devs[MAX_HC_SLOTS];
int rootdev;
u16 hci_version;
u32 quirks;
#define XHCI_MTK_HOST BIT(0)
};
unsigned long trb_addr(struct xhci_segment *seg, union xhci_trb *trb);