ci_udc.c 19.2 KB
Newer Older
1 2 3 4
/*
 * Copyright 2011, Marvell Semiconductor Inc.
 * Lei Wen <leiwen@marvell.com>
 *
5
 * SPDX-License-Identifier:	GPL-2.0+
6 7 8 9 10 11 12 13 14 15
 *
 * Back ported to the 8xx platform (from the 8260 platform) by
 * Murray.Jensen@cmst.csiro.au, 27-Jan-01.
 */

#include <common.h>
#include <command.h>
#include <config.h>
#include <net.h>
#include <malloc.h>
16 17
#include <asm/byteorder.h>
#include <asm/errno.h>
18
#include <asm/io.h>
19
#include <asm/unaligned.h>
20
#include <linux/types.h>
21 22
#include <linux/usb/ch9.h>
#include <linux/usb/gadget.h>
M
Marek Vasut 已提交
23
#include <usb/ci_udc.h>
24
#include "../host/ehci.h"
M
Marek Vasut 已提交
25
#include "ci_udc.h"
26

27 28 29 30 31 32 33 34 35 36
/*
 * Check if the system has too long cachelines. If the cachelines are
 * longer then 128b, the driver will not be able flush/invalidate data
 * cache over separate QH entries. We use 128b because one QH entry is
 * 64b long and there are always two QH list entries for each endpoint.
 */
#if ARCH_DMA_MINALIGN > 128
#error This driver can not work on systems with caches longer than 128b
#endif

37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72
#ifndef DEBUG
#define DBG(x...) do {} while (0)
#else
#define DBG(x...) printf(x)
static const char *reqname(unsigned r)
{
	switch (r) {
	case USB_REQ_GET_STATUS: return "GET_STATUS";
	case USB_REQ_CLEAR_FEATURE: return "CLEAR_FEATURE";
	case USB_REQ_SET_FEATURE: return "SET_FEATURE";
	case USB_REQ_SET_ADDRESS: return "SET_ADDRESS";
	case USB_REQ_GET_DESCRIPTOR: return "GET_DESCRIPTOR";
	case USB_REQ_SET_DESCRIPTOR: return "SET_DESCRIPTOR";
	case USB_REQ_GET_CONFIGURATION: return "GET_CONFIGURATION";
	case USB_REQ_SET_CONFIGURATION: return "SET_CONFIGURATION";
	case USB_REQ_GET_INTERFACE: return "GET_INTERFACE";
	case USB_REQ_SET_INTERFACE: return "SET_INTERFACE";
	default: return "*UNKNOWN*";
	}
}
#endif

static struct usb_endpoint_descriptor ep0_out_desc = {
	.bLength = sizeof(struct usb_endpoint_descriptor),
	.bDescriptorType = USB_DT_ENDPOINT,
	.bEndpointAddress = 0,
	.bmAttributes =	USB_ENDPOINT_XFER_CONTROL,
};

static struct usb_endpoint_descriptor ep0_in_desc = {
	.bLength = sizeof(struct usb_endpoint_descriptor),
	.bDescriptorType = USB_DT_ENDPOINT,
	.bEndpointAddress = USB_DIR_IN,
	.bmAttributes =	USB_ENDPOINT_XFER_CONTROL,
};

M
Marek Vasut 已提交
73 74
static int ci_pullup(struct usb_gadget *gadget, int is_on);
static int ci_ep_enable(struct usb_ep *ep,
75
		const struct usb_endpoint_descriptor *desc);
M
Marek Vasut 已提交
76 77
static int ci_ep_disable(struct usb_ep *ep);
static int ci_ep_queue(struct usb_ep *ep,
78 79
		struct usb_request *req, gfp_t gfp_flags);
static struct usb_request *
M
Marek Vasut 已提交
80 81
ci_ep_alloc_request(struct usb_ep *ep, unsigned int gfp_flags);
static void ci_ep_free_request(struct usb_ep *ep, struct usb_request *_req);
82

M
Marek Vasut 已提交
83 84
static struct usb_gadget_ops ci_udc_ops = {
	.pullup = ci_pullup,
85 86
};

