summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJan Weitzel <j.weitzel@phytec.de>2011-11-02 13:40:02 -0700
committerLinus Torvalds <torvalds@linux-foundation.org>2011-11-02 16:07:03 -0700
commit3fd306c85adcde7209281cb663dd8ea247e97cc3 (patch)
tree67bd829e0ef4e8e350af7fd06e4936bec616b49a
parent68a436aec345c2bcd05dbdafae1f5f608ff8f61f (diff)
w1: disable irqs in critical section
Interrupting w1_delay() in w1_read_bit() results in missing the low level on the w1 line and receiving "1" instead of "0". Add local_irq_save()/local_irq_restore() around the critical section Signed-off-by: Jan Weitzel <j.weitzel@phytec.de> Acked-by: Evgeniy Polyakov <zbr@ioremap.net> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
-rw-r--r--drivers/w1/w1_io.c5
1 files changed, 5 insertions, 0 deletions
diff --git a/drivers/w1/w1_io.c b/drivers/w1/w1_io.c
index 765b37b62a4f..3135b2c63998 100644
--- a/drivers/w1/w1_io.c
+++ b/drivers/w1/w1_io.c
@@ -158,13 +158,18 @@ EXPORT_SYMBOL_GPL(w1_write_8);
static u8 w1_read_bit(struct w1_master *dev)
{
int result;
+ unsigned long flags;
+ /* sample timing is critical here */
+ local_irq_save(flags);
dev->bus_master->write_bit(dev->bus_master->data, 0);
w1_delay(6);
dev->bus_master->write_bit(dev->bus_master->data, 1);
w1_delay(9);
result = dev->bus_master->read_bit(dev->bus_master->data);
+ local_irq_restore(flags);
+
w1_delay(55);
return result & 0x1;