diff options
| author | Olof Johansson <olof@lixom.net> | 2012-09-20 19:36:37 -0400 |
|---|---|---|
| committer | Olof Johansson <olof@lixom.net> | 2012-09-20 19:36:37 -0400 |
| commit | fc0b60ae951fab238244ed6c72bccbb66725544f (patch) | |
| tree | 660eb51d45129f5b5147c7188fc48b87a1c76a61 | |
| parent | 2843c7d2c03da38dfb14102254d0c767d2483349 (diff) | |
| parent | 172c6a13653ac8cd6a231293b87c93821e90c1d6 (diff) | |
Merge branch 'next/gpio-samsung' of git://git.kernel.org/pub/scm/linux/kernel/git/kgene/linux-samsung into next/dt
From Kukjin Kim:
Since there are many changes for gpio-samsung in my tree, this has been
included in my tree with Linus' agreement.
* 'next/gpio-samsung' of git://git.kernel.org/pub/scm/linux/kernel/git/kgene/linux-samsung:
gpio: samsung: add devicetree init for s3c24xx arches
| -rw-r--r-- | Documentation/devicetree/bindings/gpio/gpio-samsung.txt | 43 | ||||
| -rw-r--r-- | drivers/gpio/gpio-samsung.c | 63 |
2 files changed, 106 insertions, 0 deletions
diff --git a/Documentation/devicetree/bindings/gpio/gpio-samsung.txt b/Documentation/devicetree/bindings/gpio/gpio-samsung.txt index 5375625e8cd2..f1e5dfecf55d 100644 --- a/Documentation/devicetree/bindings/gpio/gpio-samsung.txt +++ b/Documentation/devicetree/bindings/gpio/gpio-samsung.txt | |||
| @@ -39,3 +39,46 @@ Example: | |||
| 39 | #gpio-cells = <4>; | 39 | #gpio-cells = <4>; |
| 40 | gpio-controller; | 40 | gpio-controller; |
| 41 | }; | 41 | }; |
| 42 | |||
| 43 | |||
| 44 | Samsung S3C24XX GPIO Controller | ||
| 45 | |||
| 46 | Required properties: | ||
| 47 | - compatible: Compatible property value should be "samsung,s3c24xx-gpio". | ||
| 48 | |||
| 49 | - reg: Physical base address of the controller and length of memory mapped | ||
| 50 | region. | ||
| 51 | |||
| 52 | - #gpio-cells: Should be 3. The syntax of the gpio specifier used by client nodes | ||
| 53 | should be the following with values derived from the SoC user manual. | ||
| 54 | <[phandle of the gpio controller node] | ||
| 55 | [pin number within the gpio controller] | ||
| 56 | [mux function] | ||
| 57 | [flags and pull up/down] | ||
| 58 | |||
| 59 | Values for gpio specifier: | ||
| 60 | - Pin number: depending on the controller a number from 0 up to 15. | ||
| 61 | - Mux function: Depending on the SoC and the gpio bank the gpio can be set | ||
| 62 | as input, output or a special function | ||
| 63 | - Flags and Pull Up/Down: the values to use differ for the individual SoCs | ||
| 64 | example S3C2416/S3C2450: | ||
| 65 | 0 - Pull Up/Down Disabled. | ||
| 66 | 1 - Pull Down Enabled. | ||
| 67 | 2 - Pull Up Enabled. | ||
| 68 | Bit 16 (0x00010000) - Input is active low. | ||
| 69 | Consult the user manual for the correct values of Mux and Pull Up/Down. | ||
| 70 | |||
| 71 | - gpio-controller: Specifies that the node is a gpio controller. | ||
| 72 | - #address-cells: should be 1. | ||
| 73 | - #size-cells: should be 1. | ||
| 74 | |||
| 75 | Example: | ||
| 76 | |||
| 77 | gpa: gpio-controller@56000000 { | ||
| 78 | #address-cells = <1>; | ||
| 79 | #size-cells = <1>; | ||
| 80 | compatible = "samsung,s3c24xx-gpio"; | ||
| 81 | reg = <0x56000000 0x10>; | ||
| 82 | #gpio-cells = <3>; | ||
| 83 | gpio-controller; | ||
| 84 | }; | ||
diff --git a/drivers/gpio/gpio-samsung.c b/drivers/gpio/gpio-samsung.c index ba126cc04073..f4814a889a5b 100644 --- a/drivers/gpio/gpio-samsung.c +++ b/drivers/gpio/gpio-samsung.c | |||
| @@ -938,6 +938,67 @@ static void __init samsung_gpiolib_add(struct samsung_gpio_chip *chip) | |||
| 938 | s3c_gpiolib_track(chip); | 938 | s3c_gpiolib_track(chip); |
| 939 | } | 939 | } |
| 940 | 940 | ||
| 941 | #if defined(CONFIG_PLAT_S3C24XX) && defined(CONFIG_OF) | ||
| 942 | static int s3c24xx_gpio_xlate(struct gpio_chip *gc, | ||
| 943 | const struct of_phandle_args *gpiospec, u32 *flags) | ||
| 944 | { | ||
| 945 | unsigned int pin; | ||
| 946 | |||
| 947 | if (WARN_ON(gc->of_gpio_n_cells < 3)) | ||
| 948 | return -EINVAL; | ||
| 949 | |||
| 950 | if (WARN_ON(gpiospec->args_count < gc->of_gpio_n_cells)) | ||
| 951 | return -EINVAL; | ||
| 952 | |||
| 953 | if (gpiospec->args[0] > gc->ngpio) | ||
| 954 | return -EINVAL; | ||
| 955 | |||
| 956 | pin = gc->base + gpiospec->args[0]; | ||
| 957 | |||
| 958 | if (s3c_gpio_cfgpin(pin, S3C_GPIO_SFN(gpiospec->args[1]))) | ||
| 959 | pr_warn("gpio_xlate: failed to set pin function\n"); | ||
| 960 | if (s3c_gpio_setpull(pin, gpiospec->args[2] & 0xffff)) | ||
| 961 | pr_warn("gpio_xlate: failed to set pin pull up/down\n"); | ||
| 962 | |||
| 963 | if (flags) | ||
| 964 | *flags = gpiospec->args[2] >> 16; | ||
| 965 | |||
| 966 | return gpiospec->args[0]; | ||
| 967 | } | ||
| 968 | |||
| 969 | static const struct of_device_id s3c24xx_gpio_dt_match[] __initdata = { | ||
| 970 | { .compatible = "samsung,s3c24xx-gpio", }, | ||
| 971 | {} | ||
| 972 | }; | ||
| 973 | |||
| 974 | static __init void s3c24xx_gpiolib_attach_ofnode(struct samsung_gpio_chip *chip, | ||
| 975 | u64 base, u64 offset) | ||
| 976 | { | ||
| 977 | struct gpio_chip *gc = &chip->chip; | ||
| 978 | u64 address; | ||
| 979 | |||
| 980 | if (!of_have_populated_dt()) | ||
| 981 | return; | ||
| 982 | |||
| 983 | address = chip->base ? base + ((u32)chip->base & 0xfff) : base + offset; | ||
| 984 | gc->of_node = of_find_matching_node_by_address(NULL, | ||
| 985 | s3c24xx_gpio_dt_match, address); | ||
| 986 | if (!gc->of_node) { | ||
| 987 | pr_info("gpio: device tree node not found for gpio controller" | ||
| 988 | " with base address %08llx\n", address); | ||
| 989 | return; | ||
| 990 | } | ||
| 991 | gc->of_gpio_n_cells = 3; | ||
| 992 | gc->of_xlate = s3c24xx_gpio_xlate; | ||
| 993 | } | ||
| 994 | #else | ||
| 995 | static __init void s3c24xx_gpiolib_attach_ofnode(struct samsung_gpio_chip *chip, | ||
| 996 | u64 base, u64 offset) | ||
| 997 | { | ||
| 998 | return; | ||
| 999 | } | ||
| 1000 | #endif /* defined(CONFIG_PLAT_S3C24XX) && defined(CONFIG_OF) */ | ||
| 1001 | |||
| 941 | static void __init s3c24xx_gpiolib_add_chips(struct samsung_gpio_chip *chip, | 1002 | static void __init s3c24xx_gpiolib_add_chips(struct samsung_gpio_chip *chip, |
| 942 | int nr_chips, void __iomem *base) | 1003 | int nr_chips, void __iomem *base) |
| 943 | { | 1004 | { |
| @@ -962,6 +1023,8 @@ static void __init s3c24xx_gpiolib_add_chips(struct samsung_gpio_chip *chip, | |||
| 962 | gc->direction_output = samsung_gpiolib_2bit_output; | 1023 | gc->direction_output = samsung_gpiolib_2bit_output; |
| 963 | 1024 | ||
| 964 | samsung_gpiolib_add(chip); | 1025 | samsung_gpiolib_add(chip); |
| 1026 | |||
| 1027 | s3c24xx_gpiolib_attach_ofnode(chip, S3C24XX_PA_GPIO, i * 0x10); | ||
| 965 | } | 1028 | } |
| 966 | } | 1029 | } |
| 967 | 1030 | ||