M
Marek Vasut 已提交
87 88 89 90 91 92
static struct usb_ep_ops ci_ep_ops = {
	.enable         = ci_ep_enable,
	.disable        = ci_ep_disable,
	.queue          = ci_ep_queue,
	.alloc_request  = ci_ep_alloc_request,
	.free_request   = ci_ep_free_request,
93 94
};

95
/* Init values for USB endpoints. */
M
Marek Vasut 已提交
96
static const struct usb_ep ci_ep_init[2] = {
97 98 99
	[0] = {	/* EP 0 */
		.maxpacket	= 64,
		.name		= "ep0",
M
Marek Vasut 已提交
100
		.ops		= &ci_ep_ops,
101 102 103 104
	},
	[1] = {	/* EP 1..n */
		.maxpacket	= 512,
		.name		= "ep-",
M
Marek Vasut 已提交
105
		.ops		= &ci_ep_ops,
106 107 108
	},
};

M
Marek Vasut 已提交
109
static struct ci_drv controller = {
110
	.gadget	= {
M
Marek Vasut 已提交
111 112
		.name	= "ci_udc",
		.ops	= &ci_udc_ops,
113
		.is_dualspeed = 1,
114 115 116
	},
};

117
/**
M
Marek Vasut 已提交
118
 * ci_get_qh() - return queue head for endpoint
119 120 121 122 123 124
 * @ep_num:	Endpoint number
 * @dir_in:	Direction of the endpoint (IN = 1, OUT = 0)
 *
 * This function returns the QH associated with particular endpoint
 * and it's direction.
 */
M
Marek Vasut 已提交
125
static struct ept_queue_head *ci_get_qh(int ep_num, int dir_in)
126 127 128 129
{
	return &controller.epts[(ep_num * 2) + dir_in];
}

130
/**
M
Marek Vasut 已提交
131
 * ci_get_qtd() - return queue item for endpoint
132 133 134 135 136 137
 * @ep_num:	Endpoint number
 * @dir_in:	Direction of the endpoint (IN = 1, OUT = 0)
 *
 * This function returns the QH associated with particular endpoint
 * and it's direction.
 */
M
Marek Vasut 已提交
138
static struct ept_queue_item *ci_get_qtd(int ep_num, int dir_in)
139 140 141 142
{
	return controller.items[(ep_num * 2) + dir_in];
}

143
/**
M
Marek Vasut 已提交
144
 * ci_flush_qh - flush cache over queue head
145 146 147 148
 * @ep_num:	Endpoint number
 *
 * This function flushes cache over QH for particular endpoint.
 */
M
Marek Vasut 已提交
149
static void ci_flush_qh(int ep_num)
150
{
M
Marek Vasut 已提交
151
	struct ept_queue_head *head = ci_get_qh(ep_num, 0);
152 153 154 155 156 157 158
	const uint32_t start = (uint32_t)head;
	const uint32_t end = start + 2 * sizeof(*head);

	flush_dcache_range(start, end);
}

/**
M
Marek Vasut 已提交
159
 * ci_invalidate_qh - invalidate cache over queue head
160 161 162 163
 * @ep_num:	Endpoint number
 *
 * This function invalidates cache over QH for particular endpoint.
 */
M
Marek Vasut 已提交
164
static void ci_invalidate_qh(int ep_num)
165
{
M
Marek Vasut 已提交
166
	struct ept_queue_head *head = ci_get_qh(ep_num, 0);
167 168 169 170 171 172 173
	uint32_t start = (uint32_t)head;
	uint32_t end = start + 2 * sizeof(*head);

	invalidate_dcache_range(start, end);
}

/**
M
Marek Vasut 已提交
174
 * ci_flush_qtd - flush cache over queue item
175 176 177 178
 * @ep_num:	Endpoint number
 *
 * This function flushes cache over qTD pair for particular endpoint.
 */
