Contents of /trunk/kernel-magellan/patches-3.7/0106-3.7.7-all-fixes.patch
Parent Directory | Revision Log
Revision 2075 -
(show annotations)
(download)
Mon Feb 18 12:04:00 2013 UTC (11 years, 7 months ago) by niro
File size: 48666 byte(s)
Mon Feb 18 12:04:00 2013 UTC (11 years, 7 months ago) by niro
File size: 48666 byte(s)
-linux-3.7.7
1 | diff --git a/arch/powerpc/mm/hash_low_64.S b/arch/powerpc/mm/hash_low_64.S |
2 | index 5658508..7443481 100644 |
3 | --- a/arch/powerpc/mm/hash_low_64.S |
4 | +++ b/arch/powerpc/mm/hash_low_64.S |
5 | @@ -115,11 +115,13 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT) |
6 | sldi r29,r5,SID_SHIFT - VPN_SHIFT |
7 | rldicl r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT - VPN_SHIFT) |
8 | or r29,r28,r29 |
9 | - |
10 | - /* Calculate hash value for primary slot and store it in r28 */ |
11 | - rldicl r5,r5,0,25 /* vsid & 0x0000007fffffffff */ |
12 | - rldicl r0,r3,64-12,48 /* (ea >> 12) & 0xffff */ |
13 | - xor r28,r5,r0 |
14 | + /* |
15 | + * Calculate hash value for primary slot and store it in r28 |
16 | + * r3 = va, r5 = vsid |
17 | + * r0 = (va >> 12) & ((1ul << (28 - 12)) -1) |
18 | + */ |
19 | + rldicl r0,r3,64-12,48 |
20 | + xor r28,r5,r0 /* hash */ |
21 | b 4f |
22 | |
23 | 3: /* Calc vpn and put it in r29 */ |
24 | @@ -130,11 +132,12 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT) |
25 | /* |
26 | * calculate hash value for primary slot and |
27 | * store it in r28 for 1T segment |
28 | + * r3 = va, r5 = vsid |
29 | */ |
30 | - rldic r28,r5,25,25 /* (vsid << 25) & 0x7fffffffff */ |
31 | - clrldi r5,r5,40 /* vsid & 0xffffff */ |
32 | - rldicl r0,r3,64-12,36 /* (ea >> 12) & 0xfffffff */ |
33 | - xor r28,r28,r5 |
34 | + sldi r28,r5,25 /* vsid << 25 */ |
35 | + /* r0 = (va >> 12) & ((1ul << (40 - 12)) -1) */ |
36 | + rldicl r0,r3,64-12,36 |
37 | + xor r28,r28,r5 /* vsid ^ ( vsid << 25) */ |
38 | xor r28,r28,r0 /* hash */ |
39 | |
40 | /* Convert linux PTE bits into HW equivalents */ |
41 | @@ -407,11 +410,13 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT) |
42 | */ |
43 | rldicl r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT - VPN_SHIFT) |
44 | or r29,r28,r29 |
45 | - |
46 | - /* Calculate hash value for primary slot and store it in r28 */ |
47 | - rldicl r5,r5,0,25 /* vsid & 0x0000007fffffffff */ |
48 | - rldicl r0,r3,64-12,48 /* (ea >> 12) & 0xffff */ |
49 | - xor r28,r5,r0 |
50 | + /* |
51 | + * Calculate hash value for primary slot and store it in r28 |
52 | + * r3 = va, r5 = vsid |
53 | + * r0 = (va >> 12) & ((1ul << (28 - 12)) -1) |
54 | + */ |
55 | + rldicl r0,r3,64-12,48 |
56 | + xor r28,r5,r0 /* hash */ |
57 | b 4f |
58 | |
59 | 3: /* Calc vpn and put it in r29 */ |
60 | @@ -426,11 +431,12 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT) |
61 | /* |
62 | * Calculate hash value for primary slot and |
63 | * store it in r28 for 1T segment |
64 | + * r3 = va, r5 = vsid |
65 | */ |
66 | - rldic r28,r5,25,25 /* (vsid << 25) & 0x7fffffffff */ |
67 | - clrldi r5,r5,40 /* vsid & 0xffffff */ |
68 | - rldicl r0,r3,64-12,36 /* (ea >> 12) & 0xfffffff */ |
69 | - xor r28,r28,r5 |
70 | + sldi r28,r5,25 /* vsid << 25 */ |
71 | + /* r0 = (va >> 12) & ((1ul << (40 - 12)) -1) */ |
72 | + rldicl r0,r3,64-12,36 |
73 | + xor r28,r28,r5 /* vsid ^ ( vsid << 25) */ |
74 | xor r28,r28,r0 /* hash */ |
75 | |
76 | /* Convert linux PTE bits into HW equivalents */ |
77 | @@ -752,25 +758,27 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT) |
78 | rldicl r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT - VPN_SHIFT) |
79 | or r29,r28,r29 |
80 | |
81 | - /* Calculate hash value for primary slot and store it in r28 */ |
82 | - rldicl r5,r5,0,25 /* vsid & 0x0000007fffffffff */ |
83 | - rldicl r0,r3,64-16,52 /* (ea >> 16) & 0xfff */ |
84 | - xor r28,r5,r0 |
85 | + /* Calculate hash value for primary slot and store it in r28 |
86 | + * r3 = va, r5 = vsid |
87 | + * r0 = (va >> 16) & ((1ul << (28 - 16)) -1) |
88 | + */ |
89 | + rldicl r0,r3,64-16,52 |
90 | + xor r28,r5,r0 /* hash */ |
91 | b 4f |
92 | |
93 | 3: /* Calc vpn and put it in r29 */ |
94 | sldi r29,r5,SID_SHIFT_1T - VPN_SHIFT |
95 | rldicl r28,r3,64 - VPN_SHIFT,64 - (SID_SHIFT_1T - VPN_SHIFT) |
96 | or r29,r28,r29 |
97 | - |
98 | /* |
99 | * calculate hash value for primary slot and |
100 | * store it in r28 for 1T segment |
101 | + * r3 = va, r5 = vsid |
102 | */ |
103 | - rldic r28,r5,25,25 /* (vsid << 25) & 0x7fffffffff */ |
104 | - clrldi r5,r5,40 /* vsid & 0xffffff */ |
105 | - rldicl r0,r3,64-16,40 /* (ea >> 16) & 0xffffff */ |
106 | - xor r28,r28,r5 |
107 | + sldi r28,r5,25 /* vsid << 25 */ |
108 | + /* r0 = (va >> 16) & ((1ul << (40 - 16)) -1) */ |
109 | + rldicl r0,r3,64-16,40 |
110 | + xor r28,r28,r5 /* vsid ^ ( vsid << 25) */ |
111 | xor r28,r28,r0 /* hash */ |
112 | |
113 | /* Convert linux PTE bits into HW equivalents */ |
114 | diff --git a/arch/x86/ia32/ia32entry.S b/arch/x86/ia32/ia32entry.S |
115 | index 076745f..e7fa545 100644 |
116 | --- a/arch/x86/ia32/ia32entry.S |
117 | +++ b/arch/x86/ia32/ia32entry.S |
118 | @@ -207,7 +207,7 @@ sysexit_from_sys_call: |
119 | testl $(_TIF_ALLWORK_MASK & ~_TIF_SYSCALL_AUDIT),TI_flags+THREAD_INFO(%rsp,RIP-ARGOFFSET) |
120 | jnz ia32_ret_from_sys_call |
121 | TRACE_IRQS_ON |
122 | - sti |
123 | + ENABLE_INTERRUPTS(CLBR_NONE) |
124 | movl %eax,%esi /* second arg, syscall return value */ |
125 | cmpl $-MAX_ERRNO,%eax /* is it an error ? */ |
126 | jbe 1f |
127 | @@ -217,7 +217,7 @@ sysexit_from_sys_call: |
128 | call __audit_syscall_exit |
129 | movq RAX-ARGOFFSET(%rsp),%rax /* reload syscall return value */ |
130 | movl $(_TIF_ALLWORK_MASK & ~_TIF_SYSCALL_AUDIT),%edi |
131 | - cli |
132 | + DISABLE_INTERRUPTS(CLBR_NONE) |
133 | TRACE_IRQS_OFF |
134 | testl %edi,TI_flags+THREAD_INFO(%rsp,RIP-ARGOFFSET) |
135 | jz \exit |
136 | diff --git a/drivers/gpu/drm/radeon/evergreen.c b/drivers/gpu/drm/radeon/evergreen.c |
137 | index 18a5382..47c737c 100644 |
138 | --- a/drivers/gpu/drm/radeon/evergreen.c |
139 | +++ b/drivers/gpu/drm/radeon/evergreen.c |
140 | @@ -1313,14 +1313,18 @@ void evergreen_mc_stop(struct radeon_device *rdev, struct evergreen_mc_save *sav |
141 | if (!(tmp & EVERGREEN_CRTC_BLANK_DATA_EN)) { |
142 | radeon_wait_for_vblank(rdev, i); |
143 | tmp |= EVERGREEN_CRTC_BLANK_DATA_EN; |
144 | + WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
145 | WREG32(EVERGREEN_CRTC_BLANK_CONTROL + crtc_offsets[i], tmp); |
146 | + WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
147 | } |
148 | } else { |
149 | tmp = RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i]); |
150 | if (!(tmp & EVERGREEN_CRTC_DISP_READ_REQUEST_DISABLE)) { |
151 | radeon_wait_for_vblank(rdev, i); |
152 | tmp |= EVERGREEN_CRTC_DISP_READ_REQUEST_DISABLE; |
153 | + WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
154 | WREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i], tmp); |
155 | + WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
156 | } |
157 | } |
158 | /* wait for the next frame */ |
159 | @@ -1345,6 +1349,8 @@ void evergreen_mc_stop(struct radeon_device *rdev, struct evergreen_mc_save *sav |
160 | blackout &= ~BLACKOUT_MODE_MASK; |
161 | WREG32(MC_SHARED_BLACKOUT_CNTL, blackout | 1); |
162 | } |
163 | + /* wait for the MC to settle */ |
164 | + udelay(100); |
165 | } |
166 | |
167 | void evergreen_mc_resume(struct radeon_device *rdev, struct evergreen_mc_save *save) |
168 | @@ -1378,11 +1384,15 @@ void evergreen_mc_resume(struct radeon_device *rdev, struct evergreen_mc_save *s |
169 | if (ASIC_IS_DCE6(rdev)) { |
170 | tmp = RREG32(EVERGREEN_CRTC_BLANK_CONTROL + crtc_offsets[i]); |
171 | tmp |= EVERGREEN_CRTC_BLANK_DATA_EN; |
172 | + WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
173 | WREG32(EVERGREEN_CRTC_BLANK_CONTROL + crtc_offsets[i], tmp); |
174 | + WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
175 | } else { |
176 | tmp = RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i]); |
177 | tmp &= ~EVERGREEN_CRTC_DISP_READ_REQUEST_DISABLE; |
178 | + WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
179 | WREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i], tmp); |
180 | + WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
181 | } |
182 | /* wait for the next frame */ |
183 | frame_count = radeon_get_vblank_counter(rdev, i); |
184 | @@ -2035,9 +2045,20 @@ static void evergreen_gpu_init(struct radeon_device *rdev) |
185 | WREG32(DMIF_ADDR_CONFIG, gb_addr_config); |
186 | WREG32(HDP_ADDR_CONFIG, gb_addr_config); |
187 | |
188 | - tmp = gb_addr_config & NUM_PIPES_MASK; |
189 | - tmp = r6xx_remap_render_backend(rdev, tmp, rdev->config.evergreen.max_backends, |
190 | - EVERGREEN_MAX_BACKENDS, disabled_rb_mask); |
191 | + if ((rdev->config.evergreen.max_backends == 1) && |
192 | + (rdev->flags & RADEON_IS_IGP)) { |
193 | + if ((disabled_rb_mask & 3) == 1) { |
194 | + /* RB0 disabled, RB1 enabled */ |
195 | + tmp = 0x11111111; |
196 | + } else { |
197 | + /* RB1 disabled, RB0 enabled */ |
198 | + tmp = 0x00000000; |
199 | + } |
200 | + } else { |
201 | + tmp = gb_addr_config & NUM_PIPES_MASK; |
202 | + tmp = r6xx_remap_render_backend(rdev, tmp, rdev->config.evergreen.max_backends, |
203 | + EVERGREEN_MAX_BACKENDS, disabled_rb_mask); |
204 | + } |
205 | WREG32(GB_BACKEND_MAP, tmp); |
206 | |
207 | WREG32(CGTS_SYS_TCC_DISABLE, 0); |
208 | diff --git a/drivers/gpu/drm/radeon/r600.c b/drivers/gpu/drm/radeon/r600.c |
209 | index cda280d..271a6db 100644 |
210 | --- a/drivers/gpu/drm/radeon/r600.c |
211 | +++ b/drivers/gpu/drm/radeon/r600.c |
212 | @@ -1382,12 +1382,15 @@ u32 r6xx_remap_render_backend(struct radeon_device *rdev, |
213 | u32 disabled_rb_mask) |
214 | { |
215 | u32 rendering_pipe_num, rb_num_width, req_rb_num; |
216 | - u32 pipe_rb_ratio, pipe_rb_remain; |
217 | + u32 pipe_rb_ratio, pipe_rb_remain, tmp; |
218 | u32 data = 0, mask = 1 << (max_rb_num - 1); |
219 | unsigned i, j; |
220 | |
221 | /* mask out the RBs that don't exist on that asic */ |
222 | - disabled_rb_mask |= (0xff << max_rb_num) & 0xff; |
223 | + tmp = disabled_rb_mask | ((0xff << max_rb_num) & 0xff); |
224 | + /* make sure at least one RB is available */ |
225 | + if ((tmp & 0xff) != 0xff) |
226 | + disabled_rb_mask = tmp; |
227 | |
228 | rendering_pipe_num = 1 << tiling_pipe_num; |
229 | req_rb_num = total_max_rb_num - r600_count_pipe_bits(disabled_rb_mask); |
230 | diff --git a/drivers/gpu/drm/radeon/radeon_combios.c b/drivers/gpu/drm/radeon/radeon_combios.c |
231 | index ced9a81..4981a20 100644 |
232 | --- a/drivers/gpu/drm/radeon/radeon_combios.c |
233 | +++ b/drivers/gpu/drm/radeon/radeon_combios.c |
234 | @@ -2470,6 +2470,14 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) |
235 | 1), |
236 | ATOM_DEVICE_CRT1_SUPPORT); |
237 | } |
238 | + /* RV100 board with external TDMS bit mis-set. |
239 | + * Actually uses internal TMDS, clear the bit. |
240 | + */ |
241 | + if (dev->pdev->device == 0x5159 && |
242 | + dev->pdev->subsystem_vendor == 0x1014 && |
243 | + dev->pdev->subsystem_device == 0x029A) { |
244 | + tmp &= ~(1 << 4); |
245 | + } |
246 | if ((tmp >> 4) & 0x1) { |
247 | devices |= ATOM_DEVICE_DFP2_SUPPORT; |
248 | radeon_add_legacy_encoder(dev, |
249 | diff --git a/drivers/gpu/drm/radeon/radeon_display.c b/drivers/gpu/drm/radeon/radeon_display.c |
250 | index 6477849..ec202c8 100644 |
251 | --- a/drivers/gpu/drm/radeon/radeon_display.c |
252 | +++ b/drivers/gpu/drm/radeon/radeon_display.c |
253 | @@ -1111,8 +1111,10 @@ radeon_user_framebuffer_create(struct drm_device *dev, |
254 | } |
255 | |
256 | radeon_fb = kzalloc(sizeof(*radeon_fb), GFP_KERNEL); |
257 | - if (radeon_fb == NULL) |
258 | + if (radeon_fb == NULL) { |
259 | + drm_gem_object_unreference_unlocked(obj); |
260 | return ERR_PTR(-ENOMEM); |
261 | + } |
262 | |
263 | ret = radeon_framebuffer_init(dev, radeon_fb, mode_cmd, obj); |
264 | if (ret) { |
265 | diff --git a/drivers/gpu/drm/radeon/radeon_ring.c b/drivers/gpu/drm/radeon/radeon_ring.c |
266 | index 47634f2..246b374 100644 |
267 | --- a/drivers/gpu/drm/radeon/radeon_ring.c |
268 | +++ b/drivers/gpu/drm/radeon/radeon_ring.c |
269 | @@ -377,6 +377,9 @@ int radeon_ring_alloc(struct radeon_device *rdev, struct radeon_ring *ring, unsi |
270 | { |
271 | int r; |
272 | |
273 | + /* make sure we aren't trying to allocate more space than there is on the ring */ |
274 | + if (ndw > (ring->ring_size / 4)) |
275 | + return -ENOMEM; |
276 | /* Align requested size with padding so unlock_commit can |
277 | * pad safely */ |
278 | ndw = (ndw + ring->align_mask) & ~ring->align_mask; |
279 | diff --git a/drivers/gpu/drm/radeon/reg_srcs/cayman b/drivers/gpu/drm/radeon/reg_srcs/cayman |
280 | index 0f656b1..a072fa8 100644 |
281 | --- a/drivers/gpu/drm/radeon/reg_srcs/cayman |
282 | +++ b/drivers/gpu/drm/radeon/reg_srcs/cayman |
283 | @@ -1,5 +1,6 @@ |
284 | cayman 0x9400 |
285 | 0x0000802C GRBM_GFX_INDEX |
286 | +0x00008040 WAIT_UNTIL |
287 | 0x000084FC CP_STRMOUT_CNTL |
288 | 0x000085F0 CP_COHER_CNTL |
289 | 0x000085F4 CP_COHER_SIZE |
290 | diff --git a/drivers/mtd/nand/davinci_nand.c b/drivers/mtd/nand/davinci_nand.c |
291 | index 945047a..92cacba 100644 |
292 | --- a/drivers/mtd/nand/davinci_nand.c |
293 | +++ b/drivers/mtd/nand/davinci_nand.c |
294 | @@ -523,7 +523,7 @@ static struct nand_ecclayout hwecc4_2048 __initconst = { |
295 | static const struct of_device_id davinci_nand_of_match[] = { |
296 | {.compatible = "ti,davinci-nand", }, |
297 | {}, |
298 | -} |
299 | +}; |
300 | MODULE_DEVICE_TABLE(of, davinci_nand_of_match); |
301 | |
302 | static struct davinci_nand_pdata |
303 | diff --git a/drivers/rtc/rtc-isl1208.c b/drivers/rtc/rtc-isl1208.c |
304 | index 26c81f2..8b68e72 100644 |
305 | --- a/drivers/rtc/rtc-isl1208.c |
306 | +++ b/drivers/rtc/rtc-isl1208.c |
307 | @@ -506,6 +506,7 @@ isl1208_rtc_interrupt(int irq, void *data) |
308 | { |
309 | unsigned long timeout = jiffies + msecs_to_jiffies(1000); |
310 | struct i2c_client *client = data; |
311 | + struct rtc_device *rtc = i2c_get_clientdata(client); |
312 | int handled = 0, sr, err; |
313 | |
314 | /* |
315 | @@ -528,6 +529,8 @@ isl1208_rtc_interrupt(int irq, void *data) |
316 | if (sr & ISL1208_REG_SR_ALM) { |
317 | dev_dbg(&client->dev, "alarm!\n"); |
318 | |
319 | + rtc_update_irq(rtc, 1, RTC_IRQF | RTC_AF); |
320 | + |
321 | /* Clear the alarm */ |
322 | sr &= ~ISL1208_REG_SR_ALM; |
323 | sr = i2c_smbus_write_byte_data(client, ISL1208_REG_SR, sr); |
324 | diff --git a/drivers/rtc/rtc-pl031.c b/drivers/rtc/rtc-pl031.c |
325 | index 08378e3..10c1a34 100644 |
326 | --- a/drivers/rtc/rtc-pl031.c |
327 | +++ b/drivers/rtc/rtc-pl031.c |
328 | @@ -44,6 +44,7 @@ |
329 | #define RTC_YMR 0x34 /* Year match register */ |
330 | #define RTC_YLR 0x38 /* Year data load register */ |
331 | |
332 | +#define RTC_CR_EN (1 << 0) /* counter enable bit */ |
333 | #define RTC_CR_CWEN (1 << 26) /* Clockwatch enable bit */ |
334 | |
335 | #define RTC_TCR_EN (1 << 1) /* Periodic timer enable bit */ |
336 | @@ -320,7 +321,7 @@ static int pl031_probe(struct amba_device *adev, const struct amba_id *id) |
337 | struct pl031_local *ldata; |
338 | struct pl031_vendor_data *vendor = id->data; |
339 | struct rtc_class_ops *ops = &vendor->ops; |
340 | - unsigned long time; |
341 | + unsigned long time, data; |
342 | |
343 | ret = amba_request_regions(adev, NULL); |
344 | if (ret) |
345 | @@ -345,10 +346,11 @@ static int pl031_probe(struct amba_device *adev, const struct amba_id *id) |
346 | dev_dbg(&adev->dev, "designer ID = 0x%02x\n", amba_manf(adev)); |
347 | dev_dbg(&adev->dev, "revision = 0x%01x\n", amba_rev(adev)); |
348 | |
349 | + data = readl(ldata->base + RTC_CR); |
350 | /* Enable the clockwatch on ST Variants */ |
351 | if (vendor->clockwatch) |
352 | - writel(readl(ldata->base + RTC_CR) | RTC_CR_CWEN, |
353 | - ldata->base + RTC_CR); |
354 | + data |= RTC_CR_CWEN; |
355 | + writel(data | RTC_CR_EN, ldata->base + RTC_CR); |
356 | |
357 | /* |
358 | * On ST PL031 variants, the RTC reset value does not provide correct |
359 | diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c |
360 | index e6cc4e6..131067d 100644 |
361 | --- a/drivers/usb/core/hub.c |
362 | +++ b/drivers/usb/core/hub.c |
363 | @@ -2799,6 +2799,23 @@ void usb_enable_ltm(struct usb_device *udev) |
364 | EXPORT_SYMBOL_GPL(usb_enable_ltm); |
365 | |
366 | #ifdef CONFIG_USB_SUSPEND |
367 | +/* |
368 | + * usb_disable_function_remotewakeup - disable usb3.0 |
369 | + * device's function remote wakeup |
370 | + * @udev: target device |
371 | + * |
372 | + * Assume there's only one function on the USB 3.0 |
373 | + * device and disable remote wake for the first |
374 | + * interface. FIXME if the interface association |
375 | + * descriptor shows there's more than one function. |
376 | + */ |
377 | +static int usb_disable_function_remotewakeup(struct usb_device *udev) |
378 | +{ |
379 | + return usb_control_msg(udev, usb_sndctrlpipe(udev, 0), |
380 | + USB_REQ_CLEAR_FEATURE, USB_RECIP_INTERFACE, |
381 | + USB_INTRF_FUNC_SUSPEND, 0, NULL, 0, |
382 | + USB_CTRL_SET_TIMEOUT); |
383 | +} |
384 | |
385 | /* |
386 | * usb_port_suspend - suspend a usb device's upstream port |
387 | @@ -2916,12 +2933,19 @@ int usb_port_suspend(struct usb_device *udev, pm_message_t msg) |
388 | dev_dbg(hub->intfdev, "can't suspend port %d, status %d\n", |
389 | port1, status); |
390 | /* paranoia: "should not happen" */ |
391 | - if (udev->do_remote_wakeup) |
392 | - (void) usb_control_msg(udev, usb_sndctrlpipe(udev, 0), |
393 | - USB_REQ_CLEAR_FEATURE, USB_RECIP_DEVICE, |
394 | - USB_DEVICE_REMOTE_WAKEUP, 0, |
395 | - NULL, 0, |
396 | - USB_CTRL_SET_TIMEOUT); |
397 | + if (udev->do_remote_wakeup) { |
398 | + if (!hub_is_superspeed(hub->hdev)) { |
399 | + (void) usb_control_msg(udev, |
400 | + usb_sndctrlpipe(udev, 0), |
401 | + USB_REQ_CLEAR_FEATURE, |
402 | + USB_RECIP_DEVICE, |
403 | + USB_DEVICE_REMOTE_WAKEUP, 0, |
404 | + NULL, 0, |
405 | + USB_CTRL_SET_TIMEOUT); |
406 | + } else |
407 | + (void) usb_disable_function_remotewakeup(udev); |
408 | + |
409 | + } |
410 | |
411 | /* Try to enable USB2 hardware LPM again */ |
412 | if (udev->usb2_hw_lpm_capable == 1) |
413 | @@ -3012,20 +3036,30 @@ static int finish_port_resume(struct usb_device *udev) |
414 | * udev->reset_resume |
415 | */ |
416 | } else if (udev->actconfig && !udev->reset_resume) { |
417 | - le16_to_cpus(&devstatus); |
418 | - if (devstatus & (1 << USB_DEVICE_REMOTE_WAKEUP)) { |
419 | - status = usb_control_msg(udev, |
420 | - usb_sndctrlpipe(udev, 0), |
421 | - USB_REQ_CLEAR_FEATURE, |
422 | + if (!hub_is_superspeed(udev->parent)) { |
423 | + le16_to_cpus(&devstatus); |
424 | + if (devstatus & (1 << USB_DEVICE_REMOTE_WAKEUP)) |
425 | + status = usb_control_msg(udev, |
426 | + usb_sndctrlpipe(udev, 0), |
427 | + USB_REQ_CLEAR_FEATURE, |
428 | USB_RECIP_DEVICE, |
429 | - USB_DEVICE_REMOTE_WAKEUP, 0, |
430 | - NULL, 0, |
431 | - USB_CTRL_SET_TIMEOUT); |
432 | - if (status) |
433 | - dev_dbg(&udev->dev, |
434 | - "disable remote wakeup, status %d\n", |
435 | - status); |
436 | + USB_DEVICE_REMOTE_WAKEUP, 0, |
437 | + NULL, 0, |
438 | + USB_CTRL_SET_TIMEOUT); |
439 | + } else { |
440 | + status = usb_get_status(udev, USB_RECIP_INTERFACE, 0, |
441 | + &devstatus); |
442 | + le16_to_cpus(&devstatus); |
443 | + if (!status && devstatus & (USB_INTRF_STAT_FUNC_RW_CAP |
444 | + | USB_INTRF_STAT_FUNC_RW)) |
445 | + status = |
446 | + usb_disable_function_remotewakeup(udev); |
447 | } |
448 | + |
449 | + if (status) |
450 | + dev_dbg(&udev->dev, |
451 | + "disable remote wakeup, status %d\n", |
452 | + status); |
453 | status = 0; |
454 | } |
455 | return status; |
456 | diff --git a/drivers/usb/host/ehci-hub.c b/drivers/usb/host/ehci-hub.c |
457 | index 914ce93..b9f7f11 100644 |
458 | --- a/drivers/usb/host/ehci-hub.c |
459 | +++ b/drivers/usb/host/ehci-hub.c |
460 | @@ -623,7 +623,11 @@ ehci_hub_status_data (struct usb_hcd *hcd, char *buf) |
461 | status = STS_PCD; |
462 | } |
463 | } |
464 | - /* FIXME autosuspend idle root hubs */ |
465 | + |
466 | + /* If a resume is in progress, make sure it can finish */ |
467 | + if (ehci->resuming_ports) |
468 | + mod_timer(&hcd->rh_timer, jiffies + msecs_to_jiffies(25)); |
469 | + |
470 | spin_unlock_irqrestore (&ehci->lock, flags); |
471 | return status ? retval : 0; |
472 | } |
473 | diff --git a/drivers/usb/host/ehci-q.c b/drivers/usb/host/ehci-q.c |
474 | index 3d98902..fd252f0 100644 |
475 | --- a/drivers/usb/host/ehci-q.c |
476 | +++ b/drivers/usb/host/ehci-q.c |
477 | @@ -1197,17 +1197,26 @@ static void start_iaa_cycle(struct ehci_hcd *ehci, bool nested) |
478 | if (ehci->async_iaa || ehci->async_unlinking) |
479 | return; |
480 | |
481 | - /* Do all the waiting QHs at once */ |
482 | - ehci->async_iaa = ehci->async_unlink; |
483 | - ehci->async_unlink = NULL; |
484 | - |
485 | /* If the controller isn't running, we don't have to wait for it */ |
486 | if (unlikely(ehci->rh_state < EHCI_RH_RUNNING)) { |
487 | + |
488 | + /* Do all the waiting QHs */ |
489 | + ehci->async_iaa = ehci->async_unlink; |
490 | + ehci->async_unlink = NULL; |
491 | + |
492 | if (!nested) /* Avoid recursion */ |
493 | end_unlink_async(ehci); |
494 | |
495 | /* Otherwise start a new IAA cycle */ |
496 | } else if (likely(ehci->rh_state == EHCI_RH_RUNNING)) { |
497 | + struct ehci_qh *qh; |
498 | + |
499 | + /* Do only the first waiting QH (nVidia bug?) */ |
500 | + qh = ehci->async_unlink; |
501 | + ehci->async_iaa = qh; |
502 | + ehci->async_unlink = qh->unlink_next; |
503 | + qh->unlink_next = NULL; |
504 | + |
505 | /* Make sure the unlinks are all visible to the hardware */ |
506 | wmb(); |
507 | |
508 | @@ -1255,34 +1264,35 @@ static void end_unlink_async(struct ehci_hcd *ehci) |
509 | } |
510 | } |
511 | |
512 | +static void start_unlink_async(struct ehci_hcd *ehci, struct ehci_qh *qh); |
513 | + |
514 | static void unlink_empty_async(struct ehci_hcd *ehci) |
515 | { |
516 | - struct ehci_qh *qh, *next; |
517 | - bool stopped = (ehci->rh_state < EHCI_RH_RUNNING); |
518 | + struct ehci_qh *qh; |
519 | + struct ehci_qh *qh_to_unlink = NULL; |
520 | bool check_unlinks_later = false; |
521 | + int count = 0; |
522 | |
523 | - /* Unlink all the async QHs that have been empty for a timer cycle */ |
524 | - next = ehci->async->qh_next.qh; |
525 | - while (next) { |
526 | - qh = next; |
527 | - next = qh->qh_next.qh; |
528 | - |
529 | + /* Find the last async QH which has been empty for a timer cycle */ |
530 | + for (qh = ehci->async->qh_next.qh; qh; qh = qh->qh_next.qh) { |
531 | if (list_empty(&qh->qtd_list) && |
532 | qh->qh_state == QH_STATE_LINKED) { |
533 | - if (!stopped && qh->unlink_cycle == |
534 | - ehci->async_unlink_cycle) |
535 | + ++count; |
536 | + if (qh->unlink_cycle == ehci->async_unlink_cycle) |
537 | check_unlinks_later = true; |
538 | else |
539 | - single_unlink_async(ehci, qh); |
540 | + qh_to_unlink = qh; |
541 | } |
542 | } |
543 | |
544 | - /* Start a new IAA cycle if any QHs are waiting for it */ |
545 | - if (ehci->async_unlink) |
546 | - start_iaa_cycle(ehci, false); |
547 | + /* If nothing else is being unlinked, unlink the last empty QH */ |
548 | + if (!ehci->async_iaa && !ehci->async_unlink && qh_to_unlink) { |
549 | + start_unlink_async(ehci, qh_to_unlink); |
550 | + --count; |
551 | + } |
552 | |
553 | - /* QHs that haven't been empty for long enough will be handled later */ |
554 | - if (check_unlinks_later) { |
555 | + /* Other QHs will be handled later */ |
556 | + if (count > 0) { |
557 | ehci_enable_event(ehci, EHCI_HRTIMER_ASYNC_UNLINKS, true); |
558 | ++ehci->async_unlink_cycle; |
559 | } |
560 | diff --git a/drivers/usb/host/ehci-sched.c b/drivers/usb/host/ehci-sched.c |
561 | index 528a540..c41063d 100644 |
562 | --- a/drivers/usb/host/ehci-sched.c |
563 | +++ b/drivers/usb/host/ehci-sched.c |
564 | @@ -236,7 +236,7 @@ static inline unsigned char tt_start_uframe(struct ehci_hcd *ehci, __hc32 mask) |
565 | } |
566 | |
567 | static const unsigned char |
568 | -max_tt_usecs[] = { 125, 125, 125, 125, 125, 125, 30, 0 }; |
569 | +max_tt_usecs[] = { 125, 125, 125, 125, 125, 125, 125, 25 }; |
570 | |
571 | /* carryover low/fullspeed bandwidth that crosses uframe boundries */ |
572 | static inline void carryover_tt_bandwidth(unsigned short tt_usecs[8]) |
573 | @@ -2336,5 +2336,5 @@ restart: |
574 | break; |
575 | frame = (frame + 1) & fmask; |
576 | } |
577 | - ehci->next_frame = now_frame; |
578 | + ehci->next_frame = (frame - 1) & fmask; |
579 | } |
580 | diff --git a/drivers/usb/host/ehci-timer.c b/drivers/usb/host/ehci-timer.c |
581 | index 20dbdcb..f904071 100644 |
582 | --- a/drivers/usb/host/ehci-timer.c |
583 | +++ b/drivers/usb/host/ehci-timer.c |
584 | @@ -113,14 +113,15 @@ static void ehci_poll_ASS(struct ehci_hcd *ehci) |
585 | |
586 | if (want != actual) { |
587 | |
588 | - /* Poll again later, but give up after about 20 ms */ |
589 | - if (ehci->ASS_poll_count++ < 20) { |
590 | - ehci_enable_event(ehci, EHCI_HRTIMER_POLL_ASS, true); |
591 | - return; |
592 | - } |
593 | - ehci_dbg(ehci, "Waited too long for the async schedule status (%x/%x), giving up\n", |
594 | - want, actual); |
595 | + /* Poll again later */ |
596 | + ehci_enable_event(ehci, EHCI_HRTIMER_POLL_ASS, true); |
597 | + ++ehci->ASS_poll_count; |
598 | + return; |
599 | } |
600 | + |
601 | + if (ehci->ASS_poll_count > 20) |
602 | + ehci_dbg(ehci, "ASS poll count reached %d\n", |
603 | + ehci->ASS_poll_count); |
604 | ehci->ASS_poll_count = 0; |
605 | |
606 | /* The status is up-to-date; restart or stop the schedule as needed */ |
607 | @@ -159,14 +160,14 @@ static void ehci_poll_PSS(struct ehci_hcd *ehci) |
608 | |
609 | if (want != actual) { |
610 | |
611 | - /* Poll again later, but give up after about 20 ms */ |
612 | - if (ehci->PSS_poll_count++ < 20) { |
613 | - ehci_enable_event(ehci, EHCI_HRTIMER_POLL_PSS, true); |
614 | - return; |
615 | - } |
616 | - ehci_dbg(ehci, "Waited too long for the periodic schedule status (%x/%x), giving up\n", |
617 | - want, actual); |
618 | + /* Poll again later */ |
619 | + ehci_enable_event(ehci, EHCI_HRTIMER_POLL_PSS, true); |
620 | + return; |
621 | } |
622 | + |
623 | + if (ehci->PSS_poll_count > 20) |
624 | + ehci_dbg(ehci, "PSS poll count reached %d\n", |
625 | + ehci->PSS_poll_count); |
626 | ehci->PSS_poll_count = 0; |
627 | |
628 | /* The status is up-to-date; restart or stop the schedule as needed */ |
629 | diff --git a/drivers/usb/host/pci-quirks.c b/drivers/usb/host/pci-quirks.c |
630 | index eb5563a..7893351 100644 |
631 | --- a/drivers/usb/host/pci-quirks.c |
632 | +++ b/drivers/usb/host/pci-quirks.c |
633 | @@ -780,6 +780,7 @@ void usb_enable_xhci_ports(struct pci_dev *xhci_pdev) |
634 | "defaulting to EHCI.\n"); |
635 | dev_warn(&xhci_pdev->dev, |
636 | "USB 3.0 devices will work at USB 2.0 speeds.\n"); |
637 | + usb_disable_xhci_ports(xhci_pdev); |
638 | return; |
639 | } |
640 | |
641 | diff --git a/drivers/usb/host/xhci-ring.c b/drivers/usb/host/xhci-ring.c |
642 | index e80c49d..68cb9a8 100644 |
643 | --- a/drivers/usb/host/xhci-ring.c |
644 | +++ b/drivers/usb/host/xhci-ring.c |
645 | @@ -1698,7 +1698,7 @@ static void handle_port_status(struct xhci_hcd *xhci, |
646 | faked_port_index + 1); |
647 | if (slot_id && xhci->devs[slot_id]) |
648 | xhci_ring_device(xhci, slot_id); |
649 | - if (bus_state->port_remote_wakeup && (1 << faked_port_index)) { |
650 | + if (bus_state->port_remote_wakeup & (1 << faked_port_index)) { |
651 | bus_state->port_remote_wakeup &= |
652 | ~(1 << faked_port_index); |
653 | xhci_test_and_clear_bit(xhci, port_array, |
654 | @@ -2589,6 +2589,8 @@ cleanup: |
655 | (trb_comp_code != COMP_STALL && |
656 | trb_comp_code != COMP_BABBLE)) |
657 | xhci_urb_free_priv(xhci, urb_priv); |
658 | + else |
659 | + kfree(urb_priv); |
660 | |
661 | usb_hcd_unlink_urb_from_ep(bus_to_hcd(urb->dev->bus), urb); |
662 | if ((urb->actual_length != urb->transfer_buffer_length && |
663 | @@ -3108,7 +3110,7 @@ static u32 xhci_v1_0_td_remainder(int running_total, int trb_buff_len, |
664 | * running_total. |
665 | */ |
666 | packets_transferred = (running_total + trb_buff_len) / |
667 | - usb_endpoint_maxp(&urb->ep->desc); |
668 | + GET_MAX_PACKET(usb_endpoint_maxp(&urb->ep->desc)); |
669 | |
670 | if ((total_packet_count - packets_transferred) > 31) |
671 | return 31 << 17; |
672 | @@ -3642,7 +3644,8 @@ static int xhci_queue_isoc_tx(struct xhci_hcd *xhci, gfp_t mem_flags, |
673 | td_len = urb->iso_frame_desc[i].length; |
674 | td_remain_len = td_len; |
675 | total_packet_count = DIV_ROUND_UP(td_len, |
676 | - usb_endpoint_maxp(&urb->ep->desc)); |
677 | + GET_MAX_PACKET( |
678 | + usb_endpoint_maxp(&urb->ep->desc))); |
679 | /* A zero-length transfer still involves at least one packet. */ |
680 | if (total_packet_count == 0) |
681 | total_packet_count++; |
682 | @@ -3664,9 +3667,11 @@ static int xhci_queue_isoc_tx(struct xhci_hcd *xhci, gfp_t mem_flags, |
683 | td = urb_priv->td[i]; |
684 | for (j = 0; j < trbs_per_td; j++) { |
685 | u32 remainder = 0; |
686 | - field = TRB_TBC(burst_count) | TRB_TLBPC(residue); |
687 | + field = 0; |
688 | |
689 | if (first_trb) { |
690 | + field = TRB_TBC(burst_count) | |
691 | + TRB_TLBPC(residue); |
692 | /* Queue the isoc TRB */ |
693 | field |= TRB_TYPE(TRB_ISOC); |
694 | /* Assume URB_ISO_ASAP is set */ |
695 | diff --git a/drivers/usb/serial/ftdi_sio.c b/drivers/usb/serial/ftdi_sio.c |
696 | index 71e80ab..b786b7d 100644 |
697 | --- a/drivers/usb/serial/ftdi_sio.c |
698 | +++ b/drivers/usb/serial/ftdi_sio.c |
699 | @@ -585,6 +585,7 @@ static struct usb_device_id id_table_combined [] = { |
700 | /* |
701 | * ELV devices: |
702 | */ |
703 | + { USB_DEVICE(FTDI_ELV_VID, FTDI_ELV_WS300_PID) }, |
704 | { USB_DEVICE(FTDI_VID, FTDI_ELV_USR_PID) }, |
705 | { USB_DEVICE(FTDI_VID, FTDI_ELV_MSM1_PID) }, |
706 | { USB_DEVICE(FTDI_VID, FTDI_ELV_KL100_PID) }, |
707 | @@ -671,6 +672,7 @@ static struct usb_device_id id_table_combined [] = { |
708 | { USB_DEVICE(FTDI_VID, XSENS_CONVERTER_5_PID) }, |
709 | { USB_DEVICE(FTDI_VID, XSENS_CONVERTER_6_PID) }, |
710 | { USB_DEVICE(FTDI_VID, XSENS_CONVERTER_7_PID) }, |
711 | + { USB_DEVICE(FTDI_VID, FTDI_OMNI1509) }, |
712 | { USB_DEVICE(MOBILITY_VID, MOBILITY_USB_SERIAL_PID) }, |
713 | { USB_DEVICE(FTDI_VID, FTDI_ACTIVE_ROBOTS_PID) }, |
714 | { USB_DEVICE(FTDI_VID, FTDI_MHAM_KW_PID) }, |
715 | diff --git a/drivers/usb/serial/ftdi_sio_ids.h b/drivers/usb/serial/ftdi_sio_ids.h |
716 | index fa5d560..9d359e1 100644 |
717 | --- a/drivers/usb/serial/ftdi_sio_ids.h |
718 | +++ b/drivers/usb/serial/ftdi_sio_ids.h |
719 | @@ -147,6 +147,11 @@ |
720 | #define XSENS_CONVERTER_6_PID 0xD38E |
721 | #define XSENS_CONVERTER_7_PID 0xD38F |
722 | |
723 | +/** |
724 | + * Zolix (www.zolix.com.cb) product ids |
725 | + */ |
726 | +#define FTDI_OMNI1509 0xD491 /* Omni1509 embedded USB-serial */ |
727 | + |
728 | /* |
729 | * NDI (www.ndigital.com) product ids |
730 | */ |
731 | @@ -204,7 +209,7 @@ |
732 | |
733 | /* |
734 | * ELV USB devices submitted by Christian Abt of ELV (www.elv.de). |
735 | - * All of these devices use FTDI's vendor ID (0x0403). |
736 | + * Almost all of these devices use FTDI's vendor ID (0x0403). |
737 | * Further IDs taken from ELV Windows .inf file. |
738 | * |
739 | * The previously included PID for the UO 100 module was incorrect. |
740 | @@ -212,6 +217,8 @@ |
741 | * |
742 | * Armin Laeuger originally sent the PID for the UM 100 module. |
743 | */ |
744 | +#define FTDI_ELV_VID 0x1B1F /* ELV AG */ |
745 | +#define FTDI_ELV_WS300_PID 0xC006 /* eQ3 WS 300 PC II */ |
746 | #define FTDI_ELV_USR_PID 0xE000 /* ELV Universal-Sound-Recorder */ |
747 | #define FTDI_ELV_MSM1_PID 0xE001 /* ELV Mini-Sound-Modul */ |
748 | #define FTDI_ELV_KL100_PID 0xE002 /* ELV Kfz-Leistungsmesser KL 100 */ |
749 | diff --git a/drivers/usb/serial/option.c b/drivers/usb/serial/option.c |
750 | index f2727e4..b32b4f3 100644 |
751 | --- a/drivers/usb/serial/option.c |
752 | +++ b/drivers/usb/serial/option.c |
753 | @@ -243,6 +243,7 @@ static void option_instat_callback(struct urb *urb); |
754 | #define TELIT_PRODUCT_CC864_DUAL 0x1005 |
755 | #define TELIT_PRODUCT_CC864_SINGLE 0x1006 |
756 | #define TELIT_PRODUCT_DE910_DUAL 0x1010 |
757 | +#define TELIT_PRODUCT_LE920 0x1200 |
758 | |
759 | /* ZTE PRODUCTS */ |
760 | #define ZTE_VENDOR_ID 0x19d2 |
761 | @@ -454,6 +455,10 @@ static void option_instat_callback(struct urb *urb); |
762 | #define TPLINK_VENDOR_ID 0x2357 |
763 | #define TPLINK_PRODUCT_MA180 0x0201 |
764 | |
765 | +/* Changhong products */ |
766 | +#define CHANGHONG_VENDOR_ID 0x2077 |
767 | +#define CHANGHONG_PRODUCT_CH690 0x7001 |
768 | + |
769 | /* some devices interfaces need special handling due to a number of reasons */ |
770 | enum option_blacklist_reason { |
771 | OPTION_BLACKLIST_NONE = 0, |
772 | @@ -535,6 +540,11 @@ static const struct option_blacklist_info zte_1255_blacklist = { |
773 | .reserved = BIT(3) | BIT(4), |
774 | }; |
775 | |
776 | +static const struct option_blacklist_info telit_le920_blacklist = { |
777 | + .sendsetup = BIT(0), |
778 | + .reserved = BIT(1) | BIT(5), |
779 | +}; |
780 | + |
781 | static const struct usb_device_id option_ids[] = { |
782 | { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_COLT) }, |
783 | { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_RICOLA) }, |
784 | @@ -785,6 +795,8 @@ static const struct usb_device_id option_ids[] = { |
785 | { USB_DEVICE(TELIT_VENDOR_ID, TELIT_PRODUCT_CC864_DUAL) }, |
786 | { USB_DEVICE(TELIT_VENDOR_ID, TELIT_PRODUCT_CC864_SINGLE) }, |
787 | { USB_DEVICE(TELIT_VENDOR_ID, TELIT_PRODUCT_DE910_DUAL) }, |
788 | + { USB_DEVICE(TELIT_VENDOR_ID, TELIT_PRODUCT_LE920), |
789 | + .driver_info = (kernel_ulong_t)&telit_le920_blacklist }, |
790 | { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, ZTE_PRODUCT_MF622, 0xff, 0xff, 0xff) }, /* ZTE WCDMA products */ |
791 | { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0002, 0xff, 0xff, 0xff), |
792 | .driver_info = (kernel_ulong_t)&net_intf1_blacklist }, |
793 | @@ -1319,6 +1331,7 @@ static const struct usb_device_id option_ids[] = { |
794 | { USB_DEVICE(PETATEL_VENDOR_ID, PETATEL_PRODUCT_NP10T) }, |
795 | { USB_DEVICE(TPLINK_VENDOR_ID, TPLINK_PRODUCT_MA180), |
796 | .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, |
797 | + { USB_DEVICE(CHANGHONG_VENDOR_ID, CHANGHONG_PRODUCT_CH690) }, |
798 | { } /* Terminating entry */ |
799 | }; |
800 | MODULE_DEVICE_TABLE(usb, option_ids); |
801 | diff --git a/drivers/usb/serial/qcserial.c b/drivers/usb/serial/qcserial.c |
802 | index aa148c2..2466254 100644 |
803 | --- a/drivers/usb/serial/qcserial.c |
804 | +++ b/drivers/usb/serial/qcserial.c |
805 | @@ -53,6 +53,7 @@ static const struct usb_device_id id_table[] = { |
806 | {DEVICE_G1K(0x05c6, 0x9221)}, /* Generic Gobi QDL device */ |
807 | {DEVICE_G1K(0x05c6, 0x9231)}, /* Generic Gobi QDL device */ |
808 | {DEVICE_G1K(0x1f45, 0x0001)}, /* Unknown Gobi QDL device */ |
809 | + {DEVICE_G1K(0x1bc7, 0x900e)}, /* Telit Gobi QDL device */ |
810 | |
811 | /* Gobi 2000 devices */ |
812 | {USB_DEVICE(0x1410, 0xa010)}, /* Novatel Gobi 2000 QDL device */ |
813 | diff --git a/drivers/usb/storage/initializers.c b/drivers/usb/storage/initializers.c |
814 | index 105d900..16b0bf0 100644 |
815 | --- a/drivers/usb/storage/initializers.c |
816 | +++ b/drivers/usb/storage/initializers.c |
817 | @@ -92,8 +92,8 @@ int usb_stor_ucr61s2b_init(struct us_data *us) |
818 | return 0; |
819 | } |
820 | |
821 | -/* This places the HUAWEI E220 devices in multi-port mode */ |
822 | -int usb_stor_huawei_e220_init(struct us_data *us) |
823 | +/* This places the HUAWEI usb dongles in multi-port mode */ |
824 | +static int usb_stor_huawei_feature_init(struct us_data *us) |
825 | { |
826 | int result; |
827 | |
828 | @@ -104,3 +104,75 @@ int usb_stor_huawei_e220_init(struct us_data *us) |
829 | US_DEBUGP("Huawei mode set result is %d\n", result); |
830 | return 0; |
831 | } |
832 | + |
833 | +/* |
834 | + * It will send a scsi switch command called rewind' to huawei dongle. |
835 | + * When the dongle receives this command at the first time, |
836 | + * it will reboot immediately. After rebooted, it will ignore this command. |
837 | + * So it is unnecessary to read its response. |
838 | + */ |
839 | +static int usb_stor_huawei_scsi_init(struct us_data *us) |
840 | +{ |
841 | + int result = 0; |
842 | + int act_len = 0; |
843 | + struct bulk_cb_wrap *bcbw = (struct bulk_cb_wrap *) us->iobuf; |
844 | + char rewind_cmd[] = {0x11, 0x06, 0x20, 0x00, 0x00, 0x01, 0x01, 0x00, |
845 | + 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}; |
846 | + |
847 | + bcbw->Signature = cpu_to_le32(US_BULK_CB_SIGN); |
848 | + bcbw->Tag = 0; |
849 | + bcbw->DataTransferLength = 0; |
850 | + bcbw->Flags = bcbw->Lun = 0; |
851 | + bcbw->Length = sizeof(rewind_cmd); |
852 | + memset(bcbw->CDB, 0, sizeof(bcbw->CDB)); |
853 | + memcpy(bcbw->CDB, rewind_cmd, sizeof(rewind_cmd)); |
854 | + |
855 | + result = usb_stor_bulk_transfer_buf(us, us->send_bulk_pipe, bcbw, |
856 | + US_BULK_CB_WRAP_LEN, &act_len); |
857 | + US_DEBUGP("transfer actual length=%d, result=%d\n", act_len, result); |
858 | + return result; |
859 | +} |
860 | + |
861 | +/* |
862 | + * It tries to find the supported Huawei USB dongles. |
863 | + * In Huawei, they assign the following product IDs |
864 | + * for all of their mobile broadband dongles, |
865 | + * including the new dongles in the future. |
866 | + * So if the product ID is not included in this list, |
867 | + * it means it is not Huawei's mobile broadband dongles. |
868 | + */ |
869 | +static int usb_stor_huawei_dongles_pid(struct us_data *us) |
870 | +{ |
871 | + struct usb_interface_descriptor *idesc; |
872 | + int idProduct; |
873 | + |
874 | + idesc = &us->pusb_intf->cur_altsetting->desc; |
875 | + idProduct = us->pusb_dev->descriptor.idProduct; |
876 | + /* The first port is CDROM, |
877 | + * means the dongle in the single port mode, |
878 | + * and a switch command is required to be sent. */ |
879 | + if (idesc && idesc->bInterfaceNumber == 0) { |
880 | + if ((idProduct == 0x1001) |
881 | + || (idProduct == 0x1003) |
882 | + || (idProduct == 0x1004) |
883 | + || (idProduct >= 0x1401 && idProduct <= 0x1500) |
884 | + || (idProduct >= 0x1505 && idProduct <= 0x1600) |
885 | + || (idProduct >= 0x1c02 && idProduct <= 0x2202)) { |
886 | + return 1; |
887 | + } |
888 | + } |
889 | + return 0; |
890 | +} |
891 | + |
892 | +int usb_stor_huawei_init(struct us_data *us) |
893 | +{ |
894 | + int result = 0; |
895 | + |
896 | + if (usb_stor_huawei_dongles_pid(us)) { |
897 | + if (us->pusb_dev->descriptor.idProduct >= 0x1446) |
898 | + result = usb_stor_huawei_scsi_init(us); |
899 | + else |
900 | + result = usb_stor_huawei_feature_init(us); |
901 | + } |
902 | + return result; |
903 | +} |
904 | diff --git a/drivers/usb/storage/initializers.h b/drivers/usb/storage/initializers.h |
905 | index 529327f..5376d4f 100644 |
906 | --- a/drivers/usb/storage/initializers.h |
907 | +++ b/drivers/usb/storage/initializers.h |
908 | @@ -46,5 +46,5 @@ int usb_stor_euscsi_init(struct us_data *us); |
909 | * flash reader */ |
910 | int usb_stor_ucr61s2b_init(struct us_data *us); |
911 | |
912 | -/* This places the HUAWEI E220 devices in multi-port mode */ |
913 | -int usb_stor_huawei_e220_init(struct us_data *us); |
914 | +/* This places the HUAWEI usb dongles in multi-port mode */ |
915 | +int usb_stor_huawei_init(struct us_data *us); |
916 | diff --git a/drivers/usb/storage/unusual_devs.h b/drivers/usb/storage/unusual_devs.h |
917 | index d305a5a..72923b5 100644 |
918 | --- a/drivers/usb/storage/unusual_devs.h |
919 | +++ b/drivers/usb/storage/unusual_devs.h |
920 | @@ -1527,335 +1527,10 @@ UNUSUAL_DEV( 0x1210, 0x0003, 0x0100, 0x0100, |
921 | /* Reported by fangxiaozhi <huananhu@huawei.com> |
922 | * This brings the HUAWEI data card devices into multi-port mode |
923 | */ |
924 | -UNUSUAL_DEV( 0x12d1, 0x1001, 0x0000, 0x0000, |
925 | +UNUSUAL_VENDOR_INTF(0x12d1, 0x08, 0x06, 0x50, |
926 | "HUAWEI MOBILE", |
927 | "Mass Storage", |
928 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
929 | - 0), |
930 | -UNUSUAL_DEV( 0x12d1, 0x1003, 0x0000, 0x0000, |
931 | - "HUAWEI MOBILE", |
932 | - "Mass Storage", |
933 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
934 | - 0), |
935 | -UNUSUAL_DEV( 0x12d1, 0x1004, 0x0000, 0x0000, |
936 | - "HUAWEI MOBILE", |
937 | - "Mass Storage", |
938 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
939 | - 0), |
940 | -UNUSUAL_DEV( 0x12d1, 0x1401, 0x0000, 0x0000, |
941 | - "HUAWEI MOBILE", |
942 | - "Mass Storage", |
943 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
944 | - 0), |
945 | -UNUSUAL_DEV( 0x12d1, 0x1402, 0x0000, 0x0000, |
946 | - "HUAWEI MOBILE", |
947 | - "Mass Storage", |
948 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
949 | - 0), |
950 | -UNUSUAL_DEV( 0x12d1, 0x1403, 0x0000, 0x0000, |
951 | - "HUAWEI MOBILE", |
952 | - "Mass Storage", |
953 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
954 | - 0), |
955 | -UNUSUAL_DEV( 0x12d1, 0x1404, 0x0000, 0x0000, |
956 | - "HUAWEI MOBILE", |
957 | - "Mass Storage", |
958 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
959 | - 0), |
960 | -UNUSUAL_DEV( 0x12d1, 0x1405, 0x0000, 0x0000, |
961 | - "HUAWEI MOBILE", |
962 | - "Mass Storage", |
963 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
964 | - 0), |
965 | -UNUSUAL_DEV( 0x12d1, 0x1406, 0x0000, 0x0000, |
966 | - "HUAWEI MOBILE", |
967 | - "Mass Storage", |
968 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
969 | - 0), |
970 | -UNUSUAL_DEV( 0x12d1, 0x1407, 0x0000, 0x0000, |
971 | - "HUAWEI MOBILE", |
972 | - "Mass Storage", |
973 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
974 | - 0), |
975 | -UNUSUAL_DEV( 0x12d1, 0x1408, 0x0000, 0x0000, |
976 | - "HUAWEI MOBILE", |
977 | - "Mass Storage", |
978 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
979 | - 0), |
980 | -UNUSUAL_DEV( 0x12d1, 0x1409, 0x0000, 0x0000, |
981 | - "HUAWEI MOBILE", |
982 | - "Mass Storage", |
983 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
984 | - 0), |
985 | -UNUSUAL_DEV( 0x12d1, 0x140A, 0x0000, 0x0000, |
986 | - "HUAWEI MOBILE", |
987 | - "Mass Storage", |
988 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
989 | - 0), |
990 | -UNUSUAL_DEV( 0x12d1, 0x140B, 0x0000, 0x0000, |
991 | - "HUAWEI MOBILE", |
992 | - "Mass Storage", |
993 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
994 | - 0), |
995 | -UNUSUAL_DEV( 0x12d1, 0x140C, 0x0000, 0x0000, |
996 | - "HUAWEI MOBILE", |
997 | - "Mass Storage", |
998 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
999 | - 0), |
1000 | -UNUSUAL_DEV( 0x12d1, 0x140D, 0x0000, 0x0000, |
1001 | - "HUAWEI MOBILE", |
1002 | - "Mass Storage", |
1003 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1004 | - 0), |
1005 | -UNUSUAL_DEV( 0x12d1, 0x140E, 0x0000, 0x0000, |
1006 | - "HUAWEI MOBILE", |
1007 | - "Mass Storage", |
1008 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1009 | - 0), |
1010 | -UNUSUAL_DEV( 0x12d1, 0x140F, 0x0000, 0x0000, |
1011 | - "HUAWEI MOBILE", |
1012 | - "Mass Storage", |
1013 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1014 | - 0), |
1015 | -UNUSUAL_DEV( 0x12d1, 0x1410, 0x0000, 0x0000, |
1016 | - "HUAWEI MOBILE", |
1017 | - "Mass Storage", |
1018 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1019 | - 0), |
1020 | -UNUSUAL_DEV( 0x12d1, 0x1411, 0x0000, 0x0000, |
1021 | - "HUAWEI MOBILE", |
1022 | - "Mass Storage", |
1023 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1024 | - 0), |
1025 | -UNUSUAL_DEV( 0x12d1, 0x1412, 0x0000, 0x0000, |
1026 | - "HUAWEI MOBILE", |
1027 | - "Mass Storage", |
1028 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1029 | - 0), |
1030 | -UNUSUAL_DEV( 0x12d1, 0x1413, 0x0000, 0x0000, |
1031 | - "HUAWEI MOBILE", |
1032 | - "Mass Storage", |
1033 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1034 | - 0), |
1035 | -UNUSUAL_DEV( 0x12d1, 0x1414, 0x0000, 0x0000, |
1036 | - "HUAWEI MOBILE", |
1037 | - "Mass Storage", |
1038 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1039 | - 0), |
1040 | -UNUSUAL_DEV( 0x12d1, 0x1415, 0x0000, 0x0000, |
1041 | - "HUAWEI MOBILE", |
1042 | - "Mass Storage", |
1043 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1044 | - 0), |
1045 | -UNUSUAL_DEV( 0x12d1, 0x1416, 0x0000, 0x0000, |
1046 | - "HUAWEI MOBILE", |
1047 | - "Mass Storage", |
1048 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1049 | - 0), |
1050 | -UNUSUAL_DEV( 0x12d1, 0x1417, 0x0000, 0x0000, |
1051 | - "HUAWEI MOBILE", |
1052 | - "Mass Storage", |
1053 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1054 | - 0), |
1055 | -UNUSUAL_DEV( 0x12d1, 0x1418, 0x0000, 0x0000, |
1056 | - "HUAWEI MOBILE", |
1057 | - "Mass Storage", |
1058 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1059 | - 0), |
1060 | -UNUSUAL_DEV( 0x12d1, 0x1419, 0x0000, 0x0000, |
1061 | - "HUAWEI MOBILE", |
1062 | - "Mass Storage", |
1063 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1064 | - 0), |
1065 | -UNUSUAL_DEV( 0x12d1, 0x141A, 0x0000, 0x0000, |
1066 | - "HUAWEI MOBILE", |
1067 | - "Mass Storage", |
1068 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1069 | - 0), |
1070 | -UNUSUAL_DEV( 0x12d1, 0x141B, 0x0000, 0x0000, |
1071 | - "HUAWEI MOBILE", |
1072 | - "Mass Storage", |
1073 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1074 | - 0), |
1075 | -UNUSUAL_DEV( 0x12d1, 0x141C, 0x0000, 0x0000, |
1076 | - "HUAWEI MOBILE", |
1077 | - "Mass Storage", |
1078 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1079 | - 0), |
1080 | -UNUSUAL_DEV( 0x12d1, 0x141D, 0x0000, 0x0000, |
1081 | - "HUAWEI MOBILE", |
1082 | - "Mass Storage", |
1083 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1084 | - 0), |
1085 | -UNUSUAL_DEV( 0x12d1, 0x141E, 0x0000, 0x0000, |
1086 | - "HUAWEI MOBILE", |
1087 | - "Mass Storage", |
1088 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1089 | - 0), |
1090 | -UNUSUAL_DEV( 0x12d1, 0x141F, 0x0000, 0x0000, |
1091 | - "HUAWEI MOBILE", |
1092 | - "Mass Storage", |
1093 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1094 | - 0), |
1095 | -UNUSUAL_DEV( 0x12d1, 0x1420, 0x0000, 0x0000, |
1096 | - "HUAWEI MOBILE", |
1097 | - "Mass Storage", |
1098 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1099 | - 0), |
1100 | -UNUSUAL_DEV( 0x12d1, 0x1421, 0x0000, 0x0000, |
1101 | - "HUAWEI MOBILE", |
1102 | - "Mass Storage", |
1103 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1104 | - 0), |
1105 | -UNUSUAL_DEV( 0x12d1, 0x1422, 0x0000, 0x0000, |
1106 | - "HUAWEI MOBILE", |
1107 | - "Mass Storage", |
1108 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1109 | - 0), |
1110 | -UNUSUAL_DEV( 0x12d1, 0x1423, 0x0000, 0x0000, |
1111 | - "HUAWEI MOBILE", |
1112 | - "Mass Storage", |
1113 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1114 | - 0), |
1115 | -UNUSUAL_DEV( 0x12d1, 0x1424, 0x0000, 0x0000, |
1116 | - "HUAWEI MOBILE", |
1117 | - "Mass Storage", |
1118 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1119 | - 0), |
1120 | -UNUSUAL_DEV( 0x12d1, 0x1425, 0x0000, 0x0000, |
1121 | - "HUAWEI MOBILE", |
1122 | - "Mass Storage", |
1123 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1124 | - 0), |
1125 | -UNUSUAL_DEV( 0x12d1, 0x1426, 0x0000, 0x0000, |
1126 | - "HUAWEI MOBILE", |
1127 | - "Mass Storage", |
1128 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1129 | - 0), |
1130 | -UNUSUAL_DEV( 0x12d1, 0x1427, 0x0000, 0x0000, |
1131 | - "HUAWEI MOBILE", |
1132 | - "Mass Storage", |
1133 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1134 | - 0), |
1135 | -UNUSUAL_DEV( 0x12d1, 0x1428, 0x0000, 0x0000, |
1136 | - "HUAWEI MOBILE", |
1137 | - "Mass Storage", |
1138 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1139 | - 0), |
1140 | -UNUSUAL_DEV( 0x12d1, 0x1429, 0x0000, 0x0000, |
1141 | - "HUAWEI MOBILE", |
1142 | - "Mass Storage", |
1143 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1144 | - 0), |
1145 | -UNUSUAL_DEV( 0x12d1, 0x142A, 0x0000, 0x0000, |
1146 | - "HUAWEI MOBILE", |
1147 | - "Mass Storage", |
1148 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1149 | - 0), |
1150 | -UNUSUAL_DEV( 0x12d1, 0x142B, 0x0000, 0x0000, |
1151 | - "HUAWEI MOBILE", |
1152 | - "Mass Storage", |
1153 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1154 | - 0), |
1155 | -UNUSUAL_DEV( 0x12d1, 0x142C, 0x0000, 0x0000, |
1156 | - "HUAWEI MOBILE", |
1157 | - "Mass Storage", |
1158 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1159 | - 0), |
1160 | -UNUSUAL_DEV( 0x12d1, 0x142D, 0x0000, 0x0000, |
1161 | - "HUAWEI MOBILE", |
1162 | - "Mass Storage", |
1163 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1164 | - 0), |
1165 | -UNUSUAL_DEV( 0x12d1, 0x142E, 0x0000, 0x0000, |
1166 | - "HUAWEI MOBILE", |
1167 | - "Mass Storage", |
1168 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1169 | - 0), |
1170 | -UNUSUAL_DEV( 0x12d1, 0x142F, 0x0000, 0x0000, |
1171 | - "HUAWEI MOBILE", |
1172 | - "Mass Storage", |
1173 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1174 | - 0), |
1175 | -UNUSUAL_DEV( 0x12d1, 0x1430, 0x0000, 0x0000, |
1176 | - "HUAWEI MOBILE", |
1177 | - "Mass Storage", |
1178 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1179 | - 0), |
1180 | -UNUSUAL_DEV( 0x12d1, 0x1431, 0x0000, 0x0000, |
1181 | - "HUAWEI MOBILE", |
1182 | - "Mass Storage", |
1183 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1184 | - 0), |
1185 | -UNUSUAL_DEV( 0x12d1, 0x1432, 0x0000, 0x0000, |
1186 | - "HUAWEI MOBILE", |
1187 | - "Mass Storage", |
1188 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1189 | - 0), |
1190 | -UNUSUAL_DEV( 0x12d1, 0x1433, 0x0000, 0x0000, |
1191 | - "HUAWEI MOBILE", |
1192 | - "Mass Storage", |
1193 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1194 | - 0), |
1195 | -UNUSUAL_DEV( 0x12d1, 0x1434, 0x0000, 0x0000, |
1196 | - "HUAWEI MOBILE", |
1197 | - "Mass Storage", |
1198 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1199 | - 0), |
1200 | -UNUSUAL_DEV( 0x12d1, 0x1435, 0x0000, 0x0000, |
1201 | - "HUAWEI MOBILE", |
1202 | - "Mass Storage", |
1203 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1204 | - 0), |
1205 | -UNUSUAL_DEV( 0x12d1, 0x1436, 0x0000, 0x0000, |
1206 | - "HUAWEI MOBILE", |
1207 | - "Mass Storage", |
1208 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1209 | - 0), |
1210 | -UNUSUAL_DEV( 0x12d1, 0x1437, 0x0000, 0x0000, |
1211 | - "HUAWEI MOBILE", |
1212 | - "Mass Storage", |
1213 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1214 | - 0), |
1215 | -UNUSUAL_DEV( 0x12d1, 0x1438, 0x0000, 0x0000, |
1216 | - "HUAWEI MOBILE", |
1217 | - "Mass Storage", |
1218 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1219 | - 0), |
1220 | -UNUSUAL_DEV( 0x12d1, 0x1439, 0x0000, 0x0000, |
1221 | - "HUAWEI MOBILE", |
1222 | - "Mass Storage", |
1223 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1224 | - 0), |
1225 | -UNUSUAL_DEV( 0x12d1, 0x143A, 0x0000, 0x0000, |
1226 | - "HUAWEI MOBILE", |
1227 | - "Mass Storage", |
1228 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1229 | - 0), |
1230 | -UNUSUAL_DEV( 0x12d1, 0x143B, 0x0000, 0x0000, |
1231 | - "HUAWEI MOBILE", |
1232 | - "Mass Storage", |
1233 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1234 | - 0), |
1235 | -UNUSUAL_DEV( 0x12d1, 0x143C, 0x0000, 0x0000, |
1236 | - "HUAWEI MOBILE", |
1237 | - "Mass Storage", |
1238 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1239 | - 0), |
1240 | -UNUSUAL_DEV( 0x12d1, 0x143D, 0x0000, 0x0000, |
1241 | - "HUAWEI MOBILE", |
1242 | - "Mass Storage", |
1243 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1244 | - 0), |
1245 | -UNUSUAL_DEV( 0x12d1, 0x143E, 0x0000, 0x0000, |
1246 | - "HUAWEI MOBILE", |
1247 | - "Mass Storage", |
1248 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1249 | - 0), |
1250 | -UNUSUAL_DEV( 0x12d1, 0x143F, 0x0000, 0x0000, |
1251 | - "HUAWEI MOBILE", |
1252 | - "Mass Storage", |
1253 | - USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_e220_init, |
1254 | + USB_SC_DEVICE, USB_PR_DEVICE, usb_stor_huawei_init, |
1255 | 0), |
1256 | |
1257 | /* Reported by Vilius Bilinkevicius <vilisas AT xxx DOT lt) */ |
1258 | diff --git a/drivers/usb/storage/usb.c b/drivers/usb/storage/usb.c |
1259 | index 12aa726..69b9eec 100644 |
1260 | --- a/drivers/usb/storage/usb.c |
1261 | +++ b/drivers/usb/storage/usb.c |
1262 | @@ -120,6 +120,17 @@ MODULE_PARM_DESC(quirks, "supplemental list of device IDs and their quirks"); |
1263 | .useTransport = use_transport, \ |
1264 | } |
1265 | |
1266 | +#define UNUSUAL_VENDOR_INTF(idVendor, cl, sc, pr, \ |
1267 | + vendor_name, product_name, use_protocol, use_transport, \ |
1268 | + init_function, Flags) \ |
1269 | +{ \ |
1270 | + .vendorName = vendor_name, \ |
1271 | + .productName = product_name, \ |
1272 | + .useProtocol = use_protocol, \ |
1273 | + .useTransport = use_transport, \ |
1274 | + .initFunction = init_function, \ |
1275 | +} |
1276 | + |
1277 | static struct us_unusual_dev us_unusual_dev_list[] = { |
1278 | # include "unusual_devs.h" |
1279 | { } /* Terminating entry */ |
1280 | @@ -131,6 +142,7 @@ static struct us_unusual_dev for_dynamic_ids = |
1281 | #undef UNUSUAL_DEV |
1282 | #undef COMPLIANT_DEV |
1283 | #undef USUAL_DEV |
1284 | +#undef UNUSUAL_VENDOR_INTF |
1285 | |
1286 | #ifdef CONFIG_LOCKDEP |
1287 | |
1288 | diff --git a/drivers/usb/storage/usual-tables.c b/drivers/usb/storage/usual-tables.c |
1289 | index b78a526..5ef8ce7 100644 |
1290 | --- a/drivers/usb/storage/usual-tables.c |
1291 | +++ b/drivers/usb/storage/usual-tables.c |
1292 | @@ -41,6 +41,20 @@ |
1293 | #define USUAL_DEV(useProto, useTrans) \ |
1294 | { USB_INTERFACE_INFO(USB_CLASS_MASS_STORAGE, useProto, useTrans) } |
1295 | |
1296 | +/* Define the device is matched with Vendor ID and interface descriptors */ |
1297 | +#define UNUSUAL_VENDOR_INTF(id_vendor, cl, sc, pr, \ |
1298 | + vendorName, productName, useProtocol, useTransport, \ |
1299 | + initFunction, flags) \ |
1300 | +{ \ |
1301 | + .match_flags = USB_DEVICE_ID_MATCH_INT_INFO \ |
1302 | + | USB_DEVICE_ID_MATCH_VENDOR, \ |
1303 | + .idVendor = (id_vendor), \ |
1304 | + .bInterfaceClass = (cl), \ |
1305 | + .bInterfaceSubClass = (sc), \ |
1306 | + .bInterfaceProtocol = (pr), \ |
1307 | + .driver_info = (flags) \ |
1308 | +} |
1309 | + |
1310 | struct usb_device_id usb_storage_usb_ids[] = { |
1311 | # include "unusual_devs.h" |
1312 | { } /* Terminating entry */ |
1313 | @@ -50,6 +64,7 @@ MODULE_DEVICE_TABLE(usb, usb_storage_usb_ids); |
1314 | #undef UNUSUAL_DEV |
1315 | #undef COMPLIANT_DEV |
1316 | #undef USUAL_DEV |
1317 | +#undef UNUSUAL_VENDOR_INTF |
1318 | |
1319 | /* |
1320 | * The table of devices to ignore |
1321 | diff --git a/fs/nilfs2/ioctl.c b/fs/nilfs2/ioctl.c |
1322 | index fdb1807..f385935 100644 |
1323 | --- a/fs/nilfs2/ioctl.c |
1324 | +++ b/fs/nilfs2/ioctl.c |
1325 | @@ -664,8 +664,11 @@ static int nilfs_ioctl_clean_segments(struct inode *inode, struct file *filp, |
1326 | if (ret < 0) |
1327 | printk(KERN_ERR "NILFS: GC failed during preparation: " |
1328 | "cannot read source blocks: err=%d\n", ret); |
1329 | - else |
1330 | + else { |
1331 | + if (nilfs_sb_need_update(nilfs)) |
1332 | + set_nilfs_discontinued(nilfs); |
1333 | ret = nilfs_clean_segments(inode->i_sb, argv, kbufs); |
1334 | + } |
1335 | |
1336 | nilfs_remove_all_gcinodes(nilfs); |
1337 | clear_nilfs_gc_running(nilfs); |
1338 | diff --git a/include/uapi/linux/usb/ch9.h b/include/uapi/linux/usb/ch9.h |
1339 | index 5059847..f738e25 100644 |
1340 | --- a/include/uapi/linux/usb/ch9.h |
1341 | +++ b/include/uapi/linux/usb/ch9.h |
1342 | @@ -152,6 +152,12 @@ |
1343 | #define USB_INTRF_FUNC_SUSPEND_LP (1 << (8 + 0)) |
1344 | #define USB_INTRF_FUNC_SUSPEND_RW (1 << (8 + 1)) |
1345 | |
1346 | +/* |
1347 | + * Interface status, Figure 9-5 USB 3.0 spec |
1348 | + */ |
1349 | +#define USB_INTRF_STAT_FUNC_RW_CAP 1 |
1350 | +#define USB_INTRF_STAT_FUNC_RW 2 |
1351 | + |
1352 | #define USB_ENDPOINT_HALT 0 /* IN/OUT will STALL */ |
1353 | |
1354 | /* Bit array elements as returned by the USB_REQ_GET_STATUS request. */ |
1355 | diff --git a/kernel/sched/rt.c b/kernel/sched/rt.c |
1356 | index 418feb0..4f02b28 100644 |
1357 | --- a/kernel/sched/rt.c |
1358 | +++ b/kernel/sched/rt.c |
1359 | @@ -566,7 +566,7 @@ static inline struct rt_bandwidth *sched_rt_bandwidth(struct rt_rq *rt_rq) |
1360 | static int do_balance_runtime(struct rt_rq *rt_rq) |
1361 | { |
1362 | struct rt_bandwidth *rt_b = sched_rt_bandwidth(rt_rq); |
1363 | - struct root_domain *rd = cpu_rq(smp_processor_id())->rd; |
1364 | + struct root_domain *rd = rq_of_rt_rq(rt_rq)->rd; |
1365 | int i, weight, more = 0; |
1366 | u64 rt_period; |
1367 | |
1368 | diff --git a/lib/digsig.c b/lib/digsig.c |
1369 | index 8c0e629..dc2be7e 100644 |
1370 | --- a/lib/digsig.c |
1371 | +++ b/lib/digsig.c |
1372 | @@ -162,6 +162,8 @@ static int digsig_verify_rsa(struct key *key, |
1373 | memset(out1, 0, head); |
1374 | memcpy(out1 + head, p, l); |
1375 | |
1376 | + kfree(p); |
1377 | + |
1378 | err = pkcs_1_v1_5_decode_emsa(out1, len, mblen, out2, &len); |
1379 | if (err) |
1380 | goto err; |
1381 | diff --git a/mm/hugetlb.c b/mm/hugetlb.c |
1382 | index f198aca..b969ed4 100644 |
1383 | --- a/mm/hugetlb.c |
1384 | +++ b/mm/hugetlb.c |
1385 | @@ -3028,6 +3028,7 @@ void hugetlb_change_protection(struct vm_area_struct *vma, |
1386 | if (!huge_pte_none(huge_ptep_get(ptep))) { |
1387 | pte = huge_ptep_get_and_clear(mm, address, ptep); |
1388 | pte = pte_mkhuge(pte_modify(pte, newprot)); |
1389 | + pte = arch_make_huge_pte(pte, vma, NULL, 0); |
1390 | set_huge_pte_at(mm, address, ptep, pte); |
1391 | } |
1392 | } |
1393 | diff --git a/mm/migrate.c b/mm/migrate.c |
1394 | index 77ed2d7..346d32d 100644 |
1395 | --- a/mm/migrate.c |
1396 | +++ b/mm/migrate.c |
1397 | @@ -143,8 +143,10 @@ static int remove_migration_pte(struct page *new, struct vm_area_struct *vma, |
1398 | if (is_write_migration_entry(entry)) |
1399 | pte = pte_mkwrite(pte); |
1400 | #ifdef CONFIG_HUGETLB_PAGE |
1401 | - if (PageHuge(new)) |
1402 | + if (PageHuge(new)) { |
1403 | pte = pte_mkhuge(pte); |
1404 | + pte = arch_make_huge_pte(pte, vma, new, 0); |
1405 | + } |
1406 | #endif |
1407 | flush_cache_page(vma, addr, pte_pfn(pte)); |
1408 | set_pte_at(mm, addr, ptep, pte); |