diff options
author | Andrew Victor <andrew@sanpeople.com> | 2006-12-08 01:44:33 -0500 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2006-12-20 13:14:27 -0500 |
commit | ffd3326bf6282b9f606e92ae57e8f47f2e10e6b5 (patch) | |
tree | a63757e053600754aeda03472427846f7eaf5b05 /drivers/usb | |
parent | 5151d04068e37e710d2cc3962351ca0979fc5ad1 (diff) |
USB: at91 udc, support at91sam926x addresses
This is an update to the AT91 USB Device (Gadget) driver.
The base I/O address provided in the platform_device resources is now
ioremap()'ed instead of using a statically mapped memory area. This
helps portability to the newer AT91sam926x processors.
The major change is that we now have to pass a 'struct at91_udc'
parameter to at91_udp_read() and at91_udp_write().
Signed-off-by: Andrew Victor <andrew@sanpeople.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/usb')
-rw-r--r-- | drivers/usb/gadget/at91_udc.c | 169 | ||||
-rw-r--r-- | drivers/usb/gadget/at91_udc.h | 1 |
2 files changed, 84 insertions, 86 deletions
diff --git a/drivers/usb/gadget/at91_udc.c b/drivers/usb/gadget/at91_udc.c index 81656337381f..b53b93700ca8 100644 --- a/drivers/usb/gadget/at91_udc.c +++ b/drivers/usb/gadget/at91_udc.c | |||
@@ -43,12 +43,12 @@ | |||
43 | #include <linux/usb_gadget.h> | 43 | #include <linux/usb_gadget.h> |
44 | 44 | ||
45 | #include <asm/byteorder.h> | 45 | #include <asm/byteorder.h> |
46 | #include <asm/hardware.h> | ||
46 | #include <asm/io.h> | 47 | #include <asm/io.h> |
47 | #include <asm/irq.h> | 48 | #include <asm/irq.h> |
48 | #include <asm/system.h> | 49 | #include <asm/system.h> |
49 | #include <asm/mach-types.h> | 50 | #include <asm/mach-types.h> |
50 | 51 | ||
51 | #include <asm/arch/hardware.h> | ||
52 | #include <asm/arch/gpio.h> | 52 | #include <asm/arch/gpio.h> |
53 | #include <asm/arch/board.h> | 53 | #include <asm/arch/board.h> |
54 | 54 | ||
@@ -78,27 +78,11 @@ | |||
78 | static const char driver_name [] = "at91_udc"; | 78 | static const char driver_name [] = "at91_udc"; |
79 | static const char ep0name[] = "ep0"; | 79 | static const char ep0name[] = "ep0"; |
80 | 80 | ||
81 | /*-------------------------------------------------------------------------*/ | ||
82 | |||
83 | /* | ||
84 | * Read from a UDP register. | ||
85 | */ | ||
86 | static inline unsigned long at91_udp_read(unsigned int reg) | ||
87 | { | ||
88 | void __iomem *udp_base = (void __iomem *)AT91_VA_BASE_UDP; | ||
89 | |||
90 | return __raw_readl(udp_base + reg); | ||
91 | } | ||
92 | |||
93 | /* | ||
94 | * Write to a UDP register. | ||
95 | */ | ||
96 | static inline void at91_udp_write(unsigned int reg, unsigned long value) | ||
97 | { | ||
98 | void __iomem *udp_base = (void __iomem *)AT91_VA_BASE_UDP; | ||
99 | 81 | ||
100 | __raw_writel(value, udp_base + reg); | 82 | #define at91_udp_read(dev, reg) \ |
101 | } | 83 | __raw_readl((dev)->udp_baseaddr + (reg)) |
84 | #define at91_udp_write(dev, reg, val) \ | ||
85 | __raw_writel((val), (dev)->udp_baseaddr + (reg)) | ||
102 | 86 | ||
103 | /*-------------------------------------------------------------------------*/ | 87 | /*-------------------------------------------------------------------------*/ |
104 | 88 | ||
@@ -210,13 +194,13 @@ static int proc_udc_show(struct seq_file *s, void *unused) | |||
210 | return 0; | 194 | return 0; |
211 | } | 195 | } |
212 | 196 | ||
213 | tmp = at91_udp_read(AT91_UDP_FRM_NUM); | 197 | tmp = at91_udp_read(udc, AT91_UDP_FRM_NUM); |
214 | seq_printf(s, "frame %05x:%s%s frame=%d\n", tmp, | 198 | seq_printf(s, "frame %05x:%s%s frame=%d\n", tmp, |
215 | (tmp & AT91_UDP_FRM_OK) ? " ok" : "", | 199 | (tmp & AT91_UDP_FRM_OK) ? " ok" : "", |
216 | (tmp & AT91_UDP_FRM_ERR) ? " err" : "", | 200 | (tmp & AT91_UDP_FRM_ERR) ? " err" : "", |
217 | (tmp & AT91_UDP_NUM)); | 201 | (tmp & AT91_UDP_NUM)); |
218 | 202 | ||
219 | tmp = at91_udp_read(AT91_UDP_GLB_STAT); | 203 | tmp = at91_udp_read(udc, AT91_UDP_GLB_STAT); |
220 | seq_printf(s, "glbstate %02x:%s" FOURBITS "\n", tmp, | 204 | seq_printf(s, "glbstate %02x:%s" FOURBITS "\n", tmp, |
221 | (tmp & AT91_UDP_RMWUPE) ? " rmwupe" : "", | 205 | (tmp & AT91_UDP_RMWUPE) ? " rmwupe" : "", |
222 | (tmp & AT91_UDP_RSMINPR) ? " rsminpr" : "", | 206 | (tmp & AT91_UDP_RSMINPR) ? " rsminpr" : "", |
@@ -224,13 +208,13 @@ static int proc_udc_show(struct seq_file *s, void *unused) | |||
224 | (tmp & AT91_UDP_CONFG) ? " confg" : "", | 208 | (tmp & AT91_UDP_CONFG) ? " confg" : "", |
225 | (tmp & AT91_UDP_FADDEN) ? " fadden" : ""); | 209 | (tmp & AT91_UDP_FADDEN) ? " fadden" : ""); |
226 | 210 | ||
227 | tmp = at91_udp_read(AT91_UDP_FADDR); | 211 | tmp = at91_udp_read(udc, AT91_UDP_FADDR); |
228 | seq_printf(s, "faddr %03x:%s fadd=%d\n", tmp, | 212 | seq_printf(s, "faddr %03x:%s fadd=%d\n", tmp, |
229 | (tmp & AT91_UDP_FEN) ? " fen" : "", | 213 | (tmp & AT91_UDP_FEN) ? " fen" : "", |
230 | (tmp & AT91_UDP_FADD)); | 214 | (tmp & AT91_UDP_FADD)); |
231 | 215 | ||
232 | proc_irq_show(s, "imr ", at91_udp_read(AT91_UDP_IMR)); | 216 | proc_irq_show(s, "imr ", at91_udp_read(udc, AT91_UDP_IMR)); |
233 | proc_irq_show(s, "isr ", at91_udp_read(AT91_UDP_ISR)); | 217 | proc_irq_show(s, "isr ", at91_udp_read(udc, AT91_UDP_ISR)); |
234 | 218 | ||
235 | if (udc->enabled && udc->vbus) { | 219 | if (udc->enabled && udc->vbus) { |
236 | proc_ep_show(s, &udc->ep[0]); | 220 | proc_ep_show(s, &udc->ep[0]); |
@@ -286,6 +270,7 @@ static inline void remove_debug_file(struct at91_udc *udc) {} | |||
286 | static void done(struct at91_ep *ep, struct at91_request *req, int status) | 270 | static void done(struct at91_ep *ep, struct at91_request *req, int status) |
287 | { | 271 | { |
288 | unsigned stopped = ep->stopped; | 272 | unsigned stopped = ep->stopped; |
273 | struct at91_udc *udc = ep->udc; | ||
289 | 274 | ||
290 | list_del_init(&req->queue); | 275 | list_del_init(&req->queue); |
291 | if (req->req.status == -EINPROGRESS) | 276 | if (req->req.status == -EINPROGRESS) |
@@ -301,7 +286,7 @@ static void done(struct at91_ep *ep, struct at91_request *req, int status) | |||
301 | 286 | ||
302 | /* ep0 is always ready; other endpoints need a non-empty queue */ | 287 | /* ep0 is always ready; other endpoints need a non-empty queue */ |
303 | if (list_empty(&ep->queue) && ep->int_mask != (1 << 0)) | 288 | if (list_empty(&ep->queue) && ep->int_mask != (1 << 0)) |
304 | at91_udp_write(AT91_UDP_IDR, ep->int_mask); | 289 | at91_udp_write(udc, AT91_UDP_IDR, ep->int_mask); |
305 | } | 290 | } |
306 | 291 | ||
307 | /*-------------------------------------------------------------------------*/ | 292 | /*-------------------------------------------------------------------------*/ |
@@ -554,8 +539,8 @@ ok: | |||
554 | * reset/init endpoint fifo. NOTE: leaves fifo_bank alone, | 539 | * reset/init endpoint fifo. NOTE: leaves fifo_bank alone, |
555 | * since endpoint resets don't reset hw pingpong state. | 540 | * since endpoint resets don't reset hw pingpong state. |
556 | */ | 541 | */ |
557 | at91_udp_write(AT91_UDP_RST_EP, ep->int_mask); | 542 | at91_udp_write(dev, AT91_UDP_RST_EP, ep->int_mask); |
558 | at91_udp_write(AT91_UDP_RST_EP, 0); | 543 | at91_udp_write(dev, AT91_UDP_RST_EP, 0); |
559 | 544 | ||
560 | local_irq_restore(flags); | 545 | local_irq_restore(flags); |
561 | return 0; | 546 | return 0; |
@@ -564,6 +549,7 @@ ok: | |||
564 | static int at91_ep_disable (struct usb_ep * _ep) | 549 | static int at91_ep_disable (struct usb_ep * _ep) |
565 | { | 550 | { |
566 | struct at91_ep *ep = container_of(_ep, struct at91_ep, ep); | 551 | struct at91_ep *ep = container_of(_ep, struct at91_ep, ep); |
552 | struct at91_udc *udc = ep->udc; | ||
567 | unsigned long flags; | 553 | unsigned long flags; |
568 | 554 | ||
569 | if (ep == &ep->udc->ep[0]) | 555 | if (ep == &ep->udc->ep[0]) |
@@ -579,8 +565,8 @@ static int at91_ep_disable (struct usb_ep * _ep) | |||
579 | 565 | ||
580 | /* reset fifos and endpoint */ | 566 | /* reset fifos and endpoint */ |
581 | if (ep->udc->clocked) { | 567 | if (ep->udc->clocked) { |
582 | at91_udp_write(AT91_UDP_RST_EP, ep->int_mask); | 568 | at91_udp_write(udc, AT91_UDP_RST_EP, ep->int_mask); |
583 | at91_udp_write(AT91_UDP_RST_EP, 0); | 569 | at91_udp_write(udc, AT91_UDP_RST_EP, 0); |
584 | __raw_writel(0, ep->creg); | 570 | __raw_writel(0, ep->creg); |
585 | } | 571 | } |
586 | 572 | ||
@@ -695,10 +681,10 @@ static int at91_ep_queue(struct usb_ep *_ep, | |||
695 | * reconfigures the endpoints. | 681 | * reconfigures the endpoints. |
696 | */ | 682 | */ |
697 | if (dev->wait_for_config_ack) { | 683 | if (dev->wait_for_config_ack) { |
698 | tmp = at91_udp_read(AT91_UDP_GLB_STAT); | 684 | tmp = at91_udp_read(dev, AT91_UDP_GLB_STAT); |
699 | tmp ^= AT91_UDP_CONFG; | 685 | tmp ^= AT91_UDP_CONFG; |
700 | VDBG("toggle config\n"); | 686 | VDBG("toggle config\n"); |
701 | at91_udp_write(AT91_UDP_GLB_STAT, tmp); | 687 | at91_udp_write(dev, AT91_UDP_GLB_STAT, tmp); |
702 | } | 688 | } |
703 | if (req->req.length == 0) { | 689 | if (req->req.length == 0) { |
704 | ep0_in_status: | 690 | ep0_in_status: |
@@ -727,7 +713,7 @@ ep0_in_status: | |||
727 | 713 | ||
728 | if (req && !status) { | 714 | if (req && !status) { |
729 | list_add_tail (&req->queue, &ep->queue); | 715 | list_add_tail (&req->queue, &ep->queue); |
730 | at91_udp_write(AT91_UDP_IER, ep->int_mask); | 716 | at91_udp_write(dev, AT91_UDP_IER, ep->int_mask); |
731 | } | 717 | } |
732 | done: | 718 | done: |
733 | local_irq_restore(flags); | 719 | local_irq_restore(flags); |
@@ -758,6 +744,7 @@ static int at91_ep_dequeue(struct usb_ep *_ep, struct usb_request *_req) | |||
758 | static int at91_ep_set_halt(struct usb_ep *_ep, int value) | 744 | static int at91_ep_set_halt(struct usb_ep *_ep, int value) |
759 | { | 745 | { |
760 | struct at91_ep *ep = container_of(_ep, struct at91_ep, ep); | 746 | struct at91_ep *ep = container_of(_ep, struct at91_ep, ep); |
747 | struct at91_udc *udc = ep->udc; | ||
761 | u32 __iomem *creg; | 748 | u32 __iomem *creg; |
762 | u32 csr; | 749 | u32 csr; |
763 | unsigned long flags; | 750 | unsigned long flags; |
@@ -785,8 +772,8 @@ static int at91_ep_set_halt(struct usb_ep *_ep, int value) | |||
785 | csr |= AT91_UDP_FORCESTALL; | 772 | csr |= AT91_UDP_FORCESTALL; |
786 | VDBG("halt %s\n", ep->ep.name); | 773 | VDBG("halt %s\n", ep->ep.name); |
787 | } else { | 774 | } else { |
788 | at91_udp_write(AT91_UDP_RST_EP, ep->int_mask); | 775 | at91_udp_write(udc, AT91_UDP_RST_EP, ep->int_mask); |
789 | at91_udp_write(AT91_UDP_RST_EP, 0); | 776 | at91_udp_write(udc, AT91_UDP_RST_EP, 0); |
790 | csr &= ~AT91_UDP_FORCESTALL; | 777 | csr &= ~AT91_UDP_FORCESTALL; |
791 | } | 778 | } |
792 | __raw_writel(csr, creg); | 779 | __raw_writel(csr, creg); |
@@ -813,9 +800,11 @@ static struct usb_ep_ops at91_ep_ops = { | |||
813 | 800 | ||
814 | static int at91_get_frame(struct usb_gadget *gadget) | 801 | static int at91_get_frame(struct usb_gadget *gadget) |
815 | { | 802 | { |
803 | struct at91_udc *udc = to_udc(gadget); | ||
804 | |||
816 | if (!to_udc(gadget)->clocked) | 805 | if (!to_udc(gadget)->clocked) |
817 | return -EINVAL; | 806 | return -EINVAL; |
818 | return at91_udp_read(AT91_UDP_FRM_NUM) & AT91_UDP_NUM; | 807 | return at91_udp_read(udc, AT91_UDP_FRM_NUM) & AT91_UDP_NUM; |
819 | } | 808 | } |
820 | 809 | ||
821 | static int at91_wakeup(struct usb_gadget *gadget) | 810 | static int at91_wakeup(struct usb_gadget *gadget) |
@@ -833,11 +822,11 @@ static int at91_wakeup(struct usb_gadget *gadget) | |||
833 | 822 | ||
834 | /* NOTE: some "early versions" handle ESR differently ... */ | 823 | /* NOTE: some "early versions" handle ESR differently ... */ |
835 | 824 | ||
836 | glbstate = at91_udp_read(AT91_UDP_GLB_STAT); | 825 | glbstate = at91_udp_read(udc, AT91_UDP_GLB_STAT); |
837 | if (!(glbstate & AT91_UDP_ESR)) | 826 | if (!(glbstate & AT91_UDP_ESR)) |
838 | goto done; | 827 | goto done; |
839 | glbstate |= AT91_UDP_ESR; | 828 | glbstate |= AT91_UDP_ESR; |
840 | at91_udp_write(AT91_UDP_GLB_STAT, glbstate); | 829 | at91_udp_write(udc, AT91_UDP_GLB_STAT, glbstate); |
841 | 830 | ||
842 | done: | 831 | done: |
843 | local_irq_restore(flags); | 832 | local_irq_restore(flags); |
@@ -861,6 +850,7 @@ static void udc_reinit(struct at91_udc *udc) | |||
861 | ep->stopped = 0; | 850 | ep->stopped = 0; |
862 | ep->fifo_bank = 0; | 851 | ep->fifo_bank = 0; |
863 | ep->ep.maxpacket = ep->maxpacket; | 852 | ep->ep.maxpacket = ep->maxpacket; |
853 | ep->creg = (void __iomem *) udc->udp_baseaddr + AT91_UDP_CSR(i); | ||
864 | // initialiser une queue par endpoint | 854 | // initialiser une queue par endpoint |
865 | INIT_LIST_HEAD(&ep->queue); | 855 | INIT_LIST_HEAD(&ep->queue); |
866 | } | 856 | } |
@@ -915,13 +905,14 @@ static void pullup(struct at91_udc *udc, int is_on) | |||
915 | if (!udc->enabled || !udc->vbus) | 905 | if (!udc->enabled || !udc->vbus) |
916 | is_on = 0; | 906 | is_on = 0; |
917 | DBG("%sactive\n", is_on ? "" : "in"); | 907 | DBG("%sactive\n", is_on ? "" : "in"); |
908 | |||
918 | if (is_on) { | 909 | if (is_on) { |
919 | clk_on(udc); | 910 | clk_on(udc); |
920 | at91_udp_write(AT91_UDP_TXVC, 0); | 911 | at91_udp_write(udc, AT91_UDP_TXVC, 0); |
921 | at91_set_gpio_value(udc->board.pullup_pin, 1); | 912 | at91_set_gpio_value(udc->board.pullup_pin, 1); |
922 | } else { | 913 | } else { |
923 | stop_activity(udc); | 914 | stop_activity(udc); |
924 | at91_udp_write(AT91_UDP_TXVC, AT91_UDP_TXVC_TXVDIS); | 915 | at91_udp_write(udc, AT91_UDP_TXVC, AT91_UDP_TXVC_TXVDIS); |
925 | at91_set_gpio_value(udc->board.pullup_pin, 0); | 916 | at91_set_gpio_value(udc->board.pullup_pin, 0); |
926 | clk_off(udc); | 917 | clk_off(udc); |
927 | } | 918 | } |
@@ -1086,7 +1077,7 @@ static void handle_setup(struct at91_udc *udc, struct at91_ep *ep, u32 csr) | |||
1086 | 1077 | ||
1087 | case ((USB_TYPE_STANDARD|USB_RECIP_DEVICE) << 8) | 1078 | case ((USB_TYPE_STANDARD|USB_RECIP_DEVICE) << 8) |
1088 | | USB_REQ_SET_CONFIGURATION: | 1079 | | USB_REQ_SET_CONFIGURATION: |
1089 | tmp = at91_udp_read(AT91_UDP_GLB_STAT) & AT91_UDP_CONFG; | 1080 | tmp = at91_udp_read(udc, AT91_UDP_GLB_STAT) & AT91_UDP_CONFG; |
1090 | if (pkt.r.wValue) | 1081 | if (pkt.r.wValue) |
1091 | udc->wait_for_config_ack = (tmp == 0); | 1082 | udc->wait_for_config_ack = (tmp == 0); |
1092 | else | 1083 | else |
@@ -1103,7 +1094,7 @@ static void handle_setup(struct at91_udc *udc, struct at91_ep *ep, u32 csr) | |||
1103 | case ((USB_DIR_IN|USB_TYPE_STANDARD|USB_RECIP_DEVICE) << 8) | 1094 | case ((USB_DIR_IN|USB_TYPE_STANDARD|USB_RECIP_DEVICE) << 8) |
1104 | | USB_REQ_GET_STATUS: | 1095 | | USB_REQ_GET_STATUS: |
1105 | tmp = (udc->selfpowered << USB_DEVICE_SELF_POWERED); | 1096 | tmp = (udc->selfpowered << USB_DEVICE_SELF_POWERED); |
1106 | if (at91_udp_read(AT91_UDP_GLB_STAT) & AT91_UDP_ESR) | 1097 | if (at91_udp_read(udc, AT91_UDP_GLB_STAT) & AT91_UDP_ESR) |
1107 | tmp |= (1 << USB_DEVICE_REMOTE_WAKEUP); | 1098 | tmp |= (1 << USB_DEVICE_REMOTE_WAKEUP); |
1108 | PACKET("get device status\n"); | 1099 | PACKET("get device status\n"); |
1109 | __raw_writeb(tmp, dreg); | 1100 | __raw_writeb(tmp, dreg); |
@@ -1114,17 +1105,17 @@ static void handle_setup(struct at91_udc *udc, struct at91_ep *ep, u32 csr) | |||
1114 | | USB_REQ_SET_FEATURE: | 1105 | | USB_REQ_SET_FEATURE: |
1115 | if (w_value != USB_DEVICE_REMOTE_WAKEUP) | 1106 | if (w_value != USB_DEVICE_REMOTE_WAKEUP) |
1116 | goto stall; | 1107 | goto stall; |
1117 | tmp = at91_udp_read(AT91_UDP_GLB_STAT); | 1108 | tmp = at91_udp_read(udc, AT91_UDP_GLB_STAT); |
1118 | tmp |= AT91_UDP_ESR; | 1109 | tmp |= AT91_UDP_ESR; |
1119 | at91_udp_write(AT91_UDP_GLB_STAT, tmp); | 1110 | at91_udp_write(udc, AT91_UDP_GLB_STAT, tmp); |
1120 | goto succeed; | 1111 | goto succeed; |
1121 | case ((USB_TYPE_STANDARD|USB_RECIP_DEVICE) << 8) | 1112 | case ((USB_TYPE_STANDARD|USB_RECIP_DEVICE) << 8) |
1122 | | USB_REQ_CLEAR_FEATURE: | 1113 | | USB_REQ_CLEAR_FEATURE: |
1123 | if (w_value != USB_DEVICE_REMOTE_WAKEUP) | 1114 | if (w_value != USB_DEVICE_REMOTE_WAKEUP) |
1124 | goto stall; | 1115 | goto stall; |
1125 | tmp = at91_udp_read(AT91_UDP_GLB_STAT); | 1116 | tmp = at91_udp_read(udc, AT91_UDP_GLB_STAT); |
1126 | tmp &= ~AT91_UDP_ESR; | 1117 | tmp &= ~AT91_UDP_ESR; |
1127 | at91_udp_write(AT91_UDP_GLB_STAT, tmp); | 1118 | at91_udp_write(udc, AT91_UDP_GLB_STAT, tmp); |
1128 | goto succeed; | 1119 | goto succeed; |
1129 | 1120 | ||
1130 | /* | 1121 | /* |
@@ -1206,8 +1197,8 @@ static void handle_setup(struct at91_udc *udc, struct at91_ep *ep, u32 csr) | |||
1206 | } else if (ep->is_in) | 1197 | } else if (ep->is_in) |
1207 | goto stall; | 1198 | goto stall; |
1208 | 1199 | ||
1209 | at91_udp_write(AT91_UDP_RST_EP, ep->int_mask); | 1200 | at91_udp_write(udc, AT91_UDP_RST_EP, ep->int_mask); |
1210 | at91_udp_write(AT91_UDP_RST_EP, 0); | 1201 | at91_udp_write(udc, AT91_UDP_RST_EP, 0); |
1211 | tmp = __raw_readl(ep->creg); | 1202 | tmp = __raw_readl(ep->creg); |
1212 | tmp |= CLR_FX; | 1203 | tmp |= CLR_FX; |
1213 | tmp &= ~(SET_FX | AT91_UDP_FORCESTALL); | 1204 | tmp &= ~(SET_FX | AT91_UDP_FORCESTALL); |
@@ -1300,13 +1291,13 @@ static void handle_ep0(struct at91_udc *udc) | |||
1300 | if (udc->wait_for_addr_ack) { | 1291 | if (udc->wait_for_addr_ack) { |
1301 | u32 tmp; | 1292 | u32 tmp; |
1302 | 1293 | ||
1303 | at91_udp_write(AT91_UDP_FADDR, | 1294 | at91_udp_write(udc, AT91_UDP_FADDR, |
1304 | AT91_UDP_FEN | udc->addr); | 1295 | AT91_UDP_FEN | udc->addr); |
1305 | tmp = at91_udp_read(AT91_UDP_GLB_STAT); | 1296 | tmp = at91_udp_read(udc, AT91_UDP_GLB_STAT); |
1306 | tmp &= ~AT91_UDP_FADDEN; | 1297 | tmp &= ~AT91_UDP_FADDEN; |
1307 | if (udc->addr) | 1298 | if (udc->addr) |
1308 | tmp |= AT91_UDP_FADDEN; | 1299 | tmp |= AT91_UDP_FADDEN; |
1309 | at91_udp_write(AT91_UDP_GLB_STAT, tmp); | 1300 | at91_udp_write(udc, AT91_UDP_GLB_STAT, tmp); |
1310 | 1301 | ||
1311 | udc->wait_for_addr_ack = 0; | 1302 | udc->wait_for_addr_ack = 0; |
1312 | VDBG("address %d\n", udc->addr); | 1303 | VDBG("address %d\n", udc->addr); |
@@ -1374,28 +1365,28 @@ static irqreturn_t at91_udc_irq (int irq, void *_udc) | |||
1374 | while (rescans--) { | 1365 | while (rescans--) { |
1375 | u32 status; | 1366 | u32 status; |
1376 | 1367 | ||
1377 | status = at91_udp_read(AT91_UDP_ISR) | 1368 | status = at91_udp_read(udc, AT91_UDP_ISR) |
1378 | & at91_udp_read(AT91_UDP_IMR); | 1369 | & at91_udp_read(udc, AT91_UDP_IMR); |
1379 | if (!status) | 1370 | if (!status) |
1380 | break; | 1371 | break; |
1381 | 1372 | ||
1382 | /* USB reset irq: not maskable */ | 1373 | /* USB reset irq: not maskable */ |
1383 | if (status & AT91_UDP_ENDBUSRES) { | 1374 | if (status & AT91_UDP_ENDBUSRES) { |
1384 | at91_udp_write(AT91_UDP_IDR, ~MINIMUS_INTERRUPTUS); | 1375 | at91_udp_write(udc, AT91_UDP_IDR, ~MINIMUS_INTERRUPTUS); |
1385 | at91_udp_write(AT91_UDP_IER, MINIMUS_INTERRUPTUS); | 1376 | at91_udp_write(udc, AT91_UDP_IER, MINIMUS_INTERRUPTUS); |
1386 | /* Atmel code clears this irq twice */ | 1377 | /* Atmel code clears this irq twice */ |
1387 | at91_udp_write(AT91_UDP_ICR, AT91_UDP_ENDBUSRES); | 1378 | at91_udp_write(udc, AT91_UDP_ICR, AT91_UDP_ENDBUSRES); |
1388 | at91_udp_write(AT91_UDP_ICR, AT91_UDP_ENDBUSRES); | 1379 | at91_udp_write(udc, AT91_UDP_ICR, AT91_UDP_ENDBUSRES); |
1389 | VDBG("end bus reset\n"); | 1380 | VDBG("end bus reset\n"); |
1390 | udc->addr = 0; | 1381 | udc->addr = 0; |
1391 | stop_activity(udc); | 1382 | stop_activity(udc); |
1392 | 1383 | ||
1393 | /* enable ep0 */ | 1384 | /* enable ep0 */ |
1394 | at91_udp_write(AT91_UDP_CSR(0), | 1385 | at91_udp_write(udc, AT91_UDP_CSR(0), |
1395 | AT91_UDP_EPEDS | AT91_UDP_EPTYPE_CTRL); | 1386 | AT91_UDP_EPEDS | AT91_UDP_EPTYPE_CTRL); |
1396 | udc->gadget.speed = USB_SPEED_FULL; | 1387 | udc->gadget.speed = USB_SPEED_FULL; |
1397 | udc->suspended = 0; | 1388 | udc->suspended = 0; |
1398 | at91_udp_write(AT91_UDP_IER, AT91_UDP_EP(0)); | 1389 | at91_udp_write(udc, AT91_UDP_IER, AT91_UDP_EP(0)); |
1399 | 1390 | ||
1400 | /* | 1391 | /* |
1401 | * NOTE: this driver keeps clocks off unless the | 1392 | * NOTE: this driver keeps clocks off unless the |
@@ -1406,9 +1397,9 @@ static irqreturn_t at91_udc_irq (int irq, void *_udc) | |||
1406 | 1397 | ||
1407 | /* host initiated suspend (3+ms bus idle) */ | 1398 | /* host initiated suspend (3+ms bus idle) */ |
1408 | } else if (status & AT91_UDP_RXSUSP) { | 1399 | } else if (status & AT91_UDP_RXSUSP) { |
1409 | at91_udp_write(AT91_UDP_IDR, AT91_UDP_RXSUSP); | 1400 | at91_udp_write(udc, AT91_UDP_IDR, AT91_UDP_RXSUSP); |
1410 | at91_udp_write(AT91_UDP_IER, AT91_UDP_RXRSM); | 1401 | at91_udp_write(udc, AT91_UDP_IER, AT91_UDP_RXRSM); |
1411 | at91_udp_write(AT91_UDP_ICR, AT91_UDP_RXSUSP); | 1402 | at91_udp_write(udc, AT91_UDP_ICR, AT91_UDP_RXSUSP); |
1412 | // VDBG("bus suspend\n"); | 1403 | // VDBG("bus suspend\n"); |
1413 | if (udc->suspended) | 1404 | if (udc->suspended) |
1414 | continue; | 1405 | continue; |
@@ -1425,9 +1416,9 @@ static irqreturn_t at91_udc_irq (int irq, void *_udc) | |||
1425 | 1416 | ||
1426 | /* host initiated resume */ | 1417 | /* host initiated resume */ |
1427 | } else if (status & AT91_UDP_RXRSM) { | 1418 | } else if (status & AT91_UDP_RXRSM) { |
1428 | at91_udp_write(AT91_UDP_IDR, AT91_UDP_RXRSM); | 1419 | at91_udp_write(udc, AT91_UDP_IDR, AT91_UDP_RXRSM); |
1429 | at91_udp_write(AT91_UDP_IER, AT91_UDP_RXSUSP); | 1420 | at91_udp_write(udc, AT91_UDP_IER, AT91_UDP_RXSUSP); |
1430 | at91_udp_write(AT91_UDP_ICR, AT91_UDP_RXRSM); | 1421 | at91_udp_write(udc, AT91_UDP_ICR, AT91_UDP_RXRSM); |
1431 | // VDBG("bus resume\n"); | 1422 | // VDBG("bus resume\n"); |
1432 | if (!udc->suspended) | 1423 | if (!udc->suspended) |
1433 | continue; | 1424 | continue; |
@@ -1485,8 +1476,6 @@ static struct at91_udc controller = { | |||
1485 | }, | 1476 | }, |
1486 | .udc = &controller, | 1477 | .udc = &controller, |
1487 | .maxpacket = 8, | 1478 | .maxpacket = 8, |
1488 | .creg = (void __iomem *)(AT91_VA_BASE_UDP | ||
1489 | + AT91_UDP_CSR(0)), | ||
1490 | .int_mask = 1 << 0, | 1479 | .int_mask = 1 << 0, |
1491 | }, | 1480 | }, |
1492 | .ep[1] = { | 1481 | .ep[1] = { |
@@ -1497,8 +1486,6 @@ static struct at91_udc controller = { | |||
1497 | .udc = &controller, | 1486 | .udc = &controller, |
1498 | .is_pingpong = 1, | 1487 | .is_pingpong = 1, |
1499 | .maxpacket = 64, | 1488 | .maxpacket = 64, |
1500 | .creg = (void __iomem *)(AT91_VA_BASE_UDP | ||
1501 | + AT91_UDP_CSR(1)), | ||
1502 | .int_mask = 1 << 1, | 1489 | .int_mask = 1 << 1, |
1503 | }, | 1490 | }, |
1504 | .ep[2] = { | 1491 | .ep[2] = { |
@@ -1509,8 +1496,6 @@ static struct at91_udc controller = { | |||
1509 | .udc = &controller, | 1496 | .udc = &controller, |
1510 | .is_pingpong = 1, | 1497 | .is_pingpong = 1, |
1511 | .maxpacket = 64, | 1498 | .maxpacket = 64, |
1512 | .creg = (void __iomem *)(AT91_VA_BASE_UDP | ||
1513 | + AT91_UDP_CSR(2)), | ||
1514 | .int_mask = 1 << 2, | 1499 | .int_mask = 1 << 2, |
1515 | }, | 1500 | }, |
1516 | .ep[3] = { | 1501 | .ep[3] = { |
@@ -1521,8 +1506,6 @@ static struct at91_udc controller = { | |||
1521 | }, | 1506 | }, |
1522 | .udc = &controller, | 1507 | .udc = &controller, |
1523 | .maxpacket = 8, | 1508 | .maxpacket = 8, |
1524 | .creg = (void __iomem *)(AT91_VA_BASE_UDP | ||
1525 | + AT91_UDP_CSR(3)), | ||
1526 | .int_mask = 1 << 3, | 1509 | .int_mask = 1 << 3, |
1527 | }, | 1510 | }, |
1528 | .ep[4] = { | 1511 | .ep[4] = { |
@@ -1533,8 +1516,6 @@ static struct at91_udc controller = { | |||
1533 | .udc = &controller, | 1516 | .udc = &controller, |
1534 | .is_pingpong = 1, | 1517 | .is_pingpong = 1, |
1535 | .maxpacket = 256, | 1518 | .maxpacket = 256, |
1536 | .creg = (void __iomem *)(AT91_VA_BASE_UDP | ||
1537 | + AT91_UDP_CSR(4)), | ||
1538 | .int_mask = 1 << 4, | 1519 | .int_mask = 1 << 4, |
1539 | }, | 1520 | }, |
1540 | .ep[5] = { | 1521 | .ep[5] = { |
@@ -1545,8 +1526,6 @@ static struct at91_udc controller = { | |||
1545 | .udc = &controller, | 1526 | .udc = &controller, |
1546 | .is_pingpong = 1, | 1527 | .is_pingpong = 1, |
1547 | .maxpacket = 256, | 1528 | .maxpacket = 256, |
1548 | .creg = (void __iomem *)(AT91_VA_BASE_UDP | ||
1549 | + AT91_UDP_CSR(5)), | ||
1550 | .int_mask = 1 << 5, | 1529 | .int_mask = 1 << 5, |
1551 | }, | 1530 | }, |
1552 | /* ep6 and ep7 are also reserved (custom silicon might use them) */ | 1531 | /* ep6 and ep7 are also reserved (custom silicon might use them) */ |
@@ -1615,7 +1594,7 @@ int usb_gadget_unregister_driver (struct usb_gadget_driver *driver) | |||
1615 | 1594 | ||
1616 | local_irq_disable(); | 1595 | local_irq_disable(); |
1617 | udc->enabled = 0; | 1596 | udc->enabled = 0; |
1618 | at91_udp_write(AT91_UDP_IDR, ~0); | 1597 | at91_udp_write(udc, AT91_UDP_IDR, ~0); |
1619 | pullup(udc, 0); | 1598 | pullup(udc, 0); |
1620 | local_irq_enable(); | 1599 | local_irq_enable(); |
1621 | 1600 | ||
@@ -1640,6 +1619,7 @@ static int __devinit at91udc_probe(struct platform_device *pdev) | |||
1640 | struct device *dev = &pdev->dev; | 1619 | struct device *dev = &pdev->dev; |
1641 | struct at91_udc *udc; | 1620 | struct at91_udc *udc; |
1642 | int retval; | 1621 | int retval; |
1622 | struct resource *res; | ||
1643 | 1623 | ||
1644 | if (!dev->platform_data) { | 1624 | if (!dev->platform_data) { |
1645 | /* small (so we copy it) but critical! */ | 1625 | /* small (so we copy it) but critical! */ |
@@ -1657,7 +1637,13 @@ static int __devinit at91udc_probe(struct platform_device *pdev) | |||
1657 | return -ENODEV; | 1637 | return -ENODEV; |
1658 | } | 1638 | } |
1659 | 1639 | ||
1660 | if (!request_mem_region(AT91RM9200_BASE_UDP, SZ_16K, driver_name)) { | 1640 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
1641 | if (!res) | ||
1642 | return -ENXIO; | ||
1643 | |||
1644 | if (!request_mem_region(res->start, | ||
1645 | res->end - res->start + 1, | ||
1646 | driver_name)) { | ||
1661 | DBG("someone's using UDC memory\n"); | 1647 | DBG("someone's using UDC memory\n"); |
1662 | return -EBUSY; | 1648 | return -EBUSY; |
1663 | } | 1649 | } |
@@ -1667,9 +1653,16 @@ static int __devinit at91udc_probe(struct platform_device *pdev) | |||
1667 | udc->gadget.dev.parent = dev; | 1653 | udc->gadget.dev.parent = dev; |
1668 | udc->board = *(struct at91_udc_data *) dev->platform_data; | 1654 | udc->board = *(struct at91_udc_data *) dev->platform_data; |
1669 | udc->pdev = pdev; | 1655 | udc->pdev = pdev; |
1670 | udc_reinit(udc); | ||
1671 | udc->enabled = 0; | 1656 | udc->enabled = 0; |
1672 | 1657 | ||
1658 | udc->udp_baseaddr = ioremap(res->start, res->end - res->start + 1); | ||
1659 | if (!udc->udp_baseaddr) { | ||
1660 | release_mem_region(res->start, res->end - res->start + 1); | ||
1661 | return -ENOMEM; | ||
1662 | } | ||
1663 | |||
1664 | udc_reinit(udc); | ||
1665 | |||
1673 | /* get interface and function clocks */ | 1666 | /* get interface and function clocks */ |
1674 | udc->iclk = clk_get(dev, "udc_clk"); | 1667 | udc->iclk = clk_get(dev, "udc_clk"); |
1675 | udc->fclk = clk_get(dev, "udpck"); | 1668 | udc->fclk = clk_get(dev, "udpck"); |
@@ -1684,8 +1677,8 @@ static int __devinit at91udc_probe(struct platform_device *pdev) | |||
1684 | 1677 | ||
1685 | /* don't do anything until we have both gadget driver and VBUS */ | 1678 | /* don't do anything until we have both gadget driver and VBUS */ |
1686 | clk_enable(udc->iclk); | 1679 | clk_enable(udc->iclk); |
1687 | at91_udp_write(AT91_UDP_TXVC, AT91_UDP_TXVC_TXVDIS); | 1680 | at91_udp_write(udc, AT91_UDP_TXVC, AT91_UDP_TXVC_TXVDIS); |
1688 | at91_udp_write(AT91_UDP_IDR, 0xffffffff); | 1681 | at91_udp_write(udc, AT91_UDP_IDR, 0xffffffff); |
1689 | clk_disable(udc->iclk); | 1682 | clk_disable(udc->iclk); |
1690 | 1683 | ||
1691 | /* request UDC and maybe VBUS irqs */ | 1684 | /* request UDC and maybe VBUS irqs */ |
@@ -1719,7 +1712,7 @@ static int __devinit at91udc_probe(struct platform_device *pdev) | |||
1719 | fail1: | 1712 | fail1: |
1720 | device_unregister(&udc->gadget.dev); | 1713 | device_unregister(&udc->gadget.dev); |
1721 | fail0: | 1714 | fail0: |
1722 | release_mem_region(AT91RM9200_BASE_UDP, SZ_16K); | 1715 | release_mem_region(res->start, res->end - res->start + 1); |
1723 | DBG("%s probe failed, %d\n", driver_name, retval); | 1716 | DBG("%s probe failed, %d\n", driver_name, retval); |
1724 | return retval; | 1717 | return retval; |
1725 | } | 1718 | } |
@@ -1727,6 +1720,7 @@ fail0: | |||
1727 | static int __devexit at91udc_remove(struct platform_device *pdev) | 1720 | static int __devexit at91udc_remove(struct platform_device *pdev) |
1728 | { | 1721 | { |
1729 | struct at91_udc *udc = platform_get_drvdata(pdev); | 1722 | struct at91_udc *udc = platform_get_drvdata(pdev); |
1723 | struct resource *res; | ||
1730 | 1724 | ||
1731 | DBG("remove\n"); | 1725 | DBG("remove\n"); |
1732 | 1726 | ||
@@ -1741,7 +1735,10 @@ static int __devexit at91udc_remove(struct platform_device *pdev) | |||
1741 | free_irq(udc->board.vbus_pin, udc); | 1735 | free_irq(udc->board.vbus_pin, udc); |
1742 | free_irq(udc->udp_irq, udc); | 1736 | free_irq(udc->udp_irq, udc); |
1743 | device_unregister(&udc->gadget.dev); | 1737 | device_unregister(&udc->gadget.dev); |
1744 | release_mem_region(AT91RM9200_BASE_UDP, SZ_16K); | 1738 | |
1739 | iounmap(udc->udp_baseaddr); | ||
1740 | res = platform_get_resource(pdev, IORESOURCE_MEM, 0); | ||
1741 | release_mem_region(res->start, res->end - res->start + 1); | ||
1745 | 1742 | ||
1746 | clk_put(udc->iclk); | 1743 | clk_put(udc->iclk); |
1747 | clk_put(udc->fclk); | 1744 | clk_put(udc->fclk); |
diff --git a/drivers/usb/gadget/at91_udc.h b/drivers/usb/gadget/at91_udc.h index 882af42e86cc..a35f3b627d3c 100644 --- a/drivers/usb/gadget/at91_udc.h +++ b/drivers/usb/gadget/at91_udc.h | |||
@@ -141,6 +141,7 @@ struct at91_udc { | |||
141 | struct clk *iclk, *fclk; | 141 | struct clk *iclk, *fclk; |
142 | struct platform_device *pdev; | 142 | struct platform_device *pdev; |
143 | struct proc_dir_entry *pde; | 143 | struct proc_dir_entry *pde; |
144 | void __iomem *udp_baseaddr; | ||
144 | int udp_irq; | 145 | int udp_irq; |
145 | }; | 146 | }; |
146 | 147 | ||