M
Marek Vasut 已提交
179
static void ci_flush_qtd(int ep_num)
180
{
M
Marek Vasut 已提交
181
	struct ept_queue_item *item = ci_get_qtd(ep_num, 0);
182 183 184 185 186 187 188 189
	const uint32_t start = (uint32_t)item;
	const uint32_t end_raw = start + 2 * sizeof(*item);
	const uint32_t end = roundup(end_raw, ARCH_DMA_MINALIGN);

	flush_dcache_range(start, end);
}

/**
M
Marek Vasut 已提交
190
 * ci_invalidate_qtd - invalidate cache over queue item
191 192 193 194
 * @ep_num:	Endpoint number
 *
 * This function invalidates cache over qTD pair for particular endpoint.
 */
M
Marek Vasut 已提交
195
static void ci_invalidate_qtd(int ep_num)
196
{
M
Marek Vasut 已提交
197
	struct ept_queue_item *item = ci_get_qtd(ep_num, 0);
198 199 200 201 202 203 204
	const uint32_t start = (uint32_t)item;
	const uint32_t end_raw = start + 2 * sizeof(*item);
	const uint32_t end = roundup(end_raw, ARCH_DMA_MINALIGN);

	invalidate_dcache_range(start, end);
}

205
static struct usb_request *
M
Marek Vasut 已提交
206
ci_ep_alloc_request(struct usb_ep *ep, unsigned int gfp_flags)
207
{
M
Marek Vasut 已提交
208 209
	struct ci_ep *ci_ep = container_of(ep, struct ci_ep, ep);
	return &ci_ep->req;
210 211
}

M
Marek Vasut 已提交
212
static void ci_ep_free_request(struct usb_ep *ep, struct usb_request *_req)
213 214 215 216
{
	return;
}

217
static void ep_enable(int num, int in, int maxpacket)
218
{
M
Marek Vasut 已提交
219
	struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
220 221 222 223 224 225 226 227
	unsigned n;

	n = readl(&udc->epctrl[num]);
	if (in)
		n |= (CTRL_TXE | CTRL_TXR | CTRL_TXT_BULK);
	else
		n |= (CTRL_RXE | CTRL_RXR | CTRL_RXT_BULK);

228
	if (num != 0) {
M
Marek Vasut 已提交
229
		struct ept_queue_head *head = ci_get_qh(num, in);
230

231
		head->config = CONFIG_MAX_PKT(maxpacket) | CONFIG_ZLT;
M
Marek Vasut 已提交
232
		ci_flush_qh(num);
233
	}
234 235 236
	writel(n, &udc->epctrl[num]);
}

M
Marek Vasut 已提交
237
static int ci_ep_enable(struct usb_ep *ep,
238 239
		const struct usb_endpoint_descriptor *desc)
{
M
Marek Vasut 已提交
240
	struct ci_ep *ci_ep = container_of(ep, struct ci_ep, ep);
241 242 243
	int num, in;
	num = desc->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK;
	in = (desc->bEndpointAddress & USB_DIR_IN) != 0;
M
Marek Vasut 已提交
244
	ci_ep->desc = desc;
245 246 247 248 249 250 251 252 253 254 255 256 257 258

	if (num) {
		int max = get_unaligned_le16(&desc->wMaxPacketSize);

		if ((max > 64) && (controller.gadget.speed == USB_SPEED_FULL))
			max = 64;
		if (ep->maxpacket != max) {
			DBG("%s: from %d to %d\n", __func__,
			    ep->maxpacket, max);
			ep->maxpacket = max;
		}
	}
	ep_enable(num, in, ep->maxpacket);
	DBG("%s: num=%d maxpacket=%d\n", __func__, num, ep->maxpacket);
259 260 261
	return 0;
}

M
Marek Vasut 已提交
262
static int ci_ep_disable(struct usb_ep *ep)
263
{
M
Marek Vasut 已提交
264
	struct ci_ep *ci_ep = container_of(ep, struct ci_ep, ep);
265

M
Marek Vasut 已提交
266
	ci_ep->desc = NULL;
267 268 269
	return 0;
}

