Commit 8d4264d8 authored by Linus Walleij's avatar Linus Walleij

Merge tag 'samsung-pinctrl-4.12' of...

Merge tag 'samsung-pinctrl-4.12' of git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/samsung into devel

Samsung pinctrl drivers update for v4.12:
1. Add support for pad retention control through pinctrl drivers which
   moves us forward to better runtime PM of pinctrl, clocks, power domains
   and other devices.
2. Fix GPIO hogs by registering pinctrl before registering gpiolib.
3. Use devm-like interface.
parents ba9e7f27 f69ae4f5
......@@ -777,6 +777,7 @@ exynos_retention_init(struct samsung_pinctrl_drv_data *drvdata,
{
struct samsung_retention_ctrl *ctrl;
struct regmap *pmu_regs;
int i;
ctrl = devm_kzalloc(drvdata->dev, sizeof(*ctrl), GFP_KERNEL);
if (!ctrl)
......@@ -794,6 +795,10 @@ exynos_retention_init(struct samsung_pinctrl_drv_data *drvdata,
ctrl->enable = exynos_retention_enable;
ctrl->disable = exynos_retention_disable;
/* Ensure that retention is disabled on driver init */
for (i = 0; i < ctrl->nr_regs; i++)
regmap_write(pmu_regs, ctrl->regs[i], ctrl->value);
return ctrl;
}
......@@ -1546,6 +1551,54 @@ static const struct samsung_pin_bank_data exynos5433_pin_banks9[] __initconst =
EXYNOS_PIN_BANK_EINTG(3, 0x000, "gpj1", 0x00),
};
/* PMU pin retention groups registers for Exynos5433 (without audio & fsys) */
static const u32 exynos5433_retention_regs[] = {
EXYNOS5433_PAD_RETENTION_TOP_OPTION,
EXYNOS5433_PAD_RETENTION_UART_OPTION,
EXYNOS5433_PAD_RETENTION_EBIA_OPTION,
EXYNOS5433_PAD_RETENTION_EBIB_OPTION,
EXYNOS5433_PAD_RETENTION_SPI_OPTION,
EXYNOS5433_PAD_RETENTION_MIF_OPTION,
EXYNOS5433_PAD_RETENTION_USBXTI_OPTION,
EXYNOS5433_PAD_RETENTION_BOOTLDO_OPTION,
EXYNOS5433_PAD_RETENTION_UFS_OPTION,
EXYNOS5433_PAD_RETENTION_FSYSGENIO_OPTION,
};
static const struct samsung_retention_data exynos5433_retention_data __initconst = {
.regs = exynos5433_retention_regs,
.nr_regs = ARRAY_SIZE(exynos5433_retention_regs),
.value = EXYNOS_WAKEUP_FROM_LOWPWR,
.refcnt = &exynos_shared_retention_refcnt,
.init = exynos_retention_init,
};
/* PMU retention control for audio pins can be tied to audio pin bank */
static const u32 exynos5433_audio_retention_regs[] = {
EXYNOS5433_PAD_RETENTION_AUD_OPTION,
};
static const struct samsung_retention_data exynos5433_audio_retention_data __initconst = {
.regs = exynos5433_audio_retention_regs,
.nr_regs = ARRAY_SIZE(exynos5433_audio_retention_regs),
.value = EXYNOS_WAKEUP_FROM_LOWPWR,
.init = exynos_retention_init,
};
/* PMU retention control for mmc pins can be tied to fsys pin bank */
static const u32 exynos5433_fsys_retention_regs[] = {
EXYNOS5433_PAD_RETENTION_MMC0_OPTION,
EXYNOS5433_PAD_RETENTION_MMC1_OPTION,
EXYNOS5433_PAD_RETENTION_MMC2_OPTION,
};
static const struct samsung_retention_data exynos5433_fsys_retention_data __initconst = {
.regs = exynos5433_fsys_retention_regs,
.nr_regs = ARRAY_SIZE(exynos5433_fsys_retention_regs),
.value = EXYNOS_WAKEUP_FROM_LOWPWR,
.init = exynos_retention_init,
};
/*
* Samsung pinctrl driver data for Exynos5433 SoC. Exynos5433 SoC includes
* ten gpio/pin-mux/pinconfig controllers.
......@@ -1559,6 +1612,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.nr_ext_resources = 1,
.retention_data = &exynos5433_retention_data,
}, {
/* pin-controller instance 1 data */
.pin_banks = exynos5433_pin_banks1,
......@@ -1566,6 +1620,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_audio_retention_data,
}, {
/* pin-controller instance 2 data */
.pin_banks = exynos5433_pin_banks2,
......@@ -1573,6 +1628,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_retention_data,
}, {
/* pin-controller instance 3 data */
.pin_banks = exynos5433_pin_banks3,
......@@ -1580,6 +1636,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_retention_data,
}, {
/* pin-controller instance 4 data */
.pin_banks = exynos5433_pin_banks4,
......@@ -1587,6 +1644,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_retention_data,
}, {
/* pin-controller instance 5 data */
.pin_banks = exynos5433_pin_banks5,
......@@ -1594,6 +1652,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_fsys_retention_data,
}, {
/* pin-controller instance 6 data */
.pin_banks = exynos5433_pin_banks6,
......@@ -1601,6 +1660,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_retention_data,
}, {
/* pin-controller instance 7 data */
.pin_banks = exynos5433_pin_banks7,
......@@ -1608,6 +1668,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_retention_data,
}, {
/* pin-controller instance 8 data */
.pin_banks = exynos5433_pin_banks8,
......@@ -1615,6 +1676,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_retention_data,
}, {
/* pin-controller instance 9 data */
.pin_banks = exynos5433_pin_banks9,
......@@ -1622,6 +1684,7 @@ const struct samsung_pin_ctrl exynos5433_pin_ctrl[] __initconst = {
.eint_gpio_init = exynos_eint_gpio_init,
.suspend = exynos_pinctrl_suspend,
.resume = exynos_pinctrl_resume,
.retention_data = &exynos5433_retention_data,
},
};
......
......@@ -882,7 +882,7 @@ static int samsung_pinctrl_register(struct platform_device *pdev,
pin_bank->grange.id = bank;
pin_bank->grange.pin_base = drvdata->pin_base
+ pin_bank->pin_base;
pin_bank->grange.base = pin_bank->gpio_chip.base;
pin_bank->grange.base = pin_bank->grange.pin_base;
pin_bank->grange.npins = pin_bank->gpio_chip.ngpio;
pin_bank->grange.gc = &pin_bank->gpio_chip;
pinctrl_add_gpio_range(drvdata->pctl_dev, &pin_bank->grange);
......@@ -891,6 +891,19 @@ static int samsung_pinctrl_register(struct platform_device *pdev,
return 0;
}
/* unregister the pinctrl interface with the pinctrl subsystem */
static int samsung_pinctrl_unregister(struct platform_device *pdev,
struct samsung_pinctrl_drv_data *drvdata)
{
struct samsung_pin_bank *bank = drvdata->pin_banks;
int i;
for (i = 0; i < drvdata->nr_banks; ++i, ++bank)
pinctrl_remove_gpio_range(drvdata->pctl_dev, &bank->grange);
return 0;
}
static const struct gpio_chip samsung_gpiolib_chip = {
.request = gpiochip_generic_request,
.free = gpiochip_generic_free,
......@@ -915,39 +928,21 @@ static int samsung_gpiolib_register(struct platform_device *pdev,
bank->gpio_chip = samsung_gpiolib_chip;
gc = &bank->gpio_chip;
gc->base = drvdata->pin_base + bank->pin_base;
gc->base = bank->grange.base;
gc->ngpio = bank->nr_pins;
gc->parent = &pdev->dev;
gc->of_node = bank->of_node;
gc->label = bank->name;
ret = gpiochip_add_data(gc, bank);
ret = devm_gpiochip_add_data(&pdev->dev, gc, bank);
if (ret) {
dev_err(&pdev->dev, "failed to register gpio_chip %s, error code: %d\n",
gc->label, ret);
goto fail;
return ret;
}
}
return 0;
fail:
for (--i, --bank; i >= 0; --i, --bank)
gpiochip_remove(&bank->gpio_chip);
return ret;
}
/* unregister the gpiolib interface with the gpiolib subsystem */
static int samsung_gpiolib_unregister(struct platform_device *pdev,
struct samsung_pinctrl_drv_data *drvdata)
{
struct samsung_pin_bank *bank = drvdata->pin_banks;
int i;
for (i = 0; i < drvdata->nr_banks; ++i, ++bank)
gpiochip_remove(&bank->gpio_chip);
return 0;
}
/* retrieve the soc specific data */
......@@ -1060,13 +1055,13 @@ static int samsung_pinctrl_probe(struct platform_device *pdev)
return PTR_ERR(drvdata->retention_ctrl);
}
ret = samsung_gpiolib_register(pdev, drvdata);
ret = samsung_pinctrl_register(pdev, drvdata);
if (ret)
return ret;
ret = samsung_pinctrl_register(pdev, drvdata);
ret = samsung_gpiolib_register(pdev, drvdata);
if (ret) {
samsung_gpiolib_unregister(pdev, drvdata);
samsung_pinctrl_unregister(pdev, drvdata);
return ret;
}
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment