Skip to content

Commit afaf7fd

Browse files
alexaringholtmann
authored andcommitted
mrf24j40: change irq trigger type behaviour
This patch changes the irq trigger type value while calling devm_request_irq by using IRQF_TRIGGER_LOW when no irq type was given. Additional we add support for change the irq polarity while hw init if high level or low level triggered irq type are given. For rising edge triggered irq's the mrf24j40 can't deal with that, this races at position of tx completion irq, while the irq is disabled we readout the irq status registers. This will resets the irq line so other irq's can occur. Wile readout the irq status register the irq is still disabled and edge triggered interrupts will be ignored. Signed-off-by: Alexander Aring <alex.aring@gmail.com> Signed-off-by: Marcel Holtmann <marcel@holtmann.org>
1 parent 8ba4041 commit afaf7fd

File tree

1 file changed

+28
-3
lines changed

1 file changed

+28
-3
lines changed

drivers/net/ieee802154/mrf24j40.c

Lines changed: 28 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
#include <linux/module.h>
2121
#include <linux/regmap.h>
2222
#include <linux/ieee802154.h>
23+
#include <linux/irq.h>
2324
#include <net/cfg802154.h>
2425
#include <net/mac802154.h>
2526

@@ -992,6 +993,7 @@ static irqreturn_t mrf24j40_isr(int irq, void *data)
992993

993994
static int mrf24j40_hw_init(struct mrf24j40 *devrec)
994995
{
996+
u32 irq_type;
995997
int ret;
996998

997999
/* Initialize the device.
@@ -1083,6 +1085,25 @@ static int mrf24j40_hw_init(struct mrf24j40 *devrec)
10831085
regmap_write(devrec->regmap_long, REG_RFCON3, 0x28);
10841086
}
10851087

1088+
irq_type = irq_get_trigger_type(devrec->spi->irq);
1089+
if (irq_type == IRQ_TYPE_EDGE_RISING ||
1090+
irq_type == IRQ_TYPE_EDGE_FALLING)
1091+
dev_warn(&devrec->spi->dev,
1092+
"Using edge triggered irq's are not recommended, because it can cause races and result in a non-functional driver!\n");
1093+
switch (irq_type) {
1094+
case IRQ_TYPE_EDGE_RISING:
1095+
case IRQ_TYPE_LEVEL_HIGH:
1096+
/* set interrupt polarity to rising */
1097+
ret = regmap_update_bits(devrec->regmap_long, REG_SLPCON0,
1098+
0x02, 0x02);
1099+
if (ret)
1100+
goto err_ret;
1101+
break;
1102+
default:
1103+
/* default is falling edge */
1104+
break;
1105+
}
1106+
10861107
return 0;
10871108

10881109
err_ret:
@@ -1182,7 +1203,7 @@ static void mrf24j40_phy_setup(struct mrf24j40 *devrec)
11821203

11831204
static int mrf24j40_probe(struct spi_device *spi)
11841205
{
1185-
int ret = -ENOMEM;
1206+
int ret = -ENOMEM, irq_type;
11861207
struct ieee802154_hw *hw;
11871208
struct mrf24j40 *devrec;
11881209

@@ -1242,9 +1263,13 @@ static int mrf24j40_probe(struct spi_device *spi)
12421263

12431264
mrf24j40_phy_setup(devrec);
12441265

1266+
/* request IRQF_TRIGGER_LOW as fallback default */
1267+
irq_type = irq_get_trigger_type(spi->irq);
1268+
if (!irq_type)
1269+
irq_type = IRQF_TRIGGER_LOW;
1270+
12451271
ret = devm_request_irq(&spi->dev, spi->irq, mrf24j40_isr,
1246-
IRQF_TRIGGER_LOW, dev_name(&spi->dev),
1247-
devrec);
1272+
irq_type, dev_name(&spi->dev), devrec);
12481273
if (ret) {
12491274
dev_err(printdev(devrec), "Unable to get IRQ");
12501275
goto err_register_device;

0 commit comments

Comments
 (0)