M
Marek Vasut 已提交
270
static int ci_bounce(struct ci_ep *ep, int in)
M
Marek Vasut 已提交
271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298
{
	uint32_t addr = (uint32_t)ep->req.buf;
	uint32_t ba;

	/* Input buffer address is not aligned. */
	if (addr & (ARCH_DMA_MINALIGN - 1))
		goto align;

	/* Input buffer length is not aligned. */
	if (ep->req.length & (ARCH_DMA_MINALIGN - 1))
		goto align;

	/* The buffer is well aligned, only flush cache. */
	ep->b_len = ep->req.length;
	ep->b_buf = ep->req.buf;
	goto flush;

align:
	/* Use internal buffer for small payloads. */
	if (ep->req.length <= 64) {
		ep->b_len = 64;
		ep->b_buf = ep->b_fast;
	} else {
		ep->b_len = roundup(ep->req.length, ARCH_DMA_MINALIGN);
		ep->b_buf = memalign(ARCH_DMA_MINALIGN, ep->b_len);
		if (!ep->b_buf)
			return -ENOMEM;
	}
T
Troy Kisky 已提交
299 300
	if (in)
		memcpy(ep->b_buf, ep->req.buf, ep->req.length);
M
Marek Vasut 已提交
301 302 303 304 305 306 307 308

flush:
	ba = (uint32_t)ep->b_buf;
	flush_dcache_range(ba, ba + ep->b_len);

	return 0;
}

M
Marek Vasut 已提交
309
static void ci_debounce(struct ci_ep *ep, int in)
M
Marek Vasut 已提交
310 311 312 313
{
	uint32_t addr = (uint32_t)ep->req.buf;
	uint32_t ba = (uint32_t)ep->b_buf;

T
Troy Kisky 已提交
314 315 316 317 318
	if (in) {
		if (addr == ba)
			return;		/* not a bounce */
		goto free;
	}
M
Marek Vasut 已提交
319 320
	invalidate_dcache_range(ba, ba + ep->b_len);

T
Troy Kisky 已提交
321 322
	if (addr == ba)
		return;		/* not a bounce */
M
Marek Vasut 已提交
323

324
	memcpy(ep->req.buf, ep->b_buf, ep->req.actual);
T
Troy Kisky 已提交
325
free:
M
Marek Vasut 已提交
326
	/* Large payloads use allocated buffer, free it. */
T
Troy Kisky 已提交
327
	if (ep->b_buf != ep->b_fast)
M
Marek Vasut 已提交
328 329 330
		free(ep->b_buf);
}

M
Marek Vasut 已提交
331
static int ci_ep_queue(struct usb_ep *ep,
332 333
		struct usb_request *req, gfp_t gfp_flags)
{
M
Marek Vasut 已提交
334 335
	struct ci_ep *ci_ep = container_of(ep, struct ci_ep, ep);
	struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
336 337
	struct ept_queue_item *item;
	struct ept_queue_head *head;
M
Marek Vasut 已提交
338
	int bit, num, len, in, ret;
M
Marek Vasut 已提交
339 340 341 342
	num = ci_ep->desc->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK;
	in = (ci_ep->desc->bEndpointAddress & USB_DIR_IN) != 0;
	item = ci_get_qtd(num, in);
	head = ci_get_qh(num, in);
343 344
	len = req->length;

M
Marek Vasut 已提交
345
	ret = ci_bounce(ci_ep, in);
M
Marek Vasut 已提交
346 347 348
	if (ret)
		return ret;

349 350
	item->next = TERMINATE;
	item->info = INFO_BYTES(len) | INFO_IOC | INFO_ACTIVE;
M
Marek Vasut 已提交
351 352
	item->page0 = (uint32_t)ci_ep->b_buf;
	item->page1 = ((uint32_t)ci_ep->b_buf & 0xfffff000) + 0x1000;
353 354 355
	item->page2 = ((uint32_t)ci_ep->b_buf & 0xfffff000) + 0x2000;
	item->page3 = ((uint32_t)ci_ep->b_buf & 0xfffff000) + 0x3000;
	item->page4 = ((uint32_t)ci_ep->b_buf & 0xfffff000) + 0x4000;
M
Marek Vasut 已提交
356
	ci_flush_qtd(num);
357 358 359 360

