Linux-ARM-Kernel Archive on lore.kernel.org
 help / color / mirror / Atom feed
* [PATCHv2] Add GPIO driver for Allwinner SoCs
From: Maxime Ripard @ 2013-01-23  9:34 UTC (permalink / raw)
  To: linux-arm-kernel

Hi,

This patch adds support for the GPIOs for the Allwinner SoCs supported so
far.

It comes on top of my previous pinctrl patchset, and has been tested on a
A13-Olinuxino from Olimex.

Thanks,
Maxime

Changes from v1:
  - Merged the gpio driver with the pinctrl one
  - Now using gpiochip_add_pin_range instead of pinctrl_add_gpio_range
  - Removed the hairy range registration function, and register 1pin ranges
    instead

Maxime Ripard (1):
  ARM: sunxi: gpio: Add Allwinner SoCs GPIO drivers

 drivers/pinctrl/pinctrl-sunxi.c |  138 ++++++++++++++++++++++++++++++++++++++-
 drivers/pinctrl/pinctrl-sunxi.h |   23 ++++++-
 2 files changed, 158 insertions(+), 3 deletions(-)

-- 
1.7.10.4

^ permalink raw reply

* [v3 2/2] ARM: tegra: Skip scu_enable(scu_base) if not Cortex A9
From: Hiroshi Doyu @ 2013-01-23  9:27 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20130123.080457.171573168772211248.hdoyu@nvidia.com>

Hiroshi Doyu <hdoyu@nvidia.com> wrote @ Wed, 23 Jan 2013 08:04:57 +0200 (EET):

> Stephen Warren <swarren@wwwdotorg.org> wrote @ Tue, 22 Jan 2013 17:57:39 +0100:
> 
> > Hiroshi, is this series the only dependency you need for your
> > Tegra114
> 
> Basically yes.
> 
> > series? So, I could merge your Tegra114 series once this series is applied?
> 
> But now "CCF" seems to be in. Then, the HACK(*1) needs to be replaced
> with "Tegra114 CCF". But "Tegra114 CCF" doesn't seem ready yet. I'll check
> if this Tegra114 series would work without "Tegra114 CCF".
> 
> *1: http://patchwork.ozlabs.org/patch/212010/

Stephen,

Verified "Tegra114 series" worked with "for-3.9/soc" branch(inc CCF)
with a little tweak.

I can post Tegra114 series again. If you want them rebased onto
another branch, let me know.

^ permalink raw reply

* [PATCH 1/4] arch: arm: gpmc: gpmc migration support
From: Philip Avinash @ 2013-01-23  9:26 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358933176-12409-1-git-send-email-avinashphilip@ti.com>

With recent GPMC driver conversion, usage of gpmc_save/restore_context
can done from gpmc driver itself. Hence removes the usage from pm34xx.c.
Also removes the conditional compilation primitives ARCH_OMAP3 for
gpmc_save/restore_context.

Signed-off-by: Philip Avinash <avinashphilip@ti.com>
---
 arch/arm/mach-omap2/gpmc.c   |    2 --
 arch/arm/mach-omap2/pm34xx.c |    5 -----
 2 files changed, 7 deletions(-)

diff --git a/arch/arm/mach-omap2/gpmc.c b/arch/arm/mach-omap2/gpmc.c
index cbf4e0d..aed958a 100644
--- a/arch/arm/mach-omap2/gpmc.c
+++ b/arch/arm/mach-omap2/gpmc.c
@@ -1426,7 +1426,6 @@ static irqreturn_t gpmc_handle_irq(int irq, void *dev)
 	return IRQ_HANDLED;
 }
 
-#ifdef CONFIG_ARCH_OMAP3
 static struct omap3_gpmc_regs gpmc_context;
 
 void omap3_gpmc_save_context(void)
@@ -1491,4 +1490,3 @@ void omap3_gpmc_restore_context(void)
 		}
 	}
 }
-#endif /* CONFIG_ARCH_OMAP3 */
diff --git a/arch/arm/mach-omap2/pm34xx.c b/arch/arm/mach-omap2/pm34xx.c
index 60fbf0a..cab4c5d 100644
--- a/arch/arm/mach-omap2/pm34xx.c
+++ b/arch/arm/mach-omap2/pm34xx.c
@@ -43,7 +43,6 @@
 #include "common.h"
 #include "cm3xxx.h"
 #include "cm-regbits-34xx.h"
-#include "gpmc.h"
 #include "prm-regbits-34xx.h"
 #include "prm3xxx.h"
 #include "pm.h"
@@ -84,8 +83,6 @@ static void omap3_core_save_context(void)
 
 	/* Save the Interrupt controller context */
 	omap_intc_save_context();
-	/* Save the GPMC context */
-	omap3_gpmc_save_context();
 	/* Save the system control module context, padconf already save above*/
 	omap3_control_save_context();
 	omap_dma_global_context_save();
@@ -95,8 +92,6 @@ static void omap3_core_restore_context(void)
 {
 	/* Restore the control module context, padconf restored by h/w */
 	omap3_control_restore_context();
-	/* Restore the GPMC context */
-	omap3_gpmc_restore_context();
 	/* Restore the interrupt controller context */
 	omap_intc_restore_context();
 	omap_dma_global_context_restore();
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH 0/4] LOW power sleep support for OMAP nand driver
From: Philip Avinash @ 2013-01-23  9:26 UTC (permalink / raw)
  To: linux-arm-kernel

This patch series adds low power transition support for OMAP NAND driver.
This includes low power transition support of
- GPMC module
- ELM module
- OMAP2 NAND driver

Low power transition support tested on am335x-evm with NAND flash support.
This patch series based on [1] and depends on [2] and is available [2]

1. ARM: OMAP2+: AM33XX: Add suspend-resume support
   http://comments.gmane.org/gmane.linux.ports.arm.omap/91405
2. https://github.com/avinashphilip/am335x_linux/commits/NAND_supend_resume_support

Philip Avinash (4):
  arch: arm: gpmc: gpmc migration support
  mtd: devices: elm: Low power transition support
  arm: gpmc: Low power transition support
  mtd: nand: omap2: Low power transition support

 arch/arm/mach-omap2/gpmc.c   |   22 ++++++++++++++++++++--
 arch/arm/mach-omap2/pm34xx.c |    5 -----
 drivers/mtd/devices/elm.c    |   40 ++++++++++++++++++++++++++++++++++++++++
 drivers/mtd/nand/omap2.c     |   19 +++++++++++++++++++
 4 files changed, 79 insertions(+), 7 deletions(-)

-- 
1.7.9.5

^ permalink raw reply

* arm: Kernel failures when several memory banks are used with starting address above 128MB
From: Russell King - ARM Linux @ 2013-01-23  9:15 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <CAHTX3dJZxuoz_0Eaa7QcoK9bF4LdLuWcDcwK3OUKc6qY_0PeuQ@mail.gmail.com>

On Tue, Jan 22, 2013 at 08:18:13PM +0100, Michal Simek wrote:
> I have a question regarding to the case where DTS specify one memory bank
> for example <0x0 0x40000000> with CONFIG_ARM_PATCH_PHYS_VIRT=y
> where the kernel can be loaded at a 16MB boundary.

That's where you're going wrong.  We assume that the kernel is loaded
within the 16MB of memory _always_.  Can't get around this on a
multiplatform kernel.

^ permalink raw reply

* [GIT PULL][for 3.9] request from pxa git tree on armsoc/board branch
From: Haojian Zhuang @ 2013-01-23  9:15 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Arnd & Olof,

Please help to merge armsoc/board branch from pxa git tree.

Regards
Haojian

The following changes since commit 7d1f9aeff1ee4a20b1aeb377dd0f579fe9647619:

  Linux 3.8-rc4 (2013-01-17 19:25:45 -0800)

are available in the git repository at:

  git://github.com/hzhuang1/linux.git armsoc/board

for you to fetch changes up to 495b21dc0e488b784ab1d4007d00db1ca2a95c98:

  ARM: pxa: pxa27x.c: add dummy SA1100 rtc clock (2013-01-23 17:05:08 +0800)

----------------------------------------------------------------
Andrea Adami (1):
      ARM: pxa: pxa27x.c: add dummy SA1100 rtc clock

Mike Dunn (2):
      ARM: palmtreo: add docg4 device initialization
      ARM: palmtreo: replace #if defined with IF_ENABLED

 arch/arm/mach-pxa/palmtreo.c |   35 +++++++++++++++++++++++++++++++++--
 arch/arm/mach-pxa/pxa27x.c   |    1 +
 2 files changed, 34 insertions(+), 2 deletions(-)

^ permalink raw reply

* [GIT PULL][for 3.8] request from armsoc/fix branch in pxa git tree
From: Haojian Zhuang @ 2013-01-23  9:15 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Arnd & Olof,

Please help to pull armsoc/fix branch in pxa git tree.

Regards
Haojian

The following changes since commit 7d1f9aeff1ee4a20b1aeb377dd0f579fe9647619:

  Linux 3.8-rc4 (2013-01-17 19:25:45 -0800)

are available in the git repository at:

  git://github.com/hzhuang1/linux.git armsoc/fix

for you to fetch changes up to eea6e39b916dd282c7fa4629be8934b5ad60e62b:

  ARM: pxa: Minor naming fixes in spitz.c (2013-01-23 17:13:07 +0800)

----------------------------------------------------------------
Igor Grinberg (1):
      ARM: PXA3xx: program the CSMSADRCFG register

Marko Katic (1):
      ARM: pxa: Minor naming fixes in spitz.c

Mike Dunn (2):
      ARM: palmtreo: fix lcd initilialization on treo680
      ARM: palmtreo: fix #ifdefs for leds-gpio device

 arch/arm/mach-pxa/include/mach/palmtreo.h |    5 +++--
 arch/arm/mach-pxa/include/mach/smemc.h    |    1 +
 arch/arm/mach-pxa/palmtreo.c              |   70
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++----------
 arch/arm/mach-pxa/smemc.c                 |   15 ++++++++++++++-
 arch/arm/mach-pxa/spitz.c                 |    4 ++--
 5 files changed, 80 insertions(+), 15 deletions(-)

^ permalink raw reply

* [PATCH] ARM: pxa: pxa27x.c: add dummy SA1100 rtc clock
From: Haojian Zhuang @ 2013-01-23  9:05 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <87ehjh3man.fsf@free.fr>

On Sun, Nov 25, 2012 at 8:21 PM, Robert Jarzmik <robert.jarzmik@free.fr> wrote:
> Acked-by: Robert Jarzmik <robert.jarzmik@free.fr>

Applied.

Thanks
Haojian

^ permalink raw reply

* [PATCH v3 1/2] mtd: Add a common JEDEC flash device table
From: Matthieu CASTET @ 2013-01-23  9:00 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358928068-12417-2-git-send-email-linux@prisktech.co.nz>

Tony Prisk a ?crit :
> This patch adds a common JEDEC flash device table which can be
> expanded on as more features are required.
> 
> A simple match function is also included to query the table for
> a match based on the JEDEC id.

Why don't you use id from include/linux/mtd/cfi.h that is used by flash driver
like drivers/mtd/devices/m25p80.c ?


#define CFI_MFR_AMD     0x0001
#define CFI_MFR_AMIC        0x0037
#define CFI_MFR_ATMEL       0x001F
#define CFI_MFR_EON     0x001C
#define CFI_MFR_FUJITSU     0x0004
#define CFI_MFR_HYUNDAI     0x00AD
#define CFI_MFR_INTEL       0x0089
#define CFI_MFR_MACRONIX    0x00C2
#define CFI_MFR_NEC     0x0010
#define CFI_MFR_PMC     0x009D
#define CFI_MFR_SAMSUNG     0x00EC
#define CFI_MFR_SHARP       0x00B0
#define CFI_MFR_SST     0x00BF
#define CFI_MFR_ST      0x0020 /* STMicroelectronics */
#define CFI_MFR_TOSHIBA     0x0098
#define CFI_MFR_WINBOND     0x00DA


