1 | // SPDX-License-Identifier: GPL-2.0 |
2 | /* |
3 | * Fusb300 UDC (USB gadget) |
4 | * |
5 | * Copyright (C) 2010 Faraday Technology Corp. |
6 | * |
7 | * Author : Yuan-hsin Chen <yhchen@faraday-tech.com> |
8 | */ |
9 | #include <linux/dma-mapping.h> |
10 | #include <linux/err.h> |
11 | #include <linux/interrupt.h> |
12 | #include <linux/io.h> |
13 | #include <linux/module.h> |
14 | #include <linux/platform_device.h> |
15 | #include <linux/usb/ch9.h> |
16 | #include <linux/usb/gadget.h> |
17 | |
18 | #include "fusb300_udc.h" |
19 | |
20 | MODULE_DESCRIPTION("FUSB300 USB gadget driver" ); |
21 | MODULE_LICENSE("GPL" ); |
22 | MODULE_AUTHOR("Yuan-Hsin Chen, Feng-Hsin Chiang <john453@faraday-tech.com>" ); |
23 | MODULE_ALIAS("platform:fusb300_udc" ); |
24 | |
25 | #define DRIVER_VERSION "20 October 2010" |
26 | |
27 | static const char udc_name[] = "fusb300_udc" ; |
28 | static const char * const fusb300_ep_name[] = { |
29 | "ep0" , "ep1" , "ep2" , "ep3" , "ep4" , "ep5" , "ep6" , "ep7" , "ep8" , "ep9" , |
30 | "ep10" , "ep11" , "ep12" , "ep13" , "ep14" , "ep15" |
31 | }; |
32 | |
33 | static void done(struct fusb300_ep *ep, struct fusb300_request *req, |
34 | int status); |
35 | |
36 | static void fusb300_enable_bit(struct fusb300 *fusb300, u32 offset, |
37 | u32 value) |
38 | { |
39 | u32 reg = ioread32(fusb300->reg + offset); |
40 | |
41 | reg |= value; |
42 | iowrite32(reg, fusb300->reg + offset); |
43 | } |
44 | |
45 | static void fusb300_disable_bit(struct fusb300 *fusb300, u32 offset, |
46 | u32 value) |
47 | { |
48 | u32 reg = ioread32(fusb300->reg + offset); |
49 | |
50 | reg &= ~value; |
51 | iowrite32(reg, fusb300->reg + offset); |
52 | } |
53 | |
54 | |
55 | static void fusb300_ep_setting(struct fusb300_ep *ep, |
56 | struct fusb300_ep_info info) |
57 | { |
58 | ep->epnum = info.epnum; |
59 | ep->type = info.type; |
60 | } |
61 | |
62 | static int fusb300_ep_release(struct fusb300_ep *ep) |
63 | { |
64 | if (!ep->epnum) |
65 | return 0; |
66 | ep->epnum = 0; |
67 | ep->stall = 0; |
68 | ep->wedged = 0; |
69 | return 0; |
70 | } |
71 | |
72 | static void fusb300_set_fifo_entry(struct fusb300 *fusb300, |
73 | u32 ep) |
74 | { |
75 | u32 val = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET1(ep)); |
76 | |
77 | val &= ~FUSB300_EPSET1_FIFOENTRY_MSK; |
78 | val |= FUSB300_EPSET1_FIFOENTRY(FUSB300_FIFO_ENTRY_NUM); |
79 | iowrite32(val, fusb300->reg + FUSB300_OFFSET_EPSET1(ep)); |
80 | } |
81 | |
82 | static void fusb300_set_start_entry(struct fusb300 *fusb300, |
83 | u8 ep) |
84 | { |
85 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET1(ep)); |
86 | u32 start_entry = fusb300->fifo_entry_num * FUSB300_FIFO_ENTRY_NUM; |
87 | |
88 | reg &= ~FUSB300_EPSET1_START_ENTRY_MSK ; |
89 | reg |= FUSB300_EPSET1_START_ENTRY(start_entry); |
90 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET1(ep)); |
91 | if (fusb300->fifo_entry_num == FUSB300_MAX_FIFO_ENTRY) { |
92 | fusb300->fifo_entry_num = 0; |
93 | fusb300->addrofs = 0; |
94 | pr_err("fifo entry is over the maximum number!\n" ); |
95 | } else |
96 | fusb300->fifo_entry_num++; |
97 | } |
98 | |
99 | /* set fusb300_set_start_entry first before fusb300_set_epaddrofs */ |
100 | static void fusb300_set_epaddrofs(struct fusb300 *fusb300, |
101 | struct fusb300_ep_info info) |
102 | { |
103 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET2(info.epnum)); |
104 | |
105 | reg &= ~FUSB300_EPSET2_ADDROFS_MSK; |
106 | reg |= FUSB300_EPSET2_ADDROFS(fusb300->addrofs); |
107 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET2(info.epnum)); |
108 | fusb300->addrofs += (info.maxpacket + 7) / 8 * FUSB300_FIFO_ENTRY_NUM; |
109 | } |
110 | |
111 | static void ep_fifo_setting(struct fusb300 *fusb300, |
112 | struct fusb300_ep_info info) |
113 | { |
114 | fusb300_set_fifo_entry(fusb300, ep: info.epnum); |
115 | fusb300_set_start_entry(fusb300, ep: info.epnum); |
116 | fusb300_set_epaddrofs(fusb300, info); |
117 | } |
118 | |
119 | static void fusb300_set_eptype(struct fusb300 *fusb300, |
120 | struct fusb300_ep_info info) |
121 | { |
122 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET1(info.epnum)); |
123 | |
124 | reg &= ~FUSB300_EPSET1_TYPE_MSK; |
125 | reg |= FUSB300_EPSET1_TYPE(info.type); |
126 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET1(info.epnum)); |
127 | } |
128 | |
129 | static void fusb300_set_epdir(struct fusb300 *fusb300, |
130 | struct fusb300_ep_info info) |
131 | { |
132 | u32 reg; |
133 | |
134 | if (!info.dir_in) |
135 | return; |
136 | reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET1(info.epnum)); |
137 | reg &= ~FUSB300_EPSET1_DIR_MSK; |
138 | reg |= FUSB300_EPSET1_DIRIN; |
139 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET1(info.epnum)); |
140 | } |
141 | |
142 | static void fusb300_set_ep_active(struct fusb300 *fusb300, |
143 | u8 ep) |
144 | { |
145 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET1(ep)); |
146 | |
147 | reg |= FUSB300_EPSET1_ACTEN; |
148 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET1(ep)); |
149 | } |
150 | |
151 | static void fusb300_set_epmps(struct fusb300 *fusb300, |
152 | struct fusb300_ep_info info) |
153 | { |
154 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET2(info.epnum)); |
155 | |
156 | reg &= ~FUSB300_EPSET2_MPS_MSK; |
157 | reg |= FUSB300_EPSET2_MPS(info.maxpacket); |
158 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET2(info.epnum)); |
159 | } |
160 | |
161 | static void fusb300_set_interval(struct fusb300 *fusb300, |
162 | struct fusb300_ep_info info) |
163 | { |
164 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET1(info.epnum)); |
165 | |
166 | reg &= ~FUSB300_EPSET1_INTERVAL(0x7); |
167 | reg |= FUSB300_EPSET1_INTERVAL(info.interval); |
168 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET1(info.epnum)); |
169 | } |
170 | |
171 | static void fusb300_set_bwnum(struct fusb300 *fusb300, |
172 | struct fusb300_ep_info info) |
173 | { |
174 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET1(info.epnum)); |
175 | |
176 | reg &= ~FUSB300_EPSET1_BWNUM(0x3); |
177 | reg |= FUSB300_EPSET1_BWNUM(info.bw_num); |
178 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET1(info.epnum)); |
179 | } |
180 | |
181 | static void set_ep_reg(struct fusb300 *fusb300, |
182 | struct fusb300_ep_info info) |
183 | { |
184 | fusb300_set_eptype(fusb300, info); |
185 | fusb300_set_epdir(fusb300, info); |
186 | fusb300_set_epmps(fusb300, info); |
187 | |
188 | if (info.interval) |
189 | fusb300_set_interval(fusb300, info); |
190 | |
191 | if (info.bw_num) |
192 | fusb300_set_bwnum(fusb300, info); |
193 | |
194 | fusb300_set_ep_active(fusb300, ep: info.epnum); |
195 | } |
196 | |
197 | static int config_ep(struct fusb300_ep *ep, |
198 | const struct usb_endpoint_descriptor *desc) |
199 | { |
200 | struct fusb300 *fusb300 = ep->fusb300; |
201 | struct fusb300_ep_info info; |
202 | |
203 | ep->ep.desc = desc; |
204 | |
205 | info.interval = 0; |
206 | info.addrofs = 0; |
207 | info.bw_num = 0; |
208 | |
209 | info.type = desc->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK; |
210 | info.dir_in = (desc->bEndpointAddress & USB_ENDPOINT_DIR_MASK) ? 1 : 0; |
211 | info.maxpacket = usb_endpoint_maxp(epd: desc); |
212 | info.epnum = desc->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK; |
213 | |
214 | if ((info.type == USB_ENDPOINT_XFER_INT) || |
215 | (info.type == USB_ENDPOINT_XFER_ISOC)) { |
216 | info.interval = desc->bInterval; |
217 | if (info.type == USB_ENDPOINT_XFER_ISOC) |
218 | info.bw_num = usb_endpoint_maxp_mult(epd: desc); |
219 | } |
220 | |
221 | ep_fifo_setting(fusb300, info); |
222 | |
223 | set_ep_reg(fusb300, info); |
224 | |
225 | fusb300_ep_setting(ep, info); |
226 | |
227 | fusb300->ep[info.epnum] = ep; |
228 | |
229 | return 0; |
230 | } |
231 | |
232 | static int fusb300_enable(struct usb_ep *_ep, |
233 | const struct usb_endpoint_descriptor *desc) |
234 | { |
235 | struct fusb300_ep *ep; |
236 | |
237 | ep = container_of(_ep, struct fusb300_ep, ep); |
238 | |
239 | if (ep->fusb300->reenum) { |
240 | ep->fusb300->fifo_entry_num = 0; |
241 | ep->fusb300->addrofs = 0; |
242 | ep->fusb300->reenum = 0; |
243 | } |
244 | |
245 | return config_ep(ep, desc); |
246 | } |
247 | |
248 | static int fusb300_disable(struct usb_ep *_ep) |
249 | { |
250 | struct fusb300_ep *ep; |
251 | struct fusb300_request *req; |
252 | unsigned long flags; |
253 | |
254 | ep = container_of(_ep, struct fusb300_ep, ep); |
255 | |
256 | BUG_ON(!ep); |
257 | |
258 | while (!list_empty(head: &ep->queue)) { |
259 | req = list_entry(ep->queue.next, struct fusb300_request, queue); |
260 | spin_lock_irqsave(&ep->fusb300->lock, flags); |
261 | done(ep, req, status: -ECONNRESET); |
262 | spin_unlock_irqrestore(lock: &ep->fusb300->lock, flags); |
263 | } |
264 | |
265 | return fusb300_ep_release(ep); |
266 | } |
267 | |
268 | static struct usb_request *fusb300_alloc_request(struct usb_ep *_ep, |
269 | gfp_t gfp_flags) |
270 | { |
271 | struct fusb300_request *req; |
272 | |
273 | req = kzalloc(size: sizeof(struct fusb300_request), flags: gfp_flags); |
274 | if (!req) |
275 | return NULL; |
276 | INIT_LIST_HEAD(list: &req->queue); |
277 | |
278 | return &req->req; |
279 | } |
280 | |
281 | static void fusb300_free_request(struct usb_ep *_ep, struct usb_request *_req) |
282 | { |
283 | struct fusb300_request *req; |
284 | |
285 | req = container_of(_req, struct fusb300_request, req); |
286 | kfree(objp: req); |
287 | } |
288 | |
289 | static int enable_fifo_int(struct fusb300_ep *ep) |
290 | { |
291 | struct fusb300 *fusb300 = ep->fusb300; |
292 | |
293 | if (ep->epnum) { |
294 | fusb300_enable_bit(fusb300, FUSB300_OFFSET_IGER0, |
295 | FUSB300_IGER0_EEPn_FIFO_INT(ep->epnum)); |
296 | } else { |
297 | pr_err("can't enable_fifo_int ep0\n" ); |
298 | return -EINVAL; |
299 | } |
300 | |
301 | return 0; |
302 | } |
303 | |
304 | static int disable_fifo_int(struct fusb300_ep *ep) |
305 | { |
306 | struct fusb300 *fusb300 = ep->fusb300; |
307 | |
308 | if (ep->epnum) { |
309 | fusb300_disable_bit(fusb300, FUSB300_OFFSET_IGER0, |
310 | FUSB300_IGER0_EEPn_FIFO_INT(ep->epnum)); |
311 | } else { |
312 | pr_err("can't disable_fifo_int ep0\n" ); |
313 | return -EINVAL; |
314 | } |
315 | |
316 | return 0; |
317 | } |
318 | |
319 | static void fusb300_set_cxlen(struct fusb300 *fusb300, u32 length) |
320 | { |
321 | u32 reg; |
322 | |
323 | reg = ioread32(fusb300->reg + FUSB300_OFFSET_CSR); |
324 | reg &= ~FUSB300_CSR_LEN_MSK; |
325 | reg |= FUSB300_CSR_LEN(length); |
326 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_CSR); |
327 | } |
328 | |
329 | /* write data to cx fifo */ |
330 | static void fusb300_wrcxf(struct fusb300_ep *ep, |
331 | struct fusb300_request *req) |
332 | { |
333 | int i = 0; |
334 | u8 *tmp; |
335 | u32 data; |
336 | struct fusb300 *fusb300 = ep->fusb300; |
337 | u32 length = req->req.length - req->req.actual; |
338 | |
339 | tmp = req->req.buf + req->req.actual; |
340 | |
341 | if (length > SS_CTL_MAX_PACKET_SIZE) { |
342 | fusb300_set_cxlen(fusb300, SS_CTL_MAX_PACKET_SIZE); |
343 | for (i = (SS_CTL_MAX_PACKET_SIZE >> 2); i > 0; i--) { |
344 | data = *tmp | *(tmp + 1) << 8 | *(tmp + 2) << 16 | |
345 | *(tmp + 3) << 24; |
346 | iowrite32(data, fusb300->reg + FUSB300_OFFSET_CXPORT); |
347 | tmp += 4; |
348 | } |
349 | req->req.actual += SS_CTL_MAX_PACKET_SIZE; |
350 | } else { /* length is less than max packet size */ |
351 | fusb300_set_cxlen(fusb300, length); |
352 | for (i = length >> 2; i > 0; i--) { |
353 | data = *tmp | *(tmp + 1) << 8 | *(tmp + 2) << 16 | |
354 | *(tmp + 3) << 24; |
355 | printk(KERN_DEBUG " 0x%x\n" , data); |
356 | iowrite32(data, fusb300->reg + FUSB300_OFFSET_CXPORT); |
357 | tmp = tmp + 4; |
358 | } |
359 | switch (length % 4) { |
360 | case 1: |
361 | data = *tmp; |
362 | printk(KERN_DEBUG " 0x%x\n" , data); |
363 | iowrite32(data, fusb300->reg + FUSB300_OFFSET_CXPORT); |
364 | break; |
365 | case 2: |
366 | data = *tmp | *(tmp + 1) << 8; |
367 | printk(KERN_DEBUG " 0x%x\n" , data); |
368 | iowrite32(data, fusb300->reg + FUSB300_OFFSET_CXPORT); |
369 | break; |
370 | case 3: |
371 | data = *tmp | *(tmp + 1) << 8 | *(tmp + 2) << 16; |
372 | printk(KERN_DEBUG " 0x%x\n" , data); |
373 | iowrite32(data, fusb300->reg + FUSB300_OFFSET_CXPORT); |
374 | break; |
375 | default: |
376 | break; |
377 | } |
378 | req->req.actual += length; |
379 | } |
380 | } |
381 | |
382 | static void fusb300_set_epnstall(struct fusb300 *fusb300, u8 ep) |
383 | { |
384 | fusb300_enable_bit(fusb300, FUSB300_OFFSET_EPSET0(ep), |
385 | FUSB300_EPSET0_STL); |
386 | } |
387 | |
388 | static void fusb300_clear_epnstall(struct fusb300 *fusb300, u8 ep) |
389 | { |
390 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET0(ep)); |
391 | |
392 | if (reg & FUSB300_EPSET0_STL) { |
393 | printk(KERN_DEBUG "EP%d stall... Clear!!\n" , ep); |
394 | reg |= FUSB300_EPSET0_STL_CLR; |
395 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_EPSET0(ep)); |
396 | } |
397 | } |
398 | |
399 | static void ep0_queue(struct fusb300_ep *ep, struct fusb300_request *req) |
400 | { |
401 | if (ep->fusb300->ep0_dir) { /* if IN */ |
402 | if (req->req.length) { |
403 | fusb300_wrcxf(ep, req); |
404 | } else |
405 | printk(KERN_DEBUG "%s : req->req.length = 0x%x\n" , |
406 | __func__, req->req.length); |
407 | if ((req->req.length == req->req.actual) || |
408 | (req->req.actual < ep->ep.maxpacket)) |
409 | done(ep, req, status: 0); |
410 | } else { /* OUT */ |
411 | if (!req->req.length) |
412 | done(ep, req, status: 0); |
413 | else |
414 | fusb300_enable_bit(fusb300: ep->fusb300, FUSB300_OFFSET_IGER1, |
415 | FUSB300_IGER1_CX_OUT_INT); |
416 | } |
417 | } |
418 | |
419 | static int fusb300_queue(struct usb_ep *_ep, struct usb_request *_req, |
420 | gfp_t gfp_flags) |
421 | { |
422 | struct fusb300_ep *ep; |
423 | struct fusb300_request *req; |
424 | unsigned long flags; |
425 | int request = 0; |
426 | |
427 | ep = container_of(_ep, struct fusb300_ep, ep); |
428 | req = container_of(_req, struct fusb300_request, req); |
429 | |
430 | if (ep->fusb300->gadget.speed == USB_SPEED_UNKNOWN) |
431 | return -ESHUTDOWN; |
432 | |
433 | spin_lock_irqsave(&ep->fusb300->lock, flags); |
434 | |
435 | if (list_empty(head: &ep->queue)) |
436 | request = 1; |
437 | |
438 | list_add_tail(new: &req->queue, head: &ep->queue); |
439 | |
440 | req->req.actual = 0; |
441 | req->req.status = -EINPROGRESS; |
442 | |
443 | if (ep->ep.desc == NULL) /* ep0 */ |
444 | ep0_queue(ep, req); |
445 | else if (request && !ep->stall) |
446 | enable_fifo_int(ep); |
447 | |
448 | spin_unlock_irqrestore(lock: &ep->fusb300->lock, flags); |
449 | |
450 | return 0; |
451 | } |
452 | |
453 | static int fusb300_dequeue(struct usb_ep *_ep, struct usb_request *_req) |
454 | { |
455 | struct fusb300_ep *ep; |
456 | struct fusb300_request *req; |
457 | unsigned long flags; |
458 | |
459 | ep = container_of(_ep, struct fusb300_ep, ep); |
460 | req = container_of(_req, struct fusb300_request, req); |
461 | |
462 | spin_lock_irqsave(&ep->fusb300->lock, flags); |
463 | if (!list_empty(head: &ep->queue)) |
464 | done(ep, req, status: -ECONNRESET); |
465 | spin_unlock_irqrestore(lock: &ep->fusb300->lock, flags); |
466 | |
467 | return 0; |
468 | } |
469 | |
470 | static int fusb300_set_halt_and_wedge(struct usb_ep *_ep, int value, int wedge) |
471 | { |
472 | struct fusb300_ep *ep; |
473 | struct fusb300 *fusb300; |
474 | unsigned long flags; |
475 | int ret = 0; |
476 | |
477 | ep = container_of(_ep, struct fusb300_ep, ep); |
478 | |
479 | fusb300 = ep->fusb300; |
480 | |
481 | spin_lock_irqsave(&ep->fusb300->lock, flags); |
482 | |
483 | if (!list_empty(head: &ep->queue)) { |
484 | ret = -EAGAIN; |
485 | goto out; |
486 | } |
487 | |
488 | if (value) { |
489 | fusb300_set_epnstall(fusb300, ep: ep->epnum); |
490 | ep->stall = 1; |
491 | if (wedge) |
492 | ep->wedged = 1; |
493 | } else { |
494 | fusb300_clear_epnstall(fusb300, ep: ep->epnum); |
495 | ep->stall = 0; |
496 | ep->wedged = 0; |
497 | } |
498 | |
499 | out: |
500 | spin_unlock_irqrestore(lock: &ep->fusb300->lock, flags); |
501 | return ret; |
502 | } |
503 | |
504 | static int fusb300_set_halt(struct usb_ep *_ep, int value) |
505 | { |
506 | return fusb300_set_halt_and_wedge(_ep, value, wedge: 0); |
507 | } |
508 | |
509 | static int fusb300_set_wedge(struct usb_ep *_ep) |
510 | { |
511 | return fusb300_set_halt_and_wedge(_ep, value: 1, wedge: 1); |
512 | } |
513 | |
514 | static void fusb300_fifo_flush(struct usb_ep *_ep) |
515 | { |
516 | } |
517 | |
518 | static const struct usb_ep_ops fusb300_ep_ops = { |
519 | .enable = fusb300_enable, |
520 | .disable = fusb300_disable, |
521 | |
522 | .alloc_request = fusb300_alloc_request, |
523 | .free_request = fusb300_free_request, |
524 | |
525 | .queue = fusb300_queue, |
526 | .dequeue = fusb300_dequeue, |
527 | |
528 | .set_halt = fusb300_set_halt, |
529 | .fifo_flush = fusb300_fifo_flush, |
530 | .set_wedge = fusb300_set_wedge, |
531 | }; |
532 | |
533 | /*****************************************************************************/ |
534 | static void fusb300_clear_int(struct fusb300 *fusb300, u32 offset, |
535 | u32 value) |
536 | { |
537 | iowrite32(value, fusb300->reg + offset); |
538 | } |
539 | |
540 | static void fusb300_reset(void) |
541 | { |
542 | } |
543 | |
544 | static void fusb300_set_cxstall(struct fusb300 *fusb300) |
545 | { |
546 | fusb300_enable_bit(fusb300, FUSB300_OFFSET_CSR, |
547 | FUSB300_CSR_STL); |
548 | } |
549 | |
550 | static void fusb300_set_cxdone(struct fusb300 *fusb300) |
551 | { |
552 | fusb300_enable_bit(fusb300, FUSB300_OFFSET_CSR, |
553 | FUSB300_CSR_DONE); |
554 | } |
555 | |
556 | /* read data from cx fifo */ |
557 | static void fusb300_rdcxf(struct fusb300 *fusb300, |
558 | u8 *buffer, u32 length) |
559 | { |
560 | int i = 0; |
561 | u8 *tmp; |
562 | u32 data; |
563 | |
564 | tmp = buffer; |
565 | |
566 | for (i = (length >> 2); i > 0; i--) { |
567 | data = ioread32(fusb300->reg + FUSB300_OFFSET_CXPORT); |
568 | printk(KERN_DEBUG " 0x%x\n" , data); |
569 | *tmp = data & 0xFF; |
570 | *(tmp + 1) = (data >> 8) & 0xFF; |
571 | *(tmp + 2) = (data >> 16) & 0xFF; |
572 | *(tmp + 3) = (data >> 24) & 0xFF; |
573 | tmp = tmp + 4; |
574 | } |
575 | |
576 | switch (length % 4) { |
577 | case 1: |
578 | data = ioread32(fusb300->reg + FUSB300_OFFSET_CXPORT); |
579 | printk(KERN_DEBUG " 0x%x\n" , data); |
580 | *tmp = data & 0xFF; |
581 | break; |
582 | case 2: |
583 | data = ioread32(fusb300->reg + FUSB300_OFFSET_CXPORT); |
584 | printk(KERN_DEBUG " 0x%x\n" , data); |
585 | *tmp = data & 0xFF; |
586 | *(tmp + 1) = (data >> 8) & 0xFF; |
587 | break; |
588 | case 3: |
589 | data = ioread32(fusb300->reg + FUSB300_OFFSET_CXPORT); |
590 | printk(KERN_DEBUG " 0x%x\n" , data); |
591 | *tmp = data & 0xFF; |
592 | *(tmp + 1) = (data >> 8) & 0xFF; |
593 | *(tmp + 2) = (data >> 16) & 0xFF; |
594 | break; |
595 | default: |
596 | break; |
597 | } |
598 | } |
599 | |
600 | static void fusb300_rdfifo(struct fusb300_ep *ep, |
601 | struct fusb300_request *req, |
602 | u32 length) |
603 | { |
604 | int i = 0; |
605 | u8 *tmp; |
606 | u32 data, reg; |
607 | struct fusb300 *fusb300 = ep->fusb300; |
608 | |
609 | tmp = req->req.buf + req->req.actual; |
610 | req->req.actual += length; |
611 | |
612 | if (req->req.actual > req->req.length) |
613 | printk(KERN_DEBUG "req->req.actual > req->req.length\n" ); |
614 | |
615 | for (i = (length >> 2); i > 0; i--) { |
616 | data = ioread32(fusb300->reg + |
617 | FUSB300_OFFSET_EPPORT(ep->epnum)); |
618 | *tmp = data & 0xFF; |
619 | *(tmp + 1) = (data >> 8) & 0xFF; |
620 | *(tmp + 2) = (data >> 16) & 0xFF; |
621 | *(tmp + 3) = (data >> 24) & 0xFF; |
622 | tmp = tmp + 4; |
623 | } |
624 | |
625 | switch (length % 4) { |
626 | case 1: |
627 | data = ioread32(fusb300->reg + |
628 | FUSB300_OFFSET_EPPORT(ep->epnum)); |
629 | *tmp = data & 0xFF; |
630 | break; |
631 | case 2: |
632 | data = ioread32(fusb300->reg + |
633 | FUSB300_OFFSET_EPPORT(ep->epnum)); |
634 | *tmp = data & 0xFF; |
635 | *(tmp + 1) = (data >> 8) & 0xFF; |
636 | break; |
637 | case 3: |
638 | data = ioread32(fusb300->reg + |
639 | FUSB300_OFFSET_EPPORT(ep->epnum)); |
640 | *tmp = data & 0xFF; |
641 | *(tmp + 1) = (data >> 8) & 0xFF; |
642 | *(tmp + 2) = (data >> 16) & 0xFF; |
643 | break; |
644 | default: |
645 | break; |
646 | } |
647 | |
648 | do { |
649 | reg = ioread32(fusb300->reg + FUSB300_OFFSET_IGR1); |
650 | reg &= FUSB300_IGR1_SYNF0_EMPTY_INT; |
651 | if (i) |
652 | printk(KERN_INFO "sync fifo is not empty!\n" ); |
653 | i++; |
654 | } while (!reg); |
655 | } |
656 | |
657 | static u8 fusb300_get_epnstall(struct fusb300 *fusb300, u8 ep) |
658 | { |
659 | u8 value; |
660 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPSET0(ep)); |
661 | |
662 | value = reg & FUSB300_EPSET0_STL; |
663 | |
664 | return value; |
665 | } |
666 | |
667 | static u8 fusb300_get_cxstall(struct fusb300 *fusb300) |
668 | { |
669 | u8 value; |
670 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_CSR); |
671 | |
672 | value = (reg & FUSB300_CSR_STL) >> 1; |
673 | |
674 | return value; |
675 | } |
676 | |
677 | static void request_error(struct fusb300 *fusb300) |
678 | { |
679 | fusb300_set_cxstall(fusb300); |
680 | printk(KERN_DEBUG "request error!!\n" ); |
681 | } |
682 | |
683 | static void get_status(struct fusb300 *fusb300, struct usb_ctrlrequest *ctrl) |
684 | __releases(fusb300->lock) |
685 | __acquires(fusb300->lock) |
686 | { |
687 | u8 ep; |
688 | u16 status = 0; |
689 | u16 w_index = ctrl->wIndex; |
690 | |
691 | switch (ctrl->bRequestType & USB_RECIP_MASK) { |
692 | case USB_RECIP_DEVICE: |
693 | status = 1 << USB_DEVICE_SELF_POWERED; |
694 | break; |
695 | case USB_RECIP_INTERFACE: |
696 | status = 0; |
697 | break; |
698 | case USB_RECIP_ENDPOINT: |
699 | ep = w_index & USB_ENDPOINT_NUMBER_MASK; |
700 | if (ep) { |
701 | if (fusb300_get_epnstall(fusb300, ep)) |
702 | status = 1 << USB_ENDPOINT_HALT; |
703 | } else { |
704 | if (fusb300_get_cxstall(fusb300)) |
705 | status = 0; |
706 | } |
707 | break; |
708 | |
709 | default: |
710 | request_error(fusb300); |
711 | return; /* exit */ |
712 | } |
713 | |
714 | fusb300->ep0_data = cpu_to_le16(status); |
715 | fusb300->ep0_req->buf = &fusb300->ep0_data; |
716 | fusb300->ep0_req->length = 2; |
717 | |
718 | spin_unlock(lock: &fusb300->lock); |
719 | fusb300_queue(ep: fusb300->gadget.ep0, req: fusb300->ep0_req, GFP_KERNEL); |
720 | spin_lock(lock: &fusb300->lock); |
721 | } |
722 | |
723 | static void set_feature(struct fusb300 *fusb300, struct usb_ctrlrequest *ctrl) |
724 | { |
725 | u8 ep; |
726 | |
727 | switch (ctrl->bRequestType & USB_RECIP_MASK) { |
728 | case USB_RECIP_DEVICE: |
729 | fusb300_set_cxdone(fusb300); |
730 | break; |
731 | case USB_RECIP_INTERFACE: |
732 | fusb300_set_cxdone(fusb300); |
733 | break; |
734 | case USB_RECIP_ENDPOINT: { |
735 | u16 w_index = le16_to_cpu(ctrl->wIndex); |
736 | |
737 | ep = w_index & USB_ENDPOINT_NUMBER_MASK; |
738 | if (ep) |
739 | fusb300_set_epnstall(fusb300, ep); |
740 | else |
741 | fusb300_set_cxstall(fusb300); |
742 | fusb300_set_cxdone(fusb300); |
743 | } |
744 | break; |
745 | default: |
746 | request_error(fusb300); |
747 | break; |
748 | } |
749 | } |
750 | |
751 | static void fusb300_clear_seqnum(struct fusb300 *fusb300, u8 ep) |
752 | { |
753 | fusb300_enable_bit(fusb300, FUSB300_OFFSET_EPSET0(ep), |
754 | FUSB300_EPSET0_CLRSEQNUM); |
755 | } |
756 | |
757 | static void clear_feature(struct fusb300 *fusb300, struct usb_ctrlrequest *ctrl) |
758 | { |
759 | struct fusb300_ep *ep = |
760 | fusb300->ep[ctrl->wIndex & USB_ENDPOINT_NUMBER_MASK]; |
761 | |
762 | switch (ctrl->bRequestType & USB_RECIP_MASK) { |
763 | case USB_RECIP_DEVICE: |
764 | fusb300_set_cxdone(fusb300); |
765 | break; |
766 | case USB_RECIP_INTERFACE: |
767 | fusb300_set_cxdone(fusb300); |
768 | break; |
769 | case USB_RECIP_ENDPOINT: |
770 | if (ctrl->wIndex & USB_ENDPOINT_NUMBER_MASK) { |
771 | if (ep->wedged) { |
772 | fusb300_set_cxdone(fusb300); |
773 | break; |
774 | } |
775 | if (ep->stall) { |
776 | ep->stall = 0; |
777 | fusb300_clear_seqnum(fusb300, ep: ep->epnum); |
778 | fusb300_clear_epnstall(fusb300, ep: ep->epnum); |
779 | if (!list_empty(head: &ep->queue)) |
780 | enable_fifo_int(ep); |
781 | } |
782 | } |
783 | fusb300_set_cxdone(fusb300); |
784 | break; |
785 | default: |
786 | request_error(fusb300); |
787 | break; |
788 | } |
789 | } |
790 | |
791 | static void fusb300_set_dev_addr(struct fusb300 *fusb300, u16 addr) |
792 | { |
793 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_DAR); |
794 | |
795 | reg &= ~FUSB300_DAR_DRVADDR_MSK; |
796 | reg |= FUSB300_DAR_DRVADDR(addr); |
797 | |
798 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_DAR); |
799 | } |
800 | |
801 | static void set_address(struct fusb300 *fusb300, struct usb_ctrlrequest *ctrl) |
802 | { |
803 | if (ctrl->wValue >= 0x0100) |
804 | request_error(fusb300); |
805 | else { |
806 | fusb300_set_dev_addr(fusb300, addr: ctrl->wValue); |
807 | fusb300_set_cxdone(fusb300); |
808 | } |
809 | } |
810 | |
811 | #define UVC_COPY_DESCRIPTORS(mem, src) \ |
812 | do { \ |
813 | const struct usb_descriptor_header * const *__src; \ |
814 | for (__src = src; *__src; ++__src) { \ |
815 | memcpy(mem, *__src, (*__src)->bLength); \ |
816 | mem += (*__src)->bLength; \ |
817 | } \ |
818 | } while (0) |
819 | |
820 | static int setup_packet(struct fusb300 *fusb300, struct usb_ctrlrequest *ctrl) |
821 | { |
822 | u8 *p = (u8 *)ctrl; |
823 | u8 ret = 0; |
824 | u8 i = 0; |
825 | |
826 | fusb300_rdcxf(fusb300, buffer: p, length: 8); |
827 | fusb300->ep0_dir = ctrl->bRequestType & USB_DIR_IN; |
828 | fusb300->ep0_length = ctrl->wLength; |
829 | |
830 | /* check request */ |
831 | if ((ctrl->bRequestType & USB_TYPE_MASK) == USB_TYPE_STANDARD) { |
832 | switch (ctrl->bRequest) { |
833 | case USB_REQ_GET_STATUS: |
834 | get_status(fusb300, ctrl); |
835 | break; |
836 | case USB_REQ_CLEAR_FEATURE: |
837 | clear_feature(fusb300, ctrl); |
838 | break; |
839 | case USB_REQ_SET_FEATURE: |
840 | set_feature(fusb300, ctrl); |
841 | break; |
842 | case USB_REQ_SET_ADDRESS: |
843 | set_address(fusb300, ctrl); |
844 | break; |
845 | case USB_REQ_SET_CONFIGURATION: |
846 | fusb300_enable_bit(fusb300, FUSB300_OFFSET_DAR, |
847 | FUSB300_DAR_SETCONFG); |
848 | /* clear sequence number */ |
849 | for (i = 1; i <= FUSB300_MAX_NUM_EP; i++) |
850 | fusb300_clear_seqnum(fusb300, ep: i); |
851 | fusb300->reenum = 1; |
852 | ret = 1; |
853 | break; |
854 | default: |
855 | ret = 1; |
856 | break; |
857 | } |
858 | } else |
859 | ret = 1; |
860 | |
861 | return ret; |
862 | } |
863 | |
864 | static void done(struct fusb300_ep *ep, struct fusb300_request *req, |
865 | int status) |
866 | { |
867 | list_del_init(entry: &req->queue); |
868 | |
869 | /* don't modify queue heads during completion callback */ |
870 | if (ep->fusb300->gadget.speed == USB_SPEED_UNKNOWN) |
871 | req->req.status = -ESHUTDOWN; |
872 | else |
873 | req->req.status = status; |
874 | |
875 | spin_unlock(lock: &ep->fusb300->lock); |
876 | usb_gadget_giveback_request(ep: &ep->ep, req: &req->req); |
877 | spin_lock(lock: &ep->fusb300->lock); |
878 | |
879 | if (ep->epnum) { |
880 | disable_fifo_int(ep); |
881 | if (!list_empty(head: &ep->queue)) |
882 | enable_fifo_int(ep); |
883 | } else |
884 | fusb300_set_cxdone(fusb300: ep->fusb300); |
885 | } |
886 | |
887 | static void fusb300_fill_idma_prdtbl(struct fusb300_ep *ep, dma_addr_t d, |
888 | u32 len) |
889 | { |
890 | u32 value; |
891 | u32 reg; |
892 | |
893 | /* wait SW owner */ |
894 | do { |
895 | reg = ioread32(ep->fusb300->reg + |
896 | FUSB300_OFFSET_EPPRD_W0(ep->epnum)); |
897 | reg &= FUSB300_EPPRD0_H; |
898 | } while (reg); |
899 | |
900 | iowrite32(d, ep->fusb300->reg + FUSB300_OFFSET_EPPRD_W1(ep->epnum)); |
901 | |
902 | value = FUSB300_EPPRD0_BTC(len) | FUSB300_EPPRD0_H | |
903 | FUSB300_EPPRD0_F | FUSB300_EPPRD0_L | FUSB300_EPPRD0_I; |
904 | iowrite32(value, ep->fusb300->reg + FUSB300_OFFSET_EPPRD_W0(ep->epnum)); |
905 | |
906 | iowrite32(0x0, ep->fusb300->reg + FUSB300_OFFSET_EPPRD_W2(ep->epnum)); |
907 | |
908 | fusb300_enable_bit(fusb300: ep->fusb300, FUSB300_OFFSET_EPPRDRDY, |
909 | FUSB300_EPPRDR_EP_PRD_RDY(ep->epnum)); |
910 | } |
911 | |
912 | static void fusb300_wait_idma_finished(struct fusb300_ep *ep) |
913 | { |
914 | u32 reg; |
915 | |
916 | do { |
917 | reg = ioread32(ep->fusb300->reg + FUSB300_OFFSET_IGR1); |
918 | if ((reg & FUSB300_IGR1_VBUS_CHG_INT) || |
919 | (reg & FUSB300_IGR1_WARM_RST_INT) || |
920 | (reg & FUSB300_IGR1_HOT_RST_INT) || |
921 | (reg & FUSB300_IGR1_USBRST_INT) |
922 | ) |
923 | goto IDMA_RESET; |
924 | reg = ioread32(ep->fusb300->reg + FUSB300_OFFSET_IGR0); |
925 | reg &= FUSB300_IGR0_EPn_PRD_INT(ep->epnum); |
926 | } while (!reg); |
927 | |
928 | fusb300_clear_int(fusb300: ep->fusb300, FUSB300_OFFSET_IGR0, |
929 | FUSB300_IGR0_EPn_PRD_INT(ep->epnum)); |
930 | return; |
931 | |
932 | IDMA_RESET: |
933 | reg = ioread32(ep->fusb300->reg + FUSB300_OFFSET_IGER0); |
934 | reg &= ~FUSB300_IGER0_EEPn_PRD_INT(ep->epnum); |
935 | iowrite32(reg, ep->fusb300->reg + FUSB300_OFFSET_IGER0); |
936 | } |
937 | |
938 | static void fusb300_set_idma(struct fusb300_ep *ep, |
939 | struct fusb300_request *req) |
940 | { |
941 | int ret; |
942 | |
943 | ret = usb_gadget_map_request(gadget: &ep->fusb300->gadget, |
944 | req: &req->req, is_in: DMA_TO_DEVICE); |
945 | if (ret) |
946 | return; |
947 | |
948 | fusb300_enable_bit(fusb300: ep->fusb300, FUSB300_OFFSET_IGER0, |
949 | FUSB300_IGER0_EEPn_PRD_INT(ep->epnum)); |
950 | |
951 | fusb300_fill_idma_prdtbl(ep, d: req->req.dma, len: req->req.length); |
952 | /* check idma is done */ |
953 | fusb300_wait_idma_finished(ep); |
954 | |
955 | usb_gadget_unmap_request(gadget: &ep->fusb300->gadget, |
956 | req: &req->req, is_in: DMA_TO_DEVICE); |
957 | } |
958 | |
959 | static void in_ep_fifo_handler(struct fusb300_ep *ep) |
960 | { |
961 | struct fusb300_request *req = list_entry(ep->queue.next, |
962 | struct fusb300_request, queue); |
963 | |
964 | if (req->req.length) |
965 | fusb300_set_idma(ep, req); |
966 | done(ep, req, status: 0); |
967 | } |
968 | |
969 | static void out_ep_fifo_handler(struct fusb300_ep *ep) |
970 | { |
971 | struct fusb300 *fusb300 = ep->fusb300; |
972 | struct fusb300_request *req = list_entry(ep->queue.next, |
973 | struct fusb300_request, queue); |
974 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_EPFFR(ep->epnum)); |
975 | u32 length = reg & FUSB300_FFR_BYCNT; |
976 | |
977 | fusb300_rdfifo(ep, req, length); |
978 | |
979 | /* finish out transfer */ |
980 | if ((req->req.length == req->req.actual) || (length < ep->ep.maxpacket)) |
981 | done(ep, req, status: 0); |
982 | } |
983 | |
984 | static void check_device_mode(struct fusb300 *fusb300) |
985 | { |
986 | u32 reg = ioread32(fusb300->reg + FUSB300_OFFSET_GCR); |
987 | |
988 | switch (reg & FUSB300_GCR_DEVEN_MSK) { |
989 | case FUSB300_GCR_DEVEN_SS: |
990 | fusb300->gadget.speed = USB_SPEED_SUPER; |
991 | break; |
992 | case FUSB300_GCR_DEVEN_HS: |
993 | fusb300->gadget.speed = USB_SPEED_HIGH; |
994 | break; |
995 | case FUSB300_GCR_DEVEN_FS: |
996 | fusb300->gadget.speed = USB_SPEED_FULL; |
997 | break; |
998 | default: |
999 | fusb300->gadget.speed = USB_SPEED_UNKNOWN; |
1000 | break; |
1001 | } |
1002 | printk(KERN_INFO "dev_mode = %d\n" , (reg & FUSB300_GCR_DEVEN_MSK)); |
1003 | } |
1004 | |
1005 | |
1006 | static void fusb300_ep0out(struct fusb300 *fusb300) |
1007 | { |
1008 | struct fusb300_ep *ep = fusb300->ep[0]; |
1009 | u32 reg; |
1010 | |
1011 | if (!list_empty(head: &ep->queue)) { |
1012 | struct fusb300_request *req; |
1013 | |
1014 | req = list_first_entry(&ep->queue, |
1015 | struct fusb300_request, queue); |
1016 | if (req->req.length) |
1017 | fusb300_rdcxf(fusb300: ep->fusb300, buffer: req->req.buf, |
1018 | length: req->req.length); |
1019 | done(ep, req, status: 0); |
1020 | reg = ioread32(fusb300->reg + FUSB300_OFFSET_IGER1); |
1021 | reg &= ~FUSB300_IGER1_CX_OUT_INT; |
1022 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_IGER1); |
1023 | } else |
1024 | pr_err("%s : empty queue\n" , __func__); |
1025 | } |
1026 | |
1027 | static void fusb300_ep0in(struct fusb300 *fusb300) |
1028 | { |
1029 | struct fusb300_request *req; |
1030 | struct fusb300_ep *ep = fusb300->ep[0]; |
1031 | |
1032 | if ((!list_empty(head: &ep->queue)) && (fusb300->ep0_dir)) { |
1033 | req = list_entry(ep->queue.next, |
1034 | struct fusb300_request, queue); |
1035 | if (req->req.length) |
1036 | fusb300_wrcxf(ep, req); |
1037 | if ((req->req.length - req->req.actual) < ep->ep.maxpacket) |
1038 | done(ep, req, status: 0); |
1039 | } else |
1040 | fusb300_set_cxdone(fusb300); |
1041 | } |
1042 | |
1043 | static void fusb300_grp2_handler(void) |
1044 | { |
1045 | } |
1046 | |
1047 | static void fusb300_grp3_handler(void) |
1048 | { |
1049 | } |
1050 | |
1051 | static void fusb300_grp4_handler(void) |
1052 | { |
1053 | } |
1054 | |
1055 | static void fusb300_grp5_handler(void) |
1056 | { |
1057 | } |
1058 | |
1059 | static irqreturn_t fusb300_irq(int irq, void *_fusb300) |
1060 | { |
1061 | struct fusb300 *fusb300 = _fusb300; |
1062 | u32 int_grp1 = ioread32(fusb300->reg + FUSB300_OFFSET_IGR1); |
1063 | u32 int_grp1_en = ioread32(fusb300->reg + FUSB300_OFFSET_IGER1); |
1064 | u32 int_grp0 = ioread32(fusb300->reg + FUSB300_OFFSET_IGR0); |
1065 | u32 int_grp0_en = ioread32(fusb300->reg + FUSB300_OFFSET_IGER0); |
1066 | struct usb_ctrlrequest ctrl; |
1067 | u8 in; |
1068 | u32 reg; |
1069 | int i; |
1070 | |
1071 | spin_lock(lock: &fusb300->lock); |
1072 | |
1073 | int_grp1 &= int_grp1_en; |
1074 | int_grp0 &= int_grp0_en; |
1075 | |
1076 | if (int_grp1 & FUSB300_IGR1_WARM_RST_INT) { |
1077 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1078 | FUSB300_IGR1_WARM_RST_INT); |
1079 | printk(KERN_INFO"fusb300_warmreset\n" ); |
1080 | fusb300_reset(); |
1081 | } |
1082 | |
1083 | if (int_grp1 & FUSB300_IGR1_HOT_RST_INT) { |
1084 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1085 | FUSB300_IGR1_HOT_RST_INT); |
1086 | printk(KERN_INFO"fusb300_hotreset\n" ); |
1087 | fusb300_reset(); |
1088 | } |
1089 | |
1090 | if (int_grp1 & FUSB300_IGR1_USBRST_INT) { |
1091 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1092 | FUSB300_IGR1_USBRST_INT); |
1093 | fusb300_reset(); |
1094 | } |
1095 | /* COMABT_INT has a highest priority */ |
1096 | |
1097 | if (int_grp1 & FUSB300_IGR1_CX_COMABT_INT) { |
1098 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1099 | FUSB300_IGR1_CX_COMABT_INT); |
1100 | printk(KERN_INFO"fusb300_ep0abt\n" ); |
1101 | } |
1102 | |
1103 | if (int_grp1 & FUSB300_IGR1_VBUS_CHG_INT) { |
1104 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1105 | FUSB300_IGR1_VBUS_CHG_INT); |
1106 | printk(KERN_INFO"fusb300_vbus_change\n" ); |
1107 | } |
1108 | |
1109 | if (int_grp1 & FUSB300_IGR1_U3_EXIT_FAIL_INT) { |
1110 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1111 | FUSB300_IGR1_U3_EXIT_FAIL_INT); |
1112 | } |
1113 | |
1114 | if (int_grp1 & FUSB300_IGR1_U2_EXIT_FAIL_INT) { |
1115 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1116 | FUSB300_IGR1_U2_EXIT_FAIL_INT); |
1117 | } |
1118 | |
1119 | if (int_grp1 & FUSB300_IGR1_U1_EXIT_FAIL_INT) { |
1120 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1121 | FUSB300_IGR1_U1_EXIT_FAIL_INT); |
1122 | } |
1123 | |
1124 | if (int_grp1 & FUSB300_IGR1_U2_ENTRY_FAIL_INT) { |
1125 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1126 | FUSB300_IGR1_U2_ENTRY_FAIL_INT); |
1127 | } |
1128 | |
1129 | if (int_grp1 & FUSB300_IGR1_U1_ENTRY_FAIL_INT) { |
1130 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1131 | FUSB300_IGR1_U1_ENTRY_FAIL_INT); |
1132 | } |
1133 | |
1134 | if (int_grp1 & FUSB300_IGR1_U3_EXIT_INT) { |
1135 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1136 | FUSB300_IGR1_U3_EXIT_INT); |
1137 | printk(KERN_INFO "FUSB300_IGR1_U3_EXIT_INT\n" ); |
1138 | } |
1139 | |
1140 | if (int_grp1 & FUSB300_IGR1_U2_EXIT_INT) { |
1141 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1142 | FUSB300_IGR1_U2_EXIT_INT); |
1143 | printk(KERN_INFO "FUSB300_IGR1_U2_EXIT_INT\n" ); |
1144 | } |
1145 | |
1146 | if (int_grp1 & FUSB300_IGR1_U1_EXIT_INT) { |
1147 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1148 | FUSB300_IGR1_U1_EXIT_INT); |
1149 | printk(KERN_INFO "FUSB300_IGR1_U1_EXIT_INT\n" ); |
1150 | } |
1151 | |
1152 | if (int_grp1 & FUSB300_IGR1_U3_ENTRY_INT) { |
1153 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1154 | FUSB300_IGR1_U3_ENTRY_INT); |
1155 | printk(KERN_INFO "FUSB300_IGR1_U3_ENTRY_INT\n" ); |
1156 | fusb300_enable_bit(fusb300, FUSB300_OFFSET_SSCR1, |
1157 | FUSB300_SSCR1_GO_U3_DONE); |
1158 | } |
1159 | |
1160 | if (int_grp1 & FUSB300_IGR1_U2_ENTRY_INT) { |
1161 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1162 | FUSB300_IGR1_U2_ENTRY_INT); |
1163 | printk(KERN_INFO "FUSB300_IGR1_U2_ENTRY_INT\n" ); |
1164 | } |
1165 | |
1166 | if (int_grp1 & FUSB300_IGR1_U1_ENTRY_INT) { |
1167 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1168 | FUSB300_IGR1_U1_ENTRY_INT); |
1169 | printk(KERN_INFO "FUSB300_IGR1_U1_ENTRY_INT\n" ); |
1170 | } |
1171 | |
1172 | if (int_grp1 & FUSB300_IGR1_RESM_INT) { |
1173 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1174 | FUSB300_IGR1_RESM_INT); |
1175 | printk(KERN_INFO "fusb300_resume\n" ); |
1176 | } |
1177 | |
1178 | if (int_grp1 & FUSB300_IGR1_SUSP_INT) { |
1179 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1180 | FUSB300_IGR1_SUSP_INT); |
1181 | printk(KERN_INFO "fusb300_suspend\n" ); |
1182 | } |
1183 | |
1184 | if (int_grp1 & FUSB300_IGR1_HS_LPM_INT) { |
1185 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1186 | FUSB300_IGR1_HS_LPM_INT); |
1187 | printk(KERN_INFO "fusb300_HS_LPM_INT\n" ); |
1188 | } |
1189 | |
1190 | if (int_grp1 & FUSB300_IGR1_DEV_MODE_CHG_INT) { |
1191 | fusb300_clear_int(fusb300, FUSB300_OFFSET_IGR1, |
1192 | FUSB300_IGR1_DEV_MODE_CHG_INT); |
1193 | check_device_mode(fusb300); |
1194 | } |
1195 | |
1196 | if (int_grp1 & FUSB300_IGR1_CX_COMFAIL_INT) { |
1197 | fusb300_set_cxstall(fusb300); |
1198 | printk(KERN_INFO "fusb300_ep0fail\n" ); |
1199 | } |
1200 | |
1201 | if (int_grp1 & FUSB300_IGR1_CX_SETUP_INT) { |
1202 | printk(KERN_INFO "fusb300_ep0setup\n" ); |
1203 | if (setup_packet(fusb300, ctrl: &ctrl)) { |
1204 | spin_unlock(lock: &fusb300->lock); |
1205 | if (fusb300->driver->setup(&fusb300->gadget, &ctrl) < 0) |
1206 | fusb300_set_cxstall(fusb300); |
1207 | spin_lock(lock: &fusb300->lock); |
1208 | } |
1209 | } |
1210 | |
1211 | if (int_grp1 & FUSB300_IGR1_CX_CMDEND_INT) |
1212 | printk(KERN_INFO "fusb300_cmdend\n" ); |
1213 | |
1214 | |
1215 | if (int_grp1 & FUSB300_IGR1_CX_OUT_INT) { |
1216 | printk(KERN_INFO "fusb300_cxout\n" ); |
1217 | fusb300_ep0out(fusb300); |
1218 | } |
1219 | |
1220 | if (int_grp1 & FUSB300_IGR1_CX_IN_INT) { |
1221 | printk(KERN_INFO "fusb300_cxin\n" ); |
1222 | fusb300_ep0in(fusb300); |
1223 | } |
1224 | |
1225 | if (int_grp1 & FUSB300_IGR1_INTGRP5) |
1226 | fusb300_grp5_handler(); |
1227 | |
1228 | if (int_grp1 & FUSB300_IGR1_INTGRP4) |
1229 | fusb300_grp4_handler(); |
1230 | |
1231 | if (int_grp1 & FUSB300_IGR1_INTGRP3) |
1232 | fusb300_grp3_handler(); |
1233 | |
1234 | if (int_grp1 & FUSB300_IGR1_INTGRP2) |
1235 | fusb300_grp2_handler(); |
1236 | |
1237 | if (int_grp0) { |
1238 | for (i = 1; i < FUSB300_MAX_NUM_EP; i++) { |
1239 | if (int_grp0 & FUSB300_IGR0_EPn_FIFO_INT(i)) { |
1240 | reg = ioread32(fusb300->reg + |
1241 | FUSB300_OFFSET_EPSET1(i)); |
1242 | in = (reg & FUSB300_EPSET1_DIRIN) ? 1 : 0; |
1243 | if (in) |
1244 | in_ep_fifo_handler(ep: fusb300->ep[i]); |
1245 | else |
1246 | out_ep_fifo_handler(ep: fusb300->ep[i]); |
1247 | } |
1248 | } |
1249 | } |
1250 | |
1251 | spin_unlock(lock: &fusb300->lock); |
1252 | |
1253 | return IRQ_HANDLED; |
1254 | } |
1255 | |
1256 | static void fusb300_set_u2_timeout(struct fusb300 *fusb300, |
1257 | u32 time) |
1258 | { |
1259 | u32 reg; |
1260 | |
1261 | reg = ioread32(fusb300->reg + FUSB300_OFFSET_TT); |
1262 | reg &= ~0xff; |
1263 | reg |= FUSB300_SSCR2_U2TIMEOUT(time); |
1264 | |
1265 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_TT); |
1266 | } |
1267 | |
1268 | static void fusb300_set_u1_timeout(struct fusb300 *fusb300, |
1269 | u32 time) |
1270 | { |
1271 | u32 reg; |
1272 | |
1273 | reg = ioread32(fusb300->reg + FUSB300_OFFSET_TT); |
1274 | reg &= ~(0xff << 8); |
1275 | reg |= FUSB300_SSCR2_U1TIMEOUT(time); |
1276 | |
1277 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_TT); |
1278 | } |
1279 | |
1280 | static void init_controller(struct fusb300 *fusb300) |
1281 | { |
1282 | u32 reg; |
1283 | u32 mask = 0; |
1284 | u32 val = 0; |
1285 | |
1286 | /* split on */ |
1287 | mask = val = FUSB300_AHBBCR_S0_SPLIT_ON | FUSB300_AHBBCR_S1_SPLIT_ON; |
1288 | reg = ioread32(fusb300->reg + FUSB300_OFFSET_AHBCR); |
1289 | reg &= ~mask; |
1290 | reg |= val; |
1291 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_AHBCR); |
1292 | |
1293 | /* enable high-speed LPM */ |
1294 | mask = val = FUSB300_HSCR_HS_LPM_PERMIT; |
1295 | reg = ioread32(fusb300->reg + FUSB300_OFFSET_HSCR); |
1296 | reg &= ~mask; |
1297 | reg |= val; |
1298 | iowrite32(reg, fusb300->reg + FUSB300_OFFSET_HSCR); |
1299 | |
1300 | /*set u1 u2 timmer*/ |
1301 | fusb300_set_u2_timeout(fusb300, time: 0xff); |
1302 | fusb300_set_u1_timeout(fusb300, time: 0xff); |
1303 | |
1304 | /* enable all grp1 interrupt */ |
1305 | iowrite32(0xcfffff9f, fusb300->reg + FUSB300_OFFSET_IGER1); |
1306 | } |
1307 | /*------------------------------------------------------------------------*/ |
1308 | static int fusb300_udc_start(struct usb_gadget *g, |
1309 | struct usb_gadget_driver *driver) |
1310 | { |
1311 | struct fusb300 *fusb300 = to_fusb300(g); |
1312 | |
1313 | /* hook up the driver */ |
1314 | fusb300->driver = driver; |
1315 | |
1316 | return 0; |
1317 | } |
1318 | |
1319 | static int fusb300_udc_stop(struct usb_gadget *g) |
1320 | { |
1321 | struct fusb300 *fusb300 = to_fusb300(g); |
1322 | |
1323 | init_controller(fusb300); |
1324 | fusb300->driver = NULL; |
1325 | |
1326 | return 0; |
1327 | } |
1328 | /*--------------------------------------------------------------------------*/ |
1329 | |
1330 | static int fusb300_udc_pullup(struct usb_gadget *_gadget, int is_active) |
1331 | { |
1332 | return 0; |
1333 | } |
1334 | |
1335 | static const struct usb_gadget_ops fusb300_gadget_ops = { |
1336 | .pullup = fusb300_udc_pullup, |
1337 | .udc_start = fusb300_udc_start, |
1338 | .udc_stop = fusb300_udc_stop, |
1339 | }; |
1340 | |
1341 | static void fusb300_remove(struct platform_device *pdev) |
1342 | { |
1343 | struct fusb300 *fusb300 = platform_get_drvdata(pdev); |
1344 | int i; |
1345 | |
1346 | usb_del_gadget_udc(gadget: &fusb300->gadget); |
1347 | iounmap(addr: fusb300->reg); |
1348 | free_irq(platform_get_irq(pdev, 0), fusb300); |
1349 | free_irq(platform_get_irq(pdev, 1), fusb300); |
1350 | |
1351 | fusb300_free_request(ep: &fusb300->ep[0]->ep, req: fusb300->ep0_req); |
1352 | for (i = 0; i < FUSB300_MAX_NUM_EP; i++) |
1353 | kfree(objp: fusb300->ep[i]); |
1354 | kfree(objp: fusb300); |
1355 | } |
1356 | |
1357 | static int fusb300_probe(struct platform_device *pdev) |
1358 | { |
1359 | struct resource *res, *ires, *ires1; |
1360 | void __iomem *reg = NULL; |
1361 | struct fusb300 *fusb300 = NULL; |
1362 | struct fusb300_ep *_ep[FUSB300_MAX_NUM_EP]; |
1363 | int ret = 0; |
1364 | int i; |
1365 | |
1366 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
1367 | if (!res) { |
1368 | ret = -ENODEV; |
1369 | pr_err("platform_get_resource error.\n" ); |
1370 | goto clean_up; |
1371 | } |
1372 | |
1373 | ires = platform_get_resource(pdev, IORESOURCE_IRQ, 0); |
1374 | if (!ires) { |
1375 | ret = -ENODEV; |
1376 | dev_err(&pdev->dev, |
1377 | "platform_get_resource IORESOURCE_IRQ error.\n" ); |
1378 | goto clean_up; |
1379 | } |
1380 | |
1381 | ires1 = platform_get_resource(pdev, IORESOURCE_IRQ, 1); |
1382 | if (!ires1) { |
1383 | ret = -ENODEV; |
1384 | dev_err(&pdev->dev, |
1385 | "platform_get_resource IORESOURCE_IRQ 1 error.\n" ); |
1386 | goto clean_up; |
1387 | } |
1388 | |
1389 | reg = ioremap(offset: res->start, size: resource_size(res)); |
1390 | if (reg == NULL) { |
1391 | ret = -ENOMEM; |
1392 | pr_err("ioremap error.\n" ); |
1393 | goto clean_up; |
1394 | } |
1395 | |
1396 | /* initialize udc */ |
1397 | fusb300 = kzalloc(size: sizeof(struct fusb300), GFP_KERNEL); |
1398 | if (fusb300 == NULL) { |
1399 | ret = -ENOMEM; |
1400 | goto clean_up; |
1401 | } |
1402 | |
1403 | for (i = 0; i < FUSB300_MAX_NUM_EP; i++) { |
1404 | _ep[i] = kzalloc(size: sizeof(struct fusb300_ep), GFP_KERNEL); |
1405 | if (_ep[i] == NULL) { |
1406 | ret = -ENOMEM; |
1407 | goto clean_up; |
1408 | } |
1409 | fusb300->ep[i] = _ep[i]; |
1410 | } |
1411 | |
1412 | spin_lock_init(&fusb300->lock); |
1413 | |
1414 | platform_set_drvdata(pdev, data: fusb300); |
1415 | |
1416 | fusb300->gadget.ops = &fusb300_gadget_ops; |
1417 | |
1418 | fusb300->gadget.max_speed = USB_SPEED_HIGH; |
1419 | fusb300->gadget.name = udc_name; |
1420 | fusb300->reg = reg; |
1421 | |
1422 | ret = request_irq(irq: ires->start, handler: fusb300_irq, IRQF_SHARED, |
1423 | name: udc_name, dev: fusb300); |
1424 | if (ret < 0) { |
1425 | pr_err("request_irq error (%d)\n" , ret); |
1426 | goto clean_up; |
1427 | } |
1428 | |
1429 | ret = request_irq(irq: ires1->start, handler: fusb300_irq, |
1430 | IRQF_SHARED, name: udc_name, dev: fusb300); |
1431 | if (ret < 0) { |
1432 | pr_err("request_irq1 error (%d)\n" , ret); |
1433 | goto err_request_irq1; |
1434 | } |
1435 | |
1436 | INIT_LIST_HEAD(list: &fusb300->gadget.ep_list); |
1437 | |
1438 | for (i = 0; i < FUSB300_MAX_NUM_EP ; i++) { |
1439 | struct fusb300_ep *ep = fusb300->ep[i]; |
1440 | |
1441 | if (i != 0) { |
1442 | INIT_LIST_HEAD(list: &fusb300->ep[i]->ep.ep_list); |
1443 | list_add_tail(new: &fusb300->ep[i]->ep.ep_list, |
1444 | head: &fusb300->gadget.ep_list); |
1445 | } |
1446 | ep->fusb300 = fusb300; |
1447 | INIT_LIST_HEAD(list: &ep->queue); |
1448 | ep->ep.name = fusb300_ep_name[i]; |
1449 | ep->ep.ops = &fusb300_ep_ops; |
1450 | usb_ep_set_maxpacket_limit(ep: &ep->ep, HS_BULK_MAX_PACKET_SIZE); |
1451 | |
1452 | if (i == 0) { |
1453 | ep->ep.caps.type_control = true; |
1454 | } else { |
1455 | ep->ep.caps.type_iso = true; |
1456 | ep->ep.caps.type_bulk = true; |
1457 | ep->ep.caps.type_int = true; |
1458 | } |
1459 | |
1460 | ep->ep.caps.dir_in = true; |
1461 | ep->ep.caps.dir_out = true; |
1462 | } |
1463 | usb_ep_set_maxpacket_limit(ep: &fusb300->ep[0]->ep, HS_CTL_MAX_PACKET_SIZE); |
1464 | fusb300->ep[0]->epnum = 0; |
1465 | fusb300->gadget.ep0 = &fusb300->ep[0]->ep; |
1466 | INIT_LIST_HEAD(list: &fusb300->gadget.ep0->ep_list); |
1467 | |
1468 | fusb300->ep0_req = fusb300_alloc_request(ep: &fusb300->ep[0]->ep, |
1469 | GFP_KERNEL); |
1470 | if (fusb300->ep0_req == NULL) { |
1471 | ret = -ENOMEM; |
1472 | goto err_alloc_request; |
1473 | } |
1474 | |
1475 | init_controller(fusb300); |
1476 | ret = usb_add_gadget_udc(parent: &pdev->dev, gadget: &fusb300->gadget); |
1477 | if (ret) |
1478 | goto err_add_udc; |
1479 | |
1480 | dev_info(&pdev->dev, "version %s\n" , DRIVER_VERSION); |
1481 | |
1482 | return 0; |
1483 | |
1484 | err_add_udc: |
1485 | fusb300_free_request(ep: &fusb300->ep[0]->ep, req: fusb300->ep0_req); |
1486 | |
1487 | err_alloc_request: |
1488 | free_irq(ires1->start, fusb300); |
1489 | |
1490 | err_request_irq1: |
1491 | free_irq(ires->start, fusb300); |
1492 | |
1493 | clean_up: |
1494 | if (fusb300) { |
1495 | if (fusb300->ep0_req) |
1496 | fusb300_free_request(ep: &fusb300->ep[0]->ep, |
1497 | req: fusb300->ep0_req); |
1498 | for (i = 0; i < FUSB300_MAX_NUM_EP; i++) |
1499 | kfree(objp: fusb300->ep[i]); |
1500 | kfree(objp: fusb300); |
1501 | } |
1502 | if (reg) |
1503 | iounmap(addr: reg); |
1504 | |
1505 | return ret; |
1506 | } |
1507 | |
1508 | static struct platform_driver fusb300_driver = { |
1509 | .probe = fusb300_probe, |
1510 | .remove_new = fusb300_remove, |
1511 | .driver = { |
1512 | .name = udc_name, |
1513 | }, |
1514 | }; |
1515 | |
1516 | module_platform_driver(fusb300_driver); |
1517 | |