	head->next = (unsigned) item;
	head->info = 0;

M
Marek Vasut 已提交
361
	DBG("ept%d %s queue len %x, buffer %p\n",
M
Marek Vasut 已提交
362 363
	    num, in ? "in" : "out", len, ci_ep->b_buf);
	ci_flush_qh(num);
364 365 366 367 368 369 370 371 372 373 374

	if (in)
		bit = EPT_TX(num);
	else
		bit = EPT_RX(num);

	writel(bit, &udc->epprime);

	return 0;
}

M
Marek Vasut 已提交
375
static void handle_ep_complete(struct ci_ep *ep)
376 377 378 379 380 381 382
{
	struct ept_queue_item *item;
	int num, in, len;
	num = ep->desc->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK;
	in = (ep->desc->bEndpointAddress & USB_DIR_IN) != 0;
	if (num == 0)
		ep->desc = &ep0_out_desc;
M
Marek Vasut 已提交
383 384
	item = ci_get_qtd(num, in);
	ci_invalidate_qtd(num);
385

386
	if (item->info & 0xff)
387 388
		printf("EP%d/%s FAIL info=%x pg0=%x\n",
		       num, in ? "in" : "out", item->info, item->page0);
389 390

	len = (item->info >> 16) & 0x7fff;
391
	ep->req.actual = ep->req.length - len;
M
Marek Vasut 已提交
392
	ci_debounce(ep, in);
T
Troy Kisky 已提交
393

394 395 396 397 398 399 400 401 402 403 404 405 406 407
	DBG("ept%d %s complete %x\n",
			num, in ? "in" : "out", len);
	ep->req.complete(&ep->ep, &ep->req);
	if (num == 0) {
		ep->req.length = 0;
		usb_ep_queue(&ep->ep, &ep->req, 0);
		ep->desc = &ep0_in_desc;
	}
}

#define SETUP(type, request) (((type) << 8) | (request))

static void handle_setup(void)
{
408
	struct usb_request *req = &controller.ep[0].req;
M
Marek Vasut 已提交
409
	struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
410 411 412 413 414
	struct ept_queue_head *head;
	struct usb_ctrlrequest r;
	int status = 0;
	int num, in, _num, _in, i;
	char *buf;
M
Marek Vasut 已提交
415
	head = ci_get_qh(0, 0);	/* EP0 OUT */
416

M
Marek Vasut 已提交
417
	ci_invalidate_qh(0);
418
	memcpy(&r, head->setup_data, sizeof(struct usb_ctrlrequest));
419 420 421
#ifdef CONFIG_CI_UDC_HAS_HOSTPC
	writel(EPT_RX(0), &udc->epsetupstat);
#else
422
	writel(EPT_RX(0), &udc->epstat);
423
#endif
424 425 426 427 428 429 430 431 432 433 434
	DBG("handle setup %s, %x, %x index %x value %x\n", reqname(r.bRequest),
	    r.bRequestType, r.bRequest, r.wIndex, r.wValue);

	switch (SETUP(r.bRequestType, r.bRequest)) {
	case SETUP(USB_RECIP_ENDPOINT, USB_REQ_CLEAR_FEATURE):
		_num = r.wIndex & 15;
		_in = !!(r.wIndex & 0x80);

		if ((r.wValue == 0) && (r.wLength == 0)) {
			req->length = 0;
			for (i = 0; i < NUM_ENDPOINTS; i++) {
M
Marek Vasut 已提交
435
				struct ci_ep *ep = &controller.ep[i];
436 437

				if (!ep->desc)
438
					continue;
439
				num = ep->desc->bEndpointAddress
440
						& USB_ENDPOINT_NUMBER_MASK;
441
				in = (ep->desc->bEndpointAddress
442 443
						& USB_DIR_IN) != 0;
				if ((num == _num) && (in == _in)) {
444
					ep_enable(num, in, ep->ep.maxpacket);
445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487
					usb_ep_queue(controller.gadget.ep0,
							req, 0);
					break;
				}
			}
		}
		return;

	case SETUP(USB_RECIP_DEVICE, USB_REQ_SET_ADDRESS):
		/*
		 * write address delayed (will take effect
		 * after the next IN txn)
		 */
		writel((r.wValue << 25) | (1 << 24), &udc->devaddr);
		req->length = 0;
		usb_ep_queue(controller.gadget.ep0, req, 0);
		return;

	case SETUP(USB_DIR_IN | USB_RECIP_DEVICE, USB_REQ_GET_STATUS):
		req->length = 2;
		buf = (char *)req->buf;
		buf[0] = 1 << USB_DEVICE_SELF_POWERED;
		buf[1] = 0;
		usb_ep_queue(controller.gadget.ep0, req, 0);
		return;
	}
	/* pass request up to the gadget driver */
	if (controller.driver)
		status = controller.driver->setup(&controller.gadget, &r);
	else
		status = -ENODEV;

	if (!status)
		return;
	DBG("STALL reqname %s type %x value %x, index %x\n",
	    reqname(r.bRequest), r.bRequestType, r.wValue, r.wIndex);
	writel((1<<16) | (1 << 0), &udc->epctrl[0]);
}

