diff options
author | Alek Du <alek.du@intel.com> | 2010-10-26 17:22:41 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2010-10-26 19:52:15 -0400 |
commit | 8a233f01b7d7dd587f85fa581274f168f1e88bb8 (patch) | |
tree | a3f48e7647dde5cd62d2931c3152a5ded590e6d5 | |
parent | 2e85c4ddd3f32d3e1da51f4129473399e505ffa3 (diff) |
pca953x: pca953x driver fixes for x86 mrst
Our Moorestown platform has two max7315 chips which is covered by pca953x
i2c gpio driver.
A while ago this driver got updated with nested irq thread support, and it
broke the compatibity with "request_irq". For example, the gpio_keys.c
driver can not work with this driver now. This patch fixes the issue by
switching to generic_handle_irq.
Also fix the irq_base issue: irq_base == 0 is valid, and a "-1" value
should mean invalid. IRQ 0 is not a valid IRQ, irq_base of 0 is valid.
Signed-off-by: Alek Du <alek.du@intel.com>
Signed-off-by: Alan Cox <alan@linux.intel.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
-rw-r--r-- | drivers/gpio/pca953x.c | 13 |
1 files changed, 7 insertions, 6 deletions
diff --git a/drivers/gpio/pca953x.c b/drivers/gpio/pca953x.c index a2b12aa1f2b9..501866662e05 100644 --- a/drivers/gpio/pca953x.c +++ b/drivers/gpio/pca953x.c | |||
@@ -345,7 +345,7 @@ static irqreturn_t pca953x_irq_handler(int irq, void *devid) | |||
345 | 345 | ||
346 | do { | 346 | do { |
347 | level = __ffs(pending); | 347 | level = __ffs(pending); |
348 | handle_nested_irq(level + chip->irq_base); | 348 | generic_handle_irq(level + chip->irq_base); |
349 | 349 | ||
350 | pending &= ~(1 << level); | 350 | pending &= ~(1 << level); |
351 | } while (pending); | 351 | } while (pending); |
@@ -360,7 +360,8 @@ static int pca953x_irq_setup(struct pca953x_chip *chip, | |||
360 | struct pca953x_platform_data *pdata = client->dev.platform_data; | 360 | struct pca953x_platform_data *pdata = client->dev.platform_data; |
361 | int ret; | 361 | int ret; |
362 | 362 | ||
363 | if (pdata->irq_base && (id->driver_data & PCA953X_INT)) { | 363 | if (pdata->irq_base != -1 |
364 | && (id->driver_data & PCA953X_INT)) { | ||
364 | int lvl; | 365 | int lvl; |
365 | 366 | ||
366 | ret = pca953x_read_reg(chip, PCA953X_INPUT, | 367 | ret = pca953x_read_reg(chip, PCA953X_INPUT, |
@@ -383,7 +384,6 @@ static int pca953x_irq_setup(struct pca953x_chip *chip, | |||
383 | set_irq_chip_data(irq, chip); | 384 | set_irq_chip_data(irq, chip); |
384 | set_irq_chip_and_handler(irq, &pca953x_irq_chip, | 385 | set_irq_chip_and_handler(irq, &pca953x_irq_chip, |
385 | handle_edge_irq); | 386 | handle_edge_irq); |
386 | set_irq_nested_thread(irq, 1); | ||
387 | #ifdef CONFIG_ARM | 387 | #ifdef CONFIG_ARM |
388 | set_irq_flags(irq, IRQF_VALID); | 388 | set_irq_flags(irq, IRQF_VALID); |
389 | #else | 389 | #else |
@@ -394,6 +394,7 @@ static int pca953x_irq_setup(struct pca953x_chip *chip, | |||
394 | ret = request_threaded_irq(client->irq, | 394 | ret = request_threaded_irq(client->irq, |
395 | NULL, | 395 | NULL, |
396 | pca953x_irq_handler, | 396 | pca953x_irq_handler, |
397 | IRQF_TRIGGER_RISING | | ||
397 | IRQF_TRIGGER_FALLING | IRQF_ONESHOT, | 398 | IRQF_TRIGGER_FALLING | IRQF_ONESHOT, |
398 | dev_name(&client->dev), chip); | 399 | dev_name(&client->dev), chip); |
399 | if (ret) { | 400 | if (ret) { |
@@ -408,13 +409,13 @@ static int pca953x_irq_setup(struct pca953x_chip *chip, | |||
408 | return 0; | 409 | return 0; |
409 | 410 | ||
410 | out_failed: | 411 | out_failed: |
411 | chip->irq_base = 0; | 412 | chip->irq_base = -1; |
412 | return ret; | 413 | return ret; |
413 | } | 414 | } |
414 | 415 | ||
415 | static void pca953x_irq_teardown(struct pca953x_chip *chip) | 416 | static void pca953x_irq_teardown(struct pca953x_chip *chip) |
416 | { | 417 | { |
417 | if (chip->irq_base) | 418 | if (chip->irq_base != -1) |
418 | free_irq(chip->client->irq, chip); | 419 | free_irq(chip->client->irq, chip); |
419 | } | 420 | } |
420 | #else /* CONFIG_GPIO_PCA953X_IRQ */ | 421 | #else /* CONFIG_GPIO_PCA953X_IRQ */ |
@@ -424,7 +425,7 @@ static int pca953x_irq_setup(struct pca953x_chip *chip, | |||
424 | struct i2c_client *client = chip->client; | 425 | struct i2c_client *client = chip->client; |
425 | struct pca953x_platform_data *pdata = client->dev.platform_data; | 426 | struct pca953x_platform_data *pdata = client->dev.platform_data; |
426 | 427 | ||
427 | if (pdata->irq_base && (id->driver_data & PCA953X_INT)) | 428 | if (pdata->irq_base != -1 && (id->driver_data & PCA953X_INT)) |
428 | dev_warn(&client->dev, "interrupt support not compiled in\n"); | 429 | dev_warn(&client->dev, "interrupt support not compiled in\n"); |
429 | 430 | ||
430 | return 0; | 431 | return 0; |