diff options
Diffstat (limited to 'firmware/target/arm/usb-fw-pp502x.c')
-rw-r--r-- | firmware/target/arm/usb-fw-pp502x.c | 215 |
1 files changed, 137 insertions, 78 deletions
diff --git a/firmware/target/arm/usb-fw-pp502x.c b/firmware/target/arm/usb-fw-pp502x.c index 8a6d78675f..883ca1e8e2 100644 --- a/firmware/target/arm/usb-fw-pp502x.c +++ b/firmware/target/arm/usb-fw-pp502x.c | |||
@@ -33,6 +33,60 @@ | |||
33 | #include "usb_core.h" | 33 | #include "usb_core.h" |
34 | #include "usb_drv.h" | 34 | #include "usb_drv.h" |
35 | 35 | ||
36 | #if defined(IPOD_4G) || defined(IPOD_COLOR) \ | ||
37 | || defined(IPOD_MINI) || defined(IPOD_MINI2G) | ||
38 | /* GPIO D bit 3 is usb detect */ | ||
39 | #define USB_GPIO GPIOD | ||
40 | #define USB_GPIO_MASK 0x08 | ||
41 | #define USB_GPIO_VAL 0x08 | ||
42 | |||
43 | #elif defined(IPOD_NANO) || defined(IPOD_VIDEO) | ||
44 | /* GPIO L bit 4 is usb detect */ | ||
45 | #define USB_GPIO GPIOL | ||
46 | #define USB_GPIO_MASK 0x10 | ||
47 | #define USB_GPIO_VAL 0x10 | ||
48 | |||
49 | #elif defined(SANSA_C200) | ||
50 | /* GPIO H bit 1 is usb/charger detect */ | ||
51 | #define USB_GPIO GPIOH | ||
52 | #define USB_GPIO_MASK 0x02 | ||
53 | #define USB_GPIO_VAL 0x02 | ||
54 | |||
55 | #elif defined(SANSA_E200) | ||
56 | /* GPIO B bit 4 is usb/charger detect */ | ||
57 | #define USB_GPIO GPIOB | ||
58 | #define USB_GPIO_MASK 0x10 | ||
59 | #define USB_GPIO_VAL 0x10 | ||
60 | |||
61 | #elif defined(IRIVER_H10) || defined(IRIVER_H10_5GB) || defined(MROBE_100) | ||
62 | /* GPIO L bit 2 is usb detect */ | ||
63 | #define USB_GPIO GPIOL | ||
64 | #define USB_GPIO_MASK 0x04 | ||
65 | #define USB_GPIO_VAL 0x04 | ||
66 | |||
67 | #elif defined(PHILIPS_SA9200) | ||
68 | /* GPIO F bit 7 (low) is usb detect */ | ||
69 | #define USB_GPIO GPIOF | ||
70 | #define USB_GPIO_MASK 0x80 | ||
71 | #define USB_GPIO_VAL 0x00 | ||
72 | |||
73 | #elif defined(PHILIPS_HDD1630) | ||
74 | /* GPIO E bit 2 is usb detect */ | ||
75 | #define USB_GPIO GPIOE | ||
76 | #define USB_GPIO_MASK 0x04 | ||
77 | #define USB_GPIO_VAL 0x04 | ||
78 | #else | ||
79 | #error No USB GPIO config specified | ||
80 | #endif | ||
81 | |||
82 | #define USB_GPIO_ENABLE GPIO_ENABLE(USB_GPIO) | ||
83 | #define USB_GPIO_OUTPUT_EN GPIO_OUTPUT_EN(USB_GPIO) | ||
84 | #define USB_GPIO_INPUT_VAL GPIO_INPUT_VAL(USB_GPIO) | ||
85 | #define USB_GPIO_INT_EN GPIO_INT_EN(USB_GPIO) | ||
86 | #define USB_GPIO_INT_LEV GPIO_INT_LEV(USB_GPIO) | ||
87 | #define USB_GPIO_INT_CLR GPIO_INT_CLR(USB_GPIO) | ||
88 | #define USB_GPIO_HI_INT_MASK GPIO_HI_INT_MASK(USB_GPIO) | ||
89 | |||
36 | void usb_init_device(void) | 90 | void usb_init_device(void) |
37 | { | 91 | { |
38 | /* enable usb module */ | 92 | /* enable usb module */ |
@@ -52,7 +106,10 @@ void usb_init_device(void) | |||
52 | while ((inl(0x70000028) & 0x80) == 0); | 106 | while ((inl(0x70000028) & 0x80) == 0); |
53 | outl(inl(0x70000028) | 0x2, 0x70000028); | 107 | outl(inl(0x70000028) | 0x2, 0x70000028); |
54 | udelay(100000); | 108 | udelay(100000); |
55 | 109 | ||
110 | /* Do one-time inits */ | ||
111 | usb_drv_startup(); | ||
112 | |||
56 | /* disable USB-devices until USB is detected via GPIO */ | 113 | /* disable USB-devices until USB is detected via GPIO */ |
57 | #ifndef BOOTLOADER | 114 | #ifndef BOOTLOADER |
58 | /* Disabling USB0 in the bootloader makes the OF not load, | 115 | /* Disabling USB0 in the bootloader makes the OF not load, |
@@ -63,17 +120,38 @@ void usb_init_device(void) | |||
63 | DEV_INIT2 &= ~INIT_USB; | 120 | DEV_INIT2 &= ~INIT_USB; |
64 | #endif | 121 | #endif |
65 | 122 | ||
66 | #if defined(IPOD_COLOR) || defined(IPOD_4G) \ | 123 | /* These set INV_LEV to the inserted level so it will fire if already |
67 | || defined(IPOD_MINI) || defined(IPOD_MINI2G) | 124 | * inserted at the time they are enabled. */ |
125 | #ifdef USB_STATUS_BY_EVENT | ||
126 | GPIO_CLEAR_BITWISE(USB_GPIO_INT_EN, USB_GPIO_MASK); | ||
127 | GPIO_CLEAR_BITWISE(USB_GPIO_OUTPUT_EN, USB_GPIO_MASK); | ||
128 | GPIO_SET_BITWISE(USB_GPIO_ENABLE, USB_GPIO_MASK); | ||
129 | GPIO_WRITE_BITWISE(USB_GPIO_INT_LEV, USB_GPIO_VAL, USB_GPIO_MASK); | ||
130 | USB_GPIO_INT_CLR = USB_GPIO_MASK; | ||
131 | GPIO_SET_BITWISE(USB_GPIO_INT_EN, USB_GPIO_MASK); | ||
132 | CPU_HI_INT_EN = USB_GPIO_HI_INT_MASK; | ||
133 | |||
134 | #ifdef USB_FIREWIRE_HANDLING | ||
68 | /* GPIO C bit 1 is firewire detect */ | 135 | /* GPIO C bit 1 is firewire detect */ |
69 | GPIOC_ENABLE |= 0x02; | 136 | GPIO_CLEAR_BITWISE(GPIOC_INT_EN, 0x02); |
70 | GPIOC_OUTPUT_EN &= ~0x02; | 137 | GPIO_CLEAR_BITWISE(GPIOC_OUTPUT_EN, 0x02); |
138 | GPIO_SET_BITWISE(GPIOC_ENABLE, 0x02); | ||
139 | GPIO_WRITE_BITWISE(GPIOC_INT_LEV, 0x00, 0x02); | ||
140 | GPIOC_INT_CLR = 0x02; | ||
141 | GPIO_SET_BITWISE(GPIOC_INT_EN, 0x02); | ||
142 | CPU_HI_INT_EN = GPIO0_MASK; | ||
71 | #endif | 143 | #endif |
72 | 144 | CPU_INT_EN = HI_MASK; | |
73 | #ifdef HAVE_USBSTACK | 145 | #else |
74 | /* Do one-time inits */ | 146 | /* No interrupt - setup pin read only (BOOTLOADER) */ |
75 | usb_drv_startup(); | 147 | GPIO_CLEAR_BITWISE(USB_GPIO_OUTPUT_EN, USB_GPIO_MASK); |
148 | GPIO_SET_BITWISE(USB_GPIO_ENABLE, USB_GPIO_MASK); | ||
149 | #ifdef USB_FIREWIRE_HANDLING | ||
150 | /* GPIO C bit 1 is firewire detect */ | ||
151 | GPIO_CLEAR_BITWISE(GPIOC_OUTPUT_EN, 0x02); | ||
152 | GPIO_SET_BITWISE(GPIOC_ENABLE, 0x02); | ||
76 | #endif | 153 | #endif |
154 | #endif /* USB_STATUS_BY_EVENT */ | ||
77 | } | 155 | } |
78 | 156 | ||
79 | void usb_enable(bool on) | 157 | void usb_enable(bool on) |
@@ -96,21 +174,27 @@ void usb_enable(bool on) | |||
96 | 174 | ||
97 | void usb_attach(void) | 175 | void usb_attach(void) |
98 | { | 176 | { |
99 | #ifdef USB_DETECT_BY_DRV | ||
100 | usb_drv_attach(); | 177 | usb_drv_attach(); |
101 | #else | ||
102 | usb_enable(true); | ||
103 | #endif | ||
104 | } | 178 | } |
105 | 179 | ||
106 | #ifdef USB_DETECT_BY_DRV | 180 | #ifdef USB_STATUS_BY_EVENT |
107 | /* Cannot tell charger pin from USB pin */ | 181 | /* Cannot always tell power pin from USB pin */ |
108 | static int usb_status = USB_EXTRACTED; | 182 | static int usb_status = USB_EXTRACTED; |
109 | 183 | ||
110 | void usb_connect_event(bool inserted) | 184 | static int usb_timeout_event(struct timeout *tmo) |
185 | { | ||
186 | usb_status_event(tmo->data == USB_GPIO_VAL ? USB_POWERED : USB_UNPOWERED); | ||
187 | return 0; | ||
188 | } | ||
189 | |||
190 | void usb_insert_int(void) | ||
111 | { | 191 | { |
112 | usb_status = inserted ? USB_INSERTED : USB_EXTRACTED; | 192 | static struct timeout usb_oneshot; |
113 | usb_status_event(inserted ? USB_POWERED : USB_UNPOWERED); | 193 | unsigned long val = USB_GPIO_INPUT_VAL & USB_GPIO_MASK; |
194 | usb_status = (val == USB_GPIO_VAL) ? USB_INSERTED : USB_EXTRACTED; | ||
195 | GPIO_WRITE_BITWISE(USB_GPIO_INT_LEV, val ^ USB_GPIO_MASK, USB_GPIO_MASK); | ||
196 | USB_GPIO_INT_CLR = USB_GPIO_MASK; | ||
197 | timeout_register(&usb_oneshot, usb_timeout_event, HZ/5, val); | ||
114 | } | 198 | } |
115 | 199 | ||
116 | /* Called during the bus reset interrupt when in detect mode */ | 200 | /* Called during the bus reset interrupt when in detect mode */ |
@@ -118,51 +202,7 @@ void usb_drv_usb_detect_event(void) | |||
118 | { | 202 | { |
119 | usb_status_event(USB_INSERTED); | 203 | usb_status_event(USB_INSERTED); |
120 | } | 204 | } |
121 | #else /* !USB_DETECT_BY_DRV */ | 205 | #endif /* USB_STATUS_BY_EVENT */ |
122 | static bool usb_pin_detect(void) | ||
123 | { | ||
124 | bool retval = false; | ||
125 | |||
126 | #if defined(IPOD_4G) || defined(IPOD_COLOR) \ | ||
127 | || defined(IPOD_MINI) || defined(IPOD_MINI2G) | ||
128 | /* GPIO D bit 3 is usb detect */ | ||
129 | if (GPIOD_INPUT_VAL & 0x08) | ||
130 | retval = true; | ||
131 | |||
132 | #elif defined(IPOD_NANO) || defined(IPOD_VIDEO) | ||
133 | /* GPIO L bit 4 is usb detect */ | ||
134 | if (GPIOL_INPUT_VAL & 0x10) | ||
135 | retval = true; | ||
136 | |||
137 | #elif defined(SANSA_C200) | ||
138 | /* GPIO H bit 1 is usb/charger detect */ | ||
139 | if (GPIOH_INPUT_VAL & 0x02) | ||
140 | retval = true; | ||
141 | |||
142 | #elif defined(SANSA_E200) | ||
143 | /* GPIO B bit 4 is usb/charger detect */ | ||
144 | if (GPIOB_INPUT_VAL & 0x10) | ||
145 | retval = true; | ||
146 | |||
147 | #elif defined(IRIVER_H10) || defined(IRIVER_H10_5GB) || defined(MROBE_100) | ||
148 | /* GPIO L bit 2 is usb detect */ | ||
149 | if (GPIOL_INPUT_VAL & 0x4) | ||
150 | retval = true; | ||
151 | |||
152 | #elif defined(PHILIPS_SA9200) | ||
153 | /* GPIO F bit 7 is usb detect */ | ||
154 | if (!(GPIOF_INPUT_VAL & 0x80)) | ||
155 | retval = true; | ||
156 | |||
157 | #elif defined(PHILIPS_HDD1630) | ||
158 | /* GPIO E bit 2 is usb detect */ | ||
159 | if (GPIOE_INPUT_VAL & 0x4) | ||
160 | retval = true; | ||
161 | #endif | ||
162 | |||
163 | return retval; | ||
164 | } | ||
165 | #endif /* USB_DETECT_BY_DRV */ | ||
166 | 206 | ||
167 | void usb_drv_int_enable(bool enable) | 207 | void usb_drv_int_enable(bool enable) |
168 | { | 208 | { |
@@ -178,27 +218,46 @@ void usb_drv_int_enable(bool enable) | |||
178 | /* detect host or charger (INSERTED or EXTRACTED) */ | 218 | /* detect host or charger (INSERTED or EXTRACTED) */ |
179 | int usb_detect(void) | 219 | int usb_detect(void) |
180 | { | 220 | { |
181 | #ifdef USB_DETECT_BY_DRV | 221 | #ifdef USB_STATUS_BY_EVENT |
182 | return usb_status; | 222 | return usb_status; |
183 | #else | 223 | #else |
184 | if(usb_pin_detect()) { | 224 | return ((USB_GPIO_INPUT_VAL & USB_GPIO_MASK) == USB_GPIO_VAL) ? |
185 | return USB_INSERTED; | 225 | USB_INSERTED : USB_EXTRACTED; |
186 | } | ||
187 | else { | ||
188 | return USB_EXTRACTED; | ||
189 | } | ||
190 | #endif | 226 | #endif |
191 | } | 227 | } |
192 | 228 | ||
193 | #if defined(IPOD_COLOR) || defined(IPOD_4G) \ | 229 | #ifdef USB_FIREWIRE_HANDLING |
194 | || defined(IPOD_MINI) || defined(IPOD_MINI2G) | 230 | #ifdef USB_STATUS_BY_EVENT |
231 | static bool firewire_status = false; | ||
232 | #endif | ||
233 | |||
195 | bool firewire_detect(void) | 234 | bool firewire_detect(void) |
196 | { | 235 | { |
236 | #ifdef USB_STATUS_BY_EVENT | ||
237 | return firewire_status; | ||
238 | #else | ||
197 | /* GPIO C bit 1 is firewire detect */ | 239 | /* GPIO C bit 1 is firewire detect */ |
198 | if (!(GPIOC_INPUT_VAL & 0x02)) | 240 | /* no charger detection needed for firewire */ |
199 | /* no charger detection needed for firewire */ | 241 | return (GPIOC_INPUT_VAL & 0x02) == 0x00; |
200 | return true; | ||
201 | else | ||
202 | return false; | ||
203 | } | ||
204 | #endif | 242 | #endif |
243 | } | ||
244 | |||
245 | #ifdef USB_STATUS_BY_EVENT | ||
246 | static int firewire_timeout_event(struct timeout *tmo) | ||
247 | { | ||
248 | if (tmo->data == 0x00) | ||
249 | usb_firewire_connect_event(); | ||
250 | return 0; | ||
251 | } | ||
252 | |||
253 | void firewire_insert_int(void) | ||
254 | { | ||
255 | static struct timeout firewire_oneshot; | ||
256 | unsigned long val = GPIOC_INPUT_VAL & 0x02; | ||
257 | firewire_status = val == 0x00; | ||
258 | GPIO_WRITE_BITWISE(GPIOC_INT_LEV, val ^ 0x02, 0x02); | ||
259 | GPIOC_INT_CLR = 0x02; | ||
260 | timeout_register(&firewire_oneshot, firewire_timeout_event, HZ/5, val); | ||
261 | } | ||
262 | #endif /* USB_STATUS_BY_EVENT */ | ||
263 | #endif /* USB_FIREWIRE_HANDLING */ | ||