static void stop_activity(void)
{
	int i, num, in;
	struct ept_queue_head *head;
M
Marek Vasut 已提交
488
	struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
489
	writel(readl(&udc->epcomp), &udc->epcomp);
490 491 492
#ifdef CONFIG_CI_UDC_HAS_HOSTPC
	writel(readl(&udc->epsetupstat), &udc->epsetupstat);
#endif
493 494 495 496 497 498 499
	writel(readl(&udc->epstat), &udc->epstat);
	writel(0xffffffff, &udc->epflush);

	/* error out any pending reqs */
	for (i = 0; i < NUM_ENDPOINTS; i++) {
		if (i != 0)
			writel(0, &udc->epctrl[i]);
500 501
		if (controller.ep[i].desc) {
			num = controller.ep[i].desc->bEndpointAddress
502
				& USB_ENDPOINT_NUMBER_MASK;
503 504
			in = (controller.ep[i].desc->bEndpointAddress
				& USB_DIR_IN) != 0;
M
Marek Vasut 已提交
505
			head = ci_get_qh(num, in);
506
			head->info = INFO_ACTIVE;
M
Marek Vasut 已提交
507
			ci_flush_qh(num);
508 509 510 511 512 513
		}
	}
}

void udc_irq(void)
{
M
Marek Vasut 已提交
514
	struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530
	unsigned n = readl(&udc->usbsts);
	writel(n, &udc->usbsts);
	int bit, i, num, in;

	n &= (STS_SLI | STS_URI | STS_PCI | STS_UI | STS_UEI);
	if (n == 0)
		return;

	if (n & STS_URI) {
		DBG("-- reset --\n");
		stop_activity();
	}
	if (n & STS_SLI)
		DBG("-- suspend --\n");

	if (n & STS_PCI) {
531 532 533
		int max = 64;
		int speed = USB_SPEED_FULL;

534 535 536
#ifdef CONFIG_CI_UDC_HAS_HOSTPC
		bit = (readl(&udc->hostpc1_devlc) >> 25) & 3;
#else
537
		bit = (readl(&udc->portsc) >> 26) & 3;
538
#endif
539
		DBG("-- portchange %x %s\n", bit, (bit == 2) ? "High" : "Full");
540
		if (bit == 2) {
541 542 543 544 545 546 547
			speed = USB_SPEED_HIGH;
			max = 512;
		}
		controller.gadget.speed = speed;
		for (i = 1; i < NUM_ENDPOINTS; i++) {
			if (controller.ep[i].ep.maxpacket > max)
				controller.ep[i].ep.maxpacket = max;
548 549 550 551 552 553 554
		}
	}

	if (n & STS_UEI)
		printf("<UEI %x>\n", readl(&udc->epcomp));

	if ((n & STS_UI) || (n & STS_UEI)) {
555 556 557
#ifdef CONFIG_CI_UDC_HAS_HOSTPC
		n = readl(&udc->epsetupstat);
#else
558
		n = readl(&udc->epstat);
559
#endif
560 561 562 563 564 565 566 567
		if (n & EPT_RX(0))
			handle_setup();

		n = readl(&udc->epcomp);
		if (n != 0)
			writel(n, &udc->epcomp);

		for (i = 0; i < NUM_ENDPOINTS && n; i++) {
568 569
			if (controller.ep[i].desc) {
				num = controller.ep[i].desc->bEndpointAddress
570
					& USB_ENDPOINT_NUMBER_MASK;
571
				in = (controller.ep[i].desc->bEndpointAddress
572 573 574
						& USB_DIR_IN) != 0;
				bit = (in) ? EPT_TX(num) : EPT_RX(num);
				if (n & bit)
575
					handle_ep_complete(&controller.ep[i]);
576 577 578 579 580 581 582 583
			}
		}
	}
}