> 
> Signed-off-by: Tony Prisk <linux@prisktech.co.nz>
> ---
>  drivers/mtd/devices/flash_jedec.c |   96 +++++++++++++++++++++++++++++++++++++
>  drivers/mtd/devices/flash_jedec.h |   30 ++++++++++++
>  2 files changed, 126 insertions(+)
>  create mode 100644 drivers/mtd/devices/flash_jedec.c
>  create mode 100644 drivers/mtd/devices/flash_jedec.h
> 
> diff --git a/drivers/mtd/devices/flash_jedec.c b/drivers/mtd/devices/flash_jedec.c
> new file mode 100644
> index 0000000..c0b2272
> --- /dev/null
> +++ b/drivers/mtd/devices/flash_jedec.c
> @@ -0,0 +1,96 @@
> +/*
> + * Copyright Tony Prisk <linux@prisktech.co.nz>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License as published by
> + * the Free Software Foundation; either version 2 of the License, or
> + * (at your option) any later version.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, write to the Free Software
> + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
> + */
> +
> +#include <linux/bug.h>
> +#include <linux/err.h>
> +#include <linux/kernel.h>
> +#include <linux/types.h>
> +
> +#include "flash_jedec.h"
> +
> +/*
> + * Device Manufacturer IDs
> + * Please keep sorted by manufacturer ID
> + */
> +#define MFR_SPANSION		0X01
> +#define MFR_EON			0X1C
> +#define MFR_ATMEL		0X1F
> +#define MFR_MICRON		0X20	/* Also Numonyx & STM */
> +#define MFR_INTEL		0x89
> +#define MFR_FUDAN		0XA1
> +#define MFR_SST			0XBF
> +#define MFR_MXIC		0XC2
> +#define MFR_WINBOND		0XEF
> +
> +#define _ID(m, d)	((m << 16) | d)
> +
> +/*
> + * Flash device information
> + * Please keep sorted by manufacturer id, then device id
> + */
> +static struct flash_device_info flash_devices[] = {
> +	/* Spansion */
> +	{ "s25fl016", _ID(MFR_SPANSION, 0x0214), 2048 },
> +	{ "s25fl064", _ID(MFR_SPANSION, 0x0216), 8192 },
> +	/* EON */
> +	{ "en25p16", _ID(MFR_EON, 0x2015), 2048 },
> +	{ "en25p64", _ID(MFR_EON, 0x2017), 8192 },
> +	{ "en25f40", _ID(MFR_EON, 0x3113),  512 },
> +	{ "en25f16", _ID(MFR_EON, 0x3115), 2048 },
> +	/* ATMEL */
> +	{ "at25df041a", _ID(MFR_ATMEL, 0x4401), 512 },
> +	/* Micron, STM & Numonyx */
> +	{ "stm25p16", _ID(MFR_MICRON, 0x2015), 2048 },
> +	{ "stm25p64", _ID(MFR_MICRON, 0x2017), 8192 },
> +	/* Fudan */
> +	{ "fm25f04", _ID(MFR_FUDAN, 0x3113), 512 },
> +	/* SST */
> +	{ "sst25vf016b", _ID(MFR_SST, 0x2541), 2048 },
> +	/* Macronix - MXIC */
> +	{ "mx25l512",   _ID(MFR_MXIC, 0x2010),    64 },
> +	{ "mx25l4005",  _ID(MFR_MXIC, 0x2013),   512 },
> +	{ "mx25l1605",  _ID(MFR_MXIC, 0x2015),  2048 },
> +	{ "mx25l3205",  _ID(MFR_MXIC, 0x2016),  4096 },
> +	{ "mx25l6405",  _ID(MFR_MXIC, 0x2017),  8192 },
> +	{ "mx25l12805", _ID(MFR_MXIC, 0x2018), 16384 },
> +	{ "mx25l1635",  _ID(MFR_MXIC, 0x2415),  2048 },
> +	{ "mx25l3235",  _ID(MFR_MXIC, 0x5E16),  4096 },
> +	/* Winbond */
> +	{ "w25x40", _ID(MFR_WINBOND, 0x3013),   512 },
> +	{ "w25x16", _ID(MFR_WINBOND, 0x3015),  2048 },
> +	{ "w25x32", _ID(MFR_WINBOND, 0x3016),  4096 },
> +	{ "w25x64", _ID(MFR_WINBOND, 0x3017),  8192 },
> +};
> +
> +/*
> + * jedec_match_device - match a jedec id against the flash_devices table
> + * @jedecid: JEDEC formatted id to match
> + *	bits 16..24: manufacturer id
> + *	bits  0..15: device id
> + * Returns a valid flash_device_info* or ERR_PTR(-ENODEV) if an entry is
> + * not found
> + */
> +struct flash_device_info *jedec_match_device(u32 jedec_id)
> +{
> +	int i;
> +	for (i = 0; i < ARRAY_SIZE(flash_devices); i++)
> +		if (flash_devices[i].jedec_id == jedec_id)
> +			return &flash_devices[i];
> +
> +	return ERR_PTR(-ENODEV);
> +}
> diff --git a/drivers/mtd/devices/flash_jedec.h b/drivers/mtd/devices/flash_jedec.h
> new file mode 100644
> index 0000000..27b978a
> --- /dev/null
> +++ b/drivers/mtd/devices/flash_jedec.h
> @@ -0,0 +1,30 @@
> +/*
> + * Copyright Tony Prisk <linux@prisktech.co.nz>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License as published by
> + * the Free Software Foundation; either version 2 of the License, or
> + * (at your option) any later version.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, write to the Free Software
> + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
> + */
> +
> +#ifndef __MTD_FLASH_JEDEC
> +#define __MTD_FLASH_JEDEC
> +
> +struct flash_device_info {
> +	const char	*name;
> +	u32		jedec_id;
> +	u32		size_kb;
> +};
> +
> +extern struct flash_device_info *jedec_match_device(u32 jedec_id);
> +
> +#endif


-- 
Matthieu Castet
Ing?nieur D?veloppement Logiciel
Parrot SA
174 Quai de Jemmapes
75010 Paris, France

T?l: +33 (0) 1 48 03 74 78
Fax: +33 (0) 1 48 03 06 66
Email: matthieu.castet at parrot.fr
http://www.parrot.biz

^ permalink raw reply

* [PATCH] [ARM] spitz/pxa: Refactor i2c init code in spitz.c
From: Haojian Zhuang @ 2013-01-23  9:00 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1355257645-27888-1-git-send-email-dromede@gmail.com>

On Wed, Dec 12, 2012 at 4:27 AM,  <dromede@gmail.com> wrote:
> From: Marko Katic <dromede.gmail.com>
>
> This patch changes the way i2c devices are defined
> and registered.
>
> I2c devices that are present in all spitz
> variants are always defined and registered while the max7310
> gpio expander specific to the akita variant is defined
> and registered only when building the kernel for akita variants.
>
> spitz_i2c_init() is simplified and is now more readable.
>
> Signed-off-by: Marko Katic <dromede@gmail.com>
> ---
>  arch/arm/mach-pxa/spitz.c |   38 ++++++++++++++++++--------------------
>  1 file changed, 18 insertions(+), 20 deletions(-)
>
> diff --git a/arch/arm/mach-pxa/spitz.c b/arch/arm/mach-pxa/spitz.c
> index 0cc9dc7..1c7dc2b 100644
> --- a/arch/arm/mach-pxa/spitz.c
> +++ b/arch/arm/mach-pxa/spitz.c
> @@ -865,17 +865,6 @@ static struct pca953x_platform_data akita_pca953x_pdata = {
>         .gpio_base              = AKITA_IOEXP_GPIO_BASE,
>  };
>
> -static struct i2c_board_info spitz_i2c_devs[] = {
> -       {
> -               .type           = "wm8750",
> -               .addr           = 0x1b,
> -       }, {
> -               .type           = "max7310",
> -               .addr           = 0x18,
> -               .platform_data  = &akita_pca953x_pdata,
> -       },
> -};
> -
>  static struct regulator_consumer_supply isl6271a_consumers[] = {
>         REGULATOR_SUPPLY("vcc_core", NULL),
>  };
> @@ -894,26 +883,35 @@ static struct regulator_init_data isl6271a_info[] = {
>         }
>  };
>
> -static struct i2c_board_info spitz_pi2c_devs[] = {
> +static struct i2c_board_info spitz_i2c_devs[2] = {
>         {
> +               .type           = "wm8750",
> +               .addr           = 0x1b,
> +       }, {
>                 .type           = "isl6271a",
>                 .addr           = 0x0c,
>                 .platform_data  = &isl6271a_info,
>         },
>  };
>
spitz_i2c_devs[] are in i2c0 bus. spitz_pi2c_devs[] are in i2c1 bus.
Why do you move wm8750 from i2c0 bus to i2c1 bus?

> +#ifdef CONFIG_MACH_AKITA
> +static struct i2c_board_info akita_i2c_max7310 = {
> +               .type           = "max7310",
> +               .addr           = 0x18,
> +               .platform_data  = &akita_pca953x_pdata,
> +};
> +#endif
> +
>  static void __init spitz_i2c_init(void)
>  {
> -       int size = ARRAY_SIZE(spitz_i2c_devs);
> -
> -       /* Only Akita has the max7310 chip */
> -       if (!machine_is_akita())
> -               size--;
> -
>         pxa_set_i2c_info(NULL);
>         pxa27x_set_i2c_power_info(NULL);
> -       i2c_register_board_info(0, spitz_i2c_devs, size);
> -       i2c_register_board_info(1, ARRAY_AND_SIZE(spitz_pi2c_devs));
> +
> +       i2c_register_board_info(0, &spitz_i2c_devs[0], 1);
> +       i2c_register_board_info(1, &spitz_i2c_devs[1], 1);
> +
> +       if (machine_is_akita())
> +               i2c_register_board_info(0, &akita_i2c_max7310, 1);
>  }
>  #else
>  static inline void spitz_i2c_init(void) {}
> --
> 1.7.10.4
>

^ permalink raw reply

* [v3 2/2] ARM: tegra: Skip scu_enable(scu_base) if not Cortex A9
From: Santosh Shilimkar @ 2013-01-23  8:58 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <CAOesGMgtaCkiv285TU_vbAokN5M2MrANQ9piDcyXu5YMmbQq3A@mail.gmail.com>

On Tuesday 22 January 2013 10:34 PM, Olof Johansson wrote:
> On Tue, Jan 22, 2013 at 8:57 AM, Stephen Warren <swarren@wwwdotorg.org> wrote:
>> On 01/21/2013 11:07 PM, Santosh Shilimkar wrote:
>>> On Tuesday 22 January 2013 11:22 AM, Hiroshi Doyu wrote:
>>>> Skip scu_enable(scu_base) if CPU is not Cortex A9 with SCU.
>>>>
>>>> Signed-off-by: Hiroshi Doyu <hdoyu@nvidia.com>
>>>> ---
>>> Looks fine. I will also update OMAP code with the new
>>> interface. Thanks.
>>
>> OK, so patch 1/2 at least needs to get into a stable arm-soc branch
>> then. Unless there are violent objections, I'll forward patch 1/2 to
>> arm-soc and request it be added into a branch so that Tegra and OMAP can
>> both merge it into their branches as a dependency. I guess patch 2/2
>> could also be included; I don't think it has any complex dependencies
>> that'd prevent that, and would help to show how patch 1/2 gets used.
>>
>> Hiroshi, is this series the only dependency you need for your Tegra114
>> series? So, I could merge your Tegra114 series once this series is applied?
>
> For something like this, it might make more sense for us to just apply
> the patches for OMAP on top, i.e. we'll pull the short branch from
> you, and then we can just apply patches (with maintainer acks) on top,
> instead of doing a bunch of single-patch pulls.
>
In case you decide to apply patches, you can use patch in the end
of the email for OMAP. Attached the same in case mailer damages it.

Btw, I noticed the build error with patch 1/1. Since I wasn't using
the first interface in OMAP code, I just bypassed it for testing.
I might be missing some dependent patch which added
read_cpuid_part_number().

---------------
In file included from arch/arm/kernel/smp_scu.c:15:0:
linux-2.6/arch/arm/include/asm/smp_scu.h: In function 'scu_a9_has_base':
linux-2.6/arch/arm/include/asm/smp_scu.h:14:2: error: implicit 
declaration of function 'read_cpuid_part_number' 
[-Werror=implicit-function-declaration]
linux-2.6/arch/arm/include/asm/smp_scu.h:14:37: error: 
'ARM_CPU_PART_CORTEX_A9' undeclared (first use in this function)
linux-2.6/arch/arm/include/asm/smp_scu.h:14:37: note: each undeclared 
identifier is reported only once for each function it appears in
cc1: some warnings being treated as errors
make[1]: *** [arch/arm/kernel/smp_scu.o] Error 1
make: *** [arch/arm/kernel] Error 2
---------------------------------

Regards
Santosh

 From 9760cd0ed93b48ec22584e89979cd4a8ec65b938 Mon Sep 17 00:00:00 2001
From: Santosh Shilimkar <santosh.shilimkar@ti.com>
Date: Wed, 23 Jan 2013 13:56:19 +0530
Subject: [PATCH] ARM: OMAP: Make use of available scu_a9_get_base() 
interface

Drop the define and make use of scu_a9_get_base() which reads
the physical address of SCU from CP15 register.

Signed-off-by: Santosh Shilimkar <santosh.shilimkar@ti.com>
---
  arch/arm/mach-omap2/omap-smp.c |    2 +-
  arch/arm/mach-omap2/omap44xx.h |    1 -
  2 files changed, 1 insertion(+), 2 deletions(-)

diff --git a/arch/arm/mach-omap2/omap-smp.c b/arch/arm/mach-omap2/omap-smp.c
index cd42d92..e683d0d 100644
--- a/arch/arm/mach-omap2/omap-smp.c
+++ b/arch/arm/mach-omap2/omap-smp.c
@@ -215,7 +215,7 @@ static void __init omap4_smp_init_cpus(void)
  		 * Currently we can't call ioremap here because
  		 * SoC detection won't work until after init_early.
  		 */
-		scu_base =  OMAP2_L4_IO_ADDRESS(OMAP44XX_SCU_BASE);
+		scu_base =  OMAP2_L4_IO_ADDRESS(scu_a9_get_base());
  		BUG_ON(!scu_base);
  		ncores = scu_get_core_count(scu_base);
  	} else if (cpu_id == CPU_CORTEX_A15) {
diff --git a/arch/arm/mach-omap2/omap44xx.h b/arch/arm/mach-omap2/omap44xx.h
index 43b927b..8a515bb 100644
--- a/arch/arm/mach-omap2/omap44xx.h
+++ b/arch/arm/mach-omap2/omap44xx.h
@@ -40,7 +40,6 @@
  #define OMAP44XX_GIC_DIST_BASE		0x48241000
  #define OMAP44XX_GIC_CPU_BASE		0x48240100
  #define OMAP44XX_IRQ_GIC_START		32
-#define OMAP44XX_SCU_BASE		0x48240000
  #define OMAP44XX_LOCAL_TWD_BASE		0x48240600
  #define OMAP44XX_L2CACHE_BASE		0x48242000
  #define OMAP44XX_WKUPGEN_BASE		0x48281000
-- 
1.7.9.5


-------------- next part --------------
A non-text attachment was scrubbed...
Name: 0001-ARM-OMAP-Make-use-of-available-scu_a9_get_base-inter.patch
Type: text/x-patch
Size: 1627 bytes
Desc: not available
URL: <http://lists.infradead.org/pipermail/linux-arm-kernel/attachments/20130123/2bd872f7/attachment.bin>

^ permalink raw reply related

* [PATCH] [ARM] spitz/pxa: Minor naming fixes in spitz.c
From: Haojian Zhuang @ 2013-01-23  8:56 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1355254812-14500-1-git-send-email-dromede@gmail.com>

On Wed, Dec 12, 2012 at 3:40 AM,  <dromede@gmail.com> wrote:
> From: Marko Katic <dromede.gmail.com>
>
> The NAND init section was erroneously named "Framebuffer".
> Gpio expander section should really be called "I2C devices"
> since it contains all i2c init code.
>
> Signed-off-by: Marko Katic <dromede@gmail.com>
> ---
>  arch/arm/mach-pxa/spitz.c |    4 ++--
>  1 file changed, 2 insertions(+), 2 deletions(-)
>
Applied.

Thanks
Haojian

^ permalink raw reply

* [[PATCH v2]] OMAP: omap4-panda: add WiLink shared transport power functions
From: Peter Ujfalusi @ 2013-01-23  8:55 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <20130118174910.GF15361@atomide.com>

Hi Tony,

On 01/18/2013 06:49 PM, Tony Lindgren wrote:
> Currently it seems that we need the following working with DT to have panda
> and blaze usable:
> 
> 1. MMC (done)
> 2. USB (patches pending for EHCI and MUSB)
> 3. Ethernet (done for blaze, needs USB for panda)
> 4. DSS (various drivers pending, probably still needs some platform init code)
> 5. WLAN (no binding, needs platform init until done)
> 6. Audio (done?)

Yes, audio is ready. We are covering OMAP2/3/4/5 (adding OMAP1 should not be a
big issue either) with SoC IPs in DT support. We have dmaengine for all OMAP
audio stuff. Codec drivers I maintain in upstream are also works with DT. We
have ASoC machine drivers to cover most of the upstream boards (OMAP3/4/5). So
audio is pretty much done in DT context, we are waiting for the DMA bindings
only AFAIK.

-- 
P?ter

^ permalink raw reply

* [PATCH] ARM: PXA3xx: program the CSMSADRCFG register
From: Haojian Zhuang @ 2013-01-23  8:51 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <CAMPhdO8LfzvjoE1Re9G44pAZh+-9U7aj5gUWj2xeUyV1ihyRSg@mail.gmail.com>

On Tue, Jan 15, 2013 at 11:01 AM, Eric Miao <eric.y.miao@gmail.com> wrote:
>
> On Sun, Jan 13, 2013 at 7:49 PM, Igor Grinberg <grinberg@compulab.co.il> wrote:
> > The Chip Select Configuration Register must be programmed to 0x2 in
> > order to achieve the correct behavior of the Static Memory Controller.
> >
> > Without this patch devices wired to DFI and accessed through SMC cannot
> > be accessed after resume from S2.
> >
> > Do not rely on the boot loader to program the CSMSADRCFG register by
> > programming it in the kernel smemc module.
> >
>
> Looks good to me. Acked-by: Eric Miao <eric.y.miao@gmail.com>
>

Appled.

Thanks.
Haojian

^ permalink raw reply

* [PATCH V5] drivers/pinctrl: grab default handles from device core
From: Linus Walleij @ 2013-01-23  8:50 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358877374-1279-1-git-send-email-swarren@wwwdotorg.org>

OK!

This modified version of the patch is way more beautiful, stupid
me for not realizing it could be written like that.

And I can sure live with the removed doc piece ... we can discuss
that separately if need be, I have some argument for it but it's
a separate issue.

I've dubbed this version the v5 variant and applied it, and included
the changelog (so I remember how it came about).

Greg/Mark: are you still confident with your ACK/Reviewed-by
tags being added on this version?

Yours,
Linus Walleij

^ permalink raw reply

* [PATCH v2] Dove: activate GPIO interrupts in DT
From: Jean-Francois Moine @ 2013-01-23  8:38 UTC (permalink / raw)
  To: linux-arm-kernel

In a DT, the interrupts of an interrupt-controller are not usable when
#interrupt-cells is missing.

This patch activates the interrupts of the GPIOs 0 and 1 for the Marvell
Dove SoC.

Signed-off-by: Jean-Fran?ois Moine <moinejf@free.fr>
---
v2
- gpio-mvebu asks for 2 cells
---
 arch/arm/boot/dts/dove.dtsi |    2 ++
 1 file changed, 2 insertions(+)

diff --git a/arch/arm/boot/dts/dove.dtsi b/arch/arm/boot/dts/dove.dtsi
index 42eac1f..740630f 100644
--- a/arch/arm/boot/dts/dove.dtsi
+++ b/arch/arm/boot/dts/dove.dtsi
@@ -93,6 +93,7 @@
 			reg = <0xd0400 0x20>;
 			ngpios = <32>;
 			interrupt-controller;
+			#interrupt-cells = <2>;
 			interrupts = <12>, <13>, <14>, <60>;
 		};
 
