aboutsummaryrefslogtreecommitdiff
path: root/drivers/gpio/gpio-xilinx.c
diff options
context:
space:
mode:
authorLinus Torvalds <[email protected]>2020-12-17 18:07:20 -0800
committerLinus Torvalds <[email protected]>2020-12-17 18:07:20 -0800
commita409ed156a90093a03fe6a93721ddf4c591eac87 (patch)
tree2a3c6f6f81c8b233627cf14da7149c7f312b475e /drivers/gpio/gpio-xilinx.c
parent345b17acb1aa7a443741d9220f66b30d5ddd7c39 (diff)
parent7ac554888233468a9fd7c4f28721396952dd9959 (diff)
Merge tag 'gpio-v5.11-1' of git://git.kernel.org/pub/scm/linux/kernel/git/linusw/linux-gpio
Pull GPIO updates from Linus Walleij: "This is the bulk of the GPIO changes for the v5.11 kernel cycle: Core changes: - Retired the old set-up function for GPIO IRQ chips. All chips now use the template struct gpio_irq_chip and pass that to the core to be set up alongside the gpio_chip. We can finally get rid of the old cruft. - Some refactoring and clean up of the core code. - Support edge event timestamps to be stamped using REALTIME (wall clock) timestamps. We have found solid use cases for this, so we support it. New drivers: - MStar MSC313 GPIO driver. - HiSilicon GPIO driver. Driver improvements: - The PCA953x driver now also supports the NXP PCAL9554B/C chips. - The mockup driver can now be probed from the device tree which is pretty useful for virtual prototyping of devices. - The Rcar driver now supports .get_multiple() - The MXC driver dropped some legacy and became a pure device tree client. - The Exar driver was moved over to the IDA interface for enumerating, and also switched over to using regmap for register access" * tag 'gpio-v5.11-1' of git://git.kernel.org/pub/scm/linux/kernel/git/linusw/linux-gpio: (87 commits) MAINTAINERS: Remove reference to non-existing file gpio: hisi: Do not require ACPI for COMPILE_TEST MAINTAINERS: Add maintainer for HiSilicon GPIO driver gpio: gpio-hisi: Add HiSilicon GPIO support gpio: cs5535: Simplify the return expression of cs5535_gpio_probe() gpiolib: irq hooks: fix recursion in gpiochip_irq_unmask dt-bindings: mt7621-gpio: convert bindings to YAML format gpiolib: cdev: Flag invalid GPIOs as used gpio: put virtual gpio device into their own submenu drivers: gpio: amd8111: use SPDX-License-Identifier drivers: gpio: amd8111: prefer dev_err()/dev_info() over raw printk drivers: gpio: bt8xx: prefer dev_err()/dev_warn() over of raw printk gpio: Add TODO item for debugfs interface gpio: just plain warning when nonexisting gpio requested tools: gpio: add option to report wall-clock time to gpio-event-mon tools: gpio: add support for reporting realtime event clock to lsgpio gpiolib: cdev: allow edge event timestamps to be configured as REALTIME gpio: msc313: MStar MSC313 GPIO driver dt-bindings: gpio: Binding for MStar MSC313 GPIO controller dt-bindings: gpio: Add a binding header for the MSC313 GPIO driver ...
Diffstat (limited to 'drivers/gpio/gpio-xilinx.c')
-rw-r--r--drivers/gpio/gpio-xilinx.c49
1 files changed, 43 insertions, 6 deletions
diff --git a/drivers/gpio/gpio-xilinx.c b/drivers/gpio/gpio-xilinx.c
index 67f9f82e0db0..be539381fd82 100644
--- a/drivers/gpio/gpio-xilinx.c
+++ b/drivers/gpio/gpio-xilinx.c
@@ -6,13 +6,14 @@
*/
#include <linux/bitops.h>
-#include <linux/init.h>
+#include <linux/clk.h>
#include <linux/errno.h>
+#include <linux/gpio/driver.h>
+#include <linux/init.h>
+#include <linux/io.h>
#include <linux/module.h>
#include <linux/of_device.h>
#include <linux/of_platform.h>
-#include <linux/io.h>
-#include <linux/gpio/driver.h>
#include <linux/slab.h>
/* Register Offset Definitions */
@@ -38,6 +39,7 @@
* @gpio_state: GPIO state shadow register
* @gpio_dir: GPIO direction shadow register
* @gpio_lock: Lock used for synchronization
+ * @clk: clock resource for this driver
*/
struct xgpio_instance {
struct gpio_chip gc;
@@ -46,6 +48,7 @@ struct xgpio_instance {
u32 gpio_state[2];
u32 gpio_dir[2];
spinlock_t gpio_lock[2];
+ struct clk *clk;
};
static inline int xgpio_index(struct xgpio_instance *chip, int gpio)
@@ -257,6 +260,23 @@ static void xgpio_save_regs(struct xgpio_instance *chip)
}
/**
+ * xgpio_remove - Remove method for the GPIO device.
+ * @pdev: pointer to the platform device
+ *
+ * This function remove gpiochips and frees all the allocated resources.
+ *
+ * Return: 0 always
+ */
+static int xgpio_remove(struct platform_device *pdev)
+{
+ struct xgpio_instance *gpio = platform_get_drvdata(pdev);
+
+ clk_disable_unprepare(gpio->clk);
+
+ return 0;
+}
+
+/**
* xgpio_of_probe - Probe method for the GPIO device.
* @pdev: pointer to the platform device
*
@@ -278,7 +298,8 @@ static int xgpio_probe(struct platform_device *pdev)
platform_set_drvdata(pdev, chip);
/* Update GPIO state shadow register with default value */
- of_property_read_u32(np, "xlnx,dout-default", &chip->gpio_state[0]);
+ if (of_property_read_u32(np, "xlnx,dout-default", &chip->gpio_state[0]))
+ chip->gpio_state[0] = 0x0;
/* Update GPIO direction shadow register with default value */
if (of_property_read_u32(np, "xlnx,tri-default", &chip->gpio_dir[0]))
@@ -298,8 +319,9 @@ static int xgpio_probe(struct platform_device *pdev)
if (is_dual) {
/* Update GPIO state shadow register with default value */
- of_property_read_u32(np, "xlnx,dout-default-2",
- &chip->gpio_state[1]);
+ if (of_property_read_u32(np, "xlnx,dout-default-2",
+ &chip->gpio_state[1]))
+ chip->gpio_state[1] = 0x0;
/* Update GPIO direction shadow register with default value */
if (of_property_read_u32(np, "xlnx,tri-default-2",
@@ -334,11 +356,25 @@ static int xgpio_probe(struct platform_device *pdev)
return PTR_ERR(chip->regs);
}
+ chip->clk = devm_clk_get_optional(&pdev->dev, NULL);
+ if (IS_ERR(chip->clk)) {
+ if (PTR_ERR(chip->clk) != -EPROBE_DEFER)
+ dev_dbg(&pdev->dev, "Input clock not found\n");
+ return PTR_ERR(chip->clk);
+ }
+
+ status = clk_prepare_enable(chip->clk);
+ if (status < 0) {
+ dev_err(&pdev->dev, "Failed to prepare clk\n");
+ return status;
+ }
+
xgpio_save_regs(chip);
status = devm_gpiochip_add_data(&pdev->dev, &chip->gc, chip);
if (status) {
dev_err(&pdev->dev, "failed to add GPIO chip\n");
+ clk_disable_unprepare(chip->clk);
return status;
}
@@ -354,6 +390,7 @@ MODULE_DEVICE_TABLE(of, xgpio_of_match);
static struct platform_driver xgpio_plat_driver = {
.probe = xgpio_probe,
+ .remove = xgpio_remove,
.driver = {
.name = "gpio-xilinx",
.of_match_table = xgpio_of_match,