int usb_gadget_handle_interrupts(void)
{
	u32 value;
M
Marek Vasut 已提交
584
	struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
585 586 587 588 589 590 591 592

	value = readl(&udc->usbsts);
	if (value)
		udc_irq();

	return value;
}

M
Marek Vasut 已提交
593
static int ci_pullup(struct usb_gadget *gadget, int is_on)
594
{
M
Marek Vasut 已提交
595
	struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
596 597 598 599 600
	if (is_on) {
		/* RESET */
		writel(USBCMD_ITC(MICRO_8FRAME) | USBCMD_RST, &udc->usbcmd);
		udelay(200);

601
		writel((unsigned)controller.epts, &udc->epinitaddr);
602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622

		/* select DEVICE mode */
		writel(USBMODE_DEVICE, &udc->usbmode);

		writel(0xffffffff, &udc->epflush);

		/* Turn on the USB connection by enabling the pullup resistor */
		writel(USBCMD_ITC(MICRO_8FRAME) | USBCMD_RUN, &udc->usbcmd);
	} else {
		stop_activity();
		writel(USBCMD_FS2, &udc->usbcmd);
		udelay(800);
		if (controller.driver)
			controller.driver->disconnect(gadget);
	}

	return 0;
}

void udc_disconnect(void)
{
M
Marek Vasut 已提交
623
	struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
624 625 626 627 628 629 630 631
	/* disable pullup */
	stop_activity();
	writel(USBCMD_FS2, &udc->usbcmd);
	udelay(800);
	if (controller.driver)
		controller.driver->disconnect(&controller.gadget);
}

