Commit f607e7fc5fb94d92030c4527287e9c149ddf9e65
Committed by
Linus Torvalds
1 parent
453a9bf347
Exists in
master
and in
4 other branches
w1: ds1wm: add a reset recovery parameter
This fixes a regression in 3.0 reported by Paul Parsons regarding the removal of the msleep(1) in the ds1wm_reset() function: : The linux-3.0-rc4 DS1WM 1-wire driver is logging "bus error, retrying" : error messages on an HP iPAQ hx4700 PDA (XScale-PXA270): : : <snip> : Driver for 1-wire Dallas network protocol. : DS1WM w1 busmaster driver - (c) 2004 Szabolcs Gyurko : 1-Wire driver for the DS2760 battery monitor chip - (c) 2004-2005, Szabolcs Gyurko : ds1wm ds1wm: pass: 1 bus error, retrying : ds1wm ds1wm: pass: 2 bus error, retrying : ds1wm ds1wm: pass: 3 bus error, retrying : ds1wm ds1wm: pass: 4 bus error, retrying : ds1wm ds1wm: pass: 5 bus error, retrying : ... : : The visible result is that the battery charging LED is erratic; sometimes : it works, mostly it doesn't. : : The linux-2.6.39 DS1WM 1-wire driver worked OK. I haven't tried 3.0-rc1, : 3.0-rc2, or 3.0-rc3. This sleep should not be required on normal circuitry provided the pull-ups on the bus are correctly adapted to the slaves. Unfortunately, this is not always the case. The sleep is restored but as a parameter to the probe function in the pdata. [akpm@linux-foundation.org: coding-style fixes] Reported-by: Paul Parsons <lost.distance@yahoo.com> Tested-by: Paul Parsons <lost.distance@yahoo.com> Signed-off-by: Jean-François Dagenais <dagenaisj@sonatest.com> Cc: Evgeniy Polyakov <johnpol@2ka.mipt.ru> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Showing 4 changed files with 14 additions and 0 deletions Side-by-side Diff
drivers/mfd/asic3.c
drivers/mfd/htc-pasic3.c
drivers/w1/masters/ds1wm.c
... | ... | @@ -109,6 +109,7 @@ |
109 | 109 | /* byte to write that makes all intr disabled, */ |
110 | 110 | /* considering active_state (IAS) (optimization) */ |
111 | 111 | u8 int_en_reg_none; |
112 | + unsigned int reset_recover_delay; /* see ds1wm.h */ | |
112 | 113 | }; |
113 | 114 | |
114 | 115 | static inline void ds1wm_write_register(struct ds1wm_data *ds1wm_data, u32 reg, |
... | ... | @@ -187,6 +188,9 @@ |
187 | 188 | return 1; |
188 | 189 | } |
189 | 190 | |
191 | + if (ds1wm_data->reset_recover_delay) | |
192 | + msleep(ds1wm_data->reset_recover_delay); | |
193 | + | |
190 | 194 | return 0; |
191 | 195 | } |
192 | 196 | |
... | ... | @@ -490,6 +494,7 @@ |
490 | 494 | } |
491 | 495 | ds1wm_data->irq = res->start; |
492 | 496 | ds1wm_data->int_en_reg_none = (plat->active_high ? DS1WM_INTEN_IAS : 0); |
497 | + ds1wm_data->reset_recover_delay = plat->reset_recover_delay; | |
493 | 498 | |
494 | 499 | if (res->flags & IORESOURCE_IRQ_HIGHEDGE) |
495 | 500 | irq_set_irq_type(ds1wm_data->irq, IRQ_TYPE_EDGE_RISING); |
include/linux/mfd/ds1wm.h
... | ... | @@ -3,5 +3,12 @@ |
3 | 3 | struct ds1wm_driver_data { |
4 | 4 | int active_high; |
5 | 5 | int clock_rate; |
6 | + /* in milliseconds, the amount of time to */ | |
7 | + /* sleep following a reset pulse. Zero */ | |
8 | + /* should work if your bus devices recover*/ | |
9 | + /* time respects the 1-wire spec since the*/ | |
10 | + /* ds1wm implements the precise timings of*/ | |
11 | + /* a reset pulse/presence detect sequence.*/ | |
12 | + unsigned int reset_recover_delay; | |
6 | 13 | }; |