i2c: designware: Add support for recovery when GPIO need pinctrl

Currently if the SoC needs pinctrl to switch the SCL and SDA from the I2C
function to GPIO function, the recovery won't work.

scl-gpio = <>;
sda-gpio = <>;

Are not enough for some SoCs to have a working recovery.
Some need:

scl-gpio = <>;
sda-gpio = <>;
pinctrl-names = "default", "recovery";
pinctrl-0 = <&i2c_pins_hw>;
pinctrl-1 = <&i2c_pins_gpio>;

The driver was not filling rinfo->pinctrl with the device node
pinctrl data which is needed by generic recovery code.

Signed-off-by: Yann Sionneau <ysionneau@kalray.eu>
Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Acked-by: Jarkko Nikula <jarkko.nikula@linux.intel.com>
Reviewed-by: Andi Shyti <andi.shyti@kernel.org>
Signed-off-by: Wolfram Sang <wsa@kernel.org>
This commit is contained in:
Yann Sionneau 2023-08-22 16:34:37 +02:00 committed by Wolfram Sang
parent 2ed4fa9cb8
commit 4ba63869a0

View File

@ -17,6 +17,7 @@
#include <linux/interrupt.h>
#include <linux/io.h>
#include <linux/module.h>
#include <linux/pinctrl/consumer.h>
#include <linux/pm_runtime.h>
#include <linux/regmap.h>
#include <linux/reset.h>
@ -905,6 +906,17 @@ static int i2c_dw_init_recovery_info(struct dw_i2c_dev *dev)
return PTR_ERR(gpio);
rinfo->sda_gpiod = gpio;
rinfo->pinctrl = devm_pinctrl_get(dev->dev);
if (IS_ERR(rinfo->pinctrl)) {
if (PTR_ERR(rinfo->pinctrl) == -EPROBE_DEFER)
return PTR_ERR(rinfo->pinctrl);
rinfo->pinctrl = NULL;
dev_err(dev->dev, "getting pinctrl info failed: bus recovery might not work\n");
} else if (!rinfo->pinctrl) {
dev_dbg(dev->dev, "pinctrl is disabled, bus recovery might not work\n");
}
rinfo->recover_bus = i2c_generic_scl_recovery;
rinfo->prepare_recovery = i2c_dw_prepare_recovery;
rinfo->unprepare_recovery = i2c_dw_unprepare_recovery;