M
Marek Vasut 已提交
632
static int ci_udc_probe(void)
633 634
{
	struct ept_queue_head *head;
635
	uint8_t *imem;
636
	int i;
637

638
	const int num = 2 * NUM_ENDPOINTS;
639

640 641 642 643 644
	const int eplist_min_align = 4096;
	const int eplist_align = roundup(eplist_min_align, ARCH_DMA_MINALIGN);
	const int eplist_raw_sz = num * sizeof(struct ept_queue_head);
	const int eplist_sz = roundup(eplist_raw_sz, ARCH_DMA_MINALIGN);

645 646 647 648 649
	const int ilist_align = roundup(ARCH_DMA_MINALIGN, 32);
	const int ilist_ent_raw_sz = 2 * sizeof(struct ept_queue_item);
	const int ilist_ent_sz = roundup(ilist_ent_raw_sz, ARCH_DMA_MINALIGN);
	const int ilist_sz = NUM_ENDPOINTS * ilist_ent_sz;

650 651 652 653 654 655
	/* The QH list must be aligned to 4096 bytes. */
	controller.epts = memalign(eplist_align, eplist_sz);
	if (!controller.epts)
		return -ENOMEM;
	memset(controller.epts, 0, eplist_sz);

656 657 658 659 660 661 662 663 664 665 666
	/*
	 * Each qTD item must be 32-byte aligned, each qTD touple must be
	 * cacheline aligned. There are two qTD items for each endpoint and
	 * only one of them is used for the endpoint at time, so we can group
	 * them together.
	 */
	controller.items_mem = memalign(ilist_align, ilist_sz);
	if (!controller.items_mem) {
		free(controller.epts);
		return -ENOMEM;
	}
667
	memset(controller.items_mem, 0, ilist_sz);
668

669 670
	for (i = 0; i < 2 * NUM_ENDPOINTS; i++) {
		/*
671 672 673 674 675
		 * Configure QH for each endpoint. The structure of the QH list
		 * is such that each two subsequent fields, N and N+1 where N is
		 * even, in the QH list represent QH for one endpoint. The Nth
		 * entry represents OUT configuration and the N+1th entry does
		 * represent IN configuration of the endpoint.
676
		 */
677
		head = controller.epts + i;
678 679 680 681 682 683 684 685 686
		if (i < 2)
			head->config = CONFIG_MAX_PKT(EP0_MAX_PACKET_SIZE)
				| CONFIG_ZLT | CONFIG_IOS;
		else
			head->config = CONFIG_MAX_PKT(EP_MAX_PACKET_SIZE)
				| CONFIG_ZLT;
		head->next = TERMINATE;
		head->info = 0;

687 688 689 690 691
		imem = controller.items_mem + ((i >> 1) * ilist_ent_sz);
		if (i & 1)
			imem += sizeof(struct ept_queue_item);

		controller.items[i] = (struct ept_queue_item *)imem;
692 693

		if (i & 1) {
M
Marek Vasut 已提交
694 695
			ci_flush_qh(i - 1);
			ci_flush_qtd(i - 1);
696
		}
697 698 699
	}

	INIT_LIST_HEAD(&controller.gadget.ep_list);
700 701

	/* Init EP 0 */
M
Marek Vasut 已提交
702
	memcpy(&controller.ep[0].ep, &ci_ep_init[0], sizeof(*ci_ep_init));
703
	controller.ep[0].desc = &ep0_in_desc;
704
	controller.gadget.ep0 = &controller.ep[0].ep;
705
	INIT_LIST_HEAD(&controller.gadget.ep0->ep_list);
706 707 708

	/* Init EP 1..n */
	for (i = 1; i < NUM_ENDPOINTS; i++) {
M
Marek Vasut 已提交
709 710
		memcpy(&controller.ep[i].ep, &ci_ep_init[1],
		       sizeof(*ci_ep_init));
711 712
		list_add_tail(&controller.ep[i].ep.ep_list,
			      &controller.gadget.ep_list);
713
	}
714

715 716 717 718 719
	return 0;
}

int usb_gadget_register_driver(struct usb_gadget_driver *driver)
{
720
	int ret;
721

722 723 724 725 726
	if (!driver)
		return -EINVAL;
	if (!driver->bind || !driver->setup || !driver->disconnect)
		return -EINVAL;
	if (driver->speed != USB_SPEED_FULL && driver->speed != USB_SPEED_HIGH)
727 728
		return -EINVAL;

729
	ret = usb_lowlevel_init(0, USB_INIT_DEVICE, (void **)&controller.ctrl);
730 731 732
	if (ret)
		return ret;

M
Marek Vasut 已提交
733
	ret = ci_udc_probe();
734 735 736 737 738
#if defined(CONFIG_USB_EHCI_MX6) || defined(CONFIG_USB_EHCI_MXS)
	/*
	 * FIXME: usb_lowlevel_init()->ehci_hcd_init() should be doing all
	 * HW-specific initialization, e.g. ULPI-vs-UTMI PHY selection
	 */
739
	if (!ret) {
740
		struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
741

742 743 744
		/* select ULPI phy */
		writel(PTS(PTS_ENABLE) | PFSC, &udc->portsc);
	}
745
#endif
746 747 748 749 750

	ret = driver->bind(&controller.gadget);
	if (ret) {
		DBG("driver->bind() returned %d\n", ret);
		return ret;
751 752 753 754 755 756 757 758 759 760
	}
	controller.driver = driver;

	return 0;
}

int usb_gadget_unregister_driver(struct usb_gadget_driver *driver)
{
	return 0;
}