diff options
author | Jason Gunthorpe <jgunthorpe@obsidianresearch.com> | 2015-11-25 16:05:34 -0500 |
---|---|---|
committer | Jarkko Sakkinen <jarkko.sakkinen@linux.intel.com> | 2015-12-20 08:26:25 -0500 |
commit | 7ab4032fa579cd54be6a986a5cfd7f374b6bf02d (patch) | |
tree | 34c4f061235c5ea09cb13fd44384ed4ad041ab82 /drivers/char | |
parent | 25112048cd59930e23775cafb88e18cfb484892c (diff) |
tpm_tis: Get rid of the duplicate IRQ probing code
The new code that works directly in tpm_tis_send is able to handle
IRQ probing duties as well, so just use it for everything.
Signed-off-by: Jason Gunthorpe <jgunthorpe@obsidianresearch.com>
Reviewed-by: Jarkko Sakkinen <jarkko.sakkinen@linux.intel.com>
Tested-by: Jarkko Sakkinen <jarkko.sakkinen@linux.intel.com>
Tested-by: Martin Wilck <Martin.Wilck@ts.fujitsu.com>
Tested-by: Scot Doyle <lkml14@scotdoyle.com>
Signed-off--by: Jarkko Sakkinen <jarkko.sakkinen@linux.intel.com>
Acked-by: Peter Huewe <peterhuewe@gmx.de>
Diffstat (limited to 'drivers/char')
-rw-r--r-- | drivers/char/tpm/tpm.h | 1 | ||||
-rw-r--r-- | drivers/char/tpm/tpm_tis.c | 64 |
2 files changed, 20 insertions, 45 deletions
diff --git a/drivers/char/tpm/tpm.h b/drivers/char/tpm/tpm.h index a4257a32964f..347fc615bcc9 100644 --- a/drivers/char/tpm/tpm.h +++ b/drivers/char/tpm/tpm.h | |||
@@ -138,7 +138,6 @@ struct tpm_vendor_specific { | |||
138 | unsigned long base; /* TPM base address */ | 138 | unsigned long base; /* TPM base address */ |
139 | 139 | ||
140 | int irq; | 140 | int irq; |
141 | int probed_irq; | ||
142 | 141 | ||
143 | int region_size; | 142 | int region_size; |
144 | int have_region; | 143 | int have_region; |
diff --git a/drivers/char/tpm/tpm_tis.c b/drivers/char/tpm/tpm_tis.c index 56a295d328c7..2580893de023 100644 --- a/drivers/char/tpm/tpm_tis.c +++ b/drivers/char/tpm/tpm_tis.c | |||
@@ -99,6 +99,7 @@ static struct tpm_info tis_default_info = { | |||
99 | #define TPM_RID(l) (0x0F04 | ((l) << 12)) | 99 | #define TPM_RID(l) (0x0F04 | ((l) << 12)) |
100 | 100 | ||
101 | struct priv_data { | 101 | struct priv_data { |
102 | bool irq_probing; | ||
102 | bool irq_tested; | 103 | bool irq_tested; |
103 | }; | 104 | }; |
104 | 105 | ||
@@ -463,8 +464,9 @@ static int tpm_tis_send(struct tpm_chip *chip, u8 *buf, size_t len) | |||
463 | msleep(1); | 464 | msleep(1); |
464 | if (!priv->irq_tested) { | 465 | if (!priv->irq_tested) { |
465 | disable_interrupts(chip); | 466 | disable_interrupts(chip); |
466 | dev_err(chip->pdev, | 467 | if (!priv->irq_probing) |
467 | FW_BUG "TPM interrupt not working, polling instead\n"); | 468 | dev_err(chip->pdev, FW_BUG |
469 | "TPM interrupt not working, polling instead\n"); | ||
468 | } | 470 | } |
469 | priv->irq_tested = true; | 471 | priv->irq_tested = true; |
470 | return rc; | 472 | return rc; |
@@ -570,26 +572,6 @@ static const struct tpm_class_ops tpm_tis = { | |||
570 | .req_canceled = tpm_tis_req_canceled, | 572 | .req_canceled = tpm_tis_req_canceled, |
571 | }; | 573 | }; |
572 | 574 | ||
573 | static irqreturn_t tis_int_probe(int irq, void *dev_id) | ||
574 | { | ||
575 | struct tpm_chip *chip = dev_id; | ||
576 | u32 interrupt; | ||
577 | |||
578 | interrupt = ioread32(chip->vendor.iobase + | ||
579 | TPM_INT_STATUS(chip->vendor.locality)); | ||
580 | |||
581 | if (interrupt == 0) | ||
582 | return IRQ_NONE; | ||
583 | |||
584 | chip->vendor.probed_irq = irq; | ||
585 | |||
586 | /* Clear interrupts handled with TPM_EOI */ | ||
587 | iowrite32(interrupt, | ||
588 | chip->vendor.iobase + | ||
589 | TPM_INT_STATUS(chip->vendor.locality)); | ||
590 | return IRQ_HANDLED; | ||
591 | } | ||
592 | |||
593 | static irqreturn_t tis_int_handler(int dummy, void *dev_id) | 575 | static irqreturn_t tis_int_handler(int dummy, void *dev_id) |
594 | { | 576 | { |
595 | struct tpm_chip *chip = dev_id; | 577 | struct tpm_chip *chip = dev_id; |
@@ -772,13 +754,14 @@ static int tpm_tis_init(struct device *dev, struct tpm_info *tpm_info, | |||
772 | iowrite8(i, chip->vendor.iobase + | 754 | iowrite8(i, chip->vendor.iobase + |
773 | TPM_INT_VECTOR(chip->vendor.locality)); | 755 | TPM_INT_VECTOR(chip->vendor.locality)); |
774 | if (devm_request_irq | 756 | if (devm_request_irq |
775 | (dev, i, tis_int_probe, IRQF_SHARED, | 757 | (dev, i, tis_int_handler, IRQF_SHARED, |
776 | chip->devname, chip) != 0) { | 758 | chip->devname, chip) != 0) { |
777 | dev_info(chip->pdev, | 759 | dev_info(chip->pdev, |
778 | "Unable to request irq: %d for probe\n", | 760 | "Unable to request irq: %d for probe\n", |
779 | i); | 761 | i); |
780 | continue; | 762 | continue; |
781 | } | 763 | } |
764 | chip->vendor.irq = i; | ||
782 | 765 | ||
783 | /* Clear all existing */ | 766 | /* Clear all existing */ |
784 | iowrite32(ioread32 | 767 | iowrite32(ioread32 |
@@ -792,7 +775,8 @@ static int tpm_tis_init(struct device *dev, struct tpm_info *tpm_info, | |||
792 | chip->vendor.iobase + | 775 | chip->vendor.iobase + |
793 | TPM_INT_ENABLE(chip->vendor.locality)); | 776 | TPM_INT_ENABLE(chip->vendor.locality)); |
794 | 777 | ||
795 | chip->vendor.probed_irq = 0; | 778 | priv->irq_tested = false; |
779 | priv->irq_probing = true; | ||
796 | 780 | ||
797 | /* Generate Interrupts */ | 781 | /* Generate Interrupts */ |
798 | if (chip->flags & TPM_CHIP_FLAG_TPM2) | 782 | if (chip->flags & TPM_CHIP_FLAG_TPM2) |
@@ -800,26 +784,20 @@ static int tpm_tis_init(struct device *dev, struct tpm_info *tpm_info, | |||
800 | else | 784 | else |
801 | tpm_gen_interrupt(chip); | 785 | tpm_gen_interrupt(chip); |
802 | 786 | ||
803 | chip->vendor.irq = chip->vendor.probed_irq; | 787 | priv->irq_probing = false; |
804 | |||
805 | /* free_irq will call into tis_int_probe; | ||
806 | clear all irqs we haven't seen while doing | ||
807 | tpm_gen_interrupt */ | ||
808 | iowrite32(ioread32 | ||
809 | (chip->vendor.iobase + | ||
810 | TPM_INT_STATUS(chip->vendor.locality)), | ||
811 | chip->vendor.iobase + | ||
812 | TPM_INT_STATUS(chip->vendor.locality)); | ||
813 | |||
814 | /* Turn off */ | ||
815 | iowrite32(intmask, | ||
816 | chip->vendor.iobase + | ||
817 | TPM_INT_ENABLE(chip->vendor.locality)); | ||
818 | 788 | ||
819 | devm_free_irq(dev, i, chip); | 789 | /* tpm_tis_send will either confirm the interrupt is |
790 | * working or it will call disable_irq which undoes | ||
791 | * all of the above. | ||
792 | */ | ||
793 | if (chip->vendor.irq) | ||
794 | break; | ||
820 | } | 795 | } |
796 | if (!chip->vendor.irq) | ||
797 | iowrite8(irq_r, chip->vendor.iobase + | ||
798 | TPM_INT_VECTOR(chip->vendor.locality)); | ||
821 | } | 799 | } |
822 | if (chip->vendor.irq) { | 800 | if (chip->vendor.irq && !priv->irq_tested) { |
823 | iowrite8(chip->vendor.irq, | 801 | iowrite8(chip->vendor.irq, |
824 | chip->vendor.iobase + | 802 | chip->vendor.iobase + |
825 | TPM_INT_VECTOR(chip->vendor.locality)); | 803 | TPM_INT_VECTOR(chip->vendor.locality)); |
@@ -843,9 +821,7 @@ static int tpm_tis_init(struct device *dev, struct tpm_info *tpm_info, | |||
843 | chip->vendor.iobase + | 821 | chip->vendor.iobase + |
844 | TPM_INT_ENABLE(chip->vendor.locality)); | 822 | TPM_INT_ENABLE(chip->vendor.locality)); |
845 | } | 823 | } |
846 | } else if (irq_r != -1) | 824 | } |
847 | iowrite8(irq_r, chip->vendor.iobase + | ||
848 | TPM_INT_VECTOR(chip->vendor.locality)); | ||
849 | 825 | ||
850 | if (tpm_get_timeouts(chip)) { | 826 | if (tpm_get_timeouts(chip)) { |
851 | dev_err(dev, "Could not get TPM timeouts and durations\n"); | 827 | dev_err(dev, "Could not get TPM timeouts and durations\n"); |