@@ -103,6 +104,7 @@
 			reg = <0xd0420 0x20>;
 			ngpios = <32>;
 			interrupt-controller;
+			#interrupt-cells = <2>;
 			interrupts = <61>;
 		};
 
 
-- 
Ken ar c'henta?	|	      ** Breizh ha Linux atav! **
Jef		|		http://moinejf.free.fr/

^ permalink raw reply related

* [PATCH 10/10] gpio: pxa: bind to pinctrl by request
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

While gpio pins is requested, request the pin of pinctrl driver first.

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 drivers/gpio/gpio-pxa.c |   13 +++++++++++++
 1 file changed, 13 insertions(+)

diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 528f742..d64ec8c 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -23,6 +23,7 @@
 #include <linux/io.h>
 #include <linux/of.h>
 #include <linux/of_device.h>
+#include <linux/pinctrl/consumer.h>
 #include <linux/platform_device.h>
 #include <linux/syscore_ops.h>
 #include <linux/slab.h>
@@ -159,6 +160,17 @@ int pxa_irq_to_gpio(struct irq_data *d)
 	return gpio;
 }
 
+static int pxa_gpio_request(struct gpio_chip *gc, unsigned offset)
+{
+	/*
+	 * Map back to global GPIO space and request muxing, the direction
+	 * parameter does not matter for this controller.
+	 */
+	int gpio = gc->base + offset;
+
+	return pinctrl_request_gpio(gpio);
+}
+
 static int pxa_gpio_direction_input(struct gpio_chip *gc, unsigned offset)
 {
 	struct pxa_gpio_chip *chip = NULL;
@@ -469,6 +481,7 @@ static int pxa_init_gpio_chip(struct platform_device *pdev, int gpio_end,
 		gc->base  = gpio;
 		gc->label = chips[i].label;
 
+		gc->request = pxa_gpio_request;
 		gc->direction_input  = pxa_gpio_direction_input;
 		gc->direction_output = pxa_gpio_direction_output;
 		gc->get = pxa_gpio_get;
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 09/10] gpio: pxa: move gpio properties into child node
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

Move gpio properties into child node. So pinctrl driver could binds to
each gpio chip with gpio range.

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 drivers/gpio/gpio-pxa.c |   33 ++++++++-------------------------
 1 file changed, 8 insertions(+), 25 deletions(-)

diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 21cf8fd..528f742 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -63,10 +63,6 @@
 
 int pxa_last_gpio;
 
-#ifdef CONFIG_OF
-static struct device_node *pxa_gpio_of_node;
-#endif
-
 struct pxa_gpio_chip {
 	struct gpio_chip chip;
 	void __iomem	*regbase;
@@ -404,9 +400,9 @@ static const struct irq_domain_ops pxa_irq_domain_ops = {
 
 static int pxa_gpio_probe_dt(struct platform_device *pdev)
 {
-	int ret, nr_banks;
+	int ret;
 	struct pxa_gpio_platform_data *pdata;
-	struct device_node *prev, *next, *np = pdev->dev.of_node;
+	struct device_node *np = pdev->dev.of_node;
 	const struct of_device_id *of_id =
 				of_match_device(pxa_gpio_dt_ids, &pdev->dev);
 
@@ -432,25 +428,7 @@ static int pxa_gpio_probe_dt(struct platform_device *pdev)
 	/* set the platform data */
 	pdev->dev.platform_data = pdata;
 
-	next = of_get_next_child(np, NULL);
-	prev = next;
-	if (!next) {
-		dev_err(&pdev->dev, "Failed to find child gpio node\n");
-		ret = -EINVAL;
-		goto err;
-	}
-	for (nr_banks = 1; ; nr_banks++) {
-		next = of_get_next_child(np, prev);
-		if (!next)
-			break;
-		prev = next;
-	}
-	of_node_put(prev);
-
 	return 0;
-err:
-	iounmap(gpio_reg_base);
-	return ret;
 }
 #else
 #define pxa_gpio_probe_dt(pdev)		(-1)
@@ -460,6 +438,7 @@ static int pxa_init_gpio_chip(struct platform_device *pdev, int gpio_end,
 			      int (*set_wake)(unsigned int, unsigned int))
 {
 	int i, gpio, nbanks = gpio_to_bank(gpio_end) + 1;
+	struct device_node *next, *np = pdev->dev.of_node;
 	struct pxa_gpio_chip *chips;
 
 	chips = devm_kzalloc(&pdev->dev, nbanks * sizeof(*chips), GFP_KERNEL);
@@ -468,6 +447,7 @@ static int pxa_init_gpio_chip(struct platform_device *pdev, int gpio_end,
 		return -ENOMEM;
 	}
 
+	next = of_get_next_child(np, NULL);
 	for (i = 0, gpio = 0; i < nbanks; i++, gpio += 32) {
 		struct gpio_chip *gc = &chips[i].chip;
 
@@ -495,7 +475,10 @@ static int pxa_init_gpio_chip(struct platform_device *pdev, int gpio_end,
 		gc->set = pxa_gpio_set;
 		gc->to_irq = pxa_gpio_to_irq;
 #ifdef CONFIG_OF_GPIO
-		gc->of_node = pxa_gpio_of_node;
+		gc->of_node = next;
+		next = of_get_next_child(np, next);
+		of_node_put(gc->of_node);
+
 		gc->of_xlate = pxa_gpio_of_xlate;
 		gc->of_gpio_n_cells = 2;
 #endif
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 08/10] gpio: pxa: remove arch related macro
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

Remove macro CONFIG_ARCH_PXA.

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 drivers/gpio/gpio-pxa.c |   30 +++++++++++++++---------------
 1 file changed, 15 insertions(+), 15 deletions(-)

diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 5870944..21cf8fd 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -570,21 +570,21 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 	}
 
 	if (!use_of) {
-#ifdef CONFIG_ARCH_PXA
-		irq = gpio_to_irq(0);
-		irq_set_chip_and_handler(irq, &pxa_muxed_gpio_chip,
-					 handle_edge_irq);
-		set_irq_flags(irq, IRQF_VALID | IRQF_PROBE);
-		irq_set_chained_handler(IRQ_GPIO0, pxa_gpio_demux_handler);
-
-		irq = gpio_to_irq(1);
-		irq_set_chip_and_handler(irq, &pxa_muxed_gpio_chip,
-					 handle_edge_irq);
-		set_irq_flags(irq, IRQF_VALID | IRQF_PROBE);
-		irq_set_chained_handler(IRQ_GPIO1, pxa_gpio_demux_handler);
-#endif
-
-		for (irq  = gpio_to_irq(gpio_offset);
+		if (irq0 > 0) {
+			irq = gpio_to_irq(0);
+			irq_set_chip_and_handler(irq, &pxa_muxed_gpio_chip,
+						 handle_edge_irq);
+			set_irq_flags(irq, IRQF_VALID | IRQF_PROBE);
+			irq_set_chained_handler(irq0, pxa_gpio_demux_handler);
+		}
+		if (irq1 > 0) {
+			irq = gpio_to_irq(1);
+			irq_set_chip_and_handler(irq, &pxa_muxed_gpio_chip,
+						 handle_edge_irq);
+			set_irq_flags(irq, IRQF_VALID | IRQF_PROBE);
+			irq_set_chained_handler(irq1, pxa_gpio_demux_handler);
+		}
+		for (irq = gpio_to_irq(gpio_offset);
 			irq <= gpio_to_irq(pxa_last_gpio); irq++) {
 			irq_set_chip_and_handler(irq, &pxa_muxed_gpio_chip,
 						 handle_edge_irq);
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 07/10] gpio: pxa: clean code for compatible name
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

Use compatible variable name in gpio pxa driver.

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 drivers/gpio/gpio-pxa.c |  194 ++++++++++++++++++++++++-----------------------
 1 file changed, 98 insertions(+), 96 deletions(-)

diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 67be225..5870944 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -95,9 +95,9 @@ static void __iomem *gpio_reg_base;
 #define for_each_gpio_chip(i, c)			\
 	for (i = 0, c = &pxa_gpio_chips[0]; i <= pxa_last_gpio; i += 32, c++)
 
-static inline void __iomem *gpio_chip_base(struct gpio_chip *c)
+static inline void __iomem *gpio_chip_base(struct gpio_chip *gc)
 {
-	return container_of(c, struct pxa_gpio_chip, chip)->regbase;
+	return container_of(gc, struct pxa_gpio_chip, chip)->regbase;
 }
 
 static inline struct pxa_gpio_chip *gpio_to_pxachip(unsigned gpio)
@@ -210,14 +210,14 @@ static int pxa_gpio_direction_output(struct gpio_chip *gc,
 	return 0;
 }
 
-static int pxa_gpio_get(struct gpio_chip *chip, unsigned offset)
+static int pxa_gpio_get(struct gpio_chip *gc, unsigned offset)
 {
-	return readl_relaxed(gpio_chip_base(chip) + GPLR_OFFSET) & (1 << offset);
+	return readl_relaxed(gpio_chip_base(gc) + GPLR_OFFSET) & (1 << offset);
 }
 
-static void pxa_gpio_set(struct gpio_chip *chip, unsigned offset, int value)
+static void pxa_gpio_set(struct gpio_chip *gc, unsigned offset, int value)
 {
-	writel_relaxed(1 << offset, gpio_chip_base(chip) +
+	writel_relaxed(1 << offset, gpio_chip_base(gc) +
 				(value ? GPSR_OFFSET : GPCR_OFFSET));
 }
 
@@ -242,57 +242,58 @@ static int pxa_gpio_of_xlate(struct gpio_chip *gc,
 /* Update only those GRERx and GFERx edge detection register bits if those
  * bits are set in c->irq_mask
  */
-static inline void update_edge_detect(struct pxa_gpio_chip *c)
+static inline void update_edge_detect(struct pxa_gpio_chip *chip)
 {
 	uint32_t grer, gfer;
 
-	grer = readl_relaxed(c->regbase + GRER_OFFSET) & ~c->irq_mask;
-	gfer = readl_relaxed(c->regbase + GFER_OFFSET) & ~c->irq_mask;
-	grer |= c->irq_edge_rise & c->irq_mask;
-	gfer |= c->irq_edge_fall & c->irq_mask;
-	writel_relaxed(grer, c->regbase + GRER_OFFSET);
-	writel_relaxed(gfer, c->regbase + GFER_OFFSET);
+	grer = readl_relaxed(chip->regbase + GRER_OFFSET) & ~chip->irq_mask;
+	gfer = readl_relaxed(chip->regbase + GFER_OFFSET) & ~chip->irq_mask;
+	grer |= chip->irq_edge_rise & chip->irq_mask;
+	gfer |= chip->irq_edge_fall & chip->irq_mask;
+	writel_relaxed(grer, chip->regbase + GRER_OFFSET);
+	writel_relaxed(gfer, chip->regbase + GFER_OFFSET);
 }
 
 static int pxa_gpio_irq_type(struct irq_data *d, unsigned int type)
 {
-	struct pxa_gpio_chip *c;
+	struct pxa_gpio_chip *chip;
 	int gpio = pxa_irq_to_gpio(d);
 	unsigned long gpdr, mask = GPIO_bit(gpio);
 
-	c = gpio_to_pxachip(gpio);
+	chip = gpio_to_pxachip(gpio);
 
 	if (type == IRQ_TYPE_PROBE) {
 		/* Don't mess with enabled GPIOs using preconfigured edges or
 		 * GPIOs set to alternate function or to output during probe
 		 */
-		if ((c->irq_edge_rise | c->irq_edge_fall) & GPIO_bit(gpio))
+		if ((chip->irq_edge_rise | chip->irq_edge_fall)
+			& GPIO_bit(gpio))
 			return 0;
 
-		if (__gpio_is_occupied(c, gpio))
+		if (__gpio_is_occupied(chip, gpio))
 			return 0;
 
 		type = IRQ_TYPE_EDGE_RISING | IRQ_TYPE_EDGE_FALLING;
 	}
 
-	gpdr = readl_relaxed(c->regbase + GPDR_OFFSET);
+	gpdr = readl_relaxed(chip->regbase + GPDR_OFFSET);
 
-	if (__gpio_is_inverted(c, gpio))
-		writel_relaxed(gpdr | mask,  c->regbase + GPDR_OFFSET);
+	if (__gpio_is_inverted(chip, gpio))
+		writel_relaxed(gpdr | mask,  chip->regbase + GPDR_OFFSET);
 	else
-		writel_relaxed(gpdr & ~mask, c->regbase + GPDR_OFFSET);
+		writel_relaxed(gpdr & ~mask, chip->regbase + GPDR_OFFSET);
 
 	if (type & IRQ_TYPE_EDGE_RISING)
-		c->irq_edge_rise |= mask;
+		chip->irq_edge_rise |= mask;
 	else
-		c->irq_edge_rise &= ~mask;
+		chip->irq_edge_rise &= ~mask;
 
 	if (type & IRQ_TYPE_EDGE_FALLING)
-		c->irq_edge_fall |= mask;
+		chip->irq_edge_fall |= mask;
 	else
-		c->irq_edge_fall &= ~mask;
+		chip->irq_edge_fall &= ~mask;
 
-	update_edge_detect(c);
+	update_edge_detect(chip);
 
 	pr_debug("%s: IRQ%d (GPIO%d) - edge%s%s\n", __func__, d->irq, gpio,
 		((type & IRQ_TYPE_EDGE_RISING)  ? " rising"  : ""),
@@ -302,21 +303,21 @@ static int pxa_gpio_irq_type(struct irq_data *d, unsigned int type)
 
 static void pxa_gpio_demux_handler(unsigned int irq, struct irq_desc *desc)
 {
-	struct pxa_gpio_chip *c;
+	struct pxa_gpio_chip *chip;
 	int loop, gpio, gpio_base, n;
 	unsigned long gedr;
-	struct irq_chip *chip = irq_desc_get_chip(desc);
+	struct irq_chip *ic = irq_desc_get_chip(desc);
 
-	chained_irq_enter(chip, desc);
+	chained_irq_enter(ic, desc);
 
 	do {
 		loop = 0;
-		for_each_gpio_chip(gpio, c) {
-			gpio_base = c->chip.base;
+		for_each_gpio_chip(gpio, chip) {
+			gpio_base = chip->chip.base;
 
-			gedr = readl_relaxed(c->regbase + GEDR_OFFSET);
-			gedr = gedr & c->irq_mask;
-			writel_relaxed(gedr, c->regbase + GEDR_OFFSET);
+			gedr = readl_relaxed(chip->regbase + GEDR_OFFSET);
+			gedr = gedr & chip->irq_mask;
+			writel_relaxed(gedr, chip->regbase + GEDR_OFFSET);
 
 			for_each_set_bit(n, &gedr, BITS_PER_LONG) {
 				loop = 1;
@@ -326,38 +327,38 @@ static void pxa_gpio_demux_handler(unsigned int irq, struct irq_desc *desc)
 		}
 	} while (loop);
 
-	chained_irq_exit(chip, desc);
+	chained_irq_exit(ic, desc);
 }
 
 static void pxa_ack_muxed_gpio(struct irq_data *d)
 {
 	int gpio = pxa_irq_to_gpio(d);
-	struct pxa_gpio_chip *c = gpio_to_pxachip(gpio);
+	struct pxa_gpio_chip *chip = gpio_to_pxachip(gpio);
 
-	writel_relaxed(GPIO_bit(gpio), c->regbase + GEDR_OFFSET);
+	writel_relaxed(GPIO_bit(gpio), chip->regbase + GEDR_OFFSET);
 }
 
 static void pxa_mask_muxed_gpio(struct irq_data *d)
 {
 	int gpio = pxa_irq_to_gpio(d);
-	struct pxa_gpio_chip *c = gpio_to_pxachip(gpio);
+	struct pxa_gpio_chip *chip = gpio_to_pxachip(gpio);
 	uint32_t grer, gfer;
 
-	c->irq_mask &= ~GPIO_bit(gpio);
+	chip->irq_mask &= ~GPIO_bit(gpio);
 
-	grer = readl_relaxed(c->regbase + GRER_OFFSET) & ~GPIO_bit(gpio);
-	gfer = readl_relaxed(c->regbase + GFER_OFFSET) & ~GPIO_bit(gpio);
-	writel_relaxed(grer, c->regbase + GRER_OFFSET);
-	writel_relaxed(gfer, c->regbase + GFER_OFFSET);
+	grer = readl_relaxed(chip->regbase + GRER_OFFSET) & ~GPIO_bit(gpio);
+	gfer = readl_relaxed(chip->regbase + GFER_OFFSET) & ~GPIO_bit(gpio);
+	writel_relaxed(grer, chip->regbase + GRER_OFFSET);
+	writel_relaxed(gfer, chip->regbase + GFER_OFFSET);
 }
 
 static int pxa_gpio_set_wake(struct irq_data *d, unsigned int on)
 {
 	int gpio = pxa_irq_to_gpio(d);
-	struct pxa_gpio_chip *c = gpio_to_pxachip(gpio);
+	struct pxa_gpio_chip *chip = gpio_to_pxachip(gpio);
 
-	if (c->set_wake)
-		return c->set_wake(gpio, on);
+	if (chip->set_wake)
+		return chip->set_wake(gpio, on);
 	else
 		return 0;
 }
@@ -365,10 +366,10 @@ static int pxa_gpio_set_wake(struct irq_data *d, unsigned int on)
 static void pxa_unmask_muxed_gpio(struct irq_data *d)
 {
 	int gpio = pxa_irq_to_gpio(d);
-	struct pxa_gpio_chip *c = gpio_to_pxachip(gpio);
+	struct pxa_gpio_chip *chip = gpio_to_pxachip(gpio);
 
-	c->irq_mask |= GPIO_bit(gpio);
-	update_edge_detect(c);
+	chip->irq_mask |= GPIO_bit(gpio);
+	update_edge_detect(chip);
 }
 
 static struct irq_chip pxa_muxed_gpio_chip = {
@@ -468,38 +469,37 @@ static int pxa_init_gpio_chip(struct platform_device *pdev, int gpio_end,
 	}
 
 	for (i = 0, gpio = 0; i < nbanks; i++, gpio += 32) {
-		struct gpio_chip *c = &chips[i].chip;
+		struct gpio_chip *gc = &chips[i].chip;
 
 		sprintf(chips[i].label, "gpio-%d", i);
 		chips[i].regbase = gpio_reg_base + BANK_OFF(i);
 		chips[i].set_wake = set_wake;
 
-		c->base  = gpio;
-		c->label = chips[i].label;
-
-		c->direction_input  = pxa_gpio_direction_input;
-		c->direction_output = pxa_gpio_direction_output;
-		c->get = pxa_gpio_get;
-		c->set = pxa_gpio_set;
-		c->to_irq = pxa_gpio_to_irq;
-#ifdef CONFIG_OF_GPIO
-		c->of_node = pxa_gpio_of_node;
-		c->of_xlate = pxa_gpio_of_xlate;
-		c->of_gpio_n_cells = 2;
-#endif
-
 		/* number of GPIOs on last bank may be less than 32 */
-		c->ngpio = (gpio + 31 > gpio_end) ? (gpio_end - gpio + 1) : 32;
+		gc->ngpio = (gpio + 31 > gpio_end) ? (gpio_end - gpio + 1) : 32;
 
-		chips[i].irq_base = irq_alloc_descs(-1, 0, c->ngpio, 0);
+		chips[i].irq_base = irq_alloc_descs(-1, 0, gc->ngpio, 0);
 		if (chips[i].irq_base < 0)
 			return -EINVAL;
-		if (!irq_domain_add_legacy(pdev->dev.of_node, c->ngpio,
+		if (!irq_domain_add_legacy(pdev->dev.of_node, gc->ngpio,
 					   chips[i].irq_base, 0,
 					   &pxa_irq_domain_ops, &chips[i]))
 			return -ENODEV;
 
-		gpiochip_add(c);
+		gc->base  = gpio;
+		gc->label = chips[i].label;
+
+		gc->direction_input  = pxa_gpio_direction_input;
+		gc->direction_output = pxa_gpio_direction_output;
+		gc->get = pxa_gpio_get;
+		gc->set = pxa_gpio_set;
+		gc->to_irq = pxa_gpio_to_irq;
+#ifdef CONFIG_OF_GPIO
+		gc->of_node = pxa_gpio_of_node;
+		gc->of_xlate = pxa_gpio_of_xlate;
+		gc->of_gpio_n_cells = 2;
+#endif
+		gpiochip_add(gc);
 	}
 	pxa_gpio_chips = chips;
 	return 0;
@@ -507,10 +507,10 @@ static int pxa_init_gpio_chip(struct platform_device *pdev, int gpio_end,
 
 static int pxa_gpio_probe(struct platform_device *pdev)
 {
-	struct pxa_gpio_chip *c;
+	struct pxa_gpio_chip *chip;
 	struct resource *res;
 	struct clk *clk;
-	struct pxa_gpio_platform_data *info;
+	struct pxa_gpio_platform_data *pdata;
 	int gpio, irq, ret, use_of = 0;
 	int irq0 = 0, irq1 = 0, irq_mux, gpio_offset = 0;
 
@@ -549,22 +549,24 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 	}
 
 	/* Initialize GPIO chips */
-	info = dev_get_platdata(&pdev->dev);
-	pxa_last_gpio = info->nr_gpios - 1;
-	pxa_init_gpio_chip(pdev, pxa_last_gpio,
-			   info ? info->gpio_set_wake : NULL);
+	pdata = dev_get_platdata(&pdev->dev);
+	pxa_last_gpio = pdata->nr_gpios - 1;
+	ret = pxa_init_gpio_chip(pdev, pxa_last_gpio,
+				 pdata ? pdata->gpio_set_wake : NULL);
+	if (ret < 0)
+		return ret;
 
 	/* clear all GPIO edge detects */
-	for_each_gpio_chip(gpio, c) {
-		writel_relaxed(0, c->regbase + GFER_OFFSET);
-		writel_relaxed(0, c->regbase + GRER_OFFSET);
-		writel_relaxed(~0,c->regbase + GEDR_OFFSET);
+	for_each_gpio_chip(gpio, chip) {
+		writel_relaxed(0, chip->regbase + GFER_OFFSET);
+		writel_relaxed(0, chip->regbase + GRER_OFFSET);
+		writel_relaxed(~0,chip->regbase + GEDR_OFFSET);
 		/* unmask GPIO edge detect for AP side */
-		if (info->ed_mask)
-			writel_relaxed(~0, c->regbase + ED_MASK_OFFSET);
+		if (pdata->ed_mask)
+			writel_relaxed(~0, chip->regbase + ED_MASK_OFFSET);
 		/* update for gpio inverted & gafr */
-		c->inverted = info->inverted;
-		c->gafr = info->gafr;
+		chip->inverted = pdata->inverted;
+		chip->gafr = pdata->gafr;
 	}
 
 	if (!use_of) {
@@ -606,34 +608,34 @@ module_platform_driver(pxa_gpio_driver);
 #ifdef CONFIG_PM
 static int pxa_gpio_suspend(void)
 {
-	struct pxa_gpio_chip *c;
+	struct pxa_gpio_chip *chip;
 	int gpio;
 
-	for_each_gpio_chip(gpio, c) {
-		c->saved_gplr = readl_relaxed(c->regbase + GPLR_OFFSET);
-		c->saved_gpdr = readl_relaxed(c->regbase + GPDR_OFFSET);
-		c->saved_grer = readl_relaxed(c->regbase + GRER_OFFSET);
-		c->saved_gfer = readl_relaxed(c->regbase + GFER_OFFSET);
+	for_each_gpio_chip(gpio, chip) {
+		chip->saved_gplr = readl_relaxed(chip->regbase + GPLR_OFFSET);
+		chip->saved_gpdr = readl_relaxed(chip->regbase + GPDR_OFFSET);
+		chip->saved_grer = readl_relaxed(chip->regbase + GRER_OFFSET);
+		chip->saved_gfer = readl_relaxed(chip->regbase + GFER_OFFSET);
 
 		/* Clear GPIO transition detect bits */
-		writel_relaxed(0xffffffff, c->regbase + GEDR_OFFSET);
+		writel_relaxed(~0, chip->regbase + GEDR_OFFSET);
 	}
 	return 0;
 }
 
 static void pxa_gpio_resume(void)
 {
-	struct pxa_gpio_chip *c;
+	struct pxa_gpio_chip *chip;
 	int gpio;
 
-	for_each_gpio_chip(gpio, c) {
+	for_each_gpio_chip(gpio, chip) {
 		/* restore level with set/clear */
-		writel_relaxed( c->saved_gplr, c->regbase + GPSR_OFFSET);
-		writel_relaxed(~c->saved_gplr, c->regbase + GPCR_OFFSET);
+		writel_relaxed( chip->saved_gplr, chip->regbase + GPSR_OFFSET);
+		writel_relaxed(~chip->saved_gplr, chip->regbase + GPCR_OFFSET);
 
-		writel_relaxed(c->saved_grer, c->regbase + GRER_OFFSET);
-		writel_relaxed(c->saved_gfer, c->regbase + GFER_OFFSET);
-		writel_relaxed(c->saved_gpdr, c->regbase + GPDR_OFFSET);
+		writel_relaxed(chip->saved_grer, chip->regbase + GRER_OFFSET);
+		writel_relaxed(chip->saved_gfer, chip->regbase + GFER_OFFSET);
+		writel_relaxed(chip->saved_gpdr, chip->regbase + GPDR_OFFSET);
 	}
 }
 #else
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 06/10] gpio: pxa: define nr gpios in platform data
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

Avoid to define gpio numbers in gpio driver. Define it in platform data
instead.

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 arch/arm/mach-mmp/aspenite.c      |    1 +
 arch/arm/mach-mmp/avengers_lite.c |    1 +
 arch/arm/mach-mmp/brownstone.c    |    1 +
 arch/arm/mach-mmp/flint.c         |    1 +
 arch/arm/mach-mmp/gplugd.c        |    1 +
 arch/arm/mach-mmp/tavorevb.c      |    1 +
 arch/arm/mach-mmp/teton_bga.c     |    1 +
 arch/arm/mach-mmp/ttc_dkb.c       |    1 +
 arch/arm/mach-pxa/pxa25x.c        |    3 +++
 arch/arm/mach-pxa/pxa27x.c        |    1 +
 arch/arm/mach-pxa/pxa3xx.c        |   15 +++++++++++-
 drivers/gpio/gpio-pxa.c           |   48 +++++++------------------------------
 include/linux/gpio-pxa.h          |    1 +
 13 files changed, 35 insertions(+), 41 deletions(-)

diff --git a/arch/arm/mach-mmp/aspenite.c b/arch/arm/mach-mmp/aspenite.c
index ee1fb62..f5aea07 100644
--- a/arch/arm/mach-mmp/aspenite.c
+++ b/arch/arm/mach-mmp/aspenite.c
@@ -112,6 +112,7 @@ static unsigned long common_pin_config[] __initdata = {
 };
 
 static struct pxa_gpio_platform_data pxa168_gpio_pdata = {
+	.nr_gpios	= 128,
 	.ed_mask	= 1,
 };
 
diff --git a/arch/arm/mach-mmp/avengers_lite.c b/arch/arm/mach-mmp/avengers_lite.c
index 8b4b1ae..2f93f8f 100644
--- a/arch/arm/mach-mmp/avengers_lite.c
+++ b/arch/arm/mach-mmp/avengers_lite.c
@@ -34,6 +34,7 @@ static unsigned long avengers_lite_pin_config_V16F[] __initdata = {
 };
 
 static struct pxa_gpio_platform_data pxa168_gpio_pdata = {
+	.nr_gpios	= 128,
 	.ed_mask	= 1,
 };
 
diff --git a/arch/arm/mach-mmp/brownstone.c b/arch/arm/mach-mmp/brownstone.c
index 0454488..7f07cc5 100644
--- a/arch/arm/mach-mmp/brownstone.c
+++ b/arch/arm/mach-mmp/brownstone.c
@@ -106,6 +106,7 @@ static unsigned long brownstone_pin_config[] __initdata = {
 };
 
 static struct pxa_gpio_platform_data mmp2_gpio_pdata = {
+	.nr_gpios	= 192,
 	.ed_mask	= 1,
 };
 
diff --git a/arch/arm/mach-mmp/flint.c b/arch/arm/mach-mmp/flint.c
index 7ec873c..bf37d97 100644
--- a/arch/arm/mach-mmp/flint.c
+++ b/arch/arm/mach-mmp/flint.c
@@ -79,6 +79,7 @@ static unsigned long flint_pin_config[] __initdata = {
 };
 
 static struct pxa_gpio_platform_data mmp2_gpio_pdata = {
+	.nr_gpios	= 192,
 	.ed_mask	= 1,
 };
 
diff --git a/arch/arm/mach-mmp/gplugd.c b/arch/arm/mach-mmp/gplugd.c
index d592041..47808e1 100644
--- a/arch/arm/mach-mmp/gplugd.c
+++ b/arch/arm/mach-mmp/gplugd.c
@@ -129,6 +129,7 @@ static unsigned long gplugd_pin_config[] __initdata = {
 };
 
 static struct pxa_gpio_platform_data pxa168_gpio_pdata = {
+	.nr_gpios	= 128,
 	.ed_mask	= 1,
 };
 
diff --git a/arch/arm/mach-mmp/tavorevb.c b/arch/arm/mach-mmp/tavorevb.c
index a855e69..dd4a22b 100644
--- a/arch/arm/mach-mmp/tavorevb.c
+++ b/arch/arm/mach-mmp/tavorevb.c
@@ -62,6 +62,7 @@ static unsigned long tavorevb_pin_config[] __initdata = {
 };
 
 static struct pxa_gpio_platform_data ttc_dkb_gpio_pdata = {
+	.nr_gpios	= 128,
 	.ed_mask	= 1,
 };
 
diff --git a/arch/arm/mach-mmp/teton_bga.c b/arch/arm/mach-mmp/teton_bga.c
index 9f64f37..b3e7bf9 100644
--- a/arch/arm/mach-mmp/teton_bga.c
+++ b/arch/arm/mach-mmp/teton_bga.c
@@ -51,6 +51,7 @@ static unsigned long teton_bga_pin_config[] __initdata = {
 };
 
 static struct pxa_gpio_platform_data pxa168_gpio_pdata = {
+	.nr_gpios	= 128,
 	.ed_mask	= 1,
 };
 
diff --git a/arch/arm/mach-mmp/ttc_dkb.c b/arch/arm/mach-mmp/ttc_dkb.c
index 74081cd..597268c 100644
--- a/arch/arm/mach-mmp/ttc_dkb.c
+++ b/arch/arm/mach-mmp/ttc_dkb.c
@@ -75,6 +75,7 @@ static unsigned long ttc_dkb_pin_config[] __initdata = {
 };
 
 static struct pxa_gpio_platform_data ttc_dkb_gpio_pdata = {
+	.nr_gpios	= 128,
 	.ed_mask	= 1,
 };
 
diff --git a/arch/arm/mach-pxa/pxa25x.c b/arch/arm/mach-pxa/pxa25x.c
index 90415a6..eb82ece 100644
--- a/arch/arm/mach-pxa/pxa25x.c
+++ b/arch/arm/mach-pxa/pxa25x.c
@@ -342,6 +342,9 @@ void __init pxa25x_map_io(void)
 static struct pxa_gpio_platform_data pxa25x_gpio_info __initdata = {
 #ifdef CONFIG_CPU_PXA26x
 	.inverted = 1,
+	.nr_gpios = 90,
+#else
+	.nr_gpios = 85,
 #endif
 	.gafr = 1,
 	.gpio_set_wake = gpio_set_wake,
diff --git a/arch/arm/mach-pxa/pxa27x.c b/arch/arm/mach-pxa/pxa27x.c
index 91ac5d9..8e6b164 100644
--- a/arch/arm/mach-pxa/pxa27x.c
+++ b/arch/arm/mach-pxa/pxa27x.c
@@ -423,6 +423,7 @@ void __init pxa27x_set_i2c_power_info(struct i2c_pxa_platform_data *info)
 
 static struct pxa_gpio_platform_data pxa27x_gpio_info __initdata = {
 	.gafr = 1,
+	.nr_gpios = 121,
 	.gpio_set_wake = gpio_set_wake,
 };
 
diff --git a/arch/arm/mach-pxa/pxa3xx.c b/arch/arm/mach-pxa/pxa3xx.c
index 656a1bb..a0cc797 100644
--- a/arch/arm/mach-pxa/pxa3xx.c
+++ b/arch/arm/mach-pxa/pxa3xx.c
@@ -435,6 +435,10 @@ void __init pxa3xx_set_i2c_power_info(struct i2c_pxa_platform_data *info)
 	pxa_register_device(&pxa3xx_device_i2c_power, info);
 }
 
+static struct pxa_gpio_platform_data pxa3xx_gpio_info __initdata = {
+	.nr_gpios = 128,
+};
+
 static struct platform_device *devices[] __initdata = {
 	&pxa_device_gpio,
 	&pxa27x_device_udc,
@@ -482,8 +486,17 @@ static int __init pxa3xx_init(void)
 		register_syscore_ops(&pxa3xx_mfp_syscore_ops);
 		register_syscore_ops(&pxa3xx_clock_syscore_ops);
 
-		if (!of_have_populated_dt())
+		if (!of_have_populated_dt()) {
+			if (cpu_is_pxa93x())
+				pxa3xx_gpio_info.nr_gpios = 192;
+			ret = platform_device_add_data(&pxa_device_gpio,
+					&pxa3xx_gpio_info,
+					sizeof(struct pxa_gpio_platform_data);
+			if (ret < 0)
+				break;
+
 			ret = platform_add_devices(devices, ARRAY_SIZE(devices));
+		}
 	}
 
 	return ret;
diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 8b3edc7..67be225 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -380,36 +380,6 @@ static struct irq_chip pxa_muxed_gpio_chip = {
 	.irq_set_wake	= pxa_gpio_set_wake,
 };
 
-static int pxa_gpio_nums(void)
-{
-	int count = 0;
-
-#ifdef CONFIG_ARCH_PXA
-	if (cpu_is_pxa25x()) {
-#ifdef CONFIG_CPU_PXA26x
-		count = 89;
-#elif defined(CONFIG_PXA25x)
-		count = 84;
-#endif /* CONFIG_CPU_PXA26x */
-	} else if (cpu_is_pxa27x()) {
-		count = 120;
-	} else if (cpu_is_pxa93x()) {
-		count = 191;
-	} else if (cpu_is_pxa3xx()) {
-		count = 127;
-	}
-#endif /* CONFIG_ARCH_PXA */
-
-#ifdef CONFIG_ARCH_MMP
-	if (cpu_is_pxa168() || cpu_is_pxa910()) {
-		count = 127;
-	} else if (cpu_is_mmp2()) {
-		count = 191;
-	}
-#endif /* CONFIG_ARCH_MMP */
-	return count;
-}
-
 #ifdef CONFIG_OF
 static struct of_device_id pxa_gpio_dt_ids[] = {
 	{ .compatible = "mrvl,pxa-gpio" },
@@ -433,7 +403,7 @@ static const struct irq_domain_ops pxa_irq_domain_ops = {
 
 static int pxa_gpio_probe_dt(struct platform_device *pdev)
 {
-	int ret, nr_banks, nr_gpios;
+	int ret, nr_banks;
 	struct pxa_gpio_platform_data *pdata;
 	struct device_node *prev, *next, *np = pdev->dev.of_node;
 	const struct of_device_id *of_id =
@@ -453,6 +423,11 @@ static int pxa_gpio_probe_dt(struct platform_device *pdev)
 	ret = of_find_property(np, "marvell,gpio-inverted", NULL);
 	if (ret)
 		pdata->inverted = 1;
+	ret = of_property_read_u32(np, "marvell,nr-gpios", &pdata->nr_gpios);
+	if (ret < 0) {
+		dev_err(&pdev->dev, "nr-gpios isn't specified\n");
+		return -ENOTSUPP;
+	}
 	/* set the platform data */
 	pdev->dev.platform_data = pdata;
 
@@ -470,8 +445,6 @@ static int pxa_gpio_probe_dt(struct platform_device *pdev)
 		prev = next;
 	}
 	of_node_put(prev);
-	nr_gpios = nr_banks << 5;
-	pxa_last_gpio = nr_gpios - 1;
 
 	return 0;
 err:
@@ -542,14 +515,8 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 	int irq0 = 0, irq1 = 0, irq_mux, gpio_offset = 0;
 
 	ret = pxa_gpio_probe_dt(pdev);
-	if (ret < 0) {
-		pxa_last_gpio = pxa_gpio_nums();
-	} else {
+	if (!ret)
 		use_of = 1;
-	}
-
-	if (!pxa_last_gpio)
-		return -EINVAL;
 
 	irq0 = platform_get_irq_byname(pdev, "gpio0");
 	irq1 = platform_get_irq_byname(pdev, "gpio1");
@@ -583,6 +550,7 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 
 	/* Initialize GPIO chips */
 	info = dev_get_platdata(&pdev->dev);
+	pxa_last_gpio = info->nr_gpios - 1;
 	pxa_init_gpio_chip(pdev, pxa_last_gpio,
 			   info ? info->gpio_set_wake : NULL);
 
diff --git a/include/linux/gpio-pxa.h b/include/linux/gpio-pxa.h
index 5a9e003..cf17f4c 100644
--- a/include/linux/gpio-pxa.h
+++ b/include/linux/gpio-pxa.h
@@ -19,6 +19,7 @@ struct pxa_gpio_platform_data {
 	unsigned ed_mask;	/* not 0 means ed_mask reg is available */
 	unsigned gafr;		/* only valid for PXA25x/PXA26x/PXA27x */
 	unsigned inverted;	/* only valid for PXA26x */
+	unsigned nr_gpios;
 	int (*gpio_set_wake)(unsigned int gpio, unsigned int on);
 };
 
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 05/10] gpio: pxa: remove gpio_type
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

Since gpio_type is used to check whether gafr register is valid. So
move it into platform data.

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 arch/arm/mach-pxa/pxa25x.c |    1 +
 arch/arm/mach-pxa/pxa27x.c |    1 +
 drivers/gpio/gpio-pxa.c    |   43 ++++++-------------------------------------
 include/linux/gpio-pxa.h   |    1 +
 4 files changed, 9 insertions(+), 37 deletions(-)

diff --git a/arch/arm/mach-pxa/pxa25x.c b/arch/arm/mach-pxa/pxa25x.c
index 8d77090..90415a6 100644
--- a/arch/arm/mach-pxa/pxa25x.c
+++ b/arch/arm/mach-pxa/pxa25x.c
@@ -343,6 +343,7 @@ static struct pxa_gpio_platform_data pxa25x_gpio_info __initdata = {
 #ifdef CONFIG_CPU_PXA26x
 	.inverted = 1,
 #endif
+	.gafr = 1,
 	.gpio_set_wake = gpio_set_wake,
 };
 
diff --git a/arch/arm/mach-pxa/pxa27x.c b/arch/arm/mach-pxa/pxa27x.c
index 257d936..91ac5d9 100644
--- a/arch/arm/mach-pxa/pxa27x.c
+++ b/arch/arm/mach-pxa/pxa27x.c
@@ -422,6 +422,7 @@ void __init pxa27x_set_i2c_power_info(struct i2c_pxa_platform_data *info)
 }
 
 static struct pxa_gpio_platform_data pxa27x_gpio_info __initdata = {
+	.gafr = 1,
 	.gpio_set_wake = gpio_set_wake,
 };
 
diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 6d61a69..8b3edc7 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -72,6 +72,7 @@ struct pxa_gpio_chip {
 	void __iomem	*regbase;
 	unsigned int	irq_base;
 	unsigned int	inverted;
+	unsigned int	gafr;
 	char label[10];
 
 	unsigned long	irq_mask;
@@ -87,18 +88,8 @@ struct pxa_gpio_chip {
 #endif
 };
 
-enum {
-	PXA25X_GPIO = 0,
-	PXA26X_GPIO,
-	PXA27X_GPIO,
-	PXA3XX_GPIO,
-	PXA93X_GPIO,
-	MMP_GPIO = 0x10,
-};
-
 static DEFINE_SPINLOCK(gpio_lock);
 static struct pxa_gpio_chip *pxa_gpio_chips;
-static int gpio_type;
 static void __iomem *gpio_reg_base;
 
 #define for_each_gpio_chip(i, c)			\
@@ -114,16 +105,6 @@ static inline struct pxa_gpio_chip *gpio_to_pxachip(unsigned gpio)
 	return &pxa_gpio_chips[gpio_to_bank(gpio)];
 }
 
-static inline int gpio_is_pxa_type(int type)
-{
-	return (type & MMP_GPIO) == 0;
-}
-
-static inline int gpio_is_mmp_type(int type)
-{
-	return (type & MMP_GPIO) != 0;
-}
-
 /* GPIO86/87/88/89 on PXA26x have their direction bits in PXA_GPDR(2 inverted,
  * as well as their Alternate Function value being '1' for GPIO in GAFRx.
  */
@@ -149,10 +130,7 @@ static inline int __gpio_is_occupied(struct pxa_gpio_chip *chip, unsigned gpio)
 	base = gpio_chip_base(&chip->chip);
 	gpdr = readl_relaxed(base + GPDR_OFFSET);
 
-	switch (gpio_type) {
-	case PXA25X_GPIO:
-	case PXA26X_GPIO:
-	case PXA27X_GPIO:
+	if (chip->gafr) {
 		gafr = readl_relaxed(base + GAFR_OFFSET);
 		af = (gafr >> ((gpio & 0xf) * 2)) & 0x3;
 		dir = gpdr & GPIO_bit(gpio);
@@ -161,10 +139,8 @@ static inline int __gpio_is_occupied(struct pxa_gpio_chip *chip, unsigned gpio)
 			ret = (af != 1) || (dir == 0);
 		else
 			ret = (af != 0) || (dir != 0);
-		break;
-	default:
+	} else {
 		ret = gpdr & GPIO_bit(gpio);
-		break;
 	}
 	return ret;
 }
@@ -412,30 +388,23 @@ static int pxa_gpio_nums(void)
 	if (cpu_is_pxa25x()) {
 #ifdef CONFIG_CPU_PXA26x
 		count = 89;
-		gpio_type = PXA26X_GPIO;
 #elif defined(CONFIG_PXA25x)
 		count = 84;
-		gpio_type = PXA26X_GPIO;
 #endif /* CONFIG_CPU_PXA26x */
 	} else if (cpu_is_pxa27x()) {
 		count = 120;
-		gpio_type = PXA27X_GPIO;
 	} else if (cpu_is_pxa93x()) {
 		count = 191;
-		gpio_type = PXA93X_GPIO;
 	} else if (cpu_is_pxa3xx()) {
 		count = 127;
-		gpio_type = PXA3XX_GPIO;
 	}
 #endif /* CONFIG_ARCH_PXA */
 
 #ifdef CONFIG_ARCH_MMP
 	if (cpu_is_pxa168() || cpu_is_pxa910()) {
 		count = 127;
-		gpio_type = MMP_GPIO;
 	} else if (cpu_is_mmp2()) {
 		count = 191;
-		gpio_type = MMP_GPIO;
 	}
 #endif /* CONFIG_ARCH_MMP */
 	return count;
@@ -444,7 +413,7 @@ static int pxa_gpio_nums(void)
 #ifdef CONFIG_OF
 static struct of_device_id pxa_gpio_dt_ids[] = {
 	{ .compatible = "mrvl,pxa-gpio" },
-	{ .compatible = "mrvl,mmp-gpio", .data = (void *)MMP_GPIO },
+	{ .compatible = "mrvl,mmp-gpio" },
 	{}
 };
 
@@ -486,7 +455,6 @@ static int pxa_gpio_probe_dt(struct platform_device *pdev)
 		pdata->inverted = 1;
 	/* set the platform data */
 	pdev->dev.platform_data = pdata;
-	gpio_type = (int)of_id->data;
 
 	next = of_get_next_child(np, NULL);
 	prev = next;
@@ -626,8 +594,9 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 		/* unmask GPIO edge detect for AP side */
 		if (info->ed_mask)
 			writel_relaxed(~0, c->regbase + ED_MASK_OFFSET);
-		/* update for gpio inverted */
+		/* update for gpio inverted & gafr */
 		c->inverted = info->inverted;
+		c->gafr = info->gafr;
 	}
 
 	if (!use_of) {
diff --git a/include/linux/gpio-pxa.h b/include/linux/gpio-pxa.h
index c8d07be5..5a9e003 100644
--- a/include/linux/gpio-pxa.h
+++ b/include/linux/gpio-pxa.h
@@ -17,6 +17,7 @@ extern int pxa_irq_to_gpio(struct irq_data *d);
 
 struct pxa_gpio_platform_data {
 	unsigned ed_mask;	/* not 0 means ed_mask reg is available */
+	unsigned gafr;		/* only valid for PXA25x/PXA26x/PXA27x */
 	unsigned inverted;	/* only valid for PXA26x */
 	int (*gpio_set_wake)(unsigned int gpio, unsigned int on);
 };
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 04/10] gpio: pxa: use platform data for gpio inverted
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

Avoid to judge whether gpio is inverted by identifying cpu in gpio
driver. Move this into platform data of gpio driver.

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 arch/arm/mach-pxa/pxa25x.c |    3 +++
 drivers/gpio/gpio-pxa.c    |   41 ++++++++++++++++++++++++++---------------
 include/linux/gpio-pxa.h   |    1 +
 3 files changed, 30 insertions(+), 15 deletions(-)

diff --git a/arch/arm/mach-pxa/pxa25x.c b/arch/arm/mach-pxa/pxa25x.c
index f4c293a..8d77090 100644
--- a/arch/arm/mach-pxa/pxa25x.c
+++ b/arch/arm/mach-pxa/pxa25x.c
@@ -340,6 +340,9 @@ void __init pxa25x_map_io(void)
 }
 
 static struct pxa_gpio_platform_data pxa25x_gpio_info __initdata = {
+#ifdef CONFIG_CPU_PXA26x
+	.inverted = 1,
+#endif
 	.gpio_set_wake = gpio_set_wake,
 };
 
diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index da6e7fd..6d61a69 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -71,6 +71,7 @@ struct pxa_gpio_chip {
 	struct gpio_chip chip;
 	void __iomem	*regbase;
 	unsigned int	irq_base;
+	unsigned int	inverted;
 	char label[10];
 
 	unsigned long	irq_mask;
@@ -126,9 +127,9 @@ static inline int gpio_is_mmp_type(int type)
 /* GPIO86/87/88/89 on PXA26x have their direction bits in PXA_GPDR(2 inverted,
  * as well as their Alternate Function value being '1' for GPIO in GAFRx.
  */
-static inline int __gpio_is_inverted(int gpio)
+static inline int __gpio_is_inverted(struct pxa_gpio_chip *chip, int gpio)
 {
-	if ((gpio_type == PXA26X_GPIO) && (gpio > 85))
+	if ((chip->inverted) && (gpio > 85))
 		return 1;
 	return 0;
 }
@@ -139,15 +140,13 @@ static inline int __gpio_is_inverted(int gpio)
  * is attributed as "occupied" here (I know this terminology isn't
  * accurate, you are welcome to propose a better one :-)
  */
-static inline int __gpio_is_occupied(unsigned gpio)
+static inline int __gpio_is_occupied(struct pxa_gpio_chip *chip, unsigned gpio)
 {
-	struct pxa_gpio_chip *pxachip;
 	void __iomem *base;
 	unsigned long gafr = 0, gpdr = 0;
 	int ret, af = 0, dir = 0;
 
-	pxachip = gpio_to_pxachip(gpio);
-	base = gpio_chip_base(&pxachip->chip);
+	base = gpio_chip_base(&chip->chip);
 	gpdr = readl_relaxed(base + GPDR_OFFSET);
 
 	switch (gpio_type) {
@@ -158,7 +157,7 @@ static inline int __gpio_is_occupied(unsigned gpio)
 		af = (gafr >> ((gpio & 0xf) * 2)) & 0x3;
 		dir = gpdr & GPIO_bit(gpio);
 
-		if (__gpio_is_inverted(gpio))
+		if (__gpio_is_inverted(chip, gpio))
 			ret = (af != 1) || (dir == 0);
 		else
 			ret = (af != 0) || (dir != 0);
@@ -188,16 +187,19 @@ int pxa_irq_to_gpio(struct irq_data *d)
 	return gpio;
 }
 
-static int pxa_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
+static int pxa_gpio_direction_input(struct gpio_chip *gc, unsigned offset)
 {
-	void __iomem *base = gpio_chip_base(chip);
+	struct pxa_gpio_chip *chip = NULL;
+	void __iomem *base = gpio_chip_base(gc);
 	uint32_t value, mask = 1 << offset;
 	unsigned long flags;
 
+	chip = container_of(gc, struct pxa_gpio_chip, chip);
+
 	spin_lock_irqsave(&gpio_lock, flags);
 
 	value = readl_relaxed(base + GPDR_OFFSET);
-	if (__gpio_is_inverted(chip->base + offset))
+	if (__gpio_is_inverted(chip, gc->base + offset))
 		value |= mask;
 	else
 		value &= ~mask;
@@ -207,19 +209,22 @@ static int pxa_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
 	return 0;
 }
 
-static int pxa_gpio_direction_output(struct gpio_chip *chip,
+static int pxa_gpio_direction_output(struct gpio_chip *gc,
 				     unsigned offset, int value)
 {
-	void __iomem *base = gpio_chip_base(chip);
+	struct pxa_gpio_chip *chip = NULL;
+	void __iomem *base = gpio_chip_base(gc);
 	uint32_t tmp, mask = 1 << offset;
 	unsigned long flags;
 
+	chip = container_of(gc, struct pxa_gpio_chip, chip);
+
 	writel_relaxed(mask, base + (value ? GPSR_OFFSET : GPCR_OFFSET));
 
 	spin_lock_irqsave(&gpio_lock, flags);
 
 	tmp = readl_relaxed(base + GPDR_OFFSET);
-	if (__gpio_is_inverted(chip->base + offset))
+	if (__gpio_is_inverted(chip, gc->base + offset))
 		tmp &= ~mask;
 	else
 		tmp |= mask;
@@ -288,7 +293,7 @@ static int pxa_gpio_irq_type(struct irq_data *d, unsigned int type)
 		if ((c->irq_edge_rise | c->irq_edge_fall) & GPIO_bit(gpio))
 			return 0;
 
-		if (__gpio_is_occupied(gpio))
+		if (__gpio_is_occupied(c, gpio))
 			return 0;
 
 		type = IRQ_TYPE_EDGE_RISING | IRQ_TYPE_EDGE_FALLING;
@@ -296,7 +301,7 @@ static int pxa_gpio_irq_type(struct irq_data *d, unsigned int type)
 
 	gpdr = readl_relaxed(c->regbase + GPDR_OFFSET);
 
-	if (__gpio_is_inverted(gpio))
+	if (__gpio_is_inverted(c, gpio))
 		writel_relaxed(gpdr | mask,  c->regbase + GPDR_OFFSET);
 	else
 		writel_relaxed(gpdr & ~mask, c->regbase + GPDR_OFFSET);
@@ -475,6 +480,10 @@ static int pxa_gpio_probe_dt(struct platform_device *pdev)
 	ret = of_find_property(np, "marvell,gpio-ed-mask", NULL);
 	if (ret)
 		pdata->ed_mask = 1;
+	/* It's only valid for PXA26x */
+	ret = of_find_property(np, "marvell,gpio-inverted", NULL);
+	if (ret)
+		pdata->inverted = 1;
 	/* set the platform data */
 	pdev->dev.platform_data = pdata;
 	gpio_type = (int)of_id->data;
@@ -617,6 +626,8 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 		/* unmask GPIO edge detect for AP side */
 		if (info->ed_mask)
 			writel_relaxed(~0, c->regbase + ED_MASK_OFFSET);
+		/* update for gpio inverted */
+		c->inverted = info->inverted;
 	}
 
 	if (!use_of) {
diff --git a/include/linux/gpio-pxa.h b/include/linux/gpio-pxa.h
index bdee118..c8d07be5 100644
--- a/include/linux/gpio-pxa.h
+++ b/include/linux/gpio-pxa.h
@@ -17,6 +17,7 @@ extern int pxa_irq_to_gpio(struct irq_data *d);
 
 struct pxa_gpio_platform_data {
 	unsigned ed_mask;	/* not 0 means ed_mask reg is available */
+	unsigned inverted;	/* only valid for PXA26x */
 	int (*gpio_set_wake)(unsigned int gpio, unsigned int on);
 };
 
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 03/10] gpio: pxa: avoid to use global irq base
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

Avoid to use global irq_base in gpio-pxa driver. Define irq_base in each
pxa_gpio_chip instead. Then we can avoid to use macro PXA_GPIO_TO_IRQ() &
MMP_GPIO_TO_IRQ().

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 arch/arm/mach-pxa/pxa25x.c |    2 +-
 arch/arm/mach-pxa/pxa27x.c |    2 +-
 drivers/gpio/gpio-pxa.c    |  142 ++++++++++++++++++++++----------------------
 include/linux/gpio-pxa.h   |    4 +-
 4 files changed, 77 insertions(+), 73 deletions(-)

diff --git a/arch/arm/mach-pxa/pxa25x.c b/arch/arm/mach-pxa/pxa25x.c
index 3f5171e..f4c293a 100644
--- a/arch/arm/mach-pxa/pxa25x.c
+++ b/arch/arm/mach-pxa/pxa25x.c
@@ -289,7 +289,7 @@ static inline void pxa25x_init_pm(void) {}
 
 static int pxa25x_set_wake(struct irq_data *d, unsigned int on)
 {
-	int gpio = pxa_irq_to_gpio(d->irq);
+	int gpio = pxa_irq_to_gpio(d);
 	uint32_t mask = 0;
 
 	if (gpio >= 0 && gpio < 85)
diff --git a/arch/arm/mach-pxa/pxa27x.c b/arch/arm/mach-pxa/pxa27x.c
index 8047ee0..257d936 100644
--- a/arch/arm/mach-pxa/pxa27x.c
+++ b/arch/arm/mach-pxa/pxa27x.c
@@ -356,7 +356,7 @@ static inline void pxa27x_init_pm(void) {}
  */
 static int pxa27x_set_wake(struct irq_data *d, unsigned int on)
 {
-	int gpio = pxa_irq_to_gpio(d->irq);
+	int gpio = pxa_irq_to_gpio(d);
 	uint32_t mask;
 
 	if (gpio >= 0 && gpio < 128)
diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 8e66c6b..da6e7fd 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -13,6 +13,7 @@
  */
 #include <linux/module.h>
 #include <linux/clk.h>
+#include <linux/device.h>
 #include <linux/err.h>
 #include <linux/gpio.h>
 #include <linux/gpio-pxa.h>
@@ -61,16 +62,15 @@
 #define BANK_OFF(n)	(((n) < 3) ? (n) << 2 : 0x100 + (((n) - 3) << 2))
 
 int pxa_last_gpio;
-static int irq_base;
 
 #ifdef CONFIG_OF
-static struct irq_domain *domain;
 static struct device_node *pxa_gpio_of_node;
 #endif
 
 struct pxa_gpio_chip {
 	struct gpio_chip chip;
 	void __iomem	*regbase;
+	unsigned int	irq_base;
 	char label[10];
 
 	unsigned long	irq_mask;
@@ -170,14 +170,22 @@ static inline int __gpio_is_occupied(unsigned gpio)
 	return ret;
 }
 
-static int pxa_gpio_to_irq(struct gpio_chip *chip, unsigned offset)
+static int pxa_gpio_to_irq(struct gpio_chip *gc, unsigned offset)
 {
-	return chip->base + offset + irq_base;
+	struct pxa_gpio_chip *chip = NULL;
+
+	chip = container_of(gc, struct pxa_gpio_chip, chip);
+	return chip->irq_base + offset;
 }
 
-int pxa_irq_to_gpio(int irq)
+int pxa_irq_to_gpio(struct irq_data *d)
 {
-	return irq - irq_base;
+	struct pxa_gpio_chip *chip;
+	int gpio;
+
+	chip = (struct pxa_gpio_chip *)d->domain->host_data;
+	gpio = d->irq - chip->irq_base + chip->chip.base;
+	return gpio;
 }
 
 static int pxa_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
@@ -250,47 +258,6 @@ static int pxa_gpio_of_xlate(struct gpio_chip *gc,
 }
 #endif
 
-static int pxa_init_gpio_chip(int gpio_end,
-					int (*set_wake)(unsigned int, unsigned int))
-{
-	int i, gpio, nbanks = gpio_to_bank(gpio_end) + 1;
-	struct pxa_gpio_chip *chips;
-
-	chips = kzalloc(nbanks * sizeof(struct pxa_gpio_chip), GFP_KERNEL);
-	if (chips == NULL) {
-		pr_err("%s: failed to allocate GPIO chips\n", __func__);
-		return -ENOMEM;
-	}
-
-	for (i = 0, gpio = 0; i < nbanks; i++, gpio += 32) {
-		struct gpio_chip *c = &chips[i].chip;
-
-		sprintf(chips[i].label, "gpio-%d", i);
-		chips[i].regbase = gpio_reg_base + BANK_OFF(i);
-		chips[i].set_wake = set_wake;
-
-		c->base  = gpio;
-		c->label = chips[i].label;
-
-		c->direction_input  = pxa_gpio_direction_input;
-		c->direction_output = pxa_gpio_direction_output;
-		c->get = pxa_gpio_get;
-		c->set = pxa_gpio_set;
-		c->to_irq = pxa_gpio_to_irq;
-#ifdef CONFIG_OF_GPIO
-		c->of_node = pxa_gpio_of_node;
-		c->of_xlate = pxa_gpio_of_xlate;
-		c->of_gpio_n_cells = 2;
-#endif
-
-		/* number of GPIOs on last bank may be less than 32 */
-		c->ngpio = (gpio + 31 > gpio_end) ? (gpio_end - gpio + 1) : 32;
-		gpiochip_add(c);
-	}
-	pxa_gpio_chips = chips;
-	return 0;
-}
-
 /* Update only those GRERx and GFERx edge detection register bits if those
  * bits are set in c->irq_mask
  */
@@ -309,7 +276,7 @@ static inline void update_edge_detect(struct pxa_gpio_chip *c)
 static int pxa_gpio_irq_type(struct irq_data *d, unsigned int type)
 {
 	struct pxa_gpio_chip *c;
-	int gpio = pxa_irq_to_gpio(d->irq);
+	int gpio = pxa_irq_to_gpio(d);
 	unsigned long gpdr, mask = GPIO_bit(gpio);
 
 	c = gpio_to_pxachip(gpio);
@@ -383,7 +350,7 @@ static void pxa_gpio_demux_handler(unsigned int irq, struct irq_desc *desc)
 
 static void pxa_ack_muxed_gpio(struct irq_data *d)
 {
-	int gpio = pxa_irq_to_gpio(d->irq);
+	int gpio = pxa_irq_to_gpio(d);
 	struct pxa_gpio_chip *c = gpio_to_pxachip(gpio);
 
 	writel_relaxed(GPIO_bit(gpio), c->regbase + GEDR_OFFSET);
@@ -391,7 +358,7 @@ static void pxa_ack_muxed_gpio(struct irq_data *d)
 
 static void pxa_mask_muxed_gpio(struct irq_data *d)
 {
-	int gpio = pxa_irq_to_gpio(d->irq);
+	int gpio = pxa_irq_to_gpio(d);
 	struct pxa_gpio_chip *c = gpio_to_pxachip(gpio);
 	uint32_t grer, gfer;
 
@@ -405,7 +372,7 @@ static void pxa_mask_muxed_gpio(struct irq_data *d)
 
 static int pxa_gpio_set_wake(struct irq_data *d, unsigned int on)
 {
-	int gpio = pxa_irq_to_gpio(d->irq);
+	int gpio = pxa_irq_to_gpio(d);
 	struct pxa_gpio_chip *c = gpio_to_pxachip(gpio);
 
 	if (c->set_wake)
@@ -416,7 +383,7 @@ static int pxa_gpio_set_wake(struct irq_data *d, unsigned int on)
 
 static void pxa_unmask_muxed_gpio(struct irq_data *d)
 {
-	int gpio = pxa_irq_to_gpio(d->irq);
+	int gpio = pxa_irq_to_gpio(d);
 	struct pxa_gpio_chip *c = gpio_to_pxachip(gpio);
 
 	c->irq_mask |= GPIO_bit(gpio);
@@ -485,7 +452,7 @@ static int pxa_irq_domain_map(struct irq_domain *d, unsigned int irq,
 	return 0;
 }
 
-const struct irq_domain_ops pxa_irq_domain_ops = {
+static const struct irq_domain_ops pxa_irq_domain_ops = {
 	.map	= pxa_irq_domain_map,
 	.xlate	= irq_domain_xlate_twocell,
 };
@@ -529,14 +496,6 @@ static int pxa_gpio_probe_dt(struct platform_device *pdev)
 	nr_gpios = nr_banks << 5;
 	pxa_last_gpio = nr_gpios - 1;
 
-	irq_base = irq_alloc_descs(-1, 0, nr_gpios, 0);
-	if (irq_base < 0) {
-		dev_err(&pdev->dev, "Failed to allocate IRQ numbers\n");
-		goto err;
-	}
-	domain = irq_domain_add_legacy(np, nr_gpios, irq_base, 0,
-				       &pxa_irq_domain_ops, NULL);
-	pxa_gpio_of_node = np;
 	return 0;
 err:
 	iounmap(gpio_reg_base);
@@ -546,6 +505,56 @@ err:
 #define pxa_gpio_probe_dt(pdev)		(-1)
 #endif
 
+static int pxa_init_gpio_chip(struct platform_device *pdev, int gpio_end,
+			      int (*set_wake)(unsigned int, unsigned int))
+{
+	int i, gpio, nbanks = gpio_to_bank(gpio_end) + 1;
+	struct pxa_gpio_chip *chips;
+
+	chips = devm_kzalloc(&pdev->dev, nbanks * sizeof(*chips), GFP_KERNEL);
+	if (chips == NULL) {
+		pr_err("%s: failed to allocate GPIO chips\n", __func__);
+		return -ENOMEM;
+	}
+
+	for (i = 0, gpio = 0; i < nbanks; i++, gpio += 32) {
+		struct gpio_chip *c = &chips[i].chip;
+
+		sprintf(chips[i].label, "gpio-%d", i);
+		chips[i].regbase = gpio_reg_base + BANK_OFF(i);
+		chips[i].set_wake = set_wake;
+
+		c->base  = gpio;
+		c->label = chips[i].label;
+
+		c->direction_input  = pxa_gpio_direction_input;
+		c->direction_output = pxa_gpio_direction_output;
+		c->get = pxa_gpio_get;
+		c->set = pxa_gpio_set;
+		c->to_irq = pxa_gpio_to_irq;
+#ifdef CONFIG_OF_GPIO
+		c->of_node = pxa_gpio_of_node;
+		c->of_xlate = pxa_gpio_of_xlate;
+		c->of_gpio_n_cells = 2;
+#endif
+
+		/* number of GPIOs on last bank may be less than 32 */
+		c->ngpio = (gpio + 31 > gpio_end) ? (gpio_end - gpio + 1) : 32;
+
+		chips[i].irq_base = irq_alloc_descs(-1, 0, c->ngpio, 0);
+		if (chips[i].irq_base < 0)
+			return -EINVAL;
+		if (!irq_domain_add_legacy(pdev->dev.of_node, c->ngpio,
+					   chips[i].irq_base, 0,
+					   &pxa_irq_domain_ops, &chips[i]))
+			return -ENODEV;
+
+		gpiochip_add(c);
+	}
+	pxa_gpio_chips = chips;
+	return 0;
+}
+
 static int pxa_gpio_probe(struct platform_device *pdev)
 {
 	struct pxa_gpio_chip *c;
@@ -558,14 +567,6 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 	ret = pxa_gpio_probe_dt(pdev);
 	if (ret < 0) {
 		pxa_last_gpio = pxa_gpio_nums();
-#ifdef CONFIG_ARCH_PXA
-		if (gpio_is_pxa_type(gpio_type))
-			irq_base = PXA_GPIO_TO_IRQ(0);
-#endif
-#ifdef CONFIG_ARCH_MMP
-		if (gpio_is_mmp_type(gpio_type))
-			irq_base = MMP_GPIO_TO_IRQ(0);
-#endif
 	} else {
 		use_of = 1;
 	}
@@ -605,7 +606,8 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 
 	/* Initialize GPIO chips */
 	info = dev_get_platdata(&pdev->dev);
-	pxa_init_gpio_chip(pxa_last_gpio, info ? info->gpio_set_wake : NULL);
+	pxa_init_gpio_chip(pdev, pxa_last_gpio,
+			   info ? info->gpio_set_wake : NULL);
 
 	/* clear all GPIO edge detects */
 	for_each_gpio_chip(gpio, c) {
diff --git a/include/linux/gpio-pxa.h b/include/linux/gpio-pxa.h
index d88d6e3..bdee118 100644
--- a/include/linux/gpio-pxa.h
+++ b/include/linux/gpio-pxa.h
@@ -1,6 +1,8 @@
 #ifndef __GPIO_PXA_H
 #define __GPIO_PXA_H
 
+#include <linux/irq.h>
+
 #define GPIO_bit(x)	(1 << ((x) & 0x1f))
 
 #define gpio_to_bank(gpio)	((gpio) >> 5)
@@ -11,7 +13,7 @@
  */
 extern int pxa_last_gpio;
 
-extern int pxa_irq_to_gpio(int irq);
+extern int pxa_irq_to_gpio(struct irq_data *d);
 
 struct pxa_gpio_platform_data {
 	unsigned ed_mask;	/* not 0 means ed_mask reg is available */
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 02/10] gpio: pxa: identify ed mask reg with platform data
From: Haojian Zhuang @ 2013-01-23  8:25 UTC (permalink / raw)
  To: linux-arm-kernel
In-Reply-To: <1358929554-32265-1-git-send-email-haojian.zhuang@linaro.org>

Avoid to judge whether edge mask register exists by CPU. Use platform
data to identify it instead. The gpio edge mask register exists in MMP
series SoC.

Signed-off-by: Haojian Zhuang <haojian.zhuang@linaro.org>
---
 arch/arm/mach-mmp/aspenite.c      |    7 +++++++
 arch/arm/mach-mmp/avengers_lite.c |    7 +++++++
 arch/arm/mach-mmp/brownstone.c    |    7 +++++++
 arch/arm/mach-mmp/flint.c         |    7 +++++++
 arch/arm/mach-mmp/gplugd.c        |    7 +++++++
 arch/arm/mach-mmp/tavorevb.c      |    7 +++++++
 arch/arm/mach-mmp/teton_bga.c     |    7 +++++++
 arch/arm/mach-mmp/ttc_dkb.c       |    7 +++++++
 drivers/gpio/gpio-pxa.c           |   11 ++++++++++-
 include/linux/gpio-pxa.h          |    1 +
 10 files changed, 67 insertions(+), 1 deletion(-)

diff --git a/arch/arm/mach-mmp/aspenite.c b/arch/arm/mach-mmp/aspenite.c
index e5dba9c..ee1fb62 100644
--- a/arch/arm/mach-mmp/aspenite.c
+++ b/arch/arm/mach-mmp/aspenite.c
@@ -9,6 +9,7 @@
  *  publishhed by the Free Software Foundation.
  */
 #include <linux/gpio.h>
+#include <linux/gpio-pxa.h>
 #include <linux/init.h>
 #include <linux/kernel.h>
 #include <linux/platform_device.h>
@@ -110,6 +111,10 @@ static unsigned long common_pin_config[] __initdata = {
 	GPIO121_KP_MKIN4,
 };
 
+static struct pxa_gpio_platform_data pxa168_gpio_pdata = {
+	.ed_mask	= 1,
+};
+
 static struct smc91x_platdata smc91x_info = {
 	.flags	= SMC91X_USE_16BIT | SMC91X_NOWAIT,
 };
@@ -248,6 +253,8 @@ static void __init common_init(void)
 	pxa168_add_nand(&aspenite_nand_info);
 	pxa168_add_fb(&aspenite_lcd_info);
 	pxa168_add_keypad(&aspenite_keypad_info);
+	platform_device_add_data(&pxa168_device_gpio, &pxa168_gpio_pdata,
+				 sizeof(struct pxa_gpio_platform_data));
 	platform_device_register(&pxa168_device_gpio);
 
 	/* off-chip devices */
diff --git a/arch/arm/mach-mmp/avengers_lite.c b/arch/arm/mach-mmp/avengers_lite.c
index 603542a..8b4b1ae 100644
--- a/arch/arm/mach-mmp/avengers_lite.c
+++ b/arch/arm/mach-mmp/avengers_lite.c
@@ -12,6 +12,7 @@
 
 #include <linux/init.h>
 #include <linux/kernel.h>
+#include <linux/gpio-pxa.h>
 #include <linux/platform_device.h>
 
 #include <asm/mach-types.h>
@@ -32,12 +33,18 @@ static unsigned long avengers_lite_pin_config_V16F[] __initdata = {
 	GPIO89_UART2_RXD,
 };
 
+static struct pxa_gpio_platform_data pxa168_gpio_pdata = {
+	.ed_mask	= 1,
+};
+
 static void __init avengers_lite_init(void)
 {
 	mfp_config(ARRAY_AND_SIZE(avengers_lite_pin_config_V16F));
 
 	/* on-chip devices */
 	pxa168_add_uart(2);
+	platform_device_add_data(&pxa168_device_gpio, &pxa168_gpio_pdata,
+				 sizeof(struct pxa_gpio_platform_data));
 	platform_device_register(&pxa168_device_gpio);
 }
 
diff --git a/arch/arm/mach-mmp/brownstone.c b/arch/arm/mach-mmp/brownstone.c
index 5cb769c..0454488 100644
--- a/arch/arm/mach-mmp/brownstone.c
+++ b/arch/arm/mach-mmp/brownstone.c
@@ -14,6 +14,7 @@
 #include <linux/kernel.h>
 #include <linux/platform_device.h>
 #include <linux/io.h>
+#include <linux/gpio-pxa.h>
 #include <linux/regulator/machine.h>
 #include <linux/regulator/max8649.h>
 #include <linux/regulator/fixed.h>
@@ -104,6 +105,10 @@ static unsigned long brownstone_pin_config[] __initdata = {
 	GPIO89_GPIO,
 };
 
+static struct pxa_gpio_platform_data mmp2_gpio_pdata = {
+	.ed_mask	= 1,
+};
+
 static struct regulator_consumer_supply max8649_supply[] = {
 	REGULATOR_SUPPLY("vcc_core", NULL),
 };
@@ -202,6 +207,8 @@ static void __init brownstone_init(void)
 	/* on-chip devices */
 	mmp2_add_uart(1);
 	mmp2_add_uart(3);
+	platform_device_add_data(&mmp2_device_gpio, &mmp2_gpio_pdata,
+				 sizeof(struct pxa_gpio_platform_data));
 	platform_device_register(&mmp2_device_gpio);
 	mmp2_add_twsi(1, NULL, ARRAY_AND_SIZE(brownstone_twsi1_info));
 	mmp2_add_sdhost(0, &mmp2_sdh_platdata_mmc0); /* SD/MMC */
diff --git a/arch/arm/mach-mmp/flint.c b/arch/arm/mach-mmp/flint.c
index 8059cc0..7ec873c 100644
--- a/arch/arm/mach-mmp/flint.c
+++ b/arch/arm/mach-mmp/flint.c
@@ -16,6 +16,7 @@
 #include <linux/smc91x.h>
 #include <linux/io.h>
 #include <linux/gpio.h>
+#include <linux/gpio-pxa.h>
 #include <linux/interrupt.h>
 
 #include <asm/mach-types.h>
@@ -77,6 +78,10 @@ static unsigned long flint_pin_config[] __initdata = {
 	GPIO160_ND_RDY1,
 };
 
+static struct pxa_gpio_platform_data mmp2_gpio_pdata = {
+	.ed_mask	= 1,
+};
+
 static struct smc91x_platdata flint_smc91x_info = {
 	.flags  = SMC91X_USE_16BIT | SMC91X_NOWAIT,
 };
@@ -111,6 +116,8 @@ static void __init flint_init(void)
 	/* on-chip devices */
 	mmp2_add_uart(1);
 	mmp2_add_uart(2);
+	platform_device_add_data(&mmp2_device_gpio, &mmp2_gpio_pdata,
+				 sizeof(struct pxa_gpio_platform_data));
 	platform_device_register(&mmp2_device_gpio);
 
 	/* off-chip devices */
diff --git a/arch/arm/mach-mmp/gplugd.c b/arch/arm/mach-mmp/gplugd.c
index 5c3d61e..d592041 100644
--- a/arch/arm/mach-mmp/gplugd.c
+++ b/arch/arm/mach-mmp/gplugd.c
@@ -10,6 +10,7 @@
 
 #include <linux/init.h>
 #include <linux/gpio.h>
+#include <linux/gpio-pxa.h>
 
 #include <asm/mach/arch.h>
 #include <asm/mach-types.h>
@@ -127,6 +128,10 @@ static unsigned long gplugd_pin_config[] __initdata = {
 	GPIO116_I2S_TXD
 };
 
+static struct pxa_gpio_platform_data pxa168_gpio_pdata = {
+	.ed_mask	= 1,
+};
+
 static struct i2c_board_info gplugd_i2c_board_info[] = {
 	{
 		.type = "isl1208",
@@ -185,6 +190,8 @@ static void __init gplugd_init(void)
 	pxa168_add_uart(3);
 	pxa168_add_ssp(1);
 	pxa168_add_twsi(0, NULL, ARRAY_AND_SIZE(gplugd_i2c_board_info));
+	platform_device_add_data(&pxa168_device_gpio, &pxa168_gpio_pdata,
+				 sizeof(struct pxa_gpio_platform_data));
 	platform_device_register(&pxa168_device_gpio);
 
 	pxa168_add_eth(&gplugd_eth_platform_data);
diff --git a/arch/arm/mach-mmp/tavorevb.c b/arch/arm/mach-mmp/tavorevb.c
index b28f908..a855e69 100644
--- a/arch/arm/mach-mmp/tavorevb.c
+++ b/arch/arm/mach-mmp/tavorevb.c
@@ -8,6 +8,7 @@
  *  publishhed by the Free Software Foundation.
  */
 #include <linux/gpio.h>
+#include <linux/gpio-pxa.h>
 #include <linux/init.h>
 #include <linux/kernel.h>
 #include <linux/platform_device.h>
@@ -60,6 +61,10 @@ static unsigned long tavorevb_pin_config[] __initdata = {
 	DF_RDY0_DF_RDY0,
 };
 
+static struct pxa_gpio_platform_data ttc_dkb_gpio_pdata = {
+	.ed_mask	= 1,
+};
+
 static struct smc91x_platdata tavorevb_smc91x_info = {
 	.flags	= SMC91X_USE_16BIT | SMC91X_NOWAIT,
 };
@@ -93,6 +98,8 @@ static void __init tavorevb_init(void)
 
 	/* on-chip devices */
 	pxa910_add_uart(1);
+	platform_device_add_data(&pxa910_device_gpio, &ttc_dkb_gpio_pdata,
+				 sizeof(struct pxa_gpio_platform_data));
 	platform_device_register(&pxa910_device_gpio);
 
 	/* off-chip devices */
diff --git a/arch/arm/mach-mmp/teton_bga.c b/arch/arm/mach-mmp/teton_bga.c
index dd30ea7..9f64f37 100644
--- a/arch/arm/mach-mmp/teton_bga.c
+++ b/arch/arm/mach-mmp/teton_bga.c
@@ -16,6 +16,7 @@
 #include <linux/kernel.h>
 #include <linux/platform_device.h>
 #include <linux/gpio.h>
+#include <linux/gpio-pxa.h>
 #include <linux/input.h>
 #include <linux/platform_data/keypad-pxa27x.h>
 #include <linux/i2c.h>
@@ -49,6 +50,10 @@ static unsigned long teton_bga_pin_config[] __initdata = {
 	GPIO78_GPIO,
 };
 
+static struct pxa_gpio_platform_data pxa168_gpio_pdata = {
+	.ed_mask	= 1,
+};
+
 static unsigned int teton_bga_matrix_key_map[] = {
 	KEY(0, 6, KEY_ESC),
 	KEY(0, 7, KEY_ENTER),
@@ -79,6 +84,8 @@ static void __init teton_bga_init(void)
 	pxa168_add_uart(1);
 	pxa168_add_keypad(&teton_bga_keypad_info);
 	pxa168_add_twsi(0, NULL, ARRAY_AND_SIZE(teton_bga_i2c_info));
+	platform_device_add_data(&pxa168_device_gpio, &pxa168_gpio_pdata,
+				 sizeof(struct pxa_gpio_platform_data));
 	platform_device_register(&pxa168_device_gpio);
 }
 
diff --git a/arch/arm/mach-mmp/ttc_dkb.c b/arch/arm/mach-mmp/ttc_dkb.c
index ce55fd8..74081cd 100644
--- a/arch/arm/mach-mmp/ttc_dkb.c
+++ b/arch/arm/mach-mmp/ttc_dkb.c
@@ -17,6 +17,7 @@
 #include <linux/interrupt.h>
 #include <linux/i2c/pca953x.h>
 #include <linux/gpio.h>
+#include <linux/gpio-pxa.h>
 #include <linux/mfd/88pm860x.h>
 #include <linux/platform_data/mv_usb.h>
 
@@ -73,6 +74,10 @@ static unsigned long ttc_dkb_pin_config[] __initdata = {
 	DF_RDY0_DF_RDY0,
 };
 
+static struct pxa_gpio_platform_data ttc_dkb_gpio_pdata = {
+	.ed_mask	= 1,
+};
+
 static struct mtd_partition ttc_dkb_onenand_partitions[] = {
 	{
 		.name		= "bootloader",
@@ -196,6 +201,8 @@ static void __init ttc_dkb_init(void)
 
 	/* off-chip devices */
 	pxa910_add_twsi(0, NULL, ARRAY_AND_SIZE(ttc_dkb_i2c_info));
+	platform_device_add_data(&pxa910_device_gpio, &ttc_dkb_gpio_pdata,
+				 sizeof(struct pxa_gpio_platform_data));
 	platform_add_devices(ARRAY_AND_SIZE(ttc_dkb_devices));
 
 #ifdef CONFIG_USB_MV_UDC
diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 9cc108d..8e66c6b 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -493,6 +493,7 @@ const struct irq_domain_ops pxa_irq_domain_ops = {
 static int pxa_gpio_probe_dt(struct platform_device *pdev)
 {
 	int ret, nr_banks, nr_gpios;
+	struct pxa_gpio_platform_data *pdata;
 	struct device_node *prev, *next, *np = pdev->dev.of_node;
 	const struct of_device_id *of_id =
 				of_match_device(pxa_gpio_dt_ids, &pdev->dev);
@@ -501,6 +502,14 @@ static int pxa_gpio_probe_dt(struct platform_device *pdev)
 		dev_err(&pdev->dev, "Failed to find gpio controller\n");
 		return -EFAULT;
 	}
+	pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL);
+	if (!pdata)
+		return -ENOMEM;
+	ret = of_find_property(np, "marvell,gpio-ed-mask", NULL);
+	if (ret)
+		pdata->ed_mask = 1;
+	/* set the platform data */
+	pdev->dev.platform_data = pdata;
 	gpio_type = (int)of_id->data;
 
 	next = of_get_next_child(np, NULL);
@@ -604,7 +613,7 @@ static int pxa_gpio_probe(struct platform_device *pdev)
 		writel_relaxed(0, c->regbase + GRER_OFFSET);
 		writel_relaxed(~0,c->regbase + GEDR_OFFSET);
 		/* unmask GPIO edge detect for AP side */
-		if (gpio_is_mmp_type(gpio_type))
+		if (info->ed_mask)
 			writel_relaxed(~0, c->regbase + ED_MASK_OFFSET);
 	}
 
diff --git a/include/linux/gpio-pxa.h b/include/linux/gpio-pxa.h
index d755b28..d88d6e3 100644
--- a/include/linux/gpio-pxa.h
+++ b/include/linux/gpio-pxa.h
@@ -14,6 +14,7 @@ extern int pxa_last_gpio;
 extern int pxa_irq_to_gpio(int irq);
 
 struct pxa_gpio_platform_data {
+	unsigned ed_mask;	/* not 0 means ed_mask reg is available */
 	int (*gpio_set_wake)(unsigned int gpio, unsigned int on);
 };
 
-- 
1.7.10.4

^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox