Linux-ARM-Kernel Archive on lore.kernel.org
 help / color / mirror / Atom feed
* Re: [PATCH 2/4] remoteproc: introduce version element into resource type field
From: Suman Anna @ 2020-05-21 19:06 UTC (permalink / raw)
  To: Bjorn Andersson
  Cc: devicetree, Mathieu Poirier, Loic Pallardy, Lokesh Vutla,
	linux-remoteproc, Arnaud Pouliquen, linux-kernel, Clement Leger,
	Rob Herring, linux-arm-kernel
In-Reply-To: <20200521175421.GI408178@builder.lan>

Hi Bjorn,

On 5/21/20 12:54 PM, Bjorn Andersson wrote:
> On Wed 25 Mar 13:46 PDT 2020, Suman Anna wrote:
> 
>> The current remoteproc core has supported only 32-bit remote
>> processors and as such some of the current resource structures
>> may not scale well for 64-bit remote processors, and would
>> require new versions of resource types. Each resource is currently
>> identified by a 32-bit type field. Introduce the concept of version
>> for these resource types by overloading this 32-bit type field
>> into two 16-bit version and type fields with the existing resources
>> behaving as version 0 thereby providing backward compatibility.
>>
>> The version field is passed as an additional argument to each of
>> the handler functions, and all the existing handlers are updated
>> accordingly. Each specific handler will be updated on a need basis
>> when a new version of the resource type is added.
>>
> 
> I really would prefer that we add additional types for the new
> structures, neither side will be compatible with new versions without
> enhancements to their respective implementations anyways.

OK.

> 
>> An alternate way would be to introduce the new types as completely
>> new resource types which would require additional customization of
>> the resource handlers based on the 32-bit or 64-bit mode of a remote
>> processor, and introduction of an additional mode flag to the rproc
>> structure.
>>
> 
> What would this "mode" indicate? If it's version 0 or 1?

No, for indicating if the remoteproc is 32-bit or 64-bit and adjust the 
loading handlers if the resource types need to be segregated accordingly.

> 
>> Signed-off-by: Suman Anna <s-anna@ti.com>
>> ---
>>   drivers/remoteproc/remoteproc_core.c    | 25 +++++++++++++++----------
>>   drivers/remoteproc/remoteproc_debugfs.c | 17 ++++++++++-------
>>   include/linux/remoteproc.h              |  8 +++++++-
>>   3 files changed, 32 insertions(+), 18 deletions(-)
>>
> [..]
>> diff --git a/include/linux/remoteproc.h b/include/linux/remoteproc.h
>> index 77788a4bb94e..526d3cb45e37 100644
>> --- a/include/linux/remoteproc.h
>> +++ b/include/linux/remoteproc.h
>> @@ -86,7 +86,13 @@ struct resource_table {
>>    * this header, and it should be parsed according to the resource type.
>>    */
>>   struct fw_rsc_hdr {
>> -	u32 type;
>> +	union {
>> +		u32 type;
>> +		struct {
>> +			u16 t;
>> +			u16 v;
>> +		} st;
> 
> I see your "type" is little endian...

Yeah, definitely a draw-back if we want to support big-endian rprocs. Do 
you have any remoteprocs following big-endian? All TI remoteprocs are 
little-endian except for really old ones.

regards
Suman

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [V8, 1/2] media: dt-bindings: media: i2c: Document OV02A10 bindings
From: Tomasz Figa @ 2020-05-21 18:59 UTC (permalink / raw)
  To: Dongchun Zhu, Rob Herring
  Cc: Mark Rutland, linux-devicetree, Andy Shevchenko, srv_heupstream,
	Linus Walleij, Shengnan Wang (王圣男),
	Louis Kuo, Bartosz Golaszewski, Sj Huang, Nicolas Boichat,
	moderated list:ARM/Mediatek SoC support, Sakari Ailus,
	Matthias Brugger, Cao Bing Bu, Mauro Carvalho Chehab,
	list@263.net:IOMMU DRIVERS <iommu@lists.linux-foundation.org>, Joerg Roedel <joro@8bytes.org>, ,
	Linux Media Mailing List
In-Reply-To: <1589251221.8804.289.camel@mhfsdcap03>

Hi Dongchun, Rob,

On Tue, May 12, 2020 at 4:41 AM Dongchun Zhu <dongchun.zhu@mediatek.com> wrote:
>
> Hi Rob,
>
> Thanks for the review.
>
> On Mon, 2020-05-11 at 11:02 -0500, Rob Herring wrote:
> > On Sat, May 09, 2020 at 04:06:26PM +0800, Dongchun Zhu wrote:
[snip]
> > > +            port {
> > > +                wcam_out: endpoint {
> > > +                    remote-endpoint = <&mipi_in_wcam>;
> > > +                    data-lanes = <1>;
> >
> > This doesn't match the schema which says this should be 4 entries.
> >
>
> Property "data-lanes" shows the number of lanes that sensor supports.
> If this property is omitted, four-lane operation is assumed.
> For OV02A10, it is one-lane operation, so the property is supposed to be
> set to <1>.
>

To clarify on this, the ov02a10 sensor supports only 1 lane. It's not
a driver limitation.

Best regards,
Tomasz

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH v2 0/4] TI K3 DSP remoteproc driver for C66x DSPs
From: Bjorn Andersson @ 2020-05-21 19:01 UTC (permalink / raw)
  To: Suman Anna
  Cc: devicetree, Mathieu Poirier, Lokesh Vutla, linux-remoteproc,
	linux-kernel, Rob Herring, linux-arm-kernel
In-Reply-To: <5f84465e-8f63-51b4-4758-59c85d3ad597@ti.com>

On Thu 21 May 11:59 PDT 2020, Suman Anna wrote:

> Hi Bjorn,
> 
> On 5/20/20 7:10 PM, Suman Anna wrote:
> > Hi All,
> > 
> > The following is v2 of the K3 DSP remoteproc driver supporting the C66x DSPs
> > on the TI K3 J721E SoCs. The patches are based on the latest commit on the
> > rproc-next branch, 7dcef3988eed ("remoteproc: Fix an error code in
> > devm_rproc_alloc()").
> 
> I realized I also had the R5F patches on my branch, so the third patch won't
> apply cleanly (conflict on Makefile). Let me know if you want a new revision
> posted for you to pick up the series.
> 

That should be fine, thanks for the heads up!

Will give Mathieu a day or two to take a look as well.

Regards,
Bjorn

> regards
> Suman
> 
> > 
> > v2 includes a new remoteproc core patch (patch 1) that adds an OF helper
> > for parsing the firmware-name property. This is refactored out to avoid
> > replicating the code in various remoteproc drivers. Please see the
> > individual patches for detailed changes.
> > 
> > The main dependent patches from the previous series are now staged in
> > rproc-next branch. The only dependency for this series is the common
> > ti-sci-proc helper between R5 and DSP drivers [1]. Please see the initial
> > cover-letter [2] for v1 details.
> > 
> > regards
> > Suman
> > 
> > [1] https://patchwork.kernel.org/patch/11456379/
> > [2] https://patchwork.kernel.org/cover/11458573/
> > 
> > Suman Anna (4):
> >    remoteproc: Introduce rproc_of_parse_firmware() helper
> >    dt-bindings: remoteproc: Add bindings for C66x DSPs on TI K3 SoCs
> >    remoteproc/k3-dsp: Add a remoteproc driver of K3 C66x DSPs
> >    remoteproc/k3-dsp: Add support for L2RAM loading on C66x DSPs
> > 
> >   .../bindings/remoteproc/ti,k3-dsp-rproc.yaml  | 190 +++++
> >   drivers/remoteproc/Kconfig                    |  13 +
> >   drivers/remoteproc/Makefile                   |   1 +
> >   drivers/remoteproc/remoteproc_core.c          |  23 +
> >   drivers/remoteproc/remoteproc_internal.h      |   2 +
> >   drivers/remoteproc/ti_k3_dsp_remoteproc.c     | 773 ++++++++++++++++++
> >   6 files changed, 1002 insertions(+)
> >   create mode 100644 Documentation/devicetree/bindings/remoteproc/ti,k3-dsp-rproc.yaml
> >   create mode 100644 drivers/remoteproc/ti_k3_dsp_remoteproc.c
> > 
> 

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH v2 1/3] ARM: pxa: remove Compulab pxa2xx boards
From: Mike Rapoport @ 2020-05-21 19:01 UTC (permalink / raw)
  To: Arnd Bergmann
  Cc: linux-mtd, Boris Brezillon, Robert Jarzmik, Linux ARM,
	Miquel Raynal
In-Reply-To: <CAK8P3a2XdG_u6_o2NbQDTb5dbdzByBkUXZNM6nZ3wz0c-LFT5w@mail.gmail.com>

On Thu, May 21, 2020 at 09:26:10AM +0200, Arnd Bergmann wrote:
> On Thu, May 21, 2020 at 9:12 AM Mike Rapoport <rppt@kernel.org> wrote:
> >
> > On Wed, May 20, 2020 at 05:21:51PM +0200, Arnd Bergmann wrote:
> > > On Wed, May 20, 2020 at 12:21 PM Robert Jarzmik <robert.jarzmik@free.fr> wrote:
> > > >
> > > > As these boards have no more users nor testers, and patching them has
> > > > become a burden, be that because of the PCI part or the MTD NAND
> > > > support, let's remove them.
> > > >
> > > > The cm-x300 will for now remain and represent Compulab boards at its
> > > > best in the PXA department.
> >
> > I think this series missed the cm-x270 NAND driver, so this could be
> > PATCH 4/3 (not even compile tested).
> >
> > From 56a11987f82ef8b32b25dfc17b849f9bbbf03e4d Mon Sep 17 00:00:00 2001
> > From: Mike Rapoport <rppt@linux.ibm.com>
> > Date: Thu, 21 May 2020 10:09:47 +0300
> > Subject: [PATCH] mtd: rawnand: remove CM-X270 NAND driver
> >
> > The cm-x270 board have been removed and theres is no point to keep this
> > driver.
> >
> > Signed-off-by: Mike Rapoport <rppt@linux.ibm.com>
> 
> Thanks! Removing that driver was actually how the discussion started,
> so we definitely want to do that. Boris earlier patch "mtd: rawnand: Get
> rid of the cmx270 driver" did it by changing the board file, now your
> patch is the right thing to do, and we should remember to do the same
> for mbxfb.

Arnd, will you pick this to the SoC tree or should I resend?

>       Arnd

-- 
Sincerely yours,
Mike.

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH v2 0/4] TI K3 DSP remoteproc driver for C66x DSPs
From: Suman Anna @ 2020-05-21 18:59 UTC (permalink / raw)
  To: Bjorn Andersson, Rob Herring, Mathieu Poirier
  Cc: Lokesh Vutla, devicetree, linux-remoteproc, linux-kernel,
	linux-arm-kernel
In-Reply-To: <20200521001006.2725-1-s-anna@ti.com>

Hi Bjorn,

On 5/20/20 7:10 PM, Suman Anna wrote:
> Hi All,
> 
> The following is v2 of the K3 DSP remoteproc driver supporting the C66x DSPs
> on the TI K3 J721E SoCs. The patches are based on the latest commit on the
> rproc-next branch, 7dcef3988eed ("remoteproc: Fix an error code in
> devm_rproc_alloc()").

I realized I also had the R5F patches on my branch, so the third patch 
won't apply cleanly (conflict on Makefile). Let me know if you want a 
new revision posted for you to pick up the series.

regards
Suman

> 
> v2 includes a new remoteproc core patch (patch 1) that adds an OF helper
> for parsing the firmware-name property. This is refactored out to avoid
> replicating the code in various remoteproc drivers. Please see the
> individual patches for detailed changes.
> 
> The main dependent patches from the previous series are now staged in
> rproc-next branch. The only dependency for this series is the common
> ti-sci-proc helper between R5 and DSP drivers [1]. Please see the initial
> cover-letter [2] for v1 details.
> 
> regards
> Suman
> 
> [1] https://patchwork.kernel.org/patch/11456379/
> [2] https://patchwork.kernel.org/cover/11458573/
> 
> Suman Anna (4):
>    remoteproc: Introduce rproc_of_parse_firmware() helper
>    dt-bindings: remoteproc: Add bindings for C66x DSPs on TI K3 SoCs
>    remoteproc/k3-dsp: Add a remoteproc driver of K3 C66x DSPs
>    remoteproc/k3-dsp: Add support for L2RAM loading on C66x DSPs
> 
>   .../bindings/remoteproc/ti,k3-dsp-rproc.yaml  | 190 +++++
>   drivers/remoteproc/Kconfig                    |  13 +
>   drivers/remoteproc/Makefile                   |   1 +
>   drivers/remoteproc/remoteproc_core.c          |  23 +
>   drivers/remoteproc/remoteproc_internal.h      |   2 +
>   drivers/remoteproc/ti_k3_dsp_remoteproc.c     | 773 ++++++++++++++++++
>   6 files changed, 1002 insertions(+)
>   create mode 100644 Documentation/devicetree/bindings/remoteproc/ti,k3-dsp-rproc.yaml
>   create mode 100644 drivers/remoteproc/ti_k3_dsp_remoteproc.c
> 


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* [PATCH v3 1/3] ARM: pxa: remove Compulab pxa2xx boards
From: Robert Jarzmik @ 2020-05-21 18:51 UTC (permalink / raw)
  To: Daniel Mack, Haojian Zhuang, Robert Jarzmik, Liam Girdwood,
	Mark Brown, Jaroslav Kysela, Takashi Iwai, soc
  Cc: Arnd Bergmann, alsa-devel, Mike Rapoport, linux-kernel,
	linux-arm-kernel

As these boards have no more users nor testers, and patching them has
become a burden, be that because of the PCI part or the MTD NAND
support, let's remove them.

The cm-x300 will for now remain and represent Compulab boards at its
best in the PXA department.

Signed-off-by: Robert Jarzmik <robert.jarzmik@free.fr>
Acked-by: Mike Rapoport <rppt@kernel.org>
Acked-by: Arnd Bergmann <arnd@arndb.de>
---
Since v1: Arnd's comments
Since v2: Acks
---
 arch/arm/configs/cm_x2xx_defconfig  |  173 ----
 arch/arm/configs/em_x270_defconfig  |  178 ----
 arch/arm/configs/pxa_defconfig      |    2 -
 arch/arm/mach-pxa/Kconfig           |   17 -
 arch/arm/mach-pxa/Makefile          |    5 -
 arch/arm/mach-pxa/cm-x255.c         |  240 -----
 arch/arm/mach-pxa/cm-x270.c         |  419 ---------
 arch/arm/mach-pxa/cm-x2xx-pci.c     |  196 ----
 arch/arm/mach-pxa/cm-x2xx-pci.h     |   14 -
 arch/arm/mach-pxa/cm-x2xx.c         |  538 -----------
 arch/arm/mach-pxa/em-x270.c         | 1286 ---------------------------
 arch/arm/mach-pxa/include/mach/io.h |   18 -
 12 files changed, 3086 deletions(-)
 delete mode 100644 arch/arm/configs/cm_x2xx_defconfig
 delete mode 100644 arch/arm/configs/em_x270_defconfig
 delete mode 100644 arch/arm/mach-pxa/cm-x255.c
 delete mode 100644 arch/arm/mach-pxa/cm-x270.c
 delete mode 100644 arch/arm/mach-pxa/cm-x2xx-pci.c
 delete mode 100644 arch/arm/mach-pxa/cm-x2xx-pci.h
 delete mode 100644 arch/arm/mach-pxa/cm-x2xx.c
 delete mode 100644 arch/arm/mach-pxa/em-x270.c
 delete mode 100644 arch/arm/mach-pxa/include/mach/io.h

diff --git a/arch/arm/configs/cm_x2xx_defconfig b/arch/arm/configs/cm_x2xx_defconfig
deleted file mode 100644
index fa997ae2673e..000000000000
--- a/arch/arm/configs/cm_x2xx_defconfig
+++ /dev/null
@@ -1,173 +0,0 @@
-# CONFIG_LOCALVERSION_AUTO is not set
-CONFIG_SYSVIPC=y
-CONFIG_IKCONFIG=y
-CONFIG_IKCONFIG_PROC=y
-CONFIG_LOG_BUF_SHIFT=14
-CONFIG_SYSFS_DEPRECATED_V2=y
-CONFIG_BLK_DEV_INITRD=y
-CONFIG_EXPERT=y
-# CONFIG_VM_EVENT_COUNTERS is not set
-# CONFIG_SLUB_DEBUG is not set
-# CONFIG_COMPAT_BRK is not set
-CONFIG_MODULES=y
-CONFIG_MODULE_UNLOAD=y
-# CONFIG_BLK_DEV_BSG is not set
-CONFIG_ARCH_PXA=y
-CONFIG_MACH_ARMCORE=y
-CONFIG_PCI=y
-CONFIG_PCCARD=m
-CONFIG_YENTA=m
-# CONFIG_YENTA_O2 is not set
-# CONFIG_YENTA_RICOH is not set
-# CONFIG_YENTA_ENE_TUNE is not set
-# CONFIG_YENTA_TOSHIBA is not set
-CONFIG_PCMCIA_PXA2XX=m
-CONFIG_NO_HZ=y
-CONFIG_AEABI=y
-CONFIG_ZBOOT_ROM_TEXT=0x0
-CONFIG_ZBOOT_ROM_BSS=0x0
-CONFIG_CMDLINE="root=1f03 mem=32M"
-CONFIG_FPE_NWFPE=y
-CONFIG_PM=y
-CONFIG_APM_EMULATION=m
-CONFIG_NET=y
-CONFIG_PACKET=y
-CONFIG_UNIX=y
-CONFIG_INET=y
-CONFIG_IP_MULTICAST=y
-CONFIG_IP_PNP=y
-CONFIG_IP_PNP_DHCP=y
-CONFIG_IP_PNP_BOOTP=y
-# CONFIG_INET_DIAG is not set
-# CONFIG_IPV6 is not set
-CONFIG_BT=m
-CONFIG_BT_RFCOMM=m
-CONFIG_BT_BNEP=m
-CONFIG_BT_HIDP=m
-CONFIG_LIB80211=m
-CONFIG_FW_LOADER=m
-CONFIG_MTD=y
-CONFIG_MTD_CMDLINE_PARTS=y
-CONFIG_MTD_BLOCK=y
-CONFIG_MTD_CFI=y
-CONFIG_MTD_JEDECPROBE=y
-CONFIG_MTD_CFI_ADV_OPTIONS=y
-CONFIG_MTD_CFI_INTELEXT=y
-CONFIG_MTD_CFI_AMDSTD=y
-CONFIG_MTD_CFI_STAA=y
-CONFIG_MTD_PHYSMAP=y
-CONFIG_MTD_PXA2XX=y
-CONFIG_MTD_RAW_NAND=y
-CONFIG_MTD_NAND_GPIO=m
-CONFIG_MTD_NAND_CM_X270=y
-CONFIG_MTD_NAND_PLATFORM=y
-CONFIG_BLK_DEV_LOOP=y
-CONFIG_BLK_DEV_RAM=y
-CONFIG_SCSI=y
-CONFIG_BLK_DEV_SD=y
-CONFIG_ATA=m
-# CONFIG_SATA_PMP is not set
-CONFIG_PATA_PCMCIA=m
-CONFIG_NETDEVICES=y
-CONFIG_NET_ETHERNET=y
-CONFIG_DM9000=y
-CONFIG_DM9000_DEBUGLEVEL=1
-CONFIG_NET_PCI=y
-CONFIG_8139TOO=m
-# CONFIG_8139TOO_PIO is not set
-CONFIG_PPP=m
-CONFIG_PPP_MULTILINK=y
-CONFIG_PPP_FILTER=y
-CONFIG_PPP_ASYNC=m
-CONFIG_PPP_DEFLATE=m
-CONFIG_PPP_BSDCOMP=m
-CONFIG_INPUT_EVDEV=y
-CONFIG_KEYBOARD_PXA27x=m
-# CONFIG_INPUT_MOUSE is not set
-CONFIG_INPUT_TOUCHSCREEN=y
-CONFIG_TOUCHSCREEN_UCB1400=m
-# CONFIG_SERIO_SERPORT is not set
-CONFIG_SERIAL_PXA=y
-CONFIG_SERIAL_PXA_CONSOLE=y
-CONFIG_LEGACY_PTY_COUNT=16
-# CONFIG_HW_RANDOM is not set
-CONFIG_I2C=y
-CONFIG_I2C_CHARDEV=m
-CONFIG_I2C_PXA=y
-CONFIG_SPI=y
-CONFIG_SPI_PXA2XX=m
-# CONFIG_HWMON is not set
-CONFIG_UCB1400_CORE=m
-CONFIG_FB=y
-CONFIG_FB_PXA=y
-CONFIG_FB_PXA_PARAMETERS=y
-CONFIG_FB_MBX=m
-# CONFIG_LCD_CLASS_DEVICE is not set
-# CONFIG_BACKLIGHT_CLASS_DEVICE is not set
-# CONFIG_VGA_CONSOLE is not set
-CONFIG_FRAMEBUFFER_CONSOLE=y
-CONFIG_LOGO=y
-CONFIG_SOUND=m
-CONFIG_SND=m
-CONFIG_SND_MIXER_OSS=m
-CONFIG_SND_PCM_OSS=m
-# CONFIG_SND_DRIVERS is not set
-# CONFIG_SND_PCI is not set
-CONFIG_SND_PXA2XX_AC97=m
-# CONFIG_SND_SPI is not set
-# CONFIG_SND_USB is not set
-# CONFIG_SND_PCMCIA is not set
-CONFIG_HID_A4TECH=y
-CONFIG_HID_APPLE=y
-CONFIG_HID_BELKIN=y
-CONFIG_HID_CHERRY=y
-CONFIG_HID_CHICONY=y
-CONFIG_HID_CYPRESS=y
-CONFIG_HID_EZKEY=y
-CONFIG_HID_GYRATION=y
-CONFIG_HID_LOGITECH=y
-CONFIG_HID_MICROSOFT=y
-CONFIG_HID_MONTEREY=y
-CONFIG_HID_PANTHERLORD=y
-CONFIG_HID_PETALYNX=y
-CONFIG_HID_SAMSUNG=y
-CONFIG_HID_SONY=y
-CONFIG_HID_SUNPLUS=y
-CONFIG_USB=y
-CONFIG_USB_MON=y
-CONFIG_USB_OHCI_HCD=y
-CONFIG_USB_STORAGE=y
-CONFIG_MMC=m
-CONFIG_MMC_PXA=m
-CONFIG_NEW_LEDS=y
-CONFIG_LEDS_CLASS=y
-CONFIG_LEDS_GPIO=m
-CONFIG_LEDS_TRIGGERS=y
-CONFIG_LEDS_TRIGGER_HEARTBEAT=y
-CONFIG_RTC_CLASS=y
-CONFIG_RTC_DRV_V3020=y
-CONFIG_RTC_DRV_PXA=y
-CONFIG_EXT2_FS=y
-CONFIG_EXT3_FS=y
-CONFIG_VFAT_FS=m
-# CONFIG_PROC_PAGE_MONITOR is not set
-CONFIG_TMPFS=y
-CONFIG_JFFS2_FS=y
-CONFIG_JFFS2_SUMMARY=y
-CONFIG_NFS_FS=y
-CONFIG_NFS_V3=y
-CONFIG_ROOT_NFS=y
-CONFIG_CIFS=m
-CONFIG_PARTITION_ADVANCED=y
-CONFIG_NLS_CODEPAGE_437=m
-CONFIG_NLS_ISO8859_1=m
-CONFIG_NLS_UTF8=m
-CONFIG_FRAME_WARN=0
-CONFIG_DEBUG_KERNEL=y
-# CONFIG_DETECT_SOFTLOCKUP is not set
-# CONFIG_SCHED_DEBUG is not set
-# CONFIG_DEBUG_BUGVERBOSE is not set
-CONFIG_DEBUG_USER=y
-CONFIG_DEBUG_LL=y
-# CONFIG_CRYPTO_ANSI_CPRNG is not set
-# CONFIG_CRYPTO_HW is not set
diff --git a/arch/arm/configs/em_x270_defconfig b/arch/arm/configs/em_x270_defconfig
deleted file mode 100644
index d08f02014755..000000000000
--- a/arch/arm/configs/em_x270_defconfig
+++ /dev/null
@@ -1,178 +0,0 @@
-# CONFIG_LOCALVERSION_AUTO is not set
-CONFIG_SYSVIPC=y
-CONFIG_IKCONFIG=y
-CONFIG_IKCONFIG_PROC=y
-CONFIG_LOG_BUF_SHIFT=14
-CONFIG_SYSFS_DEPRECATED_V2=y
-CONFIG_BLK_DEV_INITRD=y
-CONFIG_EXPERT=y
-# CONFIG_VM_EVENT_COUNTERS is not set
-# CONFIG_SLUB_DEBUG is not set
-# CONFIG_COMPAT_BRK is not set
-CONFIG_MODULES=y
-CONFIG_MODULE_UNLOAD=y
-# CONFIG_BLK_DEV_BSG is not set
-CONFIG_ARCH_PXA=y
-CONFIG_MACH_EM_X270=y
-CONFIG_MACH_EXEDA=y
-CONFIG_NO_HZ=y
-CONFIG_AEABI=y
-CONFIG_ZBOOT_ROM_TEXT=0x0
-CONFIG_ZBOOT_ROM_BSS=0x0
-CONFIG_CMDLINE="root=1f03 mem=32M"
-CONFIG_CPU_FREQ=y
-CONFIG_CPU_FREQ_GOV_USERSPACE=m
-CONFIG_FPE_NWFPE=y
-CONFIG_PM=y
-CONFIG_APM_EMULATION=y
-CONFIG_NET=y
-CONFIG_PACKET=y
-CONFIG_UNIX=y
-CONFIG_INET=y
-CONFIG_IP_MULTICAST=y
-CONFIG_IP_PNP=y
-CONFIG_IP_PNP_DHCP=y
-CONFIG_IP_PNP_BOOTP=y
-# CONFIG_INET_DIAG is not set
-# CONFIG_IPV6 is not set
-CONFIG_BT=m
-CONFIG_BT_RFCOMM=m
-CONFIG_BT_BNEP=m
-CONFIG_BT_HIDP=m
-CONFIG_BT_HCIBTUSB=m
-CONFIG_LIB80211=m
-CONFIG_FW_LOADER=m
-CONFIG_MTD=y
-CONFIG_MTD_CMDLINE_PARTS=y
-CONFIG_MTD_BLOCK=y
-CONFIG_MTD_CFI=y
-CONFIG_MTD_JEDECPROBE=y
-CONFIG_MTD_CFI_ADV_OPTIONS=y
-CONFIG_MTD_CFI_INTELEXT=y
-CONFIG_MTD_CFI_AMDSTD=y
-CONFIG_MTD_CFI_STAA=y
-CONFIG_MTD_PHYSMAP=y
-CONFIG_MTD_PXA2XX=y
-CONFIG_MTD_RAW_NAND=y
-CONFIG_MTD_NAND_PLATFORM=y
-CONFIG_BLK_DEV_LOOP=y
-CONFIG_BLK_DEV_RAM=y
-CONFIG_SCSI=y
-CONFIG_BLK_DEV_SD=y
-# CONFIG_SCSI_LOWLEVEL is not set
-CONFIG_NETDEVICES=y
-CONFIG_NET_ETHERNET=y
-CONFIG_DM9000=y
-CONFIG_DM9000_DEBUGLEVEL=1
-CONFIG_PPP=m
-CONFIG_PPP_MULTILINK=y
-CONFIG_PPP_FILTER=y
-CONFIG_PPP_ASYNC=m
-CONFIG_PPP_DEFLATE=m
-CONFIG_PPP_BSDCOMP=m
-CONFIG_INPUT_EVDEV=y
-CONFIG_INPUT_APMPOWER=y
-CONFIG_KEYBOARD_GPIO=y
-CONFIG_KEYBOARD_PXA27x=y
-# CONFIG_INPUT_MOUSE is not set
-CONFIG_INPUT_TOUCHSCREEN=y
-# CONFIG_TOUCHSCREEN_DA9034 is not set
-CONFIG_TOUCHSCREEN_WM97XX=m
-# CONFIG_TOUCHSCREEN_WM9705 is not set
-# CONFIG_TOUCHSCREEN_WM9713 is not set
-# CONFIG_SERIO_SERPORT is not set
-CONFIG_SERIAL_PXA=y
-CONFIG_SERIAL_PXA_CONSOLE=y
-CONFIG_LEGACY_PTY_COUNT=16
-# CONFIG_HW_RANDOM is not set
-CONFIG_I2C=y
-CONFIG_I2C_CHARDEV=m
-CONFIG_I2C_PXA=y
-CONFIG_SPI=y
-CONFIG_SPI_PXA2XX=y
-CONFIG_POWER_SUPPLY=y
-CONFIG_BATTERY_DA9030=y
-# CONFIG_HWMON is not set
-CONFIG_PMIC_DA903X=y
-CONFIG_REGULATOR=y
-CONFIG_REGULATOR_DA903X=y
-CONFIG_FB=y
-CONFIG_FB_PXA=y
-CONFIG_FB_PXA_PARAMETERS=y
-CONFIG_FB_MBX=m
-CONFIG_LCD_CLASS_DEVICE=y
-CONFIG_LCD_TDO24M=y
-# CONFIG_BACKLIGHT_GENERIC is not set
-CONFIG_BACKLIGHT_DA903X=m
-# CONFIG_VGA_CONSOLE is not set
-CONFIG_FRAMEBUFFER_CONSOLE=y
-CONFIG_LOGO=y
-CONFIG_SOUND=m
-CONFIG_SND=m
-CONFIG_SND_MIXER_OSS=m
-CONFIG_SND_PCM_OSS=m
-# CONFIG_SND_DRIVERS is not set
-# CONFIG_SND_SPI is not set
-# CONFIG_SND_USB is not set
-CONFIG_SND_SOC=m
-CONFIG_SND_PXA2XX_SOC=m
-CONFIG_SND_PXA2XX_SOC_EM_X270=m
-CONFIG_HID_A4TECH=y
-CONFIG_HID_APPLE=y
-CONFIG_HID_BELKIN=y
-CONFIG_HID_CHERRY=y
-CONFIG_HID_CHICONY=y
-CONFIG_HID_CYPRESS=y
-CONFIG_HID_EZKEY=y
-CONFIG_HID_GYRATION=y
-CONFIG_HID_LOGITECH=y
-CONFIG_HID_MICROSOFT=y
-CONFIG_HID_MONTEREY=y
-CONFIG_HID_PANTHERLORD=y
-CONFIG_HID_PETALYNX=y
-CONFIG_HID_SAMSUNG=y
-CONFIG_HID_SONY=y
-CONFIG_HID_SUNPLUS=y
-CONFIG_USB=y
-CONFIG_USB_MON=y
-CONFIG_USB_OHCI_HCD=y
-CONFIG_USB_STORAGE=y
-CONFIG_MMC=m
-CONFIG_MMC_PXA=m
-CONFIG_NEW_LEDS=y
-CONFIG_LEDS_CLASS=y
-CONFIG_LEDS_DA903X=y
-CONFIG_LEDS_TRIGGERS=y
-CONFIG_LEDS_TRIGGER_HEARTBEAT=y
-CONFIG_RTC_CLASS=y
-CONFIG_RTC_DRV_V3020=y
-CONFIG_RTC_DRV_PXA=y
-CONFIG_EXT2_FS=y
-CONFIG_EXT3_FS=y
-CONFIG_VFAT_FS=m
-# CONFIG_PROC_PAGE_MONITOR is not set
-CONFIG_TMPFS=y
-CONFIG_JFFS2_FS=y
-CONFIG_JFFS2_SUMMARY=y
-CONFIG_NFS_FS=y
-CONFIG_NFS_V3=y
-CONFIG_ROOT_NFS=y
-CONFIG_CIFS=m
-CONFIG_PARTITION_ADVANCED=y
-CONFIG_NLS_CODEPAGE_437=m
-CONFIG_NLS_ISO8859_1=m
-CONFIG_NLS_UTF8=m
-CONFIG_FRAME_WARN=0
-CONFIG_DEBUG_FS=y
-CONFIG_DEBUG_KERNEL=y
-# CONFIG_DETECT_SOFTLOCKUP is not set
-# CONFIG_SCHED_DEBUG is not set
-# CONFIG_DEBUG_BUGVERBOSE is not set
-CONFIG_DEBUG_USER=y
-CONFIG_DEBUG_LL=y
-CONFIG_CRYPTO_ECB=m
-CONFIG_CRYPTO_MICHAEL_MIC=m
-CONFIG_CRYPTO_AES=m
-CONFIG_CRYPTO_ARC4=m
-# CONFIG_CRYPTO_ANSI_CPRNG is not set
-# CONFIG_CRYPTO_HW is not set
diff --git a/arch/arm/configs/pxa_defconfig b/arch/arm/configs/pxa_defconfig
index b817c57f05f1..e6559e3350e6 100644
--- a/arch/arm/configs/pxa_defconfig
+++ b/arch/arm/configs/pxa_defconfig
@@ -38,8 +38,6 @@ CONFIG_MACH_ARCOM_ZEUS=y
 CONFIG_MACH_BALLOON3=y
 CONFIG_MACH_CSB726=y
 CONFIG_CSB726_CSB701=y
-CONFIG_MACH_ARMCORE=y
-CONFIG_MACH_EM_X270=y
 CONFIG_MACH_EXEDA=y
 CONFIG_MACH_CM_X300=y
 CONFIG_MACH_CAPC7117=y
diff --git a/arch/arm/mach-pxa/Kconfig b/arch/arm/mach-pxa/Kconfig
index f60bc29aef68..f7520a6cc7d4 100644
--- a/arch/arm/mach-pxa/Kconfig
+++ b/arch/arm/mach-pxa/Kconfig
@@ -123,23 +123,6 @@ config CSB726_CSB701
 	bool "Enable support for CSB701 baseboard"
 	depends on MACH_CSB726
 
-config MACH_ARMCORE
-	bool "CompuLab CM-X255/CM-X270 modules"
-	select ARCH_HAS_DMA_SET_COHERENT_MASK if PCI
-	select IWMMXT
-	select HAVE_PCI
-	select NEED_MACH_IO_H if PCI
-	select PXA25x
-	select PXA27x
-
-config MACH_EM_X270
-	bool "CompuLab EM-x270 platform"
-	select PXA27x
-
-config MACH_EXEDA
-	bool "CompuLab eXeda platform"
-	select PXA27x
-
 config MACH_CM_X300
 	bool "CompuLab CM-X300 modules"
 	select CPU_PXA300
diff --git a/arch/arm/mach-pxa/Makefile b/arch/arm/mach-pxa/Makefile
index f70728930c4f..177abe584dd5 100644
--- a/arch/arm/mach-pxa/Makefile
+++ b/arch/arm/mach-pxa/Makefile
@@ -40,11 +40,6 @@ obj-$(CONFIG_MACH_ARCOM_ZEUS)	+= zeus.o
 obj-$(CONFIG_MACH_BALLOON3)	+= balloon3.o
 obj-$(CONFIG_MACH_CSB726)	+= csb726.o
 obj-$(CONFIG_CSB726_CSB701)	+= csb701.o
-obj-$(CONFIG_MACH_ARMCORE)      += cm-x2xx.o cm-x255.o cm-x270.o
-ifeq ($(CONFIG_PCI),y)
-obj-$(CONFIG_MACH_ARMCORE)	+= cm-x2xx-pci.o
-endif
-obj-$(CONFIG_MACH_EM_X270)	+= em-x270.o
 obj-$(CONFIG_MACH_CM_X300)      += cm-x300.o
 obj-$(CONFIG_MACH_CAPC7117)     += capc7117.o mxm8x10.o
 obj-$(CONFIG_ARCH_GUMSTIX)	+= gumstix.o
diff --git a/arch/arm/mach-pxa/cm-x255.c b/arch/arm/mach-pxa/cm-x255.c
deleted file mode 100644
index ea1e85775759..000000000000
--- a/arch/arm/mach-pxa/cm-x255.c
+++ /dev/null
@@ -1,240 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0-only
-/*
- * linux/arch/arm/mach-pxa/cm-x255.c
- *
- * Copyright (C) 2007, 2008 CompuLab, Ltd.
- * Mike Rapoport <mike@compulab.co.il>
- */
-
-#include <linux/platform_device.h>
-#include <linux/irq.h>
-#include <linux/mtd/partitions.h>
-#include <linux/mtd/physmap.h>
-#include <linux/mtd/nand-gpio.h>
-#include <linux/gpio/machine.h>
-#include <linux/spi/spi.h>
-#include <linux/spi/pxa2xx_spi.h>
-
-#include <asm/mach/arch.h>
-#include <asm/mach-types.h>
-#include <asm/mach/map.h>
-
-#include "pxa25x.h"
-
-#include "generic.h"
-
-#define GPIO_NAND_CS	(5)
-#define GPIO_NAND_ALE	(4)
-#define GPIO_NAND_CLE	(3)
-#define GPIO_NAND_RB	(10)
-
-static unsigned long cmx255_pin_config[] = {
-	/* AC'97 */
-	GPIO28_AC97_BITCLK,
-	GPIO29_AC97_SDATA_IN_0,
-	GPIO30_AC97_SDATA_OUT,
-	GPIO31_AC97_SYNC,
-
-	/* BTUART */
-	GPIO42_BTUART_RXD,
-	GPIO43_BTUART_TXD,
-	GPIO44_BTUART_CTS,
-	GPIO45_BTUART_RTS,
-
-	/* STUART */
-	GPIO46_STUART_RXD,
-	GPIO47_STUART_TXD,
-
-	/* LCD */
-	GPIOxx_LCD_TFT_16BPP,
-
-	/* SSP1 */
-	GPIO23_SSP1_SCLK,
-	GPIO24_SSP1_SFRM,
-	GPIO25_SSP1_TXD,
-	GPIO26_SSP1_RXD,
-
-	/* SSP2 */
-	GPIO81_SSP2_CLK_OUT,
-	GPIO82_SSP2_FRM_OUT,
-	GPIO83_SSP2_TXD,
-	GPIO84_SSP2_RXD,
-
-	/* PC Card */
-	GPIO48_nPOE,
-	GPIO49_nPWE,
-	GPIO50_nPIOR,
-	GPIO51_nPIOW,
-	GPIO52_nPCE_1,
-	GPIO53_nPCE_2,
-	GPIO54_nPSKTSEL,
-	GPIO55_nPREG,
-	GPIO56_nPWAIT,
-	GPIO57_nIOIS16,
-
-	/* SDRAM and local bus */
-	GPIO15_nCS_1,
-	GPIO78_nCS_2,
-	GPIO79_nCS_3,
-	GPIO80_nCS_4,
-	GPIO33_nCS_5,
-	GPIO18_RDY,
-
-	/* GPIO */
-	GPIO0_GPIO	| WAKEUP_ON_EDGE_BOTH,
-	GPIO9_GPIO,				/* PC card reset */
-
-	/* NAND controls */
-	GPIO5_GPIO	| MFP_LPM_DRIVE_HIGH,	/* NAND CE# */
-	GPIO4_GPIO	| MFP_LPM_DRIVE_LOW,	/* NAND ALE */
-	GPIO3_GPIO	| MFP_LPM_DRIVE_LOW,	/* NAND CLE */
-	GPIO10_GPIO,				/* NAND Ready/Busy */
-
-	/* interrupts */
-	GPIO22_GPIO,	/* DM9000 interrupt */
-};
-
-#if defined(CONFIG_SPI_PXA2XX)
-static struct pxa2xx_spi_controller pxa_ssp_master_info = {
-	.num_chipselect	= 1,
-};
-
-static struct spi_board_info spi_board_info[] __initdata = {
-	[0] = {
-		.modalias	= "rtc-max6902",
-		.max_speed_hz	= 1000000,
-		.bus_num	= 1,
-		.chip_select	= 0,
-	},
-};
-
-static void __init cmx255_init_rtc(void)
-{
-	pxa2xx_set_spi_info(1, &pxa_ssp_master_info);
-	spi_register_board_info(ARRAY_AND_SIZE(spi_board_info));
-}
-#else
-static inline void cmx255_init_rtc(void) {}
-#endif
-
-#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE)
-static struct mtd_partition cmx255_nor_partitions[] = {
-	{
-		.name		= "ARMmon",
-		.size		= 0x00030000,
-		.offset		= 0,
-		.mask_flags	= MTD_WRITEABLE  /* force read-only */
-	} , {
-		.name		= "ARMmon setup block",
-		.size		= 0x00010000,
-		.offset		= MTDPART_OFS_APPEND,
-		.mask_flags	= MTD_WRITEABLE  /* force read-only */
-	} , {
-		.name		= "kernel",
-		.size		= 0x00160000,
-		.offset		= MTDPART_OFS_APPEND,
-	} , {
-		.name		= "ramdisk",
-		.size		= MTDPART_SIZ_FULL,
-		.offset		= MTDPART_OFS_APPEND
-	}
-};
-
-static struct physmap_flash_data cmx255_nor_flash_data[] = {
-	{
-		.width		= 2,	/* bankwidth in bytes */
-		.parts		= cmx255_nor_partitions,
-		.nr_parts	= ARRAY_SIZE(cmx255_nor_partitions)
-	}
-};
-
-static struct resource cmx255_nor_resource = {
-	.start	= PXA_CS0_PHYS,
-	.end	= PXA_CS0_PHYS + SZ_8M - 1,
-	.flags	= IORESOURCE_MEM,
-};
-
-static struct platform_device cmx255_nor = {
-	.name	= "physmap-flash",
-	.id	= -1,
-	.dev	= {
-		.platform_data = cmx255_nor_flash_data,
-	},
-	.resource = &cmx255_nor_resource,
-	.num_resources = 1,
-};
-
-static void __init cmx255_init_nor(void)
-{
-	platform_device_register(&cmx255_nor);
-}
-#else
-static inline void cmx255_init_nor(void) {}
-#endif
-
-#if defined(CONFIG_MTD_NAND_GPIO) || defined(CONFIG_MTD_NAND_GPIO_MODULE)
-
-static struct gpiod_lookup_table cmx255_nand_gpiod_table = {
-	.dev_id         = "gpio-nand",
-	.table          = {
-		GPIO_LOOKUP("gpio-pxa", GPIO_NAND_CS, "nce", GPIO_ACTIVE_HIGH),
-		GPIO_LOOKUP("gpio-pxa", GPIO_NAND_CLE, "cle", GPIO_ACTIVE_HIGH),
-		GPIO_LOOKUP("gpio-pxa", GPIO_NAND_ALE, "ale", GPIO_ACTIVE_HIGH),
-		GPIO_LOOKUP("gpio-pxa", GPIO_NAND_RB, "rdy", GPIO_ACTIVE_HIGH),
-	},
-};
-
-static struct resource cmx255_nand_resource[] = {
-	[0] = {
-		.start = PXA_CS1_PHYS,
-		.end   = PXA_CS1_PHYS + 11,
-		.flags = IORESOURCE_MEM,
-	},
-	[1] = {
-		.start = PXA_CS5_PHYS,
-		.end   = PXA_CS5_PHYS + 3,
-		.flags = IORESOURCE_MEM,
-	},
-};
-
-static struct mtd_partition cmx255_nand_parts[] = {
-	[0] = {
-		.name	= "cmx255-nand",
-		.size	= MTDPART_SIZ_FULL,
-		.offset	= 0,
-	},
-};
-
-static struct gpio_nand_platdata cmx255_nand_platdata = {
-	.parts = cmx255_nand_parts,
-	.num_parts = ARRAY_SIZE(cmx255_nand_parts),
-	.chip_delay = 25,
-};
-
-static struct platform_device cmx255_nand = {
-	.name		= "gpio-nand",
-	.num_resources	= ARRAY_SIZE(cmx255_nand_resource),
-	.resource	= cmx255_nand_resource,
-	.id		= -1,
-	.dev		= {
-		.platform_data = &cmx255_nand_platdata,
-	}
-};
-
-static void __init cmx255_init_nand(void)
-{
-	gpiod_add_lookup_table(&cmx255_nand_gpiod_table);
-	platform_device_register(&cmx255_nand);
-}
-#else
-static inline void cmx255_init_nand(void) {}
-#endif
-
-void __init cmx255_init(void)
-{
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(cmx255_pin_config));
-
-	cmx255_init_rtc();
-	cmx255_init_nor();
-	cmx255_init_nand();
-}
diff --git a/arch/arm/mach-pxa/cm-x270.c b/arch/arm/mach-pxa/cm-x270.c
deleted file mode 100644
index 9baad11314f2..000000000000
--- a/arch/arm/mach-pxa/cm-x270.c
+++ /dev/null
@@ -1,419 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0-only
-/*
- * linux/arch/arm/mach-pxa/cm-x270.c
- *
- * Copyright (C) 2007, 2008 CompuLab, Ltd.
- * Mike Rapoport <mike@compulab.co.il>
- */
-
-#include <linux/platform_device.h>
-#include <linux/irq.h>
-#include <linux/gpio.h>
-#include <linux/gpio/machine.h>
-#include <linux/delay.h>
-
-#include <linux/platform_data/rtc-v3020.h>
-#include <video/mbxfb.h>
-
-#include <linux/spi/spi.h>
-#include <linux/spi/pxa2xx_spi.h>
-#include <linux/spi/libertas_spi.h>
-
-#include "pxa27x.h"
-#include <linux/platform_data/usb-ohci-pxa27x.h>
-#include <linux/platform_data/mmc-pxamci.h>
-
-#include "generic.h"
-
-/* physical address if local-bus attached devices */
-#define RTC_PHYS_BASE		(PXA_CS1_PHYS + (5 << 22))
-
-/* GPIO IRQ usage */
-#define GPIO83_MMC_IRQ		(83)
-
-#define CMX270_MMC_IRQ		PXA_GPIO_TO_IRQ(GPIO83_MMC_IRQ)
-
-/* MMC power enable */
-#define GPIO105_MMC_POWER	(105)
-
-/* WLAN GPIOS */
-#define GPIO19_WLAN_STRAP	(19)
-#define GPIO102_WLAN_RST	(102)
-
-static unsigned long cmx270_pin_config[] = {
-	/* AC'97 */
-	GPIO28_AC97_BITCLK,
-	GPIO29_AC97_SDATA_IN_0,
-	GPIO30_AC97_SDATA_OUT,
-	GPIO31_AC97_SYNC,
-	GPIO98_AC97_SYSCLK,
-	GPIO113_AC97_nRESET,
-
-	/* BTUART */
-	GPIO42_BTUART_RXD,
-	GPIO43_BTUART_TXD,
-	GPIO44_BTUART_CTS,
-	GPIO45_BTUART_RTS,
-
-	/* STUART */
-	GPIO46_STUART_RXD,
-	GPIO47_STUART_TXD,
-
-	/* MCI controller */
-	GPIO32_MMC_CLK,
-	GPIO112_MMC_CMD,
-	GPIO92_MMC_DAT_0,
-	GPIO109_MMC_DAT_1,
-	GPIO110_MMC_DAT_2,
-	GPIO111_MMC_DAT_3,
-
-	/* LCD */
-	GPIOxx_LCD_TFT_16BPP,
-
-	/* I2C */
-	GPIO117_I2C_SCL,
-	GPIO118_I2C_SDA,
-
-	/* SSP1 */
-	GPIO23_SSP1_SCLK,
-	GPIO24_SSP1_SFRM,
-	GPIO25_SSP1_TXD,
-	GPIO26_SSP1_RXD,
-
-	/* SSP2 */
-	GPIO19_GPIO,	/* SSP2 clock is used as GPIO for Libertas pin-strap */
-	GPIO14_GPIO,
-	GPIO87_SSP2_TXD,
-	GPIO88_SSP2_RXD,
-
-	/* PC Card */
-	GPIO48_nPOE,
-	GPIO49_nPWE,
-	GPIO50_nPIOR,
-	GPIO51_nPIOW,
-	GPIO85_nPCE_1,
-	GPIO54_nPCE_2,
-	GPIO55_nPREG,
-	GPIO56_nPWAIT,
-	GPIO57_nIOIS16,
-
-	/* SDRAM and local bus */
-	GPIO15_nCS_1,
-	GPIO78_nCS_2,
-	GPIO79_nCS_3,
-	GPIO80_nCS_4,
-	GPIO33_nCS_5,
-	GPIO49_nPWE,
-	GPIO18_RDY,
-
-	/* GPIO */
-	GPIO0_GPIO	| WAKEUP_ON_EDGE_BOTH,
-	GPIO105_GPIO	| MFP_LPM_DRIVE_HIGH,	/* MMC/SD power */
-	GPIO53_GPIO,				/* PC card reset */
-	GPIO102_GPIO,				/* WLAN reset */
-
-	/* NAND controls */
-	GPIO11_GPIO	| MFP_LPM_DRIVE_HIGH,	/* NAND CE# */
-	GPIO89_GPIO,				/* NAND Ready/Busy */
-
-	/* interrupts */
-	GPIO10_GPIO,	/* DM9000 interrupt */
-	GPIO83_GPIO,	/* MMC card detect */
-	GPIO95_GPIO,	/* WLAN interrupt */
-};
-
-/* V3020 RTC */
-#if defined(CONFIG_RTC_DRV_V3020) || defined(CONFIG_RTC_DRV_V3020_MODULE)
-static struct resource cmx270_v3020_resource[] = {
-	[0] = {
-		.start = RTC_PHYS_BASE,
-		.end   = RTC_PHYS_BASE + 4,
-		.flags = IORESOURCE_MEM,
-	},
-};
-
-struct v3020_platform_data cmx270_v3020_pdata = {
-	.leftshift = 16,
-};
-
-static struct platform_device cmx270_rtc_device = {
-	.name		= "v3020",
-	.num_resources	= ARRAY_SIZE(cmx270_v3020_resource),
-	.resource	= cmx270_v3020_resource,
-	.id		= -1,
-	.dev		= {
-		.platform_data = &cmx270_v3020_pdata,
-	}
-};
-
-static void __init cmx270_init_rtc(void)
-{
-	platform_device_register(&cmx270_rtc_device);
-}
-#else
-static inline void cmx270_init_rtc(void) {}
-#endif
-
-/* 2700G graphics */
-#if defined(CONFIG_FB_MBX) || defined(CONFIG_FB_MBX_MODULE)
-static u64 fb_dma_mask = ~(u64)0;
-
-static struct resource cmx270_2700G_resource[] = {
-	/* frame buffer memory including ODFB and External SDRAM */
-	[0] = {
-		.start = PXA_CS2_PHYS,
-		.end   = PXA_CS2_PHYS + 0x01ffffff,
-		.flags = IORESOURCE_MEM,
-	},
-	/* Marathon registers */
-	[1] = {
-		.start = PXA_CS2_PHYS + 0x03fe0000,
-		.end   = PXA_CS2_PHYS + 0x03ffffff,
-		.flags = IORESOURCE_MEM,
-	},
-};
-
-static unsigned long cmx270_marathon_on[] = {
-	GPIO58_GPIO,
-	GPIO59_GPIO,
-	GPIO60_GPIO,
-	GPIO61_GPIO,
-	GPIO62_GPIO,
-	GPIO63_GPIO,
-	GPIO64_GPIO,
-	GPIO65_GPIO,
-	GPIO66_GPIO,
-	GPIO67_GPIO,
-	GPIO68_GPIO,
-	GPIO69_GPIO,
-	GPIO70_GPIO,
-	GPIO71_GPIO,
-	GPIO72_GPIO,
-	GPIO73_GPIO,
-	GPIO74_GPIO,
-	GPIO75_GPIO,
-	GPIO76_GPIO,
-	GPIO77_GPIO,
-};
-
-static unsigned long cmx270_marathon_off[] = {
-	GPIOxx_LCD_TFT_16BPP,
-};
-
-static int cmx270_marathon_probe(struct fb_info *fb)
-{
-	int gpio, err;
-
-	for (gpio = 58; gpio <= 77; gpio++) {
-		err = gpio_request(gpio, "LCD");
-		if (err)
-			return err;
-		gpio_direction_input(gpio);
-	}
-
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(cmx270_marathon_on));
-	return 0;
-}
-
-static int cmx270_marathon_remove(struct fb_info *fb)
-{
-	int gpio;
-
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(cmx270_marathon_off));
-
-	for (gpio = 58; gpio <= 77; gpio++)
-		gpio_free(gpio);
-
-	return 0;
-}
-
-static struct mbxfb_platform_data cmx270_2700G_data = {
-	.xres = {
-		.min = 240,
-		.max = 1200,
-		.defval = 640,
-	},
-	.yres = {
-		.min = 240,
-		.max = 1200,
-		.defval = 480,
-	},
-	.bpp = {
-		.min = 16,
-		.max = 32,
-		.defval = 16,
-	},
-	.memsize = 8*1024*1024,
-	.probe = cmx270_marathon_probe,
-	.remove = cmx270_marathon_remove,
-};
-
-static struct platform_device cmx270_2700G = {
-	.name		= "mbx-fb",
-	.dev		= {
-		.platform_data	= &cmx270_2700G_data,
-		.dma_mask	= &fb_dma_mask,
-		.coherent_dma_mask = 0xffffffff,
-	},
-	.num_resources	= ARRAY_SIZE(cmx270_2700G_resource),
-	.resource	= cmx270_2700G_resource,
-	.id		= -1,
-};
-
-static void __init cmx270_init_2700G(void)
-{
-	platform_device_register(&cmx270_2700G);
-}
-#else
-static inline void cmx270_init_2700G(void) {}
-#endif
-
-/* PXA27x OHCI controller setup */
-#if defined(CONFIG_USB_OHCI_HCD) || defined(CONFIG_USB_OHCI_HCD_MODULE)
-static struct pxaohci_platform_data cmx270_ohci_platform_data = {
-	.port_mode	= PMM_PERPORT_MODE,
-	.flags		= ENABLE_PORT1 | ENABLE_PORT2 | POWER_CONTROL_LOW,
-};
-
-static void __init cmx270_init_ohci(void)
-{
-	pxa_set_ohci_info(&cmx270_ohci_platform_data);
-}
-#else
-static inline void cmx270_init_ohci(void) {}
-#endif
-
-#if defined(CONFIG_MMC) || defined(CONFIG_MMC_MODULE)
-static struct pxamci_platform_data cmx270_mci_platform_data = {
-	.ocr_mask		= MMC_VDD_32_33|MMC_VDD_33_34,
-};
-
-static struct gpiod_lookup_table cmx270_mci_gpio_table = {
-	.dev_id = "pxa2xx-mci.0",
-	.table = {
-		/* Card detect on GPIO 83 */
-		GPIO_LOOKUP("gpio-pxa", GPIO83_MMC_IRQ, "cd", GPIO_ACTIVE_LOW),
-		/* Power on GPIO 105 */
-		GPIO_LOOKUP("gpio-pxa", GPIO105_MMC_POWER,
-			    "power", GPIO_ACTIVE_LOW),
-		{ },
-	},
-};
-
-static void __init cmx270_init_mmc(void)
-{
-	gpiod_add_lookup_table(&cmx270_mci_gpio_table);
-	pxa_set_mci_info(&cmx270_mci_platform_data);
-}
-#else
-static inline void cmx270_init_mmc(void) {}
-#endif
-
-#if defined(CONFIG_SPI_PXA2XX) || defined(CONFIG_SPI_PXA2XX_MODULE)
-static struct pxa2xx_spi_controller cm_x270_spi_info = {
-	.num_chipselect	= 1,
-	.enable_dma	= 1,
-};
-
-static struct pxa2xx_spi_chip cm_x270_libertas_chip = {
-	.rx_threshold	= 1,
-	.tx_threshold	= 1,
-	.timeout	= 1000,
-	.gpio_cs	= 14,
-};
-
-static unsigned long cm_x270_libertas_pin_config[] = {
-	/* SSP2 */
-	GPIO19_SSP2_SCLK,
-	GPIO14_GPIO,
-	GPIO87_SSP2_TXD,
-	GPIO88_SSP2_RXD,
-
-};
-
-static int cm_x270_libertas_setup(struct spi_device *spi)
-{
-	int err = gpio_request(GPIO19_WLAN_STRAP, "WLAN STRAP");
-	if (err)
-		return err;
-
-	err = gpio_request(GPIO102_WLAN_RST, "WLAN RST");
-	if (err)
-		goto err_free_strap;
-
-	err = gpio_direction_output(GPIO102_WLAN_RST, 0);
-	if (err)
-		goto err_free_strap;
-	msleep(100);
-
-	err = gpio_direction_output(GPIO19_WLAN_STRAP, 1);
-	if (err)
-		goto err_free_strap;
-	msleep(100);
-
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(cm_x270_libertas_pin_config));
-
-	gpio_set_value(GPIO102_WLAN_RST, 1);
-	msleep(100);
-
-	spi->bits_per_word = 16;
-	spi_setup(spi);
-
-	return 0;
-
-err_free_strap:
-	gpio_free(GPIO19_WLAN_STRAP);
-
-	return err;
-}
-
-static int cm_x270_libertas_teardown(struct spi_device *spi)
-{
-	gpio_set_value(GPIO102_WLAN_RST, 0);
-	gpio_free(GPIO102_WLAN_RST);
-	gpio_free(GPIO19_WLAN_STRAP);
-
-	return 0;
-}
-
-struct libertas_spi_platform_data cm_x270_libertas_pdata = {
-	.use_dummy_writes	= 1,
-	.setup			= cm_x270_libertas_setup,
-	.teardown		= cm_x270_libertas_teardown,
-};
-
-static struct spi_board_info cm_x270_spi_devices[] __initdata = {
-	{
-		.modalias		= "libertas_spi",
-		.max_speed_hz		= 13000000,
-		.bus_num		= 2,
-		.irq			= PXA_GPIO_TO_IRQ(95),
-		.chip_select		= 0,
-		.controller_data	= &cm_x270_libertas_chip,
-		.platform_data		= &cm_x270_libertas_pdata,
-	},
-};
-
-static void __init cmx270_init_spi(void)
-{
-	pxa2xx_set_spi_info(2, &cm_x270_spi_info);
-	spi_register_board_info(ARRAY_AND_SIZE(cm_x270_spi_devices));
-}
-#else
-static inline void cmx270_init_spi(void) {}
-#endif
-
-void __init cmx270_init(void)
-{
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(cmx270_pin_config));
-
-#ifdef CONFIG_PM
-	pxa27x_set_pwrmode(PWRMODE_DEEPSLEEP);
-#endif
-
-	cmx270_init_rtc();
-	cmx270_init_mmc();
-	cmx270_init_ohci();
-	cmx270_init_2700G();
-	cmx270_init_spi();
-}
diff --git a/arch/arm/mach-pxa/cm-x2xx-pci.c b/arch/arm/mach-pxa/cm-x2xx-pci.c
deleted file mode 100644
index f1c61c6b5610..000000000000
--- a/arch/arm/mach-pxa/cm-x2xx-pci.c
+++ /dev/null
@@ -1,196 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0-only
-/*
- * linux/arch/arm/mach-pxa/cm-x2xx-pci.c
- *
- * PCI bios-type initialisation for PCI machines
- *
- * Bits taken from various places.
- *
- * Copyright (C) 2007, 2008 Compulab, Ltd.
- * Mike Rapoport <mike@compulab.co.il>
- */
-
-#include <linux/kernel.h>
-#include <linux/pci.h>
-#include <linux/init.h>
-#include <linux/device.h>
-#include <linux/platform_device.h>
-#include <linux/irq.h>
-#include <linux/gpio.h>
-
-#include <asm/mach/pci.h>
-#include <asm/mach-types.h>
-
-#include <asm/hardware/it8152.h>
-
-void __iomem *it8152_base_address;
-static int cmx2xx_it8152_irq_gpio;
-
-static void cmx2xx_it8152_irq_demux(struct irq_desc *desc)
-{
-	/* clear our parent irq */
-	desc->irq_data.chip->irq_ack(&desc->irq_data);
-
-	it8152_irq_demux(desc);
-}
-
-void __cmx2xx_pci_init_irq(int irq_gpio)
-{
-	it8152_init_irq();
-
-	cmx2xx_it8152_irq_gpio = irq_gpio;
-
-	irq_set_irq_type(gpio_to_irq(irq_gpio), IRQ_TYPE_EDGE_RISING);
-
-	irq_set_chained_handler(gpio_to_irq(irq_gpio),
-				cmx2xx_it8152_irq_demux);
-}
-
-#ifdef CONFIG_PM
-static unsigned long sleep_save_ite[10];
-
-void __cmx2xx_pci_suspend(void)
-{
-	/* save ITE state */
-	sleep_save_ite[0] = __raw_readl(IT8152_INTC_PDCNIMR);
-	sleep_save_ite[1] = __raw_readl(IT8152_INTC_LPCNIMR);
-	sleep_save_ite[2] = __raw_readl(IT8152_INTC_LPNIAR);
-
-	/* Clear ITE IRQ's */
-	__raw_writel((0), IT8152_INTC_PDCNIRR);
-	__raw_writel((0), IT8152_INTC_LPCNIRR);
-}
-
-void __cmx2xx_pci_resume(void)
-{
-	/* restore IT8152 state */
-	__raw_writel((sleep_save_ite[0]), IT8152_INTC_PDCNIMR);
-	__raw_writel((sleep_save_ite[1]), IT8152_INTC_LPCNIMR);
-	__raw_writel((sleep_save_ite[2]), IT8152_INTC_LPNIAR);
-}
-#else
-void cmx2xx_pci_suspend(void) {}
-void cmx2xx_pci_resume(void) {}
-#endif
-
-/* PCI IRQ mapping*/
-static int __init cmx2xx_pci_map_irq(const struct pci_dev *dev, u8 slot, u8 pin)
-{
-	int irq;
-
-	dev_dbg(&dev->dev, "%s: slot=%x, pin=%x\n", __func__, slot, pin);
-
-	irq = it8152_pci_map_irq(dev, slot, pin);
-	if (irq)
-		return irq;
-
-	/*
-	  Here comes the ugly part. The routing is baseboard specific,
-	  but defining a platform for each possible base of CM-X2XX is
-	  unrealistic. Here we keep mapping for ATXBase and SB-X2XX.
-	*/
-	/* ATXBASE PCI slot */
-	if (slot == 7)
-		return IT8152_PCI_INTA;
-
-	/* ATXBase/SB-X2XX CardBus */
-	if (slot == 8 || slot == 0)
-		return IT8152_PCI_INTB;
-
-	/* ATXBase Ethernet */
-	if (slot == 9)
-		return IT8152_PCI_INTA;
-
-	/* CM-x255 Onboard Ethernet */
-	if (slot == 15)
-		return IT8152_PCI_INTC;
-
-	/* SB-x2xx Ethernet */
-	if (slot == 16)
-		return IT8152_PCI_INTA;
-
-	/* PC104+ interrupt routing */
-	if ((slot == 17) || (slot == 19))
-		return IT8152_PCI_INTA;
-	if ((slot == 18) || (slot == 20))
-		return IT8152_PCI_INTB;
-
-	return(0);
-}
-
-static void cmx2xx_pci_preinit(void)
-{
-	pr_info("Initializing CM-X2XX PCI subsystem\n");
-
-	pcibios_min_io = 0;
-	pcibios_min_mem = 0;
-
-	__raw_writel(0x800, IT8152_PCI_CFG_ADDR);
-	if (__raw_readl(IT8152_PCI_CFG_DATA) == 0x81521283) {
-		pr_info("PCI Bridge found.\n");
-
-		/* set PCI I/O base at 0 */
-		writel(0x848, IT8152_PCI_CFG_ADDR);
-		writel(0, IT8152_PCI_CFG_DATA);
-
-		/* set PCI memory base at 0 */
-		writel(0x840, IT8152_PCI_CFG_ADDR);
-		writel(0, IT8152_PCI_CFG_DATA);
-
-		writel(0x20, IT8152_GPIO_GPDR);
-
-		/* CardBus Controller on ATXbase baseboard */
-		writel(0x4000, IT8152_PCI_CFG_ADDR);
-		if (readl(IT8152_PCI_CFG_DATA) == 0xAC51104C) {
-			pr_info("CardBus Bridge found.\n");
-
-			/* Configure socket 0 */
-			writel(0x408C, IT8152_PCI_CFG_ADDR);
-			writel(0x1022, IT8152_PCI_CFG_DATA);
-
-			writel(0x4080, IT8152_PCI_CFG_ADDR);
-			writel(0x3844d060, IT8152_PCI_CFG_DATA);
-
-			writel(0x4090, IT8152_PCI_CFG_ADDR);
-			writel(((readl(IT8152_PCI_CFG_DATA) & 0xffff) |
-				0x60440000),
-			       IT8152_PCI_CFG_DATA);
-
-			writel(0x4018, IT8152_PCI_CFG_ADDR);
-			writel(0xb0000000, IT8152_PCI_CFG_DATA);
-
-			/* Configure socket 1 */
-			writel(0x418C, IT8152_PCI_CFG_ADDR);
-			writel(0x1022, IT8152_PCI_CFG_DATA);
-
-			writel(0x4180, IT8152_PCI_CFG_ADDR);
-			writel(0x3844d060, IT8152_PCI_CFG_DATA);
-
-			writel(0x4190, IT8152_PCI_CFG_ADDR);
-			writel(((readl(IT8152_PCI_CFG_DATA) & 0xffff) |
-				0x60440000),
-			       IT8152_PCI_CFG_DATA);
-
-			writel(0x4118, IT8152_PCI_CFG_ADDR);
-			writel(0xb0000000, IT8152_PCI_CFG_DATA);
-		}
-	}
-}
-
-static struct hw_pci cmx2xx_pci __initdata = {
-	.map_irq	= cmx2xx_pci_map_irq,
-	.nr_controllers	= 1,
-	.ops		= &it8152_ops,
-	.setup		= it8152_pci_setup,
-	.preinit	= cmx2xx_pci_preinit,
-};
-
-static int __init cmx2xx_init_pci(void)
-{
-	if (machine_is_armcore())
-		pci_common_init(&cmx2xx_pci);
-
-	return 0;
-}
-
-subsys_initcall(cmx2xx_init_pci);
diff --git a/arch/arm/mach-pxa/cm-x2xx-pci.h b/arch/arm/mach-pxa/cm-x2xx-pci.h
deleted file mode 100644
index 93ffaaee75d7..000000000000
--- a/arch/arm/mach-pxa/cm-x2xx-pci.h
+++ /dev/null
@@ -1,14 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-extern void __cmx2xx_pci_init_irq(int irq_gpio);
-extern void __cmx2xx_pci_suspend(void);
-extern void __cmx2xx_pci_resume(void);
-
-#ifdef CONFIG_PCI
-#define cmx2xx_pci_init_irq(x) __cmx2xx_pci_init_irq(x)
-#define cmx2xx_pci_suspend(x) __cmx2xx_pci_suspend(x)
-#define cmx2xx_pci_resume(x) __cmx2xx_pci_resume(x)
-#else
-#define cmx2xx_pci_init_irq(x) do {} while (0)
-#define cmx2xx_pci_suspend(x) do {} while (0)
-#define cmx2xx_pci_resume(x) do {} while (0)
-#endif
diff --git a/arch/arm/mach-pxa/cm-x2xx.c b/arch/arm/mach-pxa/cm-x2xx.c
deleted file mode 100644
index ff976d1217eb..000000000000
--- a/arch/arm/mach-pxa/cm-x2xx.c
+++ /dev/null
@@ -1,538 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0-only
-/*
- * linux/arch/arm/mach-pxa/cm-x2xx.c
- *
- * Copyright (C) 2008 CompuLab, Ltd.
- * Mike Rapoport <mike@compulab.co.il>
- */
-
-#include <linux/platform_device.h>
-#include <linux/syscore_ops.h>
-#include <linux/irq.h>
-#include <linux/gpio.h>
-#include <linux/regulator/machine.h>
-
-#include <linux/dm9000.h>
-#include <linux/leds.h>
-
-#include <asm/mach/arch.h>
-#include <asm/mach-types.h>
-#include <asm/mach/map.h>
-
-#include "pxa25x.h"
-#undef GPIO24_SSP1_SFRM
-#undef GPIO86_GPIO
-#undef GPIO87_GPIO
-#undef GPIO88_GPIO
-#undef GPIO89_GPIO
-#include "pxa27x.h"
-#undef GPIO24_SSP1_SFRM
-#undef GPIO86_GPIO
-#undef GPIO87_GPIO
-#undef GPIO88_GPIO
-#undef GPIO89_GPIO
-#include <mach/audio.h>
-#include <linux/platform_data/video-pxafb.h>
-#include <mach/smemc.h>
-
-#include <asm/hardware/it8152.h>
-
-#include "generic.h"
-#include "cm-x2xx-pci.h"
-
-extern void cmx255_init(void);
-extern void cmx270_init(void);
-
-/* reserve IRQs for IT8152 */
-#define CMX2XX_NR_IRQS		(IRQ_BOARD_START + 40)
-
-/* virtual addresses for statically mapped regions */
-#define CMX2XX_VIRT_BASE	(void __iomem *)(0xe8000000)
-#define CMX2XX_IT8152_VIRT	(CMX2XX_VIRT_BASE)
-
-/* physical address if local-bus attached devices */
-#define CMX255_DM9000_PHYS_BASE (PXA_CS1_PHYS + (8 << 22))
-#define CMX270_DM9000_PHYS_BASE	(PXA_CS1_PHYS + (6 << 22))
-
-/* leds */
-#define CMX255_GPIO_RED		(27)
-#define CMX255_GPIO_GREEN	(32)
-#define CMX270_GPIO_RED		(93)
-#define CMX270_GPIO_GREEN	(94)
-
-/* GPIO IRQ usage */
-#define GPIO22_ETHIRQ		(22)
-#define GPIO10_ETHIRQ		(10)
-#define CMX255_GPIO_IT8152_IRQ	(0)
-#define CMX270_GPIO_IT8152_IRQ	(22)
-
-#define CMX255_ETHIRQ		PXA_GPIO_TO_IRQ(GPIO22_ETHIRQ)
-#define CMX270_ETHIRQ		PXA_GPIO_TO_IRQ(GPIO10_ETHIRQ)
-
-#if defined(CONFIG_DM9000) || defined(CONFIG_DM9000_MODULE)
-static struct resource cmx255_dm9000_resource[] = {
-	[0] = {
-		.start = CMX255_DM9000_PHYS_BASE,
-		.end   = CMX255_DM9000_PHYS_BASE + 3,
-		.flags = IORESOURCE_MEM,
-	},
-	[1] = {
-		.start = CMX255_DM9000_PHYS_BASE + 4,
-		.end   = CMX255_DM9000_PHYS_BASE + 4 + 500,
-		.flags = IORESOURCE_MEM,
-	},
-	[2] = {
-		.start = CMX255_ETHIRQ,
-		.end   = CMX255_ETHIRQ,
-		.flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHEDGE,
-	}
-};
-
-static struct resource cmx270_dm9000_resource[] = {
-	[0] = {
-		.start = CMX270_DM9000_PHYS_BASE,
-		.end   = CMX270_DM9000_PHYS_BASE + 3,
-		.flags = IORESOURCE_MEM,
-	},
-	[1] = {
-		.start = CMX270_DM9000_PHYS_BASE + 8,
-		.end   = CMX270_DM9000_PHYS_BASE + 8 + 500,
-		.flags = IORESOURCE_MEM,
-	},
-	[2] = {
-		.start = CMX270_ETHIRQ,
-		.end   = CMX270_ETHIRQ,
-		.flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHEDGE,
-	}
-};
-
-static struct dm9000_plat_data cmx270_dm9000_platdata = {
-	.flags		= DM9000_PLATF_32BITONLY | DM9000_PLATF_NO_EEPROM,
-};
-
-static struct platform_device cmx2xx_dm9000_device = {
-	.name		= "dm9000",
-	.id		= 0,
-	.num_resources	= ARRAY_SIZE(cmx270_dm9000_resource),
-	.dev		= {
-		.platform_data = &cmx270_dm9000_platdata,
-	}
-};
-
-static void __init cmx2xx_init_dm9000(void)
-{
-	if (cpu_is_pxa25x())
-		cmx2xx_dm9000_device.resource = cmx255_dm9000_resource;
-	else
-		cmx2xx_dm9000_device.resource = cmx270_dm9000_resource;
-	platform_device_register(&cmx2xx_dm9000_device);
-}
-#else
-static inline void cmx2xx_init_dm9000(void) {}
-#endif
-
-/* UCB1400 touchscreen controller */
-#if defined(CONFIG_TOUCHSCREEN_UCB1400) || defined(CONFIG_TOUCHSCREEN_UCB1400_MODULE)
-static struct platform_device cmx2xx_ts_device = {
-	.name		= "ucb1400_core",
-	.id		= -1,
-};
-
-static void __init cmx2xx_init_touchscreen(void)
-{
-	platform_device_register(&cmx2xx_ts_device);
-}
-#else
-static inline void cmx2xx_init_touchscreen(void) {}
-#endif
-
-/* CM-X270 LEDs */
-#if defined(CONFIG_LEDS_GPIO) || defined(CONFIG_LEDS_GPIO_MODULE)
-static struct gpio_led cmx2xx_leds[] = {
-	[0] = {
-		.name = "cm-x2xx:red",
-		.default_trigger = "nand-disk",
-		.active_low = 1,
-	},
-	[1] = {
-		.name = "cm-x2xx:green",
-		.default_trigger = "heartbeat",
-		.active_low = 1,
-	},
-};
-
-static struct gpio_led_platform_data cmx2xx_gpio_led_pdata = {
-	.num_leds = ARRAY_SIZE(cmx2xx_leds),
-	.leds = cmx2xx_leds,
-};
-
-static struct platform_device cmx2xx_led_device = {
-	.name		= "leds-gpio",
-	.id		= -1,
-	.dev		= {
-		.platform_data = &cmx2xx_gpio_led_pdata,
-	},
-};
-
-static void __init cmx2xx_init_leds(void)
-{
-	if (cpu_is_pxa25x()) {
-		cmx2xx_leds[0].gpio = CMX255_GPIO_RED;
-		cmx2xx_leds[1].gpio = CMX255_GPIO_GREEN;
-	} else {
-		cmx2xx_leds[0].gpio = CMX270_GPIO_RED;
-		cmx2xx_leds[1].gpio = CMX270_GPIO_GREEN;
-	}
-	platform_device_register(&cmx2xx_led_device);
-}
-#else
-static inline void cmx2xx_init_leds(void) {}
-#endif
-
-#if defined(CONFIG_FB_PXA) || defined(CONFIG_FB_PXA_MODULE)
-/*
-  Display definitions
-  keep these for backwards compatibility, although symbolic names (as
-  e.g. in lpd270.c) looks better
-*/
-#define MTYPE_STN320x240	0
-#define MTYPE_TFT640x480	1
-#define MTYPE_CRT640x480	2
-#define MTYPE_CRT800x600	3
-#define MTYPE_TFT320x240	6
-#define MTYPE_STN640x480	7
-
-static struct pxafb_mode_info generic_stn_320x240_mode = {
-	.pixclock	= 76923,
-	.bpp		= 8,
-	.xres		= 320,
-	.yres		= 240,
-	.hsync_len	= 3,
-	.vsync_len	= 2,
-	.left_margin	= 3,
-	.upper_margin	= 0,
-	.right_margin	= 3,
-	.lower_margin	= 0,
-	.sync		= (FB_SYNC_HOR_HIGH_ACT |
-			   FB_SYNC_VERT_HIGH_ACT),
-	.cmap_greyscale = 0,
-};
-
-static struct pxafb_mach_info generic_stn_320x240 = {
-	.modes		= &generic_stn_320x240_mode,
-	.num_modes	= 1,
-	.lcd_conn	= LCD_COLOR_STN_8BPP | LCD_PCLK_EDGE_FALL |\
-			  LCD_AC_BIAS_FREQ(0xff),
-	.cmap_inverse	= 0,
-	.cmap_static	= 0,
-};
-
-static struct pxafb_mode_info generic_tft_640x480_mode = {
-	.pixclock	= 38461,
-	.bpp		= 8,
-	.xres		= 640,
-	.yres		= 480,
-	.hsync_len	= 60,
-	.vsync_len	= 2,
-	.left_margin	= 70,
-	.upper_margin	= 10,
-	.right_margin	= 70,
-	.lower_margin	= 5,
-	.sync		= 0,
-	.cmap_greyscale = 0,
-};
-
-static struct pxafb_mach_info generic_tft_640x480 = {
-	.modes		= &generic_tft_640x480_mode,
-	.num_modes	= 1,
-	.lcd_conn	= LCD_COLOR_TFT_8BPP | LCD_PCLK_EDGE_FALL |\
-			  LCD_AC_BIAS_FREQ(0xff),
-	.cmap_inverse	= 0,
-	.cmap_static	= 0,
-};
-
-static struct pxafb_mode_info generic_crt_640x480_mode = {
-	.pixclock	= 38461,
-	.bpp		= 8,
-	.xres		= 640,
-	.yres		= 480,
-	.hsync_len	= 63,
-	.vsync_len	= 2,
-	.left_margin	= 81,
-	.upper_margin	= 33,
-	.right_margin	= 16,
-	.lower_margin	= 10,
-	.sync		= (FB_SYNC_HOR_HIGH_ACT |
-			   FB_SYNC_VERT_HIGH_ACT),
-	.cmap_greyscale = 0,
-};
-
-static struct pxafb_mach_info generic_crt_640x480 = {
-	.modes		= &generic_crt_640x480_mode,
-	.num_modes	= 1,
-	.lcd_conn	= LCD_COLOR_TFT_8BPP | LCD_AC_BIAS_FREQ(0xff),
-	.cmap_inverse	= 0,
-	.cmap_static	= 0,
-};
-
-static struct pxafb_mode_info generic_crt_800x600_mode = {
-	.pixclock	= 28846,
-	.bpp		= 8,
-	.xres		= 800,
-	.yres	  	= 600,
-	.hsync_len	= 63,
-	.vsync_len	= 2,
-	.left_margin	= 26,
-	.upper_margin	= 21,
-	.right_margin	= 26,
-	.lower_margin	= 11,
-	.sync		= (FB_SYNC_HOR_HIGH_ACT |
-			   FB_SYNC_VERT_HIGH_ACT),
-	.cmap_greyscale = 0,
-};
-
-static struct pxafb_mach_info generic_crt_800x600 = {
-	.modes		= &generic_crt_800x600_mode,
-	.num_modes	= 1,
-	.lcd_conn	= LCD_COLOR_TFT_8BPP | LCD_AC_BIAS_FREQ(0xff),
-	.cmap_inverse	= 0,
-	.cmap_static	= 0,
-};
-
-static struct pxafb_mode_info generic_tft_320x240_mode = {
-	.pixclock	= 134615,
-	.bpp		= 16,
-	.xres		= 320,
-	.yres		= 240,
-	.hsync_len	= 63,
-	.vsync_len	= 7,
-	.left_margin	= 75,
-	.upper_margin	= 0,
-	.right_margin	= 15,
-	.lower_margin	= 15,
-	.sync		= 0,
-	.cmap_greyscale = 0,
-};
-
-static struct pxafb_mach_info generic_tft_320x240 = {
-	.modes		= &generic_tft_320x240_mode,
-	.num_modes	= 1,
-	.lcd_conn	= LCD_COLOR_TFT_16BPP | LCD_AC_BIAS_FREQ(0xff),
-	.cmap_inverse	= 0,
-	.cmap_static	= 0,
-};
-
-static struct pxafb_mode_info generic_stn_640x480_mode = {
-	.pixclock	= 57692,
-	.bpp		= 8,
-	.xres		= 640,
-	.yres		= 480,
-	.hsync_len	= 4,
-	.vsync_len	= 2,
-	.left_margin	= 10,
-	.upper_margin	= 5,
-	.right_margin	= 10,
-	.lower_margin	= 5,
-	.sync		= (FB_SYNC_HOR_HIGH_ACT |
-			   FB_SYNC_VERT_HIGH_ACT),
-	.cmap_greyscale = 0,
-};
-
-static struct pxafb_mach_info generic_stn_640x480 = {
-	.modes		= &generic_stn_640x480_mode,
-	.num_modes	= 1,
-	.lcd_conn	= LCD_COLOR_STN_8BPP | LCD_AC_BIAS_FREQ(0xff),
-	.cmap_inverse	= 0,
-	.cmap_static	= 0,
-};
-
-static struct pxafb_mach_info *cmx2xx_display = &generic_crt_640x480;
-
-static int __init cmx2xx_set_display(char *str)
-{
-	int disp_type = simple_strtol(str, NULL, 0);
-	switch (disp_type) {
-	case MTYPE_STN320x240:
-		cmx2xx_display = &generic_stn_320x240;
-		break;
-	case MTYPE_TFT640x480:
-		cmx2xx_display = &generic_tft_640x480;
-		break;
-	case MTYPE_CRT640x480:
-		cmx2xx_display = &generic_crt_640x480;
-		break;
-	case MTYPE_CRT800x600:
-		cmx2xx_display = &generic_crt_800x600;
-		break;
-	case MTYPE_TFT320x240:
-		cmx2xx_display = &generic_tft_320x240;
-		break;
-	case MTYPE_STN640x480:
-		cmx2xx_display = &generic_stn_640x480;
-		break;
-	default: /* fallback to CRT 640x480 */
-		cmx2xx_display = &generic_crt_640x480;
-		break;
-	}
-	return 1;
-}
-
-/*
-   This should be done really early to get proper configuration for
-   frame buffer.
-   Indeed, pxafb parameters can be used istead, but CM-X2XX bootloader
-   has limitied line length for kernel command line, and also it will
-   break compatibitlty with proprietary releases already in field.
-*/
-__setup("monitor=", cmx2xx_set_display);
-
-static void __init cmx2xx_init_display(void)
-{
-	pxa_set_fb_info(NULL, cmx2xx_display);
-}
-#else
-static inline void cmx2xx_init_display(void) {}
-#endif
-
-#ifdef CONFIG_PM
-static unsigned long sleep_save_msc[10];
-
-static int cmx2xx_suspend(void)
-{
-	cmx2xx_pci_suspend();
-
-	/* save MSC registers */
-	sleep_save_msc[0] = __raw_readl(MSC0);
-	sleep_save_msc[1] = __raw_readl(MSC1);
-	sleep_save_msc[2] = __raw_readl(MSC2);
-
-	/* setup power saving mode registers */
-	PCFR = 0x0;
-	PSLR = 0xff400000;
-	PMCR  = 0x00000005;
-	PWER  = 0x80000000;
-	PFER  = 0x00000000;
-	PRER  = 0x00000000;
-	PGSR0 = 0xC0018800;
-	PGSR1 = 0x004F0002;
-	PGSR2 = 0x6021C000;
-	PGSR3 = 0x00020000;
-
-	return 0;
-}
-
-static void cmx2xx_resume(void)
-{
-	cmx2xx_pci_resume();
-
-	/* restore MSC registers */
-	__raw_writel(sleep_save_msc[0], MSC0);
-	__raw_writel(sleep_save_msc[1], MSC1);
-	__raw_writel(sleep_save_msc[2], MSC2);
-}
-
-static struct syscore_ops cmx2xx_pm_syscore_ops = {
-	.resume = cmx2xx_resume,
-	.suspend = cmx2xx_suspend,
-};
-
-static int __init cmx2xx_pm_init(void)
-{
-	register_syscore_ops(&cmx2xx_pm_syscore_ops);
-
-	return 0;
-}
-#else
-static int __init cmx2xx_pm_init(void) { return 0; }
-#endif
-
-#if defined(CONFIG_SND_PXA2XX_AC97) || defined(CONFIG_SND_PXA2XX_AC97_MODULE)
-static void __init cmx2xx_init_ac97(void)
-{
-	pxa_set_ac97_info(NULL);
-}
-#else
-static inline void cmx2xx_init_ac97(void) {}
-#endif
-
-static void __init cmx2xx_init(void)
-{
-	pxa_set_ffuart_info(NULL);
-	pxa_set_btuart_info(NULL);
-	pxa_set_stuart_info(NULL);
-
-	cmx2xx_pm_init();
-
-	if (cpu_is_pxa25x())
-		cmx255_init();
-	else
-		cmx270_init();
-
-	cmx2xx_init_dm9000();
-	cmx2xx_init_display();
-	cmx2xx_init_ac97();
-	cmx2xx_init_touchscreen();
-	cmx2xx_init_leds();
-
-	regulator_has_full_constraints();
-}
-
-static void __init cmx2xx_init_irq(void)
-{
-	if (cpu_is_pxa25x()) {
-		pxa25x_init_irq();
-		cmx2xx_pci_init_irq(CMX255_GPIO_IT8152_IRQ);
-	} else {
-		pxa27x_init_irq();
-		cmx2xx_pci_init_irq(CMX270_GPIO_IT8152_IRQ);
-	}
-}
-
-#ifdef CONFIG_PCI
-/* Map PCI companion statically */
-static struct map_desc cmx2xx_io_desc[] __initdata = {
-	[0] = { /* PCI bridge */
-		.virtual	= (unsigned long)CMX2XX_IT8152_VIRT,
-		.pfn		= __phys_to_pfn(PXA_CS4_PHYS),
-		.length		= SZ_64M,
-		.type		= MT_DEVICE
-	},
-};
-
-static void __init cmx2xx_map_io(void)
-{
-	if (cpu_is_pxa25x())
-		pxa25x_map_io();
-
-	if (cpu_is_pxa27x())
-		pxa27x_map_io();
-
-	iotable_init(cmx2xx_io_desc, ARRAY_SIZE(cmx2xx_io_desc));
-
-	it8152_base_address = CMX2XX_IT8152_VIRT;
-}
-#else
-static void __init cmx2xx_map_io(void)
-{
-	if (cpu_is_pxa25x())
-		pxa25x_map_io();
-
-	if (cpu_is_pxa27x())
-		pxa27x_map_io();
-}
-#endif
-
-MACHINE_START(ARMCORE, "Compulab CM-X2XX")
-	.atag_offset	= 0x100,
-	.map_io		= cmx2xx_map_io,
-	.nr_irqs	= CMX2XX_NR_IRQS,
-	.init_irq	= cmx2xx_init_irq,
-	/* NOTE: pxa25x_handle_irq() works on PXA27x w/o camera support */
-	.handle_irq	= pxa25x_handle_irq,
-	.init_time	= pxa_timer_init,
-	.init_machine	= cmx2xx_init,
-#ifdef CONFIG_PCI
-	.dma_zone_size	= SZ_64M,
-#endif
-	.restart	= pxa_restart,
-MACHINE_END
diff --git a/arch/arm/mach-pxa/em-x270.c b/arch/arm/mach-pxa/em-x270.c
deleted file mode 100644
index d8681a331030..000000000000
--- a/arch/arm/mach-pxa/em-x270.c
+++ /dev/null
@@ -1,1286 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0-only
-/*
- * Support for CompuLab EM-X270 platform
- *
- * Copyright (C) 2007, 2008 CompuLab, Ltd.
- * Author: Mike Rapoport <mike@compulab.co.il>
- */
-
-#include <linux/irq.h>
-#include <linux/platform_device.h>
-#include <linux/delay.h>
-
-#include <linux/dm9000.h>
-#include <linux/platform_data/rtc-v3020.h>
-#include <linux/mtd/platnand.h>
-#include <linux/mtd/physmap.h>
-#include <linux/input.h>
-#include <linux/gpio_keys.h>
-#include <linux/gpio.h>
-#include <linux/gpio/machine.h>
-#include <linux/mfd/da903x.h>
-#include <linux/regulator/machine.h>
-#include <linux/regulator/fixed.h>
-#include <linux/spi/spi.h>
-#include <linux/spi/tdo24m.h>
-#include <linux/spi/libertas_spi.h>
-#include <linux/spi/pxa2xx_spi.h>
-#include <linux/power_supply.h>
-#include <linux/apm-emulation.h>
-#include <linux/i2c.h>
-#include <linux/platform_data/pca953x.h>
-#include <linux/platform_data/i2c-pxa.h>
-#include <linux/regulator/userspace-consumer.h>
-
-#include <asm/mach-types.h>
-#include <asm/mach/arch.h>
-
-#include "pxa27x.h"
-#include "pxa27x-udc.h"
-#include <mach/audio.h>
-#include <linux/platform_data/video-pxafb.h>
-#include <linux/platform_data/usb-ohci-pxa27x.h>
-#include <linux/platform_data/mmc-pxamci.h>
-#include <linux/platform_data/keypad-pxa27x.h>
-#include <linux/platform_data/media/camera-pxa.h>
-
-#include "generic.h"
-#include "devices.h"
-
-/* EM-X270 specific GPIOs */
-#define GPIO13_MMC_CD		(13)
-#define GPIO95_MMC_WP		(95)
-#define GPIO56_NAND_RB		(56)
-#define GPIO93_CAM_RESET	(93)
-#define GPIO16_USB_HUB_RESET	(16)
-
-/* eXeda specific GPIOs */
-#define GPIO114_MMC_CD		(114)
-#define GPIO20_NAND_RB		(20)
-#define GPIO38_SD_PWEN		(38)
-#define GPIO37_WLAN_RST		(37)
-#define GPIO95_TOUCHPAD_INT	(95)
-#define GPIO130_CAM_RESET	(130)
-#define GPIO10_USB_HUB_RESET	(10)
-
-/* common  GPIOs */
-#define GPIO11_NAND_CS		(11)
-#define GPIO41_ETHIRQ		(41)
-#define EM_X270_ETHIRQ		PXA_GPIO_TO_IRQ(GPIO41_ETHIRQ)
-#define GPIO115_WLAN_PWEN	(115)
-#define GPIO19_WLAN_STRAP	(19)
-#define GPIO9_USB_VBUS_EN	(9)
-
-static int mmc_cd;
-static int nand_rb;
-static int dm9000_flags;
-static int cam_reset;
-static int usb_hub_reset;
-
-static unsigned long common_pin_config[] = {
-	/* AC'97 */
-	GPIO28_AC97_BITCLK,
-	GPIO29_AC97_SDATA_IN_0,
-	GPIO30_AC97_SDATA_OUT,
-	GPIO31_AC97_SYNC,
-	GPIO98_AC97_SYSCLK,
-	GPIO113_AC97_nRESET,
-
-	/* BTUART */
-	GPIO42_BTUART_RXD,
-	GPIO43_BTUART_TXD,
-	GPIO44_BTUART_CTS,
-	GPIO45_BTUART_RTS,
-
-	/* STUART */
-	GPIO46_STUART_RXD,
-	GPIO47_STUART_TXD,
-
-	/* MCI controller */
-	GPIO32_MMC_CLK,
-	GPIO112_MMC_CMD,
-	GPIO92_MMC_DAT_0,
-	GPIO109_MMC_DAT_1,
-	GPIO110_MMC_DAT_2,
-	GPIO111_MMC_DAT_3,
-
-	/* LCD */
-	GPIOxx_LCD_TFT_16BPP,
-
-	/* QCI */
-	GPIO84_CIF_FV,
-	GPIO25_CIF_LV,
-	GPIO53_CIF_MCLK,
-	GPIO54_CIF_PCLK,
-	GPIO81_CIF_DD_0,
-	GPIO55_CIF_DD_1,
-	GPIO51_CIF_DD_2,
-	GPIO50_CIF_DD_3,
-	GPIO52_CIF_DD_4,
-	GPIO48_CIF_DD_5,
-	GPIO17_CIF_DD_6,
-	GPIO12_CIF_DD_7,
-
-	/* I2C */
-	GPIO117_I2C_SCL,
-	GPIO118_I2C_SDA,
-
-	/* Keypad */
-	GPIO100_KP_MKIN_0	| WAKEUP_ON_LEVEL_HIGH,
-	GPIO101_KP_MKIN_1	| WAKEUP_ON_LEVEL_HIGH,
-	GPIO102_KP_MKIN_2	| WAKEUP_ON_LEVEL_HIGH,
-	GPIO34_KP_MKIN_3	| WAKEUP_ON_LEVEL_HIGH,
-	GPIO39_KP_MKIN_4	| WAKEUP_ON_LEVEL_HIGH,
-	GPIO99_KP_MKIN_5	| WAKEUP_ON_LEVEL_HIGH,
-	GPIO91_KP_MKIN_6	| WAKEUP_ON_LEVEL_HIGH,
-	GPIO36_KP_MKIN_7	| WAKEUP_ON_LEVEL_HIGH,
-	GPIO103_KP_MKOUT_0,
-	GPIO104_KP_MKOUT_1,
-	GPIO105_KP_MKOUT_2,
-	GPIO106_KP_MKOUT_3,
-	GPIO107_KP_MKOUT_4,
-	GPIO108_KP_MKOUT_5,
-	GPIO96_KP_MKOUT_6,
-	GPIO22_KP_MKOUT_7,
-
-	/* SSP1 */
-	GPIO26_SSP1_RXD,
-	GPIO23_SSP1_SCLK,
-	GPIO24_SSP1_SFRM,
-	GPIO57_SSP1_TXD,
-
-	/* SSP2 */
-	GPIO19_GPIO,	/* SSP2 clock is used as GPIO for Libertas pin-strap */
-	GPIO14_GPIO,
-	GPIO89_SSP2_TXD,
-	GPIO88_SSP2_RXD,
-
-	/* SDRAM and local bus */
-	GPIO15_nCS_1,
-	GPIO78_nCS_2,
-	GPIO79_nCS_3,
-	GPIO80_nCS_4,
-	GPIO49_nPWE,
-	GPIO18_RDY,
-
-	/* GPIO */
-	GPIO1_GPIO | WAKEUP_ON_EDGE_BOTH,	/* sleep/resume button */
-
-	/* power controls */
-	GPIO20_GPIO	| MFP_LPM_DRIVE_LOW,	/* GPRS_PWEN */
-	GPIO115_GPIO	| MFP_LPM_DRIVE_LOW,	/* WLAN_PWEN */
-
-	/* NAND controls */
-	GPIO11_GPIO	| MFP_LPM_DRIVE_HIGH,	/* NAND CE# */
-
-	/* interrupts */
-	GPIO41_GPIO,	/* DM9000 interrupt */
-};
-
-static unsigned long em_x270_pin_config[] = {
-	GPIO13_GPIO,				/* MMC card detect */
-	GPIO16_GPIO,				/* USB hub reset */
-	GPIO56_GPIO,				/* NAND Ready/Busy */
-	GPIO93_GPIO	| MFP_LPM_DRIVE_LOW,	/* Camera reset */
-	GPIO95_GPIO,				/* MMC Write protect */
-};
-
-static unsigned long exeda_pin_config[] = {
-	GPIO10_GPIO,				/* USB hub reset */
-	GPIO20_GPIO,				/* NAND Ready/Busy */
-	GPIO38_GPIO	| MFP_LPM_DRIVE_LOW,	/* SD slot power */
-	GPIO95_GPIO,				/* touchpad IRQ */
-	GPIO114_GPIO,				/* MMC card detect */
-};
-
-#if defined(CONFIG_DM9000) || defined(CONFIG_DM9000_MODULE)
-static struct resource em_x270_dm9000_resource[] = {
-	[0] = {
-		.start = PXA_CS2_PHYS,
-		.end   = PXA_CS2_PHYS + 3,
-		.flags = IORESOURCE_MEM,
-	},
-	[1] = {
-		.start = PXA_CS2_PHYS + 8,
-		.end   = PXA_CS2_PHYS + 8 + 0x3f,
-		.flags = IORESOURCE_MEM,
-	},
-	[2] = {
-		.start = EM_X270_ETHIRQ,
-		.end   = EM_X270_ETHIRQ,
-		.flags = IORESOURCE_IRQ | IORESOURCE_IRQ_HIGHEDGE,
-	}
-};
-
-static struct dm9000_plat_data em_x270_dm9000_platdata = {
-	.flags		= DM9000_PLATF_NO_EEPROM,
-};
-
-static struct platform_device em_x270_dm9000 = {
-	.name		= "dm9000",
-	.id		= 0,
-	.num_resources	= ARRAY_SIZE(em_x270_dm9000_resource),
-	.resource	= em_x270_dm9000_resource,
-	.dev		= {
-		.platform_data = &em_x270_dm9000_platdata,
-	}
-};
-
-static void __init em_x270_init_dm9000(void)
-{
-	em_x270_dm9000_platdata.flags |= dm9000_flags;
-	platform_device_register(&em_x270_dm9000);
-}
-#else
-static inline void em_x270_init_dm9000(void) {}
-#endif
-
-/* V3020 RTC */
-#if defined(CONFIG_RTC_DRV_V3020) || defined(CONFIG_RTC_DRV_V3020_MODULE)
-static struct resource em_x270_v3020_resource[] = {
-	[0] = {
-		.start = PXA_CS4_PHYS,
-		.end   = PXA_CS4_PHYS + 3,
-		.flags = IORESOURCE_MEM,
-	},
-};
-
-static struct v3020_platform_data em_x270_v3020_platdata = {
-	.leftshift = 0,
-};
-
-static struct platform_device em_x270_rtc = {
-	.name		= "v3020",
-	.num_resources	= ARRAY_SIZE(em_x270_v3020_resource),
-	.resource	= em_x270_v3020_resource,
-	.id		= -1,
-	.dev		= {
-		.platform_data = &em_x270_v3020_platdata,
-	}
-};
-
-static void __init em_x270_init_rtc(void)
-{
-	platform_device_register(&em_x270_rtc);
-}
-#else
-static inline void em_x270_init_rtc(void) {}
-#endif
-
-/* NAND flash */
-#if defined(CONFIG_MTD_NAND_PLATFORM) || defined(CONFIG_MTD_NAND_PLATFORM_MODULE)
-static inline void nand_cs_on(void)
-{
-	gpio_set_value(GPIO11_NAND_CS, 0);
-}
-
-static void nand_cs_off(void)
-{
-	dsb();
-
-	gpio_set_value(GPIO11_NAND_CS, 1);
-}
-
-/* hardware specific access to control-lines */
-static void em_x270_nand_cmd_ctl(struct nand_chip *this, int dat,
-				 unsigned int ctrl)
-{
-	unsigned long nandaddr = (unsigned long)this->legacy.IO_ADDR_W;
-
-	dsb();
-
-	if (ctrl & NAND_CTRL_CHANGE) {
-		if (ctrl & NAND_ALE)
-			nandaddr |=  (1 << 3);
-		else
-			nandaddr &= ~(1 << 3);
-		if (ctrl & NAND_CLE)
-			nandaddr |=  (1 << 2);
-		else
-			nandaddr &= ~(1 << 2);
-		if (ctrl & NAND_NCE)
-			nand_cs_on();
-		else
-			nand_cs_off();
-	}
-
-	dsb();
-	this->legacy.IO_ADDR_W = (void __iomem *)nandaddr;
-	if (dat != NAND_CMD_NONE)
-		writel(dat, this->legacy.IO_ADDR_W);
-
-	dsb();
-}
-
-/* read device ready pin */
-static int em_x270_nand_device_ready(struct nand_chip *this)
-{
-	dsb();
-
-	return gpio_get_value(nand_rb);
-}
-
-static struct mtd_partition em_x270_partition_info[] = {
-	[0] = {
-		.name	= "em_x270-0",
-		.offset	= 0,
-		.size	= SZ_4M,
-	},
-	[1] = {
-		.name	= "em_x270-1",
-		.offset	= MTDPART_OFS_APPEND,
-		.size	= MTDPART_SIZ_FULL
-	},
-};
-
-struct platform_nand_data em_x270_nand_platdata = {
-	.chip = {
-		.nr_chips = 1,
-		.chip_offset = 0,
-		.nr_partitions = ARRAY_SIZE(em_x270_partition_info),
-		.partitions = em_x270_partition_info,
-		.chip_delay = 20,
-	},
-	.ctrl = {
-		.dev_ready = em_x270_nand_device_ready,
-		.select_chip = 0,
-		.cmd_ctrl = em_x270_nand_cmd_ctl,
-	},
-};
-
-static struct resource em_x270_nand_resource[] = {
-	[0] = {
-		.start = PXA_CS1_PHYS,
-		.end   = PXA_CS1_PHYS + 12,
-		.flags = IORESOURCE_MEM,
-	},
-};
-
-static struct platform_device em_x270_nand = {
-	.name		= "gen_nand",
-	.num_resources	= ARRAY_SIZE(em_x270_nand_resource),
-	.resource	= em_x270_nand_resource,
-	.id		= -1,
-	.dev		= {
-		.platform_data = &em_x270_nand_platdata,
-	}
-};
-
-static void __init em_x270_init_nand(void)
-{
-	int err;
-
-	err = gpio_request(GPIO11_NAND_CS, "NAND CS");
-	if (err) {
-		pr_warn("EM-X270: failed to request NAND CS gpio\n");
-		return;
-	}
-
-	gpio_direction_output(GPIO11_NAND_CS, 1);
-
-	err = gpio_request(nand_rb, "NAND R/B");
-	if (err) {
-		pr_warn("EM-X270: failed to request NAND R/B gpio\n");
-		gpio_free(GPIO11_NAND_CS);
-		return;
-	}
-
-	gpio_direction_input(nand_rb);
-
-	platform_device_register(&em_x270_nand);
-}
-#else
-static inline void em_x270_init_nand(void) {}
-#endif
-
-#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE)
-static struct mtd_partition em_x270_nor_parts[] = {
-	{
-		.name =		"Bootloader",
-		.offset =	0x00000000,
-		.size =		0x00050000,
-		.mask_flags =	MTD_WRITEABLE  /* force read-only */
-	}, {
-		.name =		"Environment",
-		.offset =	0x00050000,
-		.size =		0x00010000,
-	}, {
-		.name =		"Reserved",
-		.offset =	0x00060000,
-		.size =		0x00050000,
-		.mask_flags =	MTD_WRITEABLE  /* force read-only */
-	}, {
-		.name =		"Splashscreen",
-		.offset =	0x000b0000,
-		.size =		0x00050000,
-	}
-};
-
-static struct physmap_flash_data em_x270_nor_data[] = {
-	[0] = {
-		.width = 2,
-		.parts = em_x270_nor_parts,
-		.nr_parts = ARRAY_SIZE(em_x270_nor_parts),
-	},
-};
-
-static struct resource em_x270_nor_flash_resource = {
-	.start	= PXA_CS0_PHYS,
-	.end	= PXA_CS0_PHYS + SZ_1M - 1,
-	.flags	= IORESOURCE_MEM,
-};
-
-static struct platform_device em_x270_physmap_flash = {
-	.name		= "physmap-flash",
-	.id		= 0,
-	.num_resources	= 1,
-	.resource	= &em_x270_nor_flash_resource,
-	.dev		= {
-		.platform_data	= &em_x270_nor_data,
-	},
-};
-
-static void __init em_x270_init_nor(void)
-{
-	platform_device_register(&em_x270_physmap_flash);
-}
-#else
-static inline void em_x270_init_nor(void) {}
-#endif
-
-/* PXA27x OHCI controller setup */
-#if defined(CONFIG_USB_OHCI_HCD) || defined(CONFIG_USB_OHCI_HCD_MODULE)
-static struct regulator *em_x270_usb_ldo;
-
-static int em_x270_usb_hub_init(void)
-{
-	int err;
-
-	em_x270_usb_ldo = regulator_get(NULL, "vcc usb");
-	if (IS_ERR(em_x270_usb_ldo))
-		return PTR_ERR(em_x270_usb_ldo);
-
-	err = gpio_request(GPIO9_USB_VBUS_EN, "vbus en");
-	if (err)
-		goto err_free_usb_ldo;
-
-	err = gpio_request(usb_hub_reset, "hub rst");
-	if (err)
-		goto err_free_vbus_gpio;
-
-	/* USB Hub power-on and reset */
-	gpio_direction_output(usb_hub_reset, 1);
-	gpio_direction_output(GPIO9_USB_VBUS_EN, 0);
-	err = regulator_enable(em_x270_usb_ldo);
-	if (err)
-		goto err_free_rst_gpio;
-
-	gpio_set_value(usb_hub_reset, 0);
-	gpio_set_value(usb_hub_reset, 1);
-	regulator_disable(em_x270_usb_ldo);
-	err = regulator_enable(em_x270_usb_ldo);
-	if (err)
-		goto err_free_rst_gpio;
-
-	gpio_set_value(usb_hub_reset, 0);
-	gpio_set_value(GPIO9_USB_VBUS_EN, 1);
-
-	return 0;
-
-err_free_rst_gpio:
-	gpio_free(usb_hub_reset);
-err_free_vbus_gpio:
-	gpio_free(GPIO9_USB_VBUS_EN);
-err_free_usb_ldo:
-	regulator_put(em_x270_usb_ldo);
-
-	return err;
-}
-
-static int em_x270_ohci_init(struct device *dev)
-{
-	int err;
-
-	/* we don't want to entirely disable USB if the HUB init failed */
-	err = em_x270_usb_hub_init();
-	if (err)
-		pr_err("USB Hub initialization failed: %d\n", err);
-
-	/* enable port 2 transiever */
-	UP2OCR = UP2OCR_HXS | UP2OCR_HXOE;
-
-	return 0;
-}
-
-static void em_x270_ohci_exit(struct device *dev)
-{
-	gpio_free(usb_hub_reset);
-	gpio_free(GPIO9_USB_VBUS_EN);
-
-	if (!IS_ERR(em_x270_usb_ldo)) {
-		if (regulator_is_enabled(em_x270_usb_ldo))
-			regulator_disable(em_x270_usb_ldo);
-
-		regulator_put(em_x270_usb_ldo);
-	}
-}
-
-static struct pxaohci_platform_data em_x270_ohci_platform_data = {
-	.port_mode	= PMM_PERPORT_MODE,
-	.flags		= ENABLE_PORT1 | ENABLE_PORT2 | POWER_CONTROL_LOW,
-	.init		= em_x270_ohci_init,
-	.exit		= em_x270_ohci_exit,
-};
-
-static void __init em_x270_init_ohci(void)
-{
-	pxa_set_ohci_info(&em_x270_ohci_platform_data);
-}
-#else
-static inline void em_x270_init_ohci(void) {}
-#endif
-
-/* MCI controller setup */
-#if defined(CONFIG_MMC) || defined(CONFIG_MMC_MODULE)
-static struct regulator *em_x270_sdio_ldo;
-
-static struct gpiod_lookup_table em_x270_mci_wp_gpio_table = {
-	.dev_id = "pxa2xx-mci.0",
-	.table = {
-		/* Write protect on GPIO 95 */
-		GPIO_LOOKUP("gpio-pxa", GPIO95_MMC_WP, "wp", GPIO_ACTIVE_LOW),
-		{ },
-	},
-};
-
-static int em_x270_mci_init(struct device *dev,
-			    irq_handler_t em_x270_detect_int,
-			    void *data)
-{
-	int err;
-
-	em_x270_sdio_ldo = regulator_get(dev, "vcc sdio");
-	if (IS_ERR(em_x270_sdio_ldo)) {
-		dev_err(dev, "can't request SDIO power supply: %ld\n",
-			PTR_ERR(em_x270_sdio_ldo));
-		return PTR_ERR(em_x270_sdio_ldo);
-	}
-
-	err = request_irq(gpio_to_irq(mmc_cd), em_x270_detect_int,
-			      IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
-			      "MMC card detect", data);
-	if (err) {
-		dev_err(dev, "can't request MMC card detect IRQ: %d\n", err);
-		goto err_irq;
-	}
-
-	if (!machine_is_em_x270()) {
-		err = gpio_request(GPIO38_SD_PWEN, "sdio power");
-		if (err) {
-			dev_err(dev, "can't request MMC power control : %d\n",
-				err);
-			goto err_gpio_wp;
-		}
-		gpio_direction_output(GPIO38_SD_PWEN, 1);
-	}
-
-	return 0;
-
-err_gpio_wp:
-	free_irq(gpio_to_irq(mmc_cd), data);
-err_irq:
-	regulator_put(em_x270_sdio_ldo);
-
-	return err;
-}
-
-static int em_x270_mci_setpower(struct device *dev, unsigned int vdd)
-{
-	struct pxamci_platform_data* p_d = dev->platform_data;
-
-	if ((1 << vdd) & p_d->ocr_mask) {
-		int vdd_uV = (2000 + (vdd - __ffs(MMC_VDD_20_21)) * 100) * 1000;
-
-		regulator_set_voltage(em_x270_sdio_ldo, vdd_uV, vdd_uV);
-		return regulator_enable(em_x270_sdio_ldo);
-	} else {
-		regulator_disable(em_x270_sdio_ldo);
-	}
-	return 0;
-}
-
-static void em_x270_mci_exit(struct device *dev, void *data)
-{
-	free_irq(gpio_to_irq(mmc_cd), data);
-	regulator_put(em_x270_sdio_ldo);
-
-	if (!machine_is_em_x270())
-		gpio_free(GPIO38_SD_PWEN);
-}
-
-static struct pxamci_platform_data em_x270_mci_platform_data = {
-	.detect_delay_ms	= 250,
-	.ocr_mask		= MMC_VDD_20_21|MMC_VDD_21_22|MMC_VDD_22_23|
-				  MMC_VDD_24_25|MMC_VDD_25_26|MMC_VDD_26_27|
-				  MMC_VDD_27_28|MMC_VDD_28_29|MMC_VDD_29_30|
-				  MMC_VDD_30_31|MMC_VDD_31_32,
-	.init 			= em_x270_mci_init,
-	.setpower 		= em_x270_mci_setpower,
-	.exit			= em_x270_mci_exit,
-};
-
-static void __init em_x270_init_mmc(void)
-{
-	if (machine_is_em_x270())
-		gpiod_add_lookup_table(&em_x270_mci_wp_gpio_table);
-
-	pxa_set_mci_info(&em_x270_mci_platform_data);
-}
-#else
-static inline void em_x270_init_mmc(void) {}
-#endif
-
-/* LCD */
-#if defined(CONFIG_FB_PXA) || defined(CONFIG_FB_PXA_MODULE)
-static struct pxafb_mode_info em_x270_lcd_modes[] = {
-	[0] = {
-		.pixclock	= 38250,
-		.bpp		= 16,
-		.xres		= 480,
-		.yres		= 640,
-		.hsync_len	= 8,
-		.vsync_len	= 2,
-		.left_margin	= 8,
-		.upper_margin	= 2,
-		.right_margin	= 24,
-		.lower_margin	= 4,
-		.sync		= 0,
-	},
-	[1] = {
-		.pixclock       = 153800,
-		.bpp		= 16,
-		.xres		= 240,
-		.yres		= 320,
-		.hsync_len	= 8,
-		.vsync_len	= 2,
-		.left_margin	= 8,
-		.upper_margin	= 2,
-		.right_margin	= 88,
-		.lower_margin	= 2,
-		.sync		= 0,
-	},
-};
-
-static struct pxafb_mach_info em_x270_lcd = {
-	.modes		= em_x270_lcd_modes,
-	.num_modes	= 2,
-	.lcd_conn	= LCD_COLOR_TFT_16BPP,
-};
-
-static void __init em_x270_init_lcd(void)
-{
-	pxa_set_fb_info(NULL, &em_x270_lcd);
-}
-#else
-static inline void em_x270_init_lcd(void) {}
-#endif
-
-#if defined(CONFIG_SPI_PXA2XX) || defined(CONFIG_SPI_PXA2XX_MODULE)
-static struct pxa2xx_spi_controller em_x270_spi_info = {
-	.num_chipselect	= 1,
-};
-
-static struct pxa2xx_spi_chip em_x270_tdo24m_chip = {
-	.rx_threshold	= 1,
-	.tx_threshold	= 1,
-	.gpio_cs	= -1,
-};
-
-static struct tdo24m_platform_data em_x270_tdo24m_pdata = {
-	.model = TDO35S,
-};
-
-static struct pxa2xx_spi_controller em_x270_spi_2_info = {
-	.num_chipselect	= 1,
-	.enable_dma	= 1,
-};
-
-static struct pxa2xx_spi_chip em_x270_libertas_chip = {
-	.rx_threshold	= 1,
-	.tx_threshold	= 1,
-	.timeout	= 1000,
-	.gpio_cs	= 14,
-};
-
-static unsigned long em_x270_libertas_pin_config[] = {
-	/* SSP2 */
-	GPIO19_SSP2_SCLK,
-	GPIO14_GPIO,
-	GPIO89_SSP2_TXD,
-	GPIO88_SSP2_RXD,
-};
-
-static int em_x270_libertas_setup(struct spi_device *spi)
-{
-	int err = gpio_request(GPIO115_WLAN_PWEN, "WLAN PWEN");
-	if (err)
-		return err;
-
-	err = gpio_request(GPIO19_WLAN_STRAP, "WLAN STRAP");
-	if (err)
-		goto err_free_pwen;
-
-	if (machine_is_exeda()) {
-		err = gpio_request(GPIO37_WLAN_RST, "WLAN RST");
-		if (err)
-			goto err_free_strap;
-
-		gpio_direction_output(GPIO37_WLAN_RST, 1);
-		msleep(100);
-	}
-
-	gpio_direction_output(GPIO19_WLAN_STRAP, 1);
-	msleep(100);
-
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(em_x270_libertas_pin_config));
-
-	gpio_direction_output(GPIO115_WLAN_PWEN, 0);
-	msleep(100);
-	gpio_set_value(GPIO115_WLAN_PWEN, 1);
-	msleep(100);
-
-	spi->bits_per_word = 16;
-	spi_setup(spi);
-
-	return 0;
-
-err_free_strap:
-	gpio_free(GPIO19_WLAN_STRAP);
-err_free_pwen:
-	gpio_free(GPIO115_WLAN_PWEN);
-
-	return err;
-}
-
-static int em_x270_libertas_teardown(struct spi_device *spi)
-{
-	gpio_set_value(GPIO115_WLAN_PWEN, 0);
-	gpio_free(GPIO115_WLAN_PWEN);
-	gpio_free(GPIO19_WLAN_STRAP);
-
-	if (machine_is_exeda()) {
-		gpio_set_value(GPIO37_WLAN_RST, 0);
-		gpio_free(GPIO37_WLAN_RST);
-	}
-
-	return 0;
-}
-
-struct libertas_spi_platform_data em_x270_libertas_pdata = {
-	.use_dummy_writes	= 1,
-	.setup			= em_x270_libertas_setup,
-	.teardown		= em_x270_libertas_teardown,
-};
-
-static struct spi_board_info em_x270_spi_devices[] __initdata = {
-	{
-		.modalias		= "tdo24m",
-		.max_speed_hz		= 1000000,
-		.bus_num		= 1,
-		.chip_select		= 0,
-		.controller_data	= &em_x270_tdo24m_chip,
-		.platform_data		= &em_x270_tdo24m_pdata,
-	},
-	{
-		.modalias		= "libertas_spi",
-		.max_speed_hz		= 13000000,
-		.bus_num		= 2,
-		.irq			= PXA_GPIO_TO_IRQ(116),
-		.chip_select		= 0,
-		.controller_data	= &em_x270_libertas_chip,
-		.platform_data		= &em_x270_libertas_pdata,
-	},
-};
-
-static void __init em_x270_init_spi(void)
-{
-	pxa2xx_set_spi_info(1, &em_x270_spi_info);
-	pxa2xx_set_spi_info(2, &em_x270_spi_2_info);
-	spi_register_board_info(ARRAY_AND_SIZE(em_x270_spi_devices));
-}
-#else
-static inline void em_x270_init_spi(void) {}
-#endif
-
-#if defined(CONFIG_SND_PXA2XX_LIB_AC97)
-static pxa2xx_audio_ops_t em_x270_ac97_info = {
-	.reset_gpio = 113,
-};
-
-static void __init em_x270_init_ac97(void)
-{
-	pxa_set_ac97_info(&em_x270_ac97_info);
-}
-#else
-static inline void em_x270_init_ac97(void) {}
-#endif
-
-#if defined(CONFIG_KEYBOARD_PXA27x) || defined(CONFIG_KEYBOARD_PXA27x_MODULE)
-static const unsigned int em_x270_module_matrix_keys[] = {
-	KEY(0, 0, KEY_A), KEY(1, 0, KEY_UP), KEY(2, 1, KEY_B),
-	KEY(0, 2, KEY_LEFT), KEY(1, 1, KEY_ENTER), KEY(2, 0, KEY_RIGHT),
-	KEY(0, 1, KEY_C), KEY(1, 2, KEY_DOWN), KEY(2, 2, KEY_D),
-};
-
-static struct matrix_keymap_data em_x270_matrix_keymap_data = {
-	.keymap			= em_x270_module_matrix_keys,
-	.keymap_size		= ARRAY_SIZE(em_x270_module_matrix_keys),
-};
-
-struct pxa27x_keypad_platform_data em_x270_module_keypad_info = {
-	/* code map for the matrix keys */
-	.matrix_key_rows	= 3,
-	.matrix_key_cols	= 3,
-	.matrix_keymap_data	= &em_x270_matrix_keymap_data,
-};
-
-static const unsigned int em_x270_exeda_matrix_keys[] = {
-	KEY(0, 0, KEY_RIGHTSHIFT), KEY(0, 1, KEY_RIGHTCTRL),
-	KEY(0, 2, KEY_RIGHTALT), KEY(0, 3, KEY_SPACE),
-	KEY(0, 4, KEY_LEFTALT), KEY(0, 5, KEY_LEFTCTRL),
-	KEY(0, 6, KEY_ENTER), KEY(0, 7, KEY_SLASH),
-
-	KEY(1, 0, KEY_DOT), KEY(1, 1, KEY_M),
-	KEY(1, 2, KEY_N), KEY(1, 3, KEY_B),
-	KEY(1, 4, KEY_V), KEY(1, 5, KEY_C),
-	KEY(1, 6, KEY_X), KEY(1, 7, KEY_Z),
-
-	KEY(2, 0, KEY_LEFTSHIFT), KEY(2, 1, KEY_SEMICOLON),
-	KEY(2, 2, KEY_L), KEY(2, 3, KEY_K),
-	KEY(2, 4, KEY_J), KEY(2, 5, KEY_H),
-	KEY(2, 6, KEY_G), KEY(2, 7, KEY_F),
-
-	KEY(3, 0, KEY_D), KEY(3, 1, KEY_S),
-	KEY(3, 2, KEY_A), KEY(3, 3, KEY_TAB),
-	KEY(3, 4, KEY_BACKSPACE), KEY(3, 5, KEY_P),
-	KEY(3, 6, KEY_O), KEY(3, 7, KEY_I),
-
-	KEY(4, 0, KEY_U), KEY(4, 1, KEY_Y),
-	KEY(4, 2, KEY_T), KEY(4, 3, KEY_R),
-	KEY(4, 4, KEY_E), KEY(4, 5, KEY_W),
-	KEY(4, 6, KEY_Q), KEY(4, 7, KEY_MINUS),
-
-	KEY(5, 0, KEY_0), KEY(5, 1, KEY_9),
-	KEY(5, 2, KEY_8), KEY(5, 3, KEY_7),
-	KEY(5, 4, KEY_6), KEY(5, 5, KEY_5),
-	KEY(5, 6, KEY_4), KEY(5, 7, KEY_3),
-
-	KEY(6, 0, KEY_2), KEY(6, 1, KEY_1),
-	KEY(6, 2, KEY_ENTER), KEY(6, 3, KEY_END),
-	KEY(6, 4, KEY_DOWN), KEY(6, 5, KEY_UP),
-	KEY(6, 6, KEY_MENU), KEY(6, 7, KEY_F1),
-
-	KEY(7, 0, KEY_LEFT), KEY(7, 1, KEY_RIGHT),
-	KEY(7, 2, KEY_BACK), KEY(7, 3, KEY_HOME),
-	KEY(7, 4, 0), KEY(7, 5, 0),
-	KEY(7, 6, 0), KEY(7, 7, 0),
-};
-
-static struct matrix_keymap_data em_x270_exeda_matrix_keymap_data = {
-	.keymap			= em_x270_exeda_matrix_keys,
-	.keymap_size		= ARRAY_SIZE(em_x270_exeda_matrix_keys),
-};
-
-struct pxa27x_keypad_platform_data em_x270_exeda_keypad_info = {
-	/* code map for the matrix keys */
-	.matrix_key_rows	= 8,
-	.matrix_key_cols	= 8,
-	.matrix_keymap_data	= &em_x270_exeda_matrix_keymap_data,
-};
-
-static void __init em_x270_init_keypad(void)
-{
-	if (machine_is_em_x270())
-		pxa_set_keypad_info(&em_x270_module_keypad_info);
-	else
-		pxa_set_keypad_info(&em_x270_exeda_keypad_info);
-}
-#else
-static inline void em_x270_init_keypad(void) {}
-#endif
-
-#if defined(CONFIG_KEYBOARD_GPIO) || defined(CONFIG_KEYBOARD_GPIO_MODULE)
-static struct gpio_keys_button gpio_keys_button[] = {
-	[0] = {
-		.desc	= "sleep/wakeup",
-		.code	= KEY_SUSPEND,
-		.type	= EV_PWR,
-		.gpio	= 1,
-		.wakeup	= 1,
-	},
-};
-
-static struct gpio_keys_platform_data em_x270_gpio_keys_data = {
-	.buttons	= gpio_keys_button,
-	.nbuttons	= 1,
-};
-
-static struct platform_device em_x270_gpio_keys = {
-	.name		= "gpio-keys",
-	.id		= -1,
-	.dev		= {
-		.platform_data	= &em_x270_gpio_keys_data,
-	},
-};
-
-static void __init em_x270_init_gpio_keys(void)
-{
-	platform_device_register(&em_x270_gpio_keys);
-}
-#else
-static inline void em_x270_init_gpio_keys(void) {}
-#endif
-
-/* Quick Capture Interface and sensor setup */
-#if defined(CONFIG_VIDEO_PXA27x) || defined(CONFIG_VIDEO_PXA27x_MODULE)
-static int em_x270_sensor_init(void)
-{
-	int ret;
-
-	ret = gpio_request(cam_reset, "camera reset");
-	if (ret)
-		return ret;
-
-	gpio_direction_output(cam_reset, 0);
-	gpio_set_value(cam_reset, 1);
-
-	return 0;
-}
-
-static struct regulator_consumer_supply camera_dummy_supplies[] = {
-	REGULATOR_SUPPLY("vdd", "0-005d"),
-};
-
-static struct regulator_init_data camera_dummy_initdata = {
-	.consumer_supplies = camera_dummy_supplies,
-	.num_consumer_supplies = ARRAY_SIZE(camera_dummy_supplies),
-	.constraints = {
-		.valid_ops_mask = REGULATOR_CHANGE_STATUS,
-	},
-};
-
-static struct fixed_voltage_config camera_dummy_config = {
-	.supply_name		= "camera_vdd",
-	.input_supply		= "vcc cam",
-	.microvolts		= 2800000,
-	.init_data		= &camera_dummy_initdata,
-};
-
-static struct platform_device camera_supply_dummy_device = {
-	.name	= "reg-fixed-voltage",
-	.id	= 1,
-	.dev	= {
-		.platform_data = &camera_dummy_config,
-	},
-};
-
-struct pxacamera_platform_data em_x270_camera_platform_data = {
-	.flags  = PXA_CAMERA_MASTER | PXA_CAMERA_DATAWIDTH_8 |
-		PXA_CAMERA_PCLK_EN | PXA_CAMERA_MCLK_EN,
-	.mclk_10khz = 2600,
-	.sensor_i2c_adapter_id = 0,
-	.sensor_i2c_address = 0x5d,
-};
-
-static void  __init em_x270_init_camera(void)
-{
-	if (em_x270_sensor_init() == 0)
-		pxa_set_camera_info(&em_x270_camera_platform_data);
-	platform_device_register(&camera_supply_dummy_device);
-}
-#else
-static inline void em_x270_init_camera(void) {}
-#endif
-
-static struct regulator_bulk_data em_x270_gps_consumer_supply = {
-	.supply		= "vcc gps",
-};
-
-static struct regulator_userspace_consumer_data em_x270_gps_consumer_data = {
-	.name		= "vcc gps",
-	.num_supplies	= 1,
-	.supplies	= &em_x270_gps_consumer_supply,
-};
-
-static struct platform_device em_x270_gps_userspace_consumer = {
-	.name		= "reg-userspace-consumer",
-	.id		= 0,
-	.dev		= {
-		.platform_data = &em_x270_gps_consumer_data,
-	},
-};
-
-static struct regulator_bulk_data em_x270_gprs_consumer_supply = {
-	.supply		= "vcc gprs",
-};
-
-static struct regulator_userspace_consumer_data em_x270_gprs_consumer_data = {
-	.name		= "vcc gprs",
-	.num_supplies	= 1,
-	.supplies	= &em_x270_gprs_consumer_supply
-};
-
-static struct platform_device em_x270_gprs_userspace_consumer = {
-	.name		= "reg-userspace-consumer",
-	.id		= 1,
-	.dev		= {
-		.platform_data = &em_x270_gprs_consumer_data,
-	}
-};
-
-static struct platform_device *em_x270_userspace_consumers[] = {
-	&em_x270_gps_userspace_consumer,
-	&em_x270_gprs_userspace_consumer,
-};
-
-static void __init em_x270_userspace_consumers_init(void)
-{
-	platform_add_devices(ARRAY_AND_SIZE(em_x270_userspace_consumers));
-}
-
-/* DA9030 related initializations */
-#define REGULATOR_CONSUMER(_name, _dev_name, _supply)		        \
-	static struct regulator_consumer_supply _name##_consumers[] = {	\
-		REGULATOR_SUPPLY(_supply, _dev_name),			\
-	}
-
-REGULATOR_CONSUMER(ldo3, "reg-userspace-consumer.0", "vcc gps");
-REGULATOR_CONSUMER(ldo5, NULL, "vcc cam");
-REGULATOR_CONSUMER(ldo10, "pxa2xx-mci", "vcc sdio");
-REGULATOR_CONSUMER(ldo12, NULL, "vcc usb");
-REGULATOR_CONSUMER(ldo19, "reg-userspace-consumer.1", "vcc gprs");
-REGULATOR_CONSUMER(buck2, NULL, "vcc_core");
-
-#define REGULATOR_INIT(_ldo, _min_uV, _max_uV, _ops_mask)		\
-	static struct regulator_init_data _ldo##_data = {		\
-		.constraints = {					\
-			.min_uV = _min_uV,				\
-			.max_uV = _max_uV,				\
-			.state_mem = {					\
-				.enabled = 0,				\
-			},						\
-			.valid_ops_mask = _ops_mask,			\
-			.apply_uV = 1,					\
-		},							\
-		.num_consumer_supplies = ARRAY_SIZE(_ldo##_consumers),	\
-		.consumer_supplies = _ldo##_consumers,			\
-	};
-
-REGULATOR_INIT(ldo3, 3200000, 3200000, REGULATOR_CHANGE_STATUS);
-REGULATOR_INIT(ldo5, 3000000, 3000000, REGULATOR_CHANGE_STATUS);
-REGULATOR_INIT(ldo10, 2000000, 3200000,
-	       REGULATOR_CHANGE_STATUS | REGULATOR_CHANGE_VOLTAGE);
-REGULATOR_INIT(ldo12, 3000000, 3000000, REGULATOR_CHANGE_STATUS);
-REGULATOR_INIT(ldo19, 3200000, 3200000, REGULATOR_CHANGE_STATUS);
-REGULATOR_INIT(buck2, 1000000, 1650000, REGULATOR_CHANGE_VOLTAGE);
-
-struct led_info em_x270_led_info = {
-	.name = "em-x270:orange",
-	.default_trigger = "battery-charging-or-full",
-};
-
-struct power_supply_info em_x270_psy_info = {
-	.name = "battery",
-	.technology = POWER_SUPPLY_TECHNOLOGY_LIPO,
-	.voltage_max_design = 4200000,
-	.voltage_min_design = 3000000,
-	.use_for_apm = 1,
-};
-
-static void em_x270_battery_low(void)
-{
-#if defined(CONFIG_APM_EMULATION)
-	apm_queue_event(APM_LOW_BATTERY);
-#endif
-}
-
-static void em_x270_battery_critical(void)
-{
-#if defined(CONFIG_APM_EMULATION)
-	apm_queue_event(APM_CRITICAL_SUSPEND);
-#endif
-}
-
-struct da9030_battery_info em_x270_batterty_info = {
-	.battery_info = &em_x270_psy_info,
-
-	.charge_milliamp = 1000,
-	.charge_millivolt = 4200,
-
-	.vbat_low = 3600,
-	.vbat_crit = 3400,
-	.vbat_charge_start = 4100,
-	.vbat_charge_stop = 4200,
-	.vbat_charge_restart = 4000,
-
-	.vcharge_min = 3200,
-	.vcharge_max = 5500,
-
-	.tbat_low = 197,
-	.tbat_high = 78,
-	.tbat_restart = 100,
-
-	.batmon_interval = 0,
-
-	.battery_low = em_x270_battery_low,
-	.battery_critical = em_x270_battery_critical,
-};
-
-#define DA9030_SUBDEV(_name, _id, _pdata)	\
-	{					\
-		.name = "da903x-" #_name,	\
-		.id = DA9030_ID_##_id,		\
-		.platform_data = _pdata,	\
-	}
-
-#define DA9030_LDO(num)	DA9030_SUBDEV(regulator, LDO##num, &ldo##num##_data)
-
-struct da903x_subdev_info em_x270_da9030_subdevs[] = {
-	DA9030_LDO(3),
-	DA9030_LDO(5),
-	DA9030_LDO(10),
-	DA9030_LDO(12),
-	DA9030_LDO(19),
-
-	DA9030_SUBDEV(regulator, BUCK2, &buck2_data),
-
-	DA9030_SUBDEV(led, LED_PC, &em_x270_led_info),
-	DA9030_SUBDEV(backlight, WLED, &em_x270_led_info),
-	DA9030_SUBDEV(battery, BAT, &em_x270_batterty_info),
-};
-
-static struct da903x_platform_data em_x270_da9030_info = {
-	.num_subdevs = ARRAY_SIZE(em_x270_da9030_subdevs),
-	.subdevs = em_x270_da9030_subdevs,
-};
-
-static struct i2c_board_info em_x270_i2c_pmic_info = {
-	I2C_BOARD_INFO("da9030", 0x49),
-	.irq = PXA_GPIO_TO_IRQ(0),
-	.platform_data = &em_x270_da9030_info,
-};
-
-static struct i2c_pxa_platform_data em_x270_pwr_i2c_info = {
-	.use_pio = 1,
-};
-
-static void __init em_x270_init_da9030(void)
-{
-	pxa27x_set_i2c_power_info(&em_x270_pwr_i2c_info);
-	i2c_register_board_info(1, &em_x270_i2c_pmic_info, 1);
-}
-
-static struct pca953x_platform_data exeda_gpio_ext_pdata = {
-	.gpio_base = 128,
-};
-
-static struct i2c_board_info exeda_i2c_info[] = {
-	{
-		I2C_BOARD_INFO("pca9555", 0x21),
-		.platform_data = &exeda_gpio_ext_pdata,
-	},
-};
-
-static struct i2c_pxa_platform_data em_x270_i2c_info = {
-	.fast_mode = 1,
-};
-
-static void __init em_x270_init_i2c(void)
-{
-	pxa_set_i2c_info(&em_x270_i2c_info);
-
-	if (machine_is_exeda())
-		i2c_register_board_info(0, ARRAY_AND_SIZE(exeda_i2c_info));
-}
-
-static void __init em_x270_module_init(void)
-{
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(em_x270_pin_config));
-
-	mmc_cd = GPIO13_MMC_CD;
-	nand_rb = GPIO56_NAND_RB;
-	dm9000_flags = DM9000_PLATF_32BITONLY;
-	cam_reset = GPIO93_CAM_RESET;
-	usb_hub_reset = GPIO16_USB_HUB_RESET;
-}
-
-static void __init em_x270_exeda_init(void)
-{
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(exeda_pin_config));
-
-	mmc_cd = GPIO114_MMC_CD;
-	nand_rb = GPIO20_NAND_RB;
-	dm9000_flags = DM9000_PLATF_16BITONLY;
-	cam_reset = GPIO130_CAM_RESET;
-	usb_hub_reset = GPIO10_USB_HUB_RESET;
-}
-
-static void __init em_x270_init(void)
-{
-	pxa2xx_mfp_config(ARRAY_AND_SIZE(common_pin_config));
-
-	pxa_set_ffuart_info(NULL);
-	pxa_set_btuart_info(NULL);
-	pxa_set_stuart_info(NULL);
-
-#ifdef CONFIG_PM
-	pxa27x_set_pwrmode(PWRMODE_DEEPSLEEP);
-#endif
-
-	if (machine_is_em_x270())
-		em_x270_module_init();
-	else if (machine_is_exeda())
-		em_x270_exeda_init();
-	else
-		panic("Unsupported machine: %d\n", machine_arch_type);
-
-	em_x270_init_da9030();
-	em_x270_init_dm9000();
-	em_x270_init_rtc();
-	em_x270_init_nand();
-	em_x270_init_nor();
-	em_x270_init_lcd();
-	em_x270_init_mmc();
-	em_x270_init_ohci();
-	em_x270_init_keypad();
-	em_x270_init_gpio_keys();
-	em_x270_init_ac97();
-	em_x270_init_spi();
-	em_x270_init_i2c();
-	em_x270_init_camera();
-	em_x270_userspace_consumers_init();
-
-	regulator_has_full_constraints();
-}
-
-MACHINE_START(EM_X270, "Compulab EM-X270")
-	.atag_offset	= 0x100,
-	.map_io		= pxa27x_map_io,
-	.nr_irqs	= PXA_NR_IRQS,
-	.init_irq	= pxa27x_init_irq,
-	.handle_irq	= pxa27x_handle_irq,
-	.init_time	= pxa_timer_init,
-	.init_machine	= em_x270_init,
-	.restart	= pxa_restart,
-MACHINE_END
-
-MACHINE_START(EXEDA, "Compulab eXeda")
-	.atag_offset	= 0x100,
-	.map_io		= pxa27x_map_io,
-	.nr_irqs	= PXA_NR_IRQS,
-	.init_irq	= pxa27x_init_irq,
-	.handle_irq	= pxa27x_handle_irq,
-	.init_time	= pxa_timer_init,
-	.init_machine	= em_x270_init,
-	.restart	= pxa_restart,
-MACHINE_END
diff --git a/arch/arm/mach-pxa/include/mach/io.h b/arch/arm/mach-pxa/include/mach/io.h
deleted file mode 100644
index d54031c4f3df..000000000000
--- a/arch/arm/mach-pxa/include/mach/io.h
+++ /dev/null
@@ -1,18 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-/*
- * arch/arm/mach-pxa/include/mach/io.h
- *
- * Copied from asm/arch/sa1100/io.h
- */
-#ifndef __ASM_ARM_ARCH_IO_H
-#define __ASM_ARM_ARCH_IO_H
-
-#define IO_SPACE_LIMIT 0xffffffff
-
-/*
- * We don't actually have real ISA nor PCI buses, but there is so many
- * drivers out there that might just work if we fake them...
- */
-#define __io(a)		__typesafe_io(a)
-
-#endif
-- 
2.26.2


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related

* [PATCH v3 3/3] ASoC: pxa: remove Compulab pxa2xx boards
From: Robert Jarzmik @ 2020-05-21 18:51 UTC (permalink / raw)
  To: Daniel Mack, Haojian Zhuang, Robert Jarzmik, Liam Girdwood,
	Mark Brown, Jaroslav Kysela, Takashi Iwai, soc
  Cc: Arnd Bergmann, alsa-devel, Mike Rapoport, linux-kernel,
	linux-arm-kernel
In-Reply-To: <20200521185140.27276-1-robert.jarzmik@free.fr>

As these boards have been removed from the pxa tree, amend accordingly
the sound subsystem.

Signed-off-by: Robert Jarzmik <robert.jarzmik@free.fr>
Acked-by: Mike Rapoport <rppt@kernel.org>
Acked-by: Arnd Bergmann <arnd@arndb.de>
---
 sound/soc/pxa/Kconfig | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/sound/soc/pxa/Kconfig b/sound/soc/pxa/Kconfig
index d4c0f580a565..fb2d5ab02b0d 100644
--- a/sound/soc/pxa/Kconfig
+++ b/sound/soc/pxa/Kconfig
@@ -128,9 +128,8 @@ config SND_PXA2XX_SOC_E800
 	  Toshiba e800 PDA
 
 config SND_PXA2XX_SOC_EM_X270
-	tristate "SoC Audio support for CompuLab EM-x270, eXeda and CM-X300"
-	depends on SND_PXA2XX_SOC && (MACH_EM_X270 || MACH_EXEDA || \
-			MACH_CM_X300)
+	tristate "SoC Audio support for CompuLab CM-X300"
+	depends on SND_PXA2XX_SOC && MACH_CM_X300
 	depends on AC97_BUS=n
 	select REGMAP
 	select AC97_BUS_NEW
-- 
2.26.2


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related

* [PATCH v3 2/3] MAINTAINERS: pxa: remove Compulab arm/pxa support
From: Robert Jarzmik @ 2020-05-21 18:51 UTC (permalink / raw)
  To: Daniel Mack, Haojian Zhuang, Robert Jarzmik, Liam Girdwood,
	Mark Brown, Jaroslav Kysela, Takashi Iwai, soc
  Cc: Arnd Bergmann, alsa-devel, Mike Rapoport, linux-kernel,
	linux-arm-kernel
In-Reply-To: <20200521185140.27276-1-robert.jarzmik@free.fr>

These boards support is removed from the kernel, so remove the
MAINTAINERS entry for them.

Signed-off-by: Robert Jarzmik <robert.jarzmik@free.fr>
Acked-by: Mike Rapoport <rppt@kernel.org>
Acked-by: Arnd Bergmann <arnd@arndb.de>
---
 MAINTAINERS | 5 -----
 1 file changed, 5 deletions(-)

diff --git a/MAINTAINERS b/MAINTAINERS
index 091ec22c1a23..ad58388fa822 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -1684,11 +1684,6 @@ S:	Maintained
 T:	git git://git.armlinux.org.uk/~rmk/linux-arm.git clkdev
 F:	drivers/clk/clkdev.c
 
-ARM/COMPULAB CM-X270/EM-X270 and CM-X300 MACHINE SUPPORT
-M:	Mike Rapoport <mike@compulab.co.il>
-L:	linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
-S:	Maintained
-
 ARM/CONEXANT DIGICOLOR MACHINE SUPPORT
 M:	Baruch Siach <baruch@tkos.co.il>
 L:	linux-arm-kernel@lists.infradead.org (moderated for non-subscribers)
-- 
2.26.2


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related

* Re: [PATCH v2 4/4] remoteproc/k3-dsp: Add support for L2RAM loading on C66x DSPs
From: Bjorn Andersson @ 2020-05-21 18:48 UTC (permalink / raw)
  To: Suman Anna
  Cc: devicetree, Mathieu Poirier, Lokesh Vutla, linux-remoteproc,
	linux-kernel, Rob Herring, linux-arm-kernel
In-Reply-To: <20200521001006.2725-5-s-anna@ti.com>

On Wed 20 May 17:10 PDT 2020, Suman Anna wrote:

> The resets for the DSP processors on K3 SoCs are managed through the
> Power and Sleep Controller (PSC) module. Each DSP typically has two
> resets - a global module reset for powering on the device, and a local
> reset that affects only the CPU while allowing access to the other
> sub-modules within the DSP processor sub-systems.
> 
> The C66x DSPs have two levels of internal RAMs that can be used to
> boot from, and the firmware loading into these RAMs require the
> local reset to be asserted with the device powered on/enabled using
> the module reset. Enhance the K3 DSP remoteproc driver to add support
> for loading into the internal RAMs. The local reset is deasserted on
> SoC power-on-reset, so logic has to be added in probe in remoteproc
> mode to balance the remoteproc state-machine.
> 
> Note that the local resets are a no-op on C71x cores, and the hardware
> does not supporting loading into its internal RAMs.
> 
> Signed-off-by: Suman Anna <s-anna@ti.com>

Reviewed-by: Bjorn Andersson <bjorn.andersson@linaro.org>

Regards,
Bjorn

> ---
> v2:
>  - Dropped the local-reset no-op checks from k3_dsp_rproc_prepare/unprepare()
>    callbacks. The logic will be adjusted back in the C71 patch series.
>  - The C71 local reset references are also removed from the comments for the
>    k3_dsp_rproc_prepare() function.
> v1: https://patchwork.kernel.org/patch/11458579/
> 
>  drivers/remoteproc/ti_k3_dsp_remoteproc.c | 72 +++++++++++++++++++++++
>  1 file changed, 72 insertions(+)
> 
> diff --git a/drivers/remoteproc/ti_k3_dsp_remoteproc.c b/drivers/remoteproc/ti_k3_dsp_remoteproc.c
> index e4036f5992fe..610fbbf85ee6 100644
> --- a/drivers/remoteproc/ti_k3_dsp_remoteproc.c
> +++ b/drivers/remoteproc/ti_k3_dsp_remoteproc.c
> @@ -174,6 +174,9 @@ static int k3_dsp_rproc_reset(struct k3_dsp_rproc *kproc)
>  		return ret;
>  	}
>  
> +	if (kproc->data->uses_lreset)
> +		return ret;
> +
>  	ret = kproc->ti_sci->ops.dev_ops.put_device(kproc->ti_sci,
>  						    kproc->ti_sci_id);
>  	if (ret) {
> @@ -191,6 +194,9 @@ static int k3_dsp_rproc_release(struct k3_dsp_rproc *kproc)
>  	struct device *dev = kproc->dev;
>  	int ret;
>  
> +	if (kproc->data->uses_lreset)
> +		goto lreset;
> +
>  	ret = kproc->ti_sci->ops.dev_ops.get_device(kproc->ti_sci,
>  						    kproc->ti_sci_id);
>  	if (ret) {
> @@ -198,6 +204,7 @@ static int k3_dsp_rproc_release(struct k3_dsp_rproc *kproc)
>  		return ret;
>  	}
>  
> +lreset:
>  	ret = reset_control_deassert(kproc->reset);
>  	if (ret) {
>  		dev_err(dev, "local-reset deassert failed, ret = %d\n", ret);
> @@ -209,6 +216,53 @@ static int k3_dsp_rproc_release(struct k3_dsp_rproc *kproc)
>  	return ret;
>  }
>  
> +/*
> + * The C66x DSP cores have a local reset that affects only the CPU, and a
> + * generic module reset that powers on the device and allows the DSP internal
> + * memories to be accessed while the local reset is asserted. This function is
> + * used to release the global reset on C66x DSPs to allow loading into the DSP
> + * internal RAMs. The .prepare() ops is invoked by remoteproc core before any
> + * firmware loading, and is followed by the .start() ops after loading to
> + * actually let the C66x DSP cores run.
> + */
> +static int k3_dsp_rproc_prepare(struct rproc *rproc)
> +{
> +	struct k3_dsp_rproc *kproc = rproc->priv;
> +	struct device *dev = kproc->dev;
> +	int ret;
> +
> +	ret = kproc->ti_sci->ops.dev_ops.get_device(kproc->ti_sci,
> +						    kproc->ti_sci_id);
> +	if (ret)
> +		dev_err(dev, "module-reset deassert failed, cannot enable internal RAM loading, ret = %d\n",
> +			ret);
> +
> +	return ret;
> +}
> +
> +/*
> + * This function implements the .unprepare() ops and performs the complimentary
> + * operations to that of the .prepare() ops. The function is used to assert the
> + * global reset on applicable C66x cores. This completes the second portion of
> + * powering down the C66x DSP cores. The cores themselves are only halted in the
> + * .stop() callback through the local reset, and the .unprepare() ops is invoked
> + * by the remoteproc core after the remoteproc is stopped to balance the global
> + * reset.
> + */
> +static int k3_dsp_rproc_unprepare(struct rproc *rproc)
> +{
> +	struct k3_dsp_rproc *kproc = rproc->priv;
> +	struct device *dev = kproc->dev;
> +	int ret;
> +
> +	ret = kproc->ti_sci->ops.dev_ops.put_device(kproc->ti_sci,
> +						    kproc->ti_sci_id);
> +	if (ret)
> +		dev_err(dev, "module-reset assert failed, ret = %d\n", ret);
> +
> +	return ret;
> +}
> +
>  /*
>   * Power up the DSP remote processor.
>   *
> @@ -352,6 +406,8 @@ static void *k3_dsp_rproc_da_to_va(struct rproc *rproc, u64 da, size_t len)
>  }
>  
>  static const struct rproc_ops k3_dsp_rproc_ops = {
> +	.prepare	= k3_dsp_rproc_prepare,
> +	.unprepare	= k3_dsp_rproc_unprepare,
>  	.start		= k3_dsp_rproc_start,
>  	.stop		= k3_dsp_rproc_stop,
>  	.kick		= k3_dsp_rproc_kick,
> @@ -614,6 +670,22 @@ static int k3_dsp_rproc_probe(struct platform_device *pdev)
>  		goto release_tsp;
>  	}
>  
> +	/*
> +	 * ensure the DSP local reset is asserted to ensure the DSP doesn't
> +	 * execute bogus code in .prepare() when the module reset is released.
> +	 */
> +	if (data->uses_lreset) {
> +		ret = reset_control_status(kproc->reset);
> +		if (ret < 0) {
> +			dev_err(dev, "failed to get reset status, status = %d\n",
> +				ret);
> +			goto release_mem;
> +		} else if (ret == 0) {
> +			dev_warn(dev, "local reset is deasserted for device\n");
> +			k3_dsp_rproc_reset(kproc);
> +		}
> +	}
> +
>  	ret = rproc_add(rproc);
>  	if (ret) {
>  		dev_err(dev, "failed to add register device with remoteproc core, status = %d\n",
> -- 
> 2.26.0
> 

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH v2 1/4] remoteproc: Introduce rproc_of_parse_firmware() helper
From: Bjorn Andersson @ 2020-05-21 18:44 UTC (permalink / raw)
  To: Suman Anna
  Cc: devicetree, Mathieu Poirier, Lokesh Vutla, linux-remoteproc,
	linux-kernel, Rob Herring, linux-arm-kernel
In-Reply-To: <20200521001006.2725-2-s-anna@ti.com>

On Wed 20 May 17:10 PDT 2020, Suman Anna wrote:

> Add a new helper function rproc_of_parse_firmware() to the remoteproc
> core that can be used by various remoteproc drivers to look up the
> the "firmware-name" property from a rproc device node. This property
> is already being used by multiple drivers, so this helper can avoid
> repeating equivalent code in remoteproc drivers.
> 
> Signed-off-by: Suman Anna <s-anna@ti.com>

Reviewed-by: Bjorn Andersson <bjorn.andersson@linaro.org>

Regards,
Bjorn

> ---
> v2: New patch
> 
>  drivers/remoteproc/remoteproc_core.c     | 23 +++++++++++++++++++++++
>  drivers/remoteproc/remoteproc_internal.h |  2 ++
>  2 files changed, 25 insertions(+)
> 
> diff --git a/drivers/remoteproc/remoteproc_core.c b/drivers/remoteproc/remoteproc_core.c
> index 9f04c30c4aaf..c458b218d524 100644
> --- a/drivers/remoteproc/remoteproc_core.c
> +++ b/drivers/remoteproc/remoteproc_core.c
> @@ -1034,6 +1034,29 @@ rproc_of_resm_mem_entry_init(struct device *dev, u32 of_resm_idx, size_t len,
>  }
>  EXPORT_SYMBOL(rproc_of_resm_mem_entry_init);
>  
> +/**
> + * rproc_of_parse_firmware() - parse and return the firmware-name
> + * @dev: pointer on device struct representing a rproc
> + * @index: index to use for the firmware-name retrieval
> + * @fw_name: pointer to a character string, in which the firmware
> + *           name is returned on success and unmodified otherwise.
> + *
> + * This is an OF helper function that parses a device's DT node for
> + * the "firmware-name" property and returns the firmware name pointer
> + * in @fw_name on success.
> + *
> + * Return: 0 on success, or an appropriate failure.
> + */
> +int rproc_of_parse_firmware(struct device *dev, int index, const char **fw_name)
> +{
> +	int ret;
> +
> +	ret = of_property_read_string_index(dev->of_node, "firmware-name",
> +					    index, fw_name);
> +	return ret ? ret : 0;
> +}
> +EXPORT_SYMBOL(rproc_of_parse_firmware);
> +
>  /*
>   * A lookup table for resource handlers. The indices are defined in
>   * enum fw_resource_type.
> diff --git a/drivers/remoteproc/remoteproc_internal.h b/drivers/remoteproc/remoteproc_internal.h
> index 4ba7cb59d3e8..e5341e91d2fc 100644
> --- a/drivers/remoteproc/remoteproc_internal.h
> +++ b/drivers/remoteproc/remoteproc_internal.h
> @@ -28,6 +28,8 @@ struct rproc_debug_trace {
>  void rproc_release(struct kref *kref);
>  irqreturn_t rproc_vq_interrupt(struct rproc *rproc, int vq_id);
>  void rproc_vdev_release(struct kref *ref);
> +int rproc_of_parse_firmware(struct device *dev, int index,
> +			    const char **fw_name);
>  
>  /* from remoteproc_virtio.c */
>  int rproc_add_virtio_dev(struct rproc_vdev *rvdev, int id);
> -- 
> 2.26.0
> 

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [RFC PATCH V4 0/4] media: platform: Add support for Face Detection (FD) on mt8183 SoC
From: Tomasz Figa @ 2020-05-21 18:38 UTC (permalink / raw)
  To: Jerry-ch Chen
  Cc: devicetree@vger.kernel.org, Sean Cheng (鄭昇弘),
	laurent.pinchart+renesas@ideasonboard.com, zwisler@chromium.org,
	srv_heupstream, Christie Yu (游雅惠),
	Jungo Lin (林明俊),
	Sj Huang (黃信璋), yuzhao@chromium.org,
	hans.verkuil@cisco.com, pihsun@chromium.org,
	Frederic Chen (陳俊元), matthias.bgg@gmail.com,
	linux-mediatek@lists.infradead.org, mchehab@kernel.org,
	linux-arm-kernel@lists.infradead.org, linux-media@vger.kernel.org
In-Reply-To: <CAAFQd5CP+gH3zG9fejBv_hTzeAExMoY+L38W8e4e3OSc-gVRHg@mail.gmail.com>

Hi Jerry,

On Wed, May 13, 2020 at 11:45:37PM +0200, Tomasz Figa wrote:
> Hi Jerry,
> 
> On Fri, May 8, 2020 at 4:03 AM Jerry-ch Chen <Jerry-ch.Chen@mediatek.com> wrote:
> >
> > Hi Laurent, Tomasz, Matthias,
> >
> > gentle ping for this patch set,
> > If no new comments, I would like to send a newer version.
> >
> 
> Sorry, I still haven't had a chance to look at the series, so feel
> free to send a new version and I will take a look at the new one.
> 

Finally found some time to review the series. Again sorry for the delay
and thanks for your patience.

Some general comments:
1) The metadata format FourCC should be added in a separate patch,
together with documentation for it.
2) Control IDs, structs used by the userspace, etc. should be defined in
a header under include/uapi/linux.

Please also check my replies to particular patches for further comments.

Best regards,
Tomasz

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH v2 3/4] remoteproc/k3-dsp: Add a remoteproc driver of K3 C66x DSPs
From: Bjorn Andersson @ 2020-05-21 18:34 UTC (permalink / raw)
  To: Suman Anna
  Cc: devicetree, Mathieu Poirier, Lokesh Vutla, linux-remoteproc,
	linux-kernel, Rob Herring, linux-arm-kernel
In-Reply-To: <20200521001006.2725-4-s-anna@ti.com>

On Wed 20 May 17:10 PDT 2020, Suman Anna wrote:

> The Texas Instrument's K3 J721E SoCs have two C66x DSP Subsystems in MAIN
> voltage domain that are based on the TI's standard TMS320C66x DSP CorePac
> module. Each subsystem has a Fixed/Floating-Point DSP CPU, with 32 KB each
> of L1P & L1D SRAMs that can be configured and partitioned as either RAM
> and/or Cache, and 288 KB of L2 SRAM with 256 KB of memory configurable as
> either RAM and/or Cache. The CorePac also includes an Internal DMA (IDMA),
> External Memory Controller (EMC), Extended Memory Controller (XMC) with a
> Region Address Translator (RAT) unit for 32-bit to 48-bit address
> extension/translations, an Interrupt Controller (INTC) and a Powerdown
> Controller (PDC).
> 
> A new remoteproc module is added to perform the device management of
> these DSP devices. The support is limited to images using only external
> DDR memory at the moment, the loading support to internal memories and
> any on-chip RAM memories will be added in a subsequent patch. RAT support
> is also left for a future patch, and as such the reserved memory carveout
> regions are all expected to be using memory regions within the first 2 GB.
> Error Recovery and Power Management features are not currently supported.
> 
> The C66x remote processors do not have an MMU, and so require fixed memory
> carveout regions matching the firmware image addresses. Support for this
> is provided by mandating multiple memory regions to be attached to the
> remoteproc device. The first memory region will be used to serve as the
> DMA pool for all dynamic allocations like the vrings and vring buffers.
> The remaining memory regions are mapped into the kernel at device probe
> time, and are used to provide address translations for firmware image
> segments without the need for any RSC_CARVEOUT entries. Any firmware
> image using memory outside of the supplied reserved memory carveout
> regions will be errored out.
> 
> The driver uses various TI-SCI interfaces to talk to the System Controller
> (DMSC) for managing configuration, power and reset management of these
> cores. IPC between the A72 cores and the DSP cores is supported through
> the virtio rpmsg stack using shared memory and OMAP Mailboxes.
> 

There's room for more devm_ usage, but this looks good to me.

Reviewed-by: Bjorn Andersson <bjorn.andersson@linaro.org>

Regards,
Bjorn

> Signed-off-by: Suman Anna <s-anna@ti.com>
> ---
> v2:
>  - Dropped the pm_runtime usage
>  - Replaced the private k3_dsp_rproc_get_firmware() with the newly introduced
>    rproc_of_parse_firmware()
>  - Addressed other minor comments from Mathieu - Revised help on Kconfig, reordered
>    header files, whitespace indentation fixes, remove the stale memset comment on
>    internal memories, renamed struct k3_dsp_rproc_mem to struct k3_dsp_mem.
> v1: https://patchwork.kernel.org/patch/11458577/
> 
>  drivers/remoteproc/Kconfig                |  13 +
>  drivers/remoteproc/Makefile               |   1 +
>  drivers/remoteproc/ti_k3_dsp_remoteproc.c | 701 ++++++++++++++++++++++
>  3 files changed, 715 insertions(+)
>  create mode 100644 drivers/remoteproc/ti_k3_dsp_remoteproc.c
> 
> diff --git a/drivers/remoteproc/Kconfig b/drivers/remoteproc/Kconfig
> index 2c9fb870a276..ef787774b52b 100644
> --- a/drivers/remoteproc/Kconfig
> +++ b/drivers/remoteproc/Kconfig
> @@ -265,6 +265,19 @@ config TI_K3_R5_REMOTEPROC
>  	  It's safe to say N here if you're not interested in utilizing
>  	  a slave processor
>  
> +config TI_K3_DSP_REMOTEPROC
> +	tristate "TI K3 DSP remoteproc support"
> +	depends on ARCH_K3
> +	select MAILBOX
> +	select OMAP2PLUS_MBOX
> +	help
> +	  Say m here to support TI's C66x and C71x DSP remote processor
> +	  subsystems on various TI K3 family of SoCs through the remote
> +	  processor framework.
> +
> +	  It's safe to say N here if you're not interested in utilizing
> +	  the DSP slave processors.
> +
>  endif # REMOTEPROC
>  
>  endmenu
> diff --git a/drivers/remoteproc/Makefile b/drivers/remoteproc/Makefile
> index ea0c6812e4fc..9f87d222744c 100644
> --- a/drivers/remoteproc/Makefile
> +++ b/drivers/remoteproc/Makefile
> @@ -31,3 +31,4 @@ obj-$(CONFIG_ST_REMOTEPROC)		+= st_remoteproc.o
>  obj-$(CONFIG_ST_SLIM_REMOTEPROC)	+= st_slim_rproc.o
>  obj-$(CONFIG_STM32_RPROC)		+= stm32_rproc.o
>  obj-$(CONFIG_TI_K3_R5_REMOTEPROC)	+= ti_k3_r5_remoteproc.o
> +obj-$(CONFIG_TI_K3_DSP_REMOTEPROC)	+= ti_k3_dsp_remoteproc.o
> diff --git a/drivers/remoteproc/ti_k3_dsp_remoteproc.c b/drivers/remoteproc/ti_k3_dsp_remoteproc.c
> new file mode 100644
> index 000000000000..e4036f5992fe
> --- /dev/null
> +++ b/drivers/remoteproc/ti_k3_dsp_remoteproc.c
> @@ -0,0 +1,701 @@
> +// SPDX-License-Identifier: GPL-2.0-only
> +/*
> + * TI K3 DSP Remote Processor(s) driver
> + *
> + * Copyright (C) 2018-2020 Texas Instruments Incorporated - http://www.ti.com/
> + *	Suman Anna <s-anna@ti.com>
> + */
> +
> +#include <linux/io.h>
> +#include <linux/mailbox_client.h>
> +#include <linux/module.h>
> +#include <linux/of_device.h>
> +#include <linux/of_reserved_mem.h>
> +#include <linux/omap-mailbox.h>
> +#include <linux/platform_device.h>
> +#include <linux/remoteproc.h>
> +#include <linux/reset.h>
> +#include <linux/soc/ti/ti_sci_protocol.h>
> +
> +#include "omap_remoteproc.h"
> +#include "remoteproc_internal.h"
> +#include "ti_sci_proc.h"
> +
> +#define KEYSTONE_RPROC_LOCAL_ADDRESS_MASK	(SZ_16M - 1)
> +
> +/**
> + * struct k3_dsp_mem - internal memory structure
> + * @cpu_addr: MPU virtual address of the memory region
> + * @bus_addr: Bus address used to access the memory region
> + * @dev_addr: Device address of the memory region from DSP view
> + * @size: Size of the memory region
> + */
> +struct k3_dsp_mem {
> +	void __iomem *cpu_addr;
> +	phys_addr_t bus_addr;
> +	u32 dev_addr;
> +	size_t size;
> +};
> +
> +/**
> + * struct k3_dsp_mem_data - memory definitions for a DSP
> + * @name: name for this memory entry
> + * @dev_addr: device address for the memory entry
> + */
> +struct k3_dsp_mem_data {
> +	const char *name;
> +	const u32 dev_addr;
> +};
> +
> +/**
> + * struct k3_dsp_dev_data - device data structure for a DSP
> + * @mems: pointer to memory definitions for a DSP
> + * @num_mems: number of memory regions in @mems
> + * @boot_align_addr: boot vector address alignment granularity
> + * @uses_lreset: flag to denote the need for local reset management
> + */
> +struct k3_dsp_dev_data {
> +	const struct k3_dsp_mem_data *mems;
> +	u32 num_mems;
> +	u32 boot_align_addr;
> +	bool uses_lreset;
> +};
> +
> +/**
> + * struct k3_dsp_rproc - k3 DSP remote processor driver structure
> + * @dev: cached device pointer
> + * @rproc: remoteproc device handle
> + * @mem: internal memory regions data
> + * @num_mems: number of internal memory regions
> + * @rmem: reserved memory regions data
> + * @num_rmems: number of reserved memory regions
> + * @reset: reset control handle
> + * @data: pointer to DSP-specific device data
> + * @tsp: TI-SCI processor control handle
> + * @ti_sci: TI-SCI handle
> + * @ti_sci_id: TI-SCI device identifier
> + * @mbox: mailbox channel handle
> + * @client: mailbox client to request the mailbox channel
> + */
> +struct k3_dsp_rproc {
> +	struct device *dev;
> +	struct rproc *rproc;
> +	struct k3_dsp_mem *mem;
> +	int num_mems;
> +	struct k3_dsp_mem *rmem;
> +	int num_rmems;
> +	struct reset_control *reset;
> +	const struct k3_dsp_dev_data *data;
> +	struct ti_sci_proc *tsp;
> +	const struct ti_sci_handle *ti_sci;
> +	u32 ti_sci_id;
> +	struct mbox_chan *mbox;
> +	struct mbox_client client;
> +};
> +
> +/**
> + * k3_dsp_rproc_mbox_callback() - inbound mailbox message handler
> + * @client: mailbox client pointer used for requesting the mailbox channel
> + * @data: mailbox payload
> + *
> + * This handler is invoked by the OMAP mailbox driver whenever a mailbox
> + * message is received. Usually, the mailbox payload simply contains
> + * the index of the virtqueue that is kicked by the remote processor,
> + * and we let remoteproc core handle it.
> + *
> + * In addition to virtqueue indices, we also have some out-of-band values
> + * that indicate different events. Those values are deliberately very
> + * large so they don't coincide with virtqueue indices.
> + */
> +static void k3_dsp_rproc_mbox_callback(struct mbox_client *client, void *data)
> +{
> +	struct k3_dsp_rproc *kproc = container_of(client, struct k3_dsp_rproc,
> +						  client);
> +	struct device *dev = kproc->rproc->dev.parent;
> +	const char *name = kproc->rproc->name;
> +	u32 msg = omap_mbox_message(data);
> +
> +	dev_dbg(dev, "mbox msg: 0x%x\n", msg);
> +
> +	switch (msg) {
> +	case RP_MBOX_CRASH:
> +		/*
> +		 * remoteproc detected an exception, but error recovery is not
> +		 * supported. So, just log this for now
> +		 */
> +		dev_err(dev, "K3 DSP rproc %s crashed\n", name);
> +		break;
> +	case RP_MBOX_ECHO_REPLY:
> +		dev_info(dev, "received echo reply from %s\n", name);
> +		break;
> +	default:
> +		/* silently handle all other valid messages */
> +		if (msg >= RP_MBOX_READY && msg < RP_MBOX_END_MSG)
> +			return;
> +		if (msg > kproc->rproc->max_notifyid) {
> +			dev_dbg(dev, "dropping unknown message 0x%x", msg);
> +			return;
> +		}
> +		/* msg contains the index of the triggered vring */
> +		if (rproc_vq_interrupt(kproc->rproc, msg) == IRQ_NONE)
> +			dev_dbg(dev, "no message was found in vqid %d\n", msg);
> +	}
> +}
> +
> +/*
> + * Kick the remote processor to notify about pending unprocessed messages.
> + * The vqid usage is not used and is inconsequential, as the kick is performed
> + * through a simulated GPIO (a bit in an IPC interrupt-triggering register),
> + * the remote processor is expected to process both its Tx and Rx virtqueues.
> + */
> +static void k3_dsp_rproc_kick(struct rproc *rproc, int vqid)
> +{
> +	struct k3_dsp_rproc *kproc = rproc->priv;
> +	struct device *dev = rproc->dev.parent;
> +	mbox_msg_t msg = (mbox_msg_t)vqid;
> +	int ret;
> +
> +	/* send the index of the triggered virtqueue in the mailbox payload */
> +	ret = mbox_send_message(kproc->mbox, (void *)msg);
> +	if (ret < 0)
> +		dev_err(dev, "failed to send mailbox message, status = %d\n",
> +			ret);
> +}
> +
> +/* Put the DSP processor into reset */
> +static int k3_dsp_rproc_reset(struct k3_dsp_rproc *kproc)
> +{
> +	struct device *dev = kproc->dev;
> +	int ret;
> +
> +	ret = reset_control_assert(kproc->reset);
> +	if (ret) {
> +		dev_err(dev, "local-reset assert failed, ret = %d\n", ret);
> +		return ret;
> +	}
> +
> +	ret = kproc->ti_sci->ops.dev_ops.put_device(kproc->ti_sci,
> +						    kproc->ti_sci_id);
> +	if (ret) {
> +		dev_err(dev, "module-reset assert failed, ret = %d\n", ret);
> +		if (reset_control_deassert(kproc->reset))
> +			dev_warn(dev, "local-reset deassert back failed\n");
> +	}
> +
> +	return ret;
> +}
> +
> +/* Release the DSP processor from reset */
> +static int k3_dsp_rproc_release(struct k3_dsp_rproc *kproc)
> +{
> +	struct device *dev = kproc->dev;
> +	int ret;
> +
> +	ret = kproc->ti_sci->ops.dev_ops.get_device(kproc->ti_sci,
> +						    kproc->ti_sci_id);
> +	if (ret) {
> +		dev_err(dev, "module-reset deassert failed, ret = %d\n", ret);
> +		return ret;
> +	}
> +
> +	ret = reset_control_deassert(kproc->reset);
> +	if (ret) {
> +		dev_err(dev, "local-reset deassert failed, ret = %d\n", ret);
> +		if (kproc->ti_sci->ops.dev_ops.put_device(kproc->ti_sci,
> +							  kproc->ti_sci_id))
> +			dev_warn(dev, "module-reset assert back failed\n");
> +	}
> +
> +	return ret;
> +}
> +
> +/*
> + * Power up the DSP remote processor.
> + *
> + * This function will be invoked only after the firmware for this rproc
> + * was loaded, parsed successfully, and all of its resource requirements
> + * were met.
> + */
> +static int k3_dsp_rproc_start(struct rproc *rproc)
> +{
> +	struct k3_dsp_rproc *kproc = rproc->priv;
> +	struct mbox_client *client = &kproc->client;
> +	struct device *dev = kproc->dev;
> +	u32 boot_addr;
> +	int ret;
> +
> +	client->dev = dev;
> +	client->tx_done = NULL;
> +	client->rx_callback = k3_dsp_rproc_mbox_callback;
> +	client->tx_block = false;
> +	client->knows_txdone = false;
> +
> +	kproc->mbox = mbox_request_channel(client, 0);
> +	if (IS_ERR(kproc->mbox)) {
> +		ret = -EBUSY;
> +		dev_err(dev, "mbox_request_channel failed: %ld\n",
> +			PTR_ERR(kproc->mbox));
> +		return ret;
> +	}
> +
> +	/*
> +	 * Ping the remote processor, this is only for sanity-sake for now;
> +	 * there is no functional effect whatsoever.
> +	 *
> +	 * Note that the reply will _not_ arrive immediately: this message
> +	 * will wait in the mailbox fifo until the remote processor is booted.
> +	 */
> +	ret = mbox_send_message(kproc->mbox, (void *)RP_MBOX_ECHO_REQUEST);
> +	if (ret < 0) {
> +		dev_err(dev, "mbox_send_message failed: %d\n", ret);
> +		goto put_mbox;
> +	}
> +
> +	boot_addr = rproc->bootaddr;
> +	if (boot_addr & (kproc->data->boot_align_addr - 1)) {
> +		dev_err(dev, "invalid boot address 0x%x, must be aligned on a 0x%x boundary\n",
> +			boot_addr, kproc->data->boot_align_addr);
> +		ret = -EINVAL;
> +		goto put_mbox;
> +	}
> +
> +	dev_err(dev, "booting DSP core using boot addr = 0x%x\n", boot_addr);
> +	ret = ti_sci_proc_set_config(kproc->tsp, boot_addr, 0, 0);
> +	if (ret)
> +		goto put_mbox;
> +
> +	ret = k3_dsp_rproc_release(kproc);
> +	if (ret)
> +		goto put_mbox;
> +
> +	return 0;
> +
> +put_mbox:
> +	mbox_free_channel(kproc->mbox);
> +	return ret;
> +}
> +
> +/*
> + * Stop the DSP remote processor.
> + *
> + * This function puts the DSP processor into reset, and finishes processing
> + * of any pending messages.
> + */
> +static int k3_dsp_rproc_stop(struct rproc *rproc)
> +{
> +	struct k3_dsp_rproc *kproc = rproc->priv;
> +
> +	mbox_free_channel(kproc->mbox);
> +
> +	k3_dsp_rproc_reset(kproc);
> +
> +	return 0;
> +}
> +
> +/*
> + * Custom function to translate a DSP device address (internal RAMs only) to a
> + * kernel virtual address.  The DSPs can access their RAMs at either an internal
> + * address visible only from a DSP, or at the SoC-level bus address. Both these
> + * addresses need to be looked through for translation. The translated addresses
> + * can be used either by the remoteproc core for loading (when using kernel
> + * remoteproc loader), or by any rpmsg bus drivers.
> + */
> +static void *k3_dsp_rproc_da_to_va(struct rproc *rproc, u64 da, size_t len)
> +{
> +	struct k3_dsp_rproc *kproc = rproc->priv;
> +	void __iomem *va = NULL;
> +	phys_addr_t bus_addr;
> +	u32 dev_addr, offset;
> +	size_t size;
> +	int i;
> +
> +	if (len == 0)
> +		return NULL;
> +
> +	for (i = 0; i < kproc->num_mems; i++) {
> +		bus_addr = kproc->mem[i].bus_addr;
> +		dev_addr = kproc->mem[i].dev_addr;
> +		size = kproc->mem[i].size;
> +
> +		if (da < KEYSTONE_RPROC_LOCAL_ADDRESS_MASK) {
> +			/* handle DSP-view addresses */
> +			if (da >= dev_addr &&
> +			    ((da + len) <= (dev_addr + size))) {
> +				offset = da - dev_addr;
> +				va = kproc->mem[i].cpu_addr + offset;
> +				return (__force void *)va;
> +			}
> +		} else {
> +			/* handle SoC-view addresses */
> +			if (da >= bus_addr &&
> +			    (da + len) <= (bus_addr + size)) {
> +				offset = da - bus_addr;
> +				va = kproc->mem[i].cpu_addr + offset;
> +				return (__force void *)va;
> +			}
> +		}
> +	}
> +
> +	/* handle static DDR reserved memory regions */
> +	for (i = 0; i < kproc->num_rmems; i++) {
> +		dev_addr = kproc->rmem[i].dev_addr;
> +		size = kproc->rmem[i].size;
> +
> +		if (da >= dev_addr && ((da + len) <= (dev_addr + size))) {
> +			offset = da - dev_addr;
> +			va = kproc->rmem[i].cpu_addr + offset;
> +			return (__force void *)va;
> +		}
> +	}
> +
> +	return NULL;
> +}
> +
> +static const struct rproc_ops k3_dsp_rproc_ops = {
> +	.start		= k3_dsp_rproc_start,
> +	.stop		= k3_dsp_rproc_stop,
> +	.kick		= k3_dsp_rproc_kick,
> +	.da_to_va	= k3_dsp_rproc_da_to_va,
> +};
> +
> +static int k3_dsp_rproc_of_get_memories(struct platform_device *pdev,
> +					struct k3_dsp_rproc *kproc)
> +{
> +	const struct k3_dsp_dev_data *data = kproc->data;
> +	struct device *dev = &pdev->dev;
> +	struct resource *res;
> +	int num_mems = 0;
> +	int i;
> +
> +	num_mems = kproc->data->num_mems;
> +	kproc->mem = devm_kcalloc(kproc->dev, num_mems,
> +				  sizeof(*kproc->mem), GFP_KERNEL);
> +	if (!kproc->mem)
> +		return -ENOMEM;
> +
> +	for (i = 0; i < num_mems; i++) {
> +		res = platform_get_resource_byname(pdev, IORESOURCE_MEM,
> +						   data->mems[i].name);
> +		if (!res) {
> +			dev_err(dev, "found no memory resource for %s\n",
> +				data->mems[i].name);
> +			return -EINVAL;
> +		}
> +		if (!devm_request_mem_region(dev, res->start,
> +					     resource_size(res),
> +					     dev_name(dev))) {
> +			dev_err(dev, "could not request %s region for resource\n",
> +				data->mems[i].name);
> +			return -EBUSY;
> +		}
> +
> +		kproc->mem[i].cpu_addr = devm_ioremap_wc(dev, res->start,
> +							 resource_size(res));
> +		if (IS_ERR(kproc->mem[i].cpu_addr)) {
> +			dev_err(dev, "failed to map %s memory\n",
> +				data->mems[i].name);
> +			return PTR_ERR(kproc->mem[i].cpu_addr);
> +		}
> +		kproc->mem[i].bus_addr = res->start;
> +		kproc->mem[i].dev_addr = data->mems[i].dev_addr;
> +		kproc->mem[i].size = resource_size(res);
> +
> +		dev_dbg(dev, "memory %8s: bus addr %pa size 0x%zx va %pK da 0x%x\n",
> +			data->mems[i].name, &kproc->mem[i].bus_addr,
> +			kproc->mem[i].size, kproc->mem[i].cpu_addr,
> +			kproc->mem[i].dev_addr);
> +	}
> +	kproc->num_mems = num_mems;
> +
> +	return 0;
> +}
> +
> +static int k3_dsp_reserved_mem_init(struct k3_dsp_rproc *kproc)
> +{
> +	struct device *dev = kproc->dev;
> +	struct device_node *np = dev->of_node;
> +	struct device_node *rmem_np;
> +	struct reserved_mem *rmem;
> +	int num_rmems;
> +	int ret, i;
> +
> +	num_rmems = of_property_count_elems_of_size(np, "memory-region",
> +						    sizeof(phandle));
> +	if (num_rmems <= 0) {
> +		dev_err(dev, "device does not reserved memory regions, ret = %d\n",
> +			num_rmems);
> +		return -EINVAL;
> +	}
> +	if (num_rmems < 2) {
> +		dev_err(dev, "device needs atleast two memory regions to be defined, num = %d\n",
> +			num_rmems);
> +		return -EINVAL;
> +	}
> +
> +	/* use reserved memory region 0 for vring DMA allocations */
> +	ret = of_reserved_mem_device_init_by_idx(dev, np, 0);
> +	if (ret) {
> +		dev_err(dev, "device cannot initialize DMA pool, ret = %d\n",
> +			ret);
> +		return ret;
> +	}
> +
> +	num_rmems--;
> +	kproc->rmem = kcalloc(num_rmems, sizeof(*kproc->rmem), GFP_KERNEL);
> +	if (!kproc->rmem) {
> +		ret = -ENOMEM;
> +		goto release_rmem;
> +	}
> +
> +	/* use remaining reserved memory regions for static carveouts */
> +	for (i = 0; i < num_rmems; i++) {
> +		rmem_np = of_parse_phandle(np, "memory-region", i + 1);
> +		if (!rmem_np) {
> +			ret = -EINVAL;
> +			goto unmap_rmem;
> +		}
> +
> +		rmem = of_reserved_mem_lookup(rmem_np);
> +		if (!rmem) {
> +			of_node_put(rmem_np);
> +			ret = -EINVAL;
> +			goto unmap_rmem;
> +		}
> +		of_node_put(rmem_np);
> +
> +		kproc->rmem[i].bus_addr = rmem->base;
> +		/* 64-bit address regions currently not supported */
> +		kproc->rmem[i].dev_addr = (u32)rmem->base;
> +		kproc->rmem[i].size = rmem->size;
> +		kproc->rmem[i].cpu_addr = ioremap_wc(rmem->base, rmem->size);
> +		if (!kproc->rmem[i].cpu_addr) {
> +			dev_err(dev, "failed to map reserved memory#%d at %pa of size %pa\n",
> +				i + 1, &rmem->base, &rmem->size);
> +			ret = -ENOMEM;
> +			goto unmap_rmem;
> +		}
> +
> +		dev_dbg(dev, "reserved memory%d: bus addr %pa size 0x%zx va %pK da 0x%x\n",
> +			i + 1, &kproc->rmem[i].bus_addr,
> +			kproc->rmem[i].size, kproc->rmem[i].cpu_addr,
> +			kproc->rmem[i].dev_addr);
> +	}
> +	kproc->num_rmems = num_rmems;
> +
> +	return 0;
> +
> +unmap_rmem:
> +	for (i--; i >= 0; i--) {
> +		if (kproc->rmem[i].cpu_addr)
> +			iounmap(kproc->rmem[i].cpu_addr);
> +	}
> +	kfree(kproc->rmem);
> +release_rmem:
> +	of_reserved_mem_device_release(kproc->dev);
> +	return ret;
> +}
> +
> +static void k3_dsp_reserved_mem_exit(struct k3_dsp_rproc *kproc)
> +{
> +	int i;
> +
> +	for (i = 0; i < kproc->num_rmems; i++)
> +		iounmap(kproc->rmem[i].cpu_addr);
> +	kfree(kproc->rmem);
> +
> +	of_reserved_mem_device_release(kproc->dev);
> +}
> +
> +static
> +struct ti_sci_proc *k3_dsp_rproc_of_get_tsp(struct device *dev,
> +					    const struct ti_sci_handle *sci)
> +{
> +	struct ti_sci_proc *tsp;
> +	u32 temp[2];
> +	int ret;
> +
> +	ret = of_property_read_u32_array(dev->of_node, "ti,sci-proc-ids",
> +					 temp, 2);
> +	if (ret < 0)
> +		return ERR_PTR(ret);
> +
> +	tsp = kzalloc(sizeof(*tsp), GFP_KERNEL);
> +	if (!tsp)
> +		return ERR_PTR(-ENOMEM);
> +
> +	tsp->dev = dev;
> +	tsp->sci = sci;
> +	tsp->ops = &sci->ops.proc_ops;
> +	tsp->proc_id = temp[0];
> +	tsp->host_id = temp[1];
> +
> +	return tsp;
> +}
> +
> +static int k3_dsp_rproc_probe(struct platform_device *pdev)
> +{
> +	struct device *dev = &pdev->dev;
> +	struct device_node *np = dev->of_node;
> +	const struct k3_dsp_dev_data *data;
> +	struct k3_dsp_rproc *kproc;
> +	struct rproc *rproc;
> +	const char *fw_name;
> +	int ret = 0;
> +	int ret1;
> +
> +	data = of_device_get_match_data(dev);
> +	if (!data)
> +		return -ENODEV;
> +
> +	ret = rproc_of_parse_firmware(dev, 0, &fw_name);
> +	if (ret) {
> +		dev_err(dev, "failed to parse firmware-name property, ret = %d\n",
> +			ret);
> +		return ret;
> +	}
> +
> +	rproc = rproc_alloc(dev, dev_name(dev), &k3_dsp_rproc_ops, fw_name,
> +			    sizeof(*kproc));
> +	if (!rproc)
> +		return -ENOMEM;
> +
> +	rproc->has_iommu = false;
> +	rproc->recovery_disabled = true;
> +	kproc = rproc->priv;
> +	kproc->rproc = rproc;
> +	kproc->dev = dev;
> +	kproc->data = data;
> +
> +	kproc->ti_sci = ti_sci_get_by_phandle(np, "ti,sci");
> +	if (IS_ERR(kproc->ti_sci)) {
> +		ret = PTR_ERR(kproc->ti_sci);
> +		if (ret != -EPROBE_DEFER) {
> +			dev_err(dev, "failed to get ti-sci handle, ret = %d\n",
> +				ret);
> +		}
> +		kproc->ti_sci = NULL;
> +		goto free_rproc;
> +	}
> +
> +	ret = of_property_read_u32(np, "ti,sci-dev-id", &kproc->ti_sci_id);
> +	if (ret) {
> +		dev_err(dev, "missing 'ti,sci-dev-id' property\n");
> +		goto put_sci;
> +	}
> +
> +	kproc->reset = devm_reset_control_get_exclusive(dev, NULL);
> +	if (IS_ERR(kproc->reset)) {
> +		ret = PTR_ERR(kproc->reset);
> +		dev_err(dev, "failed to get reset, status = %d\n", ret);
> +		goto put_sci;
> +	}
> +
> +	kproc->tsp = k3_dsp_rproc_of_get_tsp(dev, kproc->ti_sci);
> +	if (IS_ERR(kproc->tsp)) {
> +		dev_err(dev, "failed to construct ti-sci proc control, ret = %d\n",
> +			ret);
> +		ret = PTR_ERR(kproc->tsp);
> +		goto put_sci;
> +	}
> +
> +	ret = ti_sci_proc_request(kproc->tsp);
> +	if (ret < 0) {
> +		dev_err(dev, "ti_sci_proc_request failed, ret = %d\n", ret);
> +		goto free_tsp;
> +	}
> +
> +	ret = k3_dsp_rproc_of_get_memories(pdev, kproc);
> +	if (ret)
> +		goto release_tsp;
> +
> +	ret = k3_dsp_reserved_mem_init(kproc);
> +	if (ret) {
> +		dev_err(dev, "reserved memory init failed, ret = %d\n", ret);
> +		goto release_tsp;
> +	}
> +
> +	ret = rproc_add(rproc);
> +	if (ret) {
> +		dev_err(dev, "failed to add register device with remoteproc core, status = %d\n",
> +			ret);
> +		goto release_mem;
> +	}
> +
> +	platform_set_drvdata(pdev, kproc);
> +
> +	return 0;
> +
> +release_mem:
> +	k3_dsp_reserved_mem_exit(kproc);
> +release_tsp:
> +	ret1 = ti_sci_proc_release(kproc->tsp);
> +	if (ret1)
> +		dev_err(dev, "failed to release proc, ret = %d\n", ret1);
> +free_tsp:
> +	kfree(kproc->tsp);
> +put_sci:
> +	ret1 = ti_sci_put_handle(kproc->ti_sci);
> +	if (ret1)
> +		dev_err(dev, "failed to put ti_sci handle, ret = %d\n", ret1);
> +free_rproc:
> +	rproc_free(rproc);
> +	return ret;
> +}
> +
> +static int k3_dsp_rproc_remove(struct platform_device *pdev)
> +{
> +	struct k3_dsp_rproc *kproc = platform_get_drvdata(pdev);
> +	struct device *dev = &pdev->dev;
> +	int ret;
> +
> +	rproc_del(kproc->rproc);
> +
> +	ret = ti_sci_proc_release(kproc->tsp);
> +	if (ret)
> +		dev_err(dev, "failed to release proc, ret = %d\n", ret);
> +
> +	kfree(kproc->tsp);
> +
> +	ret = ti_sci_put_handle(kproc->ti_sci);
> +	if (ret)
> +		dev_err(dev, "failed to put ti_sci handle, ret = %d\n", ret);
> +
> +	k3_dsp_reserved_mem_exit(kproc);
> +	rproc_free(kproc->rproc);
> +
> +	return 0;
> +}
> +
> +static const struct k3_dsp_mem_data c66_mems[] = {
> +	{ .name = "l2sram", .dev_addr = 0x800000 },
> +	{ .name = "l1pram", .dev_addr = 0xe00000 },
> +	{ .name = "l1dram", .dev_addr = 0xf00000 },
> +};
> +
> +static const struct k3_dsp_dev_data c66_data = {
> +	.mems = c66_mems,
> +	.num_mems = ARRAY_SIZE(c66_mems),
> +	.boot_align_addr = SZ_1K,
> +	.uses_lreset = true,
> +};
> +
> +static const struct of_device_id k3_dsp_of_match[] = {
> +	{ .compatible = "ti,j721e-c66-dsp", .data = &c66_data, },
> +	{ /* sentinel */ },
> +};
> +MODULE_DEVICE_TABLE(of, k3_dsp_of_match);
> +
> +static struct platform_driver k3_dsp_rproc_driver = {
> +	.probe	= k3_dsp_rproc_probe,
> +	.remove	= k3_dsp_rproc_remove,
> +	.driver	= {
> +		.name = "k3-dsp-rproc",
> +		.of_match_table = k3_dsp_of_match,
> +	},
> +};
> +
> +module_platform_driver(k3_dsp_rproc_driver);
> +
> +MODULE_AUTHOR("Suman Anna <s-anna@ti.com>");
> +MODULE_LICENSE("GPL v2");
> +MODULE_DESCRIPTION("TI K3 DSP Remoteproc driver");
> -- 
> 2.26.0
> 

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [RFC PATCH V4 4/4] platform: mtk-isp: Add Mediatek FD driver
From: Tomasz Figa @ 2020-05-21 18:28 UTC (permalink / raw)
  To: Jerry-ch Chen
  Cc: devicetree, Sean.Cheng, laurent.pinchart+renesas, Rynn.Wu,
	zwisler, srv_heupstream, christie.yu, jungo.lin, sj.huang, yuzhao,
	hans.verkuil, pihsun, frederic.chen, matthias.bgg, linux-mediatek,
	mchehab, linux-arm-kernel, linux-media
In-Reply-To: <20191204124732.10932-5-Jerry-Ch.chen@mediatek.com>

Hi Jerry,

On Wed, Dec 04, 2019 at 08:47:32PM +0800, Jerry-ch Chen wrote:
> From: Jerry-ch Chen <jerry-ch.chen@mediatek.com>
> 
> This patch adds the driver of Face Detection (FD) unit in
> Mediatek camera system, providing face detection function.
> 
> The mtk-isp directory will contain drivers for multiple IP
> blocks found in Mediatek ISP system. It will include ISP Pass 1
> driver (CAM), sensor interface driver, DIP driver and face
> detection driver.
> 
> Signed-off-by: Jerry-ch Chen <jerry-ch.chen@mediatek.com>
> ---
>  drivers/media/platform/Kconfig                |    2 +
>  drivers/media/platform/Makefile               |    2 +
>  drivers/media/platform/mtk-isp/fd/Kconfig     |   19 +
>  drivers/media/platform/mtk-isp/fd/Makefile    |    5 +
>  drivers/media/platform/mtk-isp/fd/mtk_fd.h    |  149 ++
>  drivers/media/platform/mtk-isp/fd/mtk_fd_40.c | 1279 +++++++++++++++++
>  include/uapi/linux/v4l2-controls.h            |    4 +
>  include/uapi/linux/videodev2.h                |    3 +
>  8 files changed, 1463 insertions(+)
>  create mode 100644 drivers/media/platform/mtk-isp/fd/Kconfig
>  create mode 100644 drivers/media/platform/mtk-isp/fd/Makefile
>  create mode 100644 drivers/media/platform/mtk-isp/fd/mtk_fd.h
>  create mode 100644 drivers/media/platform/mtk-isp/fd/mtk_fd_40.c
> 

Thank you for the patch. Please see my comments inline. Really sorry for
the much delayed review.

[snip]
> +config VIDEO_MEDIATEK_FD
> +	tristate "Mediatek face detection processing function"
> +	depends on VIDEO_V4L2
> +	depends on ARCH_MEDIATEK
> +	select VIDEOBUF2_DMA_CONTIG
> +	select VIDEOBUF2_CORE
> +	select VIDEOBUF2_V4L2
> +	select VIDEOBUF2_MEMOPS
> +	select MEDIA_CONTROLLER
> +	select MTK_SCP
> +
> +	default n
> +	help
> +		Support the Face Detection (FD) feature in the Mediatek
> +		mt8183 Soc.

MT8183?

> +
> +		FD driver is a V4L2 memory-to-memory device driver which
> +		provides hardware accelerated face detection function,
> +		it can detect different sizes of faces in a raw image.

A YUV image I guess?

[snip]
> diff --git a/drivers/media/platform/mtk-isp/fd/mtk_fd.h b/drivers/media/platform/mtk-isp/fd/mtk_fd.h
> new file mode 100644
> index 000000000000..d85bdcb70d6d
> --- /dev/null
> +++ b/drivers/media/platform/mtk-isp/fd/mtk_fd.h
> @@ -0,0 +1,149 @@
> +/* SPDX-License-Identifier: GPL-2.0 */
> +//
> +// Copyright (c) 2018 MediaTek Inc.
> +
> +#ifndef __MTK_FD_HW_H__
> +#define __MTK_FD_HW_H__
> +
> +#include <linux/completion.h>
> +#include <linux/io.h>
> +#include <linux/types.h>
> +#include <linux/platform_device.h>
> +#include <media/v4l2-ctrls.h>
> +#include <media/v4l2-device.h>
> +#include <media/videobuf2-v4l2.h>
> +
> +#define MTK_FD_OUTPUT_MIN_WIDTH			26U
> +#define MTK_FD_OUTPUT_MIN_HEIGHT		26U
> +#define MTK_FD_OUTPUT_MAX_WIDTH			640U
> +#define MTK_FD_OUTPUT_MAX_HEIGHT		480U
> +
> +#define MTK_FD_HW_FMT_VYUY			2
> +#define MTK_FD_HW_FMT_UYVY			3
> +#define MTK_FD_HW_FMT_YVYU			4
> +#define MTK_FD_HW_FMT_YUYV			5
> +#define MTK_FD_HW_FMT_YVU_2P			6
> +#define MTK_FD_HW_FMT_YUV_2P			7
> +#define MTK_FD_HW_FMT_UNKNOWN			8

What is an unknown format?

> +
> +#define MTK_FD_IPI_CMD_INIT			0
> +#define MTK_FD_IPI_CMD_INIT_ACK			1
> +#define MTK_FD_IPI_CMD_ENQUEUE			2
> +#define MTK_FD_IPI_CMD_ENQ_ACK			3
> +#define MTK_FD_IPI_CMD_EXIT			4
> +#define MTK_FD_IPI_CMD_EXIT_ACK			5
> +#define MTK_FD_IPI_CMD_RESET			6
> +#define MTK_FD_IPI_CMD_RESET_ACK		7
> +
> +#define MTK_FD_REG_OFFSET_HW_ENABLE		0x4
> +#define MTK_FD_REG_OFFSET_INT_EN		0x15c
> +#define MTK_FD_REG_OFFSET_INT_VAL		0x168
> +#define MTK_FD_REG_OFFSET_RESULT		0x178
> +
> +#define MTK_FD_SET_HW_ENABLE			0x111
> +#define MTK_FD_RS_BUF_SIZE			2289664
> +#define MTK_FD_HW_WORK_BUF_SIZE			0x100000

How about using the SZ_1M?

> +#define MTK_FD_MAX_SPEEDUP			7
> +#define MTK_FD_MAX_RESULT_NUM			1026

Perhaps NUM_RESULTS?

> +
> +/* Max scale size counts */
> +#define MTK_FD_SCALE_ARR_NUM			15

Perhaps NUM_SCALE_SIZES?

> +
> +#define MTK_FD_HW_TIMEOUT			1000

What's the unit?

> +
> +enum face_angle {
> +	MTK_FD_FACE_FRONT,
> +	MTK_FD_FACE_RIGHT_50,
> +	MTK_FD_FACE_LEFT_50,
> +	MTK_FD_FACE_RIGHT_90,
> +	MTK_FD_FACE_LEFT_90,
> +	MTK_FD_FACE_ANGLE_NUM,
> +};

This enum seems to define values for the V4L2_CID_MTK_FD_DETECT_POSE
control. Considering that this is an enumeration and the values are
actually integers (-90, -50, 0, 50, 90), perhaps this should be an
INTEGER_MENU control instead?

> +
> +struct fd_buffer {
> +	__u32 scp_addr;	/* used by SCP */
> +	__u32 dma_addr;	/* used by DMA HW */
> +} __packed;
> +
> +struct fd_face_result {
> +	char data[16];
> +};
> +
> +struct fd_user_output {
> +	struct fd_face_result results[MTK_FD_MAX_RESULT_NUM];
> +	__u16 number;

Is this perhaps the number of results? If so, would num_results be a better
name?

> +};

Since this struct is the meta buffer format, it is a part of the userspace
interface and should be defined in a header under include/uapi/linux/.

> +
> +struct user_param {
> +	u8 fd_speedup;
> +	u8 fd_extra_model;
> +	u8 scale_img_num;
> +	u8 src_img_fmt;
> +	__u16 scale_img_width[MTK_FD_SCALE_ARR_NUM];
> +	__u16 scale_img_height[MTK_FD_SCALE_ARR_NUM];
> +	__u16 face_directions[MTK_FD_FACE_ANGLE_NUM];

Is this a user-facing definition or an interface between the kernel driver
and firmware? If the latter, the __ types shouldn't be used.

> +} __packed;
> +
> +struct fd_init_param {
> +	struct fd_buffer fd_manager;
> +	__u32 rs_dma_addr;

Ditto.

> +} __packed;
> +
> +struct fd_enq_param {
> +	__u64 output_vaddr;

Ditto.

> +	struct fd_buffer src_img[2];
> +	struct fd_buffer user_result;
> +	struct user_param user_param;
> +} __packed;
> +
> +struct fd_ack_param {
> +	__u32 ret_code;
> +	__u32 ret_msg;

Ditto.

> +} __packed;
[snip]
> +/*  */

Was there supposed to be a comment here? :)

> +static int mtk_fd_hw_alloc_rs_dma_addr(struct mtk_fd_dev *fd)
> +{
> +	struct device *dev = fd->dev;
> +	void *va;
> +	dma_addr_t dma_handle;
> +
> +	va = dma_alloc_coherent(dev, MTK_FD_RS_BUF_SIZE, &dma_handle,
> +				GFP_KERNEL);
> +	if (!va) {
> +		dev_err(dev, "dma_alloc null va\n");

No need to print errors for memory allocation failures, because one will be
printed automatically.

[snip]
> +static int mtk_fd_hw_connect(struct mtk_fd_dev *fd)
> +{
> +	int ret;
> +
> +	ret = rproc_boot(fd->rproc_handle);
> +

nit: Unnecessary blank line.

[snip]
> +static int mtk_fd_vb2_queue_setup(struct vb2_queue *vq,
> +				  unsigned int *num_buffers,
> +				  unsigned int *num_planes,
> +				  unsigned int sizes[],
> +				  struct device *alloc_devs[])
> +{
> +	struct mtk_fd_ctx *ctx = vb2_get_drv_priv(vq);
> +	unsigned int size[2];
> +	unsigned int plane;
> +
> +	switch (vq->type) {
> +	case V4L2_BUF_TYPE_META_CAPTURE:
> +		size[0] = ctx->dst_fmt.buffersize;
> +		break;
> +	case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
> +		size[0] = ctx->src_fmt.plane_fmt[0].sizeimage;
> +		if (*num_planes == 2)
> +			size[1] = ctx->src_fmt.plane_fmt[1].sizeimage;
> +		break;
> +	}

Is this code above needed? The code below sets sizes[] and it uses a for loop,
without opencoded assignment for the second plane.

> +
> +	if (*num_planes > 2)
> +		return -EINVAL;
> +	if (*num_planes == 0) {
> +		if (vq->type == V4L2_BUF_TYPE_META_CAPTURE) {
> +			sizes[0] = ctx->dst_fmt.buffersize;
> +			*num_planes = 1;
> +			return 0;
> +		}
> +
> +		*num_planes = ctx->src_fmt.num_planes;
> +		for (plane = 0; plane < *num_planes; plane++)
> +			sizes[plane] = ctx->src_fmt.plane_fmt[plane].sizeimage;
> +		return 0;
> +	}
> +
> +	for (plane = 0; plane < *num_planes; plane++) {
> +		if (sizes[plane] < size[plane])
> +			return -EINVAL;
> +	}
> +	return 0;
> +}
[snip]
> +static int mtk_fd_enum_fmt_out_mp(struct file *file, void *fh,
> +				  struct v4l2_fmtdesc *f)
> +{
> +	if (f->index >= NUM_FORMATS)

Please use ARRAY_SIZE().

> +		return -EINVAL;
> +
> +	f->pixelformat = mtk_fd_img_fmts[f->index].pixelformat;
> +	return 0;
> +}
> +
> +static void mtk_fd_fill_pixfmt_mp(struct v4l2_pix_format_mplane *dfmt,
> +				  const struct v4l2_pix_format_mplane *sfmt)
> +{
> +	dfmt->field = V4L2_FIELD_NONE;
> +	dfmt->colorspace = V4L2_COLORSPACE_BT2020;
> +	dfmt->num_planes = sfmt->num_planes;
> +	dfmt->ycbcr_enc = V4L2_YCBCR_ENC_DEFAULT;
> +	dfmt->quantization = V4L2_QUANTIZATION_DEFAULT;
> +	dfmt->xfer_func =
> +		V4L2_MAP_XFER_FUNC_DEFAULT(dfmt->colorspace);
> +
> +	/* Keep user setting as possible */
> +	dfmt->width = clamp(dfmt->width,
> +			    MTK_FD_OUTPUT_MIN_WIDTH,
> +			    MTK_FD_OUTPUT_MAX_WIDTH);
> +	dfmt->height = clamp(dfmt->height,
> +			     MTK_FD_OUTPUT_MIN_HEIGHT,
> +			     MTK_FD_OUTPUT_MAX_HEIGHT);
> +
> +	if (sfmt->num_planes == 2) {
> +		/* NV16M and NV61M has 1 byte per pixel */
> +		dfmt->plane_fmt[0].bytesperline = dfmt->width;
> +		dfmt->plane_fmt[1].bytesperline = dfmt->width;
> +	} else {
> +		/* 2 bytes per pixel */
> +		dfmt->plane_fmt[0].bytesperline = dfmt->width * 2;
> +	}
> +
> +	dfmt->plane_fmt[0].sizeimage =
> +		dfmt->height * dfmt->plane_fmt[0].bytesperline;

Could some of the code above be replaced with v4l2_fill_pixfmt_mp()?

> +}
> +
> +static const struct v4l2_pix_format_mplane *mtk_fd_find_fmt(u32 format)
> +{
> +	unsigned int i;
> +	const struct v4l2_pix_format_mplane *dev_fmt;
> +
> +	for (i = 0; i < NUM_FORMATS; i++) {

Please use ARRAY_SIZE rather than a custom macro.

> +		dev_fmt = &mtk_fd_img_fmts[i];
> +		if (dev_fmt->pixelformat == format)
> +			return dev_fmt;
> +	}
> +
> +	return NULL;
> +}
> +
> +static int mtk_fd_try_fmt_out_mp(struct file *file,
> +				 void *fh,
> +				 struct v4l2_format *f)
> +{
> +	struct v4l2_pix_format_mplane *pix_mp = &f->fmt.pix_mp;
> +	const struct v4l2_pix_format_mplane *fmt;
> +
> +	fmt = mtk_fd_find_fmt(pix_mp->pixelformat);
> +	if (!fmt)
> +		fmt = &mtk_fd_img_fmts[0];	/* Get default img fmt */

nit: Please move the comment to a separate line and add braces.

> +
> +	mtk_fd_fill_pixfmt_mp(pix_mp, fmt);
> +	return 0;
> +}
[snip]
> +static unsigned int get_fd_img_fmt(unsigned int fourcc)
> +{
> +	switch (fourcc) {
> +	case V4L2_PIX_FMT_VYUY:
> +		return MTK_FD_HW_FMT_VYUY;
> +	case V4L2_PIX_FMT_YUYV:
> +		return MTK_FD_HW_FMT_YUYV;
> +	case V4L2_PIX_FMT_YVYU:
> +		return MTK_FD_HW_FMT_YVYU;
> +	case V4L2_PIX_FMT_UYVY:
> +		return MTK_FD_HW_FMT_UYVY;
> +	case V4L2_PIX_FMT_NV16M:
> +		return MTK_FD_HW_FMT_YUV_2P;
> +	case V4L2_PIX_FMT_NV61M:
> +		return MTK_FD_HW_FMT_YVU_2P;
> +	default:
> +		return MTK_FD_HW_FMT_UNKNOWN;

If we want to be paranoid, we can just add a WARN here and return 0.
Shouldn't be a need to define an unknown format.

[snip]
> +static void mtk_fd_fill_user_param(struct user_param *user_param,
> +				   struct v4l2_ctrl_handler *hdl)
> +{
> +	struct v4l2_ctrl *ctrl;
> +	int i;
> +
> +	ctrl = v4l2_ctrl_find(hdl, V4L2_CID_MTK_FD_SCALE_DOWN_IMG_WIDTH);
> +	if (ctrl)
> +		for (i = 0; i < ctrl->elems; i++)
> +			user_param->scale_img_width[i] = ctrl->p_new.p_u16[i];
> +	ctrl = v4l2_ctrl_find(hdl, V4L2_CID_MTK_FD_SCALE_DOWN_IMG_HEIGHT);
> +	if (ctrl)
> +		for (i = 0; i < ctrl->elems; i++)
> +			user_param->scale_img_height[i] = ctrl->p_new.p_u16[i];
> +	ctrl = v4l2_ctrl_find(hdl, V4L2_CID_MTK_FD_SCALE_IMG_NUM);
> +	if (ctrl)
> +		user_param->scale_img_num = ctrl->val;
> +

nit: Either separate the code dealing with all controls from each other, or
none.

> +	ctrl = v4l2_ctrl_find(hdl, V4L2_CID_MTK_FD_DETECT_POSE);
> +	if (ctrl)
> +		for (i = 0; i < ctrl->elems; i++)
> +			user_param->face_directions[i] = ctrl->p_new.p_u16[i];
> +	ctrl = v4l2_ctrl_find(hdl, V4L2_CID_MTK_FD_DETECT_SPEED);
> +	if (ctrl)
> +		user_param->fd_speedup = ctrl->val;
> +	ctrl = v4l2_ctrl_find(hdl, V4L2_CID_MTK_FD_DETECTION_MODEL);
> +	if (ctrl)
> +		user_param->fd_extra_model = ctrl->val;
> +}
> +
> +static void mtk_fd_device_run(void *priv)
> +{
> +	struct mtk_fd_ctx *ctx = priv;
> +	struct mtk_fd_dev *fd = ctx->fd_dev;
> +	struct vb2_v4l2_buffer *src_buf, *dst_buf;
> +	struct fd_enq_param fd_param;
> +	void *plane_vaddr;
> +
> +	src_buf = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx);
> +	dst_buf = v4l2_m2m_next_dst_buf(ctx->fh.m2m_ctx);
> +
> +	fd_param.src_img[0].dma_addr =
> +		vb2_dma_contig_plane_dma_addr(&src_buf->vb2_buf, 0);
> +	fd_param.user_result.dma_addr =
> +		vb2_dma_contig_plane_dma_addr(&dst_buf->vb2_buf, 0);
> +	plane_vaddr = vb2_plane_vaddr(&dst_buf->vb2_buf, 0);
> +	fd_param.output_vaddr = (u64)(unsigned long)plane_vaddr;

Why is the vaddr needed here? Specfically, it could pose a security problem
if CPU virtual addresses are exchanged with firmware.

> +	fd_param.user_param.src_img_fmt =
> +		get_fd_img_fmt(ctx->src_fmt.pixelformat);
> +	if (ctx->src_fmt.num_planes == 2)
> +		fd_param.src_img[1].dma_addr =
> +			vb2_dma_contig_plane_dma_addr(&src_buf->vb2_buf, 1);

nit: Could this be moved above, to be just below src_img[0] initialization,
for readability reasons?

> +	mtk_fd_fill_user_param(&fd_param.user_param, &ctx->hdl);
> +
> +	/* Complete request controls if any */
> +	v4l2_ctrl_request_complete(src_buf->vb2_buf.req_obj.req, &ctx->hdl);
> +
> +	fd->output = plane_vaddr;
> +	mtk_fd_hw_job_exec(fd, &fd_param);
> +}
> +
> +static struct v4l2_m2m_ops fd_m2m_ops = {
> +	.device_run = mtk_fd_device_run,
> +};
> +
> +static const struct media_device_ops fd_m2m_media_ops = {
> +	.req_validate	= vb2_request_validate,
> +	.req_queue	= v4l2_m2m_request_queue,
> +};
> +
> +static int mtk_fd_video_device_register(struct mtk_fd_dev *fd)
> +{
> +	struct video_device *vfd = &fd->vfd;
> +	struct v4l2_m2m_dev *m2m_dev = fd->m2m_dev;
> +	struct device *dev = fd->dev;
> +	int ret;
> +
> +	vfd->fops = &fd_video_fops;
> +	vfd->release = video_device_release;
> +	vfd->lock = &fd->vfd_lock;
> +	vfd->v4l2_dev = &fd->v4l2_dev;
> +	vfd->vfl_dir = VFL_DIR_M2M;
> +	vfd->device_caps = V4L2_CAP_STREAMING | V4L2_CAP_VIDEO_OUTPUT_MPLANE |
> +		V4L2_CAP_META_CAPTURE;
> +	vfd->ioctl_ops = &mtk_fd_v4l2_video_out_ioctl_ops;
> +
> +	strscpy(vfd->name, dev_driver_string(dev), sizeof(vfd->name));
> +
> +	video_set_drvdata(vfd, fd);
> +
> +	ret = video_register_device(vfd, VFL_TYPE_GRABBER, 0);
> +	if (ret) {
> +		dev_err(dev, "Failed to register video device\n");
> +		goto err_free_dev;
> +	}
> +
> +	ret = v4l2_m2m_register_media_controller(m2m_dev, vfd,
> +					     MEDIA_ENT_F_PROC_VIDEO_STATISTICS);
> +	if (ret) {
> +		dev_err(dev, "Failed to init mem2mem media controller\n");
> +		goto err_unreg_video;
> +	}
> +	return 0;
> +
> +err_unreg_video:
> +	video_unregister_device(vfd);
> +err_free_dev:
> +	video_device_release(vfd);
> +	return ret;
> +}
> +
> +static int mtk_fd_dev_v4l2_init(struct mtk_fd_dev *fd)
> +{
> +	struct media_device *mdev = &fd->mdev;
> +	struct device *dev = fd->dev;
> +	int ret;
> +
> +	ret = v4l2_device_register(dev, &fd->v4l2_dev);
> +	if (ret) {
> +		dev_err(dev, "Failed to register v4l2 device\n");
> +		return ret;
> +	}
> +
> +	fd->m2m_dev = v4l2_m2m_init(&fd_m2m_ops);
> +	if (IS_ERR(fd->m2m_dev)) {
> +		dev_err(dev, "Failed to init mem2mem device\n");
> +		ret = PTR_ERR(fd->m2m_dev);
> +		goto err_unreg_v4l2_dev;
> +	}
> +
> +	mdev->dev = dev;
> +	strscpy(mdev->model, dev_driver_string(dev), sizeof(mdev->model));
> +	snprintf(mdev->bus_info, sizeof(mdev->bus_info),
> +		 "platform:%s", dev_name(dev));
> +	media_device_init(mdev);
> +	mdev->ops = &fd_m2m_media_ops;
> +	fd->v4l2_dev.mdev = mdev;
> +
> +	ret = mtk_fd_video_device_register(fd);
> +	if (ret) {
> +		dev_err(dev, "Failed to register video device\n");
> +		goto err_cleanup_mdev;
> +	}
> +
> +	ret = media_device_register(mdev);
> +	if (ret) {
> +		dev_err(dev, "Failed to register mem2mem media device\n");
> +		goto err_unreg_vdev;
> +	}
> +
> +	return 0;
> +
> +err_unreg_vdev:
> +	v4l2_m2m_unregister_media_controller(fd->m2m_dev);
> +	video_unregister_device(&fd->vfd);
> +	video_device_release(&fd->vfd);

This is inconsistent with the registration, which registers all of these in
a function. Perhaps it would be worth to move this cleanup to a
mtk_fd_video_device_unregister() function?

> +err_cleanup_mdev:
> +	media_device_cleanup(mdev);
> +	v4l2_m2m_release(fd->m2m_dev);
> +err_unreg_v4l2_dev:
> +	v4l2_device_unregister(&fd->v4l2_dev);
> +	return ret;
> +}
> +
> +static void mtk_fd_dev_v4l2_release(struct mtk_fd_dev *fd)
> +{
> +	v4l2_m2m_unregister_media_controller(fd->m2m_dev);
> +	video_unregister_device(&fd->vfd);
> +	video_device_release(&fd->vfd);
> +	media_device_cleanup(&fd->mdev);
> +	v4l2_m2m_release(fd->m2m_dev);
> +	v4l2_device_unregister(&fd->v4l2_dev);
> +}
> +
> +static irqreturn_t mtk_fd_irq(int irq, void *data)
> +{
> +	struct mtk_fd_dev *fd = (struct mtk_fd_dev *)data;
> +
> +	/* must read this register otherwise HW will keep sending irq */
> +	readl(fd->fd_base + MTK_FD_REG_OFFSET_INT_VAL);
> +	fd->output->number = readl(fd->fd_base + MTK_FD_REG_OFFSET_RESULT);
> +	dev_dbg(fd->dev, "mtk_fd_face_num:%d\n", fd->output->number);
> +
> +	mtk_fd_hw_done(fd, VB2_BUF_STATE_DONE);
> +	return IRQ_HANDLED;
> +}
> +
> +static int mtk_fd_hw_get_scp_mem(struct mtk_fd_dev *fd)
> +{
> +	struct device *dev = fd->dev;
> +	dma_addr_t addr;
> +	void *ptr;
> +	u32 ret;
> +
> +	/*
> +	 * Allocate coherent reserved memory for SCP firmware usage.
> +	 * The size of SCP composer's memory is fixed to 0x100000
> +	 * for the requirement of firmware.
> +	 */
> +	ptr = dma_alloc_coherent(&fd->scp_pdev->dev,
> +				 MTK_FD_HW_WORK_BUF_SIZE, &addr, GFP_KERNEL);
> +	if (!ptr)
> +		return -ENOMEM;
> +
> +	fd->scp_mem.scp_addr = addr;
> +	fd->scp_mem_virt_addr = ptr;
> +	dev_info(dev, "scp addr:%pad va:%pK\n", &addr, ptr);

These addresses are nothing a user should be concerned about, so please
don't use the _info level here. If you think this is an important debugging
information, please make it dev_dbg(). Otherwise, please just remove.

> +
> +	/*
> +	 * This reserved memory is also be used by FD HW.
> +	 * Need to get iova address for FD DMA.
> +	 */
> +	addr = dma_map_resource(dev, addr, MTK_FD_HW_WORK_BUF_SIZE,
> +				DMA_TO_DEVICE, DMA_ATTR_SKIP_CPU_SYNC);

Note that the second argument to dma_map_resource() is phys_addr_t, but the
code above passes a DMA address. This works only by luck, because both
physical and SCP DMA address space have the same addresses. To be fully
correct, dma_map_single() needs to be used, with the kernel virtual address
passed to it, but currently it doesn't handle the memory from a reserved
pool. Thus, we can only keep the hack as is, but please add a comment
explaining it, e.g.

/*
 * FIXME: Assume SCP DMA and physical addresses are the same until
 * dma_map_single() is fixed to handle reserved memory allocations.
 */

> +	if (dma_mapping_error(dev, addr)) {
> +		dev_err(dev, "Failed to map scp iova\n");
> +		ret = -ENOMEM;
> +		goto fail_free_mem;
> +	}
> +	fd->scp_mem.dma_addr = addr;
> +	dev_info(dev, "scp iova addr:%pad\n", &addr);

Ditto.

Best regards,
Tomasz

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH v6 04/19] spi: spi-mem: allow specifying a command's extension
From: Boris Brezillon @ 2020-05-21 18:22 UTC (permalink / raw)
  To: Pratyush Yadav
  Cc: Alexandre Belloni, Mason Yang, Vignesh Raghavendra, Tudor Ambarus,
	Richard Weinberger, Sekhar Nori, linux-kernel, Ludovic Desroches,
	Mark Brown, linux-mtd, Miquel Raynal, Matthias Brugger,
	linux-mediatek, linux-spi, linux-arm-kernel
In-Reply-To: <20200520163053.24357-5-p.yadav@ti.com>

On Wed, 20 May 2020 22:00:38 +0530
Pratyush Yadav <p.yadav@ti.com> wrote:

> In xSPI mode, flashes expect 2-byte opcodes. The second byte is called
> the "command extension". There can be 3 types of extensions in xSPI:
> repeat, invert, and hex. When the extension type is "repeat", the same
> opcode is sent twice. When it is "invert", the second byte is the
> inverse of the opcode. When it is "hex" an additional opcode byte based
> is sent with the command whose value can be anything.
> 
> So, make opcode a 16-bit value and add a 'nbytes', similar to how
> multiple address widths are handled.
> 
> Signed-off-by: Pratyush Yadav <p.yadav@ti.com>
> ---
>  include/linux/spi/spi-mem.h | 5 ++++-
>  1 file changed, 4 insertions(+), 1 deletion(-)
> 
> diff --git a/include/linux/spi/spi-mem.h b/include/linux/spi/spi-mem.h
> index e3dcb956bf61..731bb64c6ba6 100644
> --- a/include/linux/spi/spi-mem.h
> +++ b/include/linux/spi/spi-mem.h
> @@ -69,6 +69,8 @@ enum spi_mem_data_dir {
>  
>  /**
>   * struct spi_mem_op - describes a SPI memory operation
> + * @cmd.nbytes: number of opcode bytes (only 1 or 2 are valid). The opcode is
> + *		sent MSB-first.
>   * @cmd.buswidth: number of IO lines used to transmit the command
>   * @cmd.opcode: operation opcode
>   * @cmd.dtr: whether the command opcode should be sent in DTR mode or not
> @@ -94,9 +96,10 @@ enum spi_mem_data_dir {
>   */
>  struct spi_mem_op {
>  	struct {
> +		u8 nbytes;
>  		u8 buswidth;
>  		u8 dtr : 1;
> -		u8 opcode;
> +		u16 opcode;
>  	} cmd;
>  
>  	struct {

As mentioned in one of my previous review, you should patch the mxic
driver before extending the opcode field:

--->8---
diff --git a/drivers/spi/spi-mxic.c b/drivers/spi/spi-mxic.c
index 69491f3a515d..c3f4136a7c1d 100644
--- a/drivers/spi/spi-mxic.c
+++ b/drivers/spi/spi-mxic.c
@@ -356,6 +356,7 @@ static int mxic_spi_mem_exec_op(struct spi_mem *mem,
        int nio = 1, i, ret;
        u32 ss_ctrl;
        u8 addr[8];
+       u8 cmd[2];
 
        ret = mxic_spi_set_freq(mxic, mem->spi->max_speed_hz);
        if (ret)
@@ -393,7 +394,10 @@ static int mxic_spi_mem_exec_op(struct spi_mem *mem,
        writel(readl(mxic->regs + HC_CFG) | HC_CFG_MAN_CS_ASSERT,
               mxic->regs + HC_CFG);
 
-       ret = mxic_spi_data_xfer(mxic, &op->cmd.opcode, NULL, 1);
+       for (i = 0; i < op->cmd.nbytes; i++)
+               cmd[i] = op->cmd.opcode >> (8 * (op->cmd.nbytes - i - 1));
+
+       ret = mxic_spi_data_xfer(mxic, cmd, NULL, op->cmd.nbytes);
        if (ret)
                goto out;
 

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related

* Re: [PATCH v2 3/8] iio: at91_adc: pass ref to IIO device via param for int function
From: Jonathan Cameron @ 2020-05-21 18:19 UTC (permalink / raw)
  To: Ardelean, Alexandru
  Cc: alexandre.belloni@bootlin.com, alexandre.torgue@st.com,
	linux-iio@vger.kernel.org, linux-kernel@vger.kernel.org,
	ludovic.desroches@microchip.com, ak@it-klinger.de,
	mcoquelin.stm32@gmail.com, eugen.hristev@microchip.com,
	linux-stm32@st-md-mailman.stormreply.com,
	linux-arm-kernel@lists.infradead.org
In-Reply-To: <99993df0dce7f7561e9659985265d6c1f5839208.camel@analog.com>

On Mon, 18 May 2020 08:32:11 +0000
"Ardelean, Alexandru" <alexandru.Ardelean@analog.com> wrote:

> On Sat, 2020-05-16 at 18:17 +0100, Jonathan Cameron wrote:
> > [External]
> > 
> > On Thu, 14 May 2020 16:17:05 +0300
> > Alexandru Ardelean <alexandru.ardelean@analog.com> wrote:
> >   
> > > Since there will be some changes to how iio_priv_to_dev() is implemented,
> > > it could be that the helper becomes a bit slower, as it will be hidden away
> > > in the IIO core.
> > > 
> > > For this driver, the IIO device can be passed directly as a parameter to
> > > the at91_ts_sample() function, thus making it immune to the change of
> > > iio_priv_to_dev().
> > > The function gets called in an interrupt context.
> > > 
> > > Signed-off-by: Alexandru Ardelean <alexandru.ardelean@analog.com>  
> > I wonder. Should we just pass the struct device?  It's only used for
> > error printing I think, so we could make that explicit.  
> 
> I was also thinking that for this series, [for some drivers] it would make sense
> to put a reference to indio_dev on the state-struct; and just return it.
> I'll see about it.
> I am feeling that sometimes these IIO core cleanups end up being more than I
> want to do. But I'll try to see about it. Maybe I can make time or delegate some
> of this.

Absolutely understood.  No problem if you don't have time / energy to
do this stuff.  I very much appreciate it when you do, but I know how
unrewarding it can be!

> 
> My personal interest with them, is to reduce my complaints during reviews.
> People starting to write IIO drivers: well, I can see their frustration [on
> their faces] when I complain that they shouldn't use something, and they copied
> it from somewhere.
> 

That's more or less the only reason I write IIO patches currently!
Though I get to mostly avoid seeing the faces of those who fall
into the traps of old code we should have tidied up years ago :(
Not gotten near any of new hardware pile of IIO hardware in a long time.
Plenty of other new hardware, but not IIO stuff!

Jonathan

> 
> > 
> > I'm not that bothered either way though.
> > 
> > Jonathan
> >   
> > > ---
> > >  drivers/iio/adc/at91_adc.c | 5 ++---
> > >  1 file changed, 2 insertions(+), 3 deletions(-)
> > > 
> > > diff --git a/drivers/iio/adc/at91_adc.c b/drivers/iio/adc/at91_adc.c
> > > index 0368b6dc6d60..5999defe47cd 100644
> > > --- a/drivers/iio/adc/at91_adc.c
> > > +++ b/drivers/iio/adc/at91_adc.c
> > > @@ -287,13 +287,12 @@ static void handle_adc_eoc_trigger(int irq, struct
> > > iio_dev *idev)
> > >  	}
> > >  }
> > >  
> > > -static int at91_ts_sample(struct at91_adc_state *st)
> > > +static int at91_ts_sample(struct iio_dev *idev, struct at91_adc_state *st)
> > >  {
> > >  	unsigned int xscale, yscale, reg, z1, z2;
> > >  	unsigned int x, y, pres, xpos, ypos;
> > >  	unsigned int rxp = 1;
> > >  	unsigned int factor = 1000;
> > > -	struct iio_dev *idev = iio_priv_to_dev(st);
> > >  
> > >  	unsigned int xyz_mask_bits = st->res;
> > >  	unsigned int xyz_mask = (1 << xyz_mask_bits) - 1;
> > > @@ -449,7 +448,7 @@ static irqreturn_t at91_adc_9x5_interrupt(int irq, void
> > > *private)
> > >  
> > >  		if (status & AT91_ADC_ISR_PENS) {
> > >  			/* validate data by pen contact */
> > > -			at91_ts_sample(st);
> > > +			at91_ts_sample(idev, st);
> > >  		} else {
> > >  			/* triggered by event that is no pen contact, just read
> > >  			 * them to clean the interrupt and discard all.  


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH 3/4] remoteproc: add support for a new 64-bit trace version
From: Bjorn Andersson @ 2020-05-21 18:04 UTC (permalink / raw)
  To: Suman Anna
  Cc: devicetree, Mathieu Poirier, Loic Pallardy, Lokesh Vutla,
	linux-remoteproc, Arnaud Pouliquen, linux-kernel, Clement Leger,
	Rob Herring, linux-arm-kernel
In-Reply-To: <20200325204701.16862-4-s-anna@ti.com>

On Wed 25 Mar 13:47 PDT 2020, Suman Anna wrote:

> Introduce a new trace entry resource structure that accommodates
> a 64-bit device address to support 64-bit processors. This is to
> be used using an overloaded version value of 1 in the upper 32-bits
> of the previous resource type field. The new resource still uses
> 32-bits for the length field (followed by a 32-bit reserved field,
> so can be updated in the future), which is a sufficiently large
> trace buffer size. A 32-bit padding field also had to be added
> to align the device address on a 64-bit boundary, and match the
> usage on the firmware side.
> 
> The remoteproc debugfs logic also has been adjusted accordingly.
> 
> Signed-off-by: Suman Anna <s-anna@ti.com>
> ---
>  drivers/remoteproc/remoteproc_core.c    | 40 ++++++++++++++++++++-----
>  drivers/remoteproc/remoteproc_debugfs.c | 37 ++++++++++++++++++-----
>  include/linux/remoteproc.h              | 26 ++++++++++++++++
>  3 files changed, 87 insertions(+), 16 deletions(-)
> 
> diff --git a/drivers/remoteproc/remoteproc_core.c b/drivers/remoteproc/remoteproc_core.c
> index 53bc37c508c6..b9a097990862 100644
> --- a/drivers/remoteproc/remoteproc_core.c
> +++ b/drivers/remoteproc/remoteproc_core.c
> @@ -609,21 +609,45 @@ void rproc_vdev_release(struct kref *ref)
>   *
>   * Returns 0 on success, or an appropriate error code otherwise
>   */
> -static int rproc_handle_trace(struct rproc *rproc, struct fw_rsc_trace *rsc,
> +static int rproc_handle_trace(struct rproc *rproc, void *rsc,
>  			      int offset, int avail, u16 ver)
>  {
>  	struct rproc_debug_trace *trace;
>  	struct device *dev = &rproc->dev;
> +	struct fw_rsc_trace *rsc1;
> +	struct fw_rsc_trace2 *rsc2;
>  	char name[15];
> +	size_t rsc_size;
> +	u32 reserved;
> +	u64 da;
> +	u32 len;
> +
> +	if (!ver) {

This looks like a switch to me, but I also do think this looks rather
crude, if you spin off the tail of this function and call it from a
rproc_handle_trace() and rproc_handle_trace64() I believe this would be
cleaner.

> +		rsc1 = (struct fw_rsc_trace *)rsc;
> +		rsc_size = sizeof(*rsc1);
> +		reserved = rsc1->reserved;
> +		da = rsc1->da;
> +		len = rsc1->len;
> +	} else if (ver == 1) {
> +		rsc2 = (struct fw_rsc_trace2 *)rsc;
> +		rsc_size = sizeof(*rsc2);
> +		reserved = rsc2->reserved;
> +		da = rsc2->da;
> +		len = rsc2->len;
> +	} else {
> +		dev_err(dev, "unsupported trace rsc version %d\n", ver);

If we use "type" to describe your 64-bit-da-trace then this sanity check
would have been taken care of by the core.

> +		return -EINVAL;
> +	}
>  
> -	if (sizeof(*rsc) > avail) {
> +	if (rsc_size > avail) {
>  		dev_err(dev, "trace rsc is truncated\n");
>  		return -EINVAL;
>  	}
>  
>  	/* make sure reserved bytes are zeroes */
> -	if (rsc->reserved) {
> -		dev_err(dev, "trace rsc has non zero reserved bytes\n");
> +	if (reserved) {
> +		dev_err(dev, "trace rsc has non zero reserved bytes, value = 0x%x\n",
> +			reserved);
>  		return -EINVAL;
>  	}
>  
> @@ -632,8 +656,8 @@ static int rproc_handle_trace(struct rproc *rproc, struct fw_rsc_trace *rsc,
>  		return -ENOMEM;
>  
>  	/* set the trace buffer dma properties */
> -	trace->trace_mem.len = rsc->len;
> -	trace->trace_mem.da = rsc->da;
> +	trace->trace_mem.len = len;
> +	trace->trace_mem.da = da;
>  
>  	/* set pointer on rproc device */
>  	trace->rproc = rproc;
> @@ -652,8 +676,8 @@ static int rproc_handle_trace(struct rproc *rproc, struct fw_rsc_trace *rsc,
>  
>  	rproc->num_traces++;
>  
> -	dev_dbg(dev, "%s added: da 0x%x, len 0x%x\n",
> -		name, rsc->da, rsc->len);
> +	dev_dbg(dev, "%s added: da 0x%llx, len 0x%x\n",
> +		name, da, len);
>  
>  	return 0;
>  }
> diff --git a/drivers/remoteproc/remoteproc_debugfs.c b/drivers/remoteproc/remoteproc_debugfs.c
> index 3560eed7a360..ff43736db45a 100644
> --- a/drivers/remoteproc/remoteproc_debugfs.c
> +++ b/drivers/remoteproc/remoteproc_debugfs.c
> @@ -192,7 +192,8 @@ static int rproc_rsc_table_show(struct seq_file *seq, void *p)
>  	struct resource_table *table = rproc->table_ptr;
>  	struct fw_rsc_carveout *c;
>  	struct fw_rsc_devmem *d;
> -	struct fw_rsc_trace *t;
> +	struct fw_rsc_trace *t1;
> +	struct fw_rsc_trace2 *t2;
>  	struct fw_rsc_vdev *v;
>  	int i, j;
>  
> @@ -205,6 +206,7 @@ static int rproc_rsc_table_show(struct seq_file *seq, void *p)
>  		int offset = table->offset[i];
>  		struct fw_rsc_hdr *hdr = (void *)table + offset;
>  		void *rsc = (void *)hdr + sizeof(*hdr);
> +		u16 ver = hdr->st.v;
>  
>  		switch (hdr->st.t) {
>  		case RSC_CARVEOUT:
> @@ -230,13 +232,32 @@ static int rproc_rsc_table_show(struct seq_file *seq, void *p)
>  			seq_printf(seq, "  Name %s\n\n", d->name);
>  			break;
>  		case RSC_TRACE:
> -			t = rsc;
> -			seq_printf(seq, "Entry %d is of type %s\n",
> -				   i, types[hdr->st.t]);
> -			seq_printf(seq, "  Device Address 0x%x\n", t->da);
> -			seq_printf(seq, "  Length 0x%x Bytes\n", t->len);
> -			seq_printf(seq, "  Reserved (should be zero) [%d]\n", t->reserved);
> -			seq_printf(seq, "  Name %s\n\n", t->name);
> +			if (ver == 0) {

Again, this is a switch, here in a switch. Just defining a new
RSC_TRACE64 type would reduce the amount of code here...

> +				t1 = rsc;
> +				seq_printf(seq, "Entry %d is version %d of type %s\n",
> +					   i, ver, types[hdr->st.t]);
> +				seq_printf(seq, "  Device Address 0x%x\n",
> +					   t1->da);
> +				seq_printf(seq, "  Length 0x%x Bytes\n",
> +					   t1->len);
> +				seq_printf(seq, "  Reserved (should be zero) [%d]\n",
> +					   t1->reserved);
> +				seq_printf(seq, "  Name %s\n\n", t1->name);
> +			} else if (ver == 1) {
> +				t2 = rsc;
> +				seq_printf(seq, "Entry %d is version %d of type %s\n",
> +					   i, ver, types[hdr->st.t]);
> +				seq_printf(seq, "  Device Address 0x%llx\n",
> +					   t2->da);
> +				seq_printf(seq, "  Length 0x%x Bytes\n",
> +					   t2->len);
> +				seq_printf(seq, "  Reserved (should be zero) [%d]\n",
> +					   t2->reserved);
> +				seq_printf(seq, "  Name %s\n\n", t2->name);
> +			} else {
> +				seq_printf(seq, "Entry %d is an unsupported version %d of type %s\n",
> +					   i, ver, types[hdr->st.t]);
> +			}
>  			break;
>  		case RSC_VDEV:
>  			v = rsc;
> diff --git a/include/linux/remoteproc.h b/include/linux/remoteproc.h
> index 526d3cb45e37..3b3bea42f8b1 100644
> --- a/include/linux/remoteproc.h
> +++ b/include/linux/remoteproc.h
> @@ -243,6 +243,32 @@ struct fw_rsc_trace {
>  	u8 name[32];
>  } __packed;
>  
> +/**
> + * struct fw_rsc_trace2 - trace buffer declaration supporting 64-bits
> + * @padding: initial padding after type field for aligned 64-bit access
> + * @da: device address (64-bit)
> + * @len: length (in bytes)
> + * @reserved: reserved (must be zero)
> + * @name: human-readable name of the trace buffer
> + *
> + * This resource entry is an enhanced version of the fw_rsc_trace resourec entry
> + * and the provides equivalent functionality but designed for 64-bit remote
> + * processors.
> + *
> + * @da specifies the device address of the buffer, @len specifies
> + * its size, and @name may contain a human readable name of the trace buffer.
> + *
> + * After booting the remote processor, the trace buffers are exposed to the
> + * user via debugfs entries (called trace0, trace1, etc..).
> + */
> +struct fw_rsc_trace2 {

Sounds more like fw_rsc_trace64 to me - in particular since the version
of trace2 is 1...

> +	u32 padding;
> +	u64 da;
> +	u32 len;
> +	u32 reserved;

What's the purpose of this reserved field?

Regards,
Bjorn

> +	u8 name[32];
> +} __packed;
> +
>  /**
>   * struct fw_rsc_vdev_vring - vring descriptor entry
>   * @da: device address
> -- 
> 2.23.0
> 

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH v6 00/19] mtd: spi-nor: add xSPI Octal DTR support
From: Pratyush Yadav @ 2020-05-21 18:05 UTC (permalink / raw)
  To: Mark Brown
  Cc: Alexandre Belloni, Mason Yang, Vignesh Raghavendra, Tudor Ambarus,
	Richard Weinberger, Sekhar Nori, linux-kernel, Ludovic Desroches,
	Boris Brezillon, linux-mtd, Miquel Raynal, Matthias Brugger,
	linux-mediatek, linux-spi, linux-arm-kernel
In-Reply-To: <20200521163957.GG4770@sirena.org.uk>

Hi Mark,

On 21/05/20 05:39PM, Mark Brown wrote:
> On Wed, May 20, 2020 at 10:00:34PM +0530, Pratyush Yadav wrote:
> > Hi,
> > 
> > This series adds support for octal DTR flashes in the spi-nor framework,
> > and then adds hooks for the Cypress Semper and Mircom Xcella flashes to
> > allow running them in octal DTR mode. This series assumes that the flash
> > is handed to the kernel in Legacy SPI mode.
> 
> Are people happy with the SPI bits of this from a MTD point of view?  I
> don't have any concerns and could apply them on a branch even if more
> revisions are needed for the MTD side.

There were a couple small changes suggested for spi-mem. Will send a 
re-roll in a few minutes.

-- 
Regards,
Pratyush Yadav
Texas Instruments India

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH v6] arm64: Expose FAR_EL1 tag bits in sigcontext
From: Peter Collingbourne @ 2020-05-21 18:03 UTC (permalink / raw)
  To: Eric W. Biederman
  Cc: Andrey Konovalov, Kevin Brodsky, Oleg Nesterov, Kostya Serebryany,
	Linux ARM, Catalin Marinas, Vincenzo Frascino, Will Deacon,
	Dave Martin, Evgenii Stepanov, Richard Henderson
In-Reply-To: <87zha1ea98.fsf@x220.int.ebiederm.org>

On Thu, May 21, 2020 at 5:39 AM Eric W. Biederman <ebiederm@xmission.com> wrote:
>
> Peter Collingbourne <pcc@google.com> writes:
>
> > On Wed, May 20, 2020 at 2:26 AM Dave Martin <Dave.Martin@arm.com> wrote:
> >>
> >> On Wed, May 20, 2020 at 09:55:03AM +0100, Will Deacon wrote:
> >> > On Tue, May 19, 2020 at 03:00:12PM -0700, Peter Collingbourne wrote:
> >> > > On Mon, May 18, 2020 at 2:53 AM Dave Martin <Dave.Martin@arm.com> wrote:
> >> > > > On Thu, May 14, 2020 at 05:58:21PM -0700, Peter Collingbourne wrote:
> >> > > > > diff --git a/arch/arm64/kernel/signal.c b/arch/arm64/kernel/signal.c
> >> > > > > index baa88dc02e5c..5867f2fdbe64 100644
> >> > > > > --- a/arch/arm64/kernel/signal.c
> >> > > > > +++ b/arch/arm64/kernel/signal.c
> >> > > > > @@ -648,6 +648,7 @@ static int setup_sigframe(struct
> >> > > > > rt_sigframe_user_layout *user,
> >> > > > >                 __put_user_error(ESR_MAGIC, &esr_ctx->head.magic, err);
> >> > > > >                 __put_user_error(sizeof(*esr_ctx), &esr_ctx->head.size, err);
> >> > > > >                 __put_user_error(current->thread.fault_code,
> >> > > > > &esr_ctx->esr, err);
> >> > > > > +               current->thread.fault_code = 0;
> >> > > >
> >> > > > Perhaps, but we'd need to be careful.  For example, can we run out of
> >> > > > user stack before this and deliver a SIGSEGV, but with the old
> >> > > > fault_code still set?  Then we'd emit the old fault code with the
> >> > > > new "can't deliver signal" signal, which doesn't make sense.
> >> > > >
> >> > > > Stuff may also go wrong with signal prioritisation.
> >> > > >
> >> > > > If a higher-priority signal (say SIGINT) comes in after a data abort
> >> > > > enters the kernel but before the resulting SIGSEGV is dequeued for
> >> > > > delivery, wouldn't we deliver SIGINT first, with the bogus fault code?
> >> > > > With your change we'd then have cleared the fault code by the time we
> >> > > > deliver the SIGSEGV it actually relates to, if I've understood right.
> >> > > >
> >> > > > Today, I think we just attach that fault code to every signal that's
> >> > > > delivered until something overwrites or resets it, which means that
> >> > > > a signal that needs fault_code gets it, at the expense of attaching
> >> > > > it to a bunch of other random signals too.
> >> > > >
> >> > > >
> >> > > > Checking the signal number and si_code might help us to know what we
> >> > > > should be doing with fault_code.  We need to have sure userspace can't
> >> > > > trick us with a non kernel generated signal here.  It would also be
> >> > > > necessary to check how PTRACE_SETSIGINFO interacts with this.
> >> > >
> >> > > With these possible interactions in mind I think we should store the
> >> > > fault code and fault address in kernel_siginfo instead of
> >> > > thread_struct (and clear these fields when we receive a siginfo from
> >> > > userspace, i.e. in copy_siginfo_from_user which is used by
> >> > > ptrace(PTRACE_SETSIGINFO) among other places). That way, the
> >> > > information is clearly associated with the signal itself and not the
> >> > > thread, so we don't need to worry about our signal being delivered out
> >> > > of order.
> >> >
> >> > Hmm, I can't see a way to do that that isn't horribly invasive in the core
> >> > signal code. Can you?
> >
> > I think I've come up with a way that doesn't seem to be too invasive.
> > See patch #1 of the series that I'm about to send out.
> >
> >> > But generally, I agree: the per-thread handling of fault_address and
> >> > fault_code appears to be quite broken in the face of signal prioritisation
> >> > and signals that don't correspond directly to hardware trap. It would be
> >> > nice to have some tests for this...
> >> >
> >> > If we want to pile on more bodges, perhaps we could stash the signal number
> >> > to which the fault_{address,code} relate, and then check that at delivery
> >> > and clear on a match. I hate it.
> >>
> >> I agree with Daniel's suggestion in principle, but I was also concerned
> >> about whether it would be too invasive elsewhere.
> >>
> >> Question though: does the core code take special care to make sure that
> >> a force_sig cannot be outprioritised by a regular signal?  If so,
> >> perhaps we get away with it.  I ask this, because the same same issue
> >> may be hitting other arches otherwise.
> >
> > Not as far as I can tell. There does appear to be prioritisation for
> > synchronous signals [1] but as far as I can tell nothing to
> > distinguish one of these signals from one with the same signal number
> > sent from userspace (e.g. via kill(2)).
>
> The si_code will differ between signals generated between userspace
> and signals generated by the kernel.
>
> We do allow a little bit of ptrace and sending to yourself to spoof
> kernel generated signals, for reasons of debugging and process migration
> where an existing process needs to be reconstructed.  But the defenses
> should be strong enough you can assume that we reliably distinguish
> between a signal from userspace and a signal from the kernel.

So check for SIGBUS || SIGSEGV and one of the below si_codes, and only
add the context in that case? Seems fragile to me, but I suppose I
could live with it.

> I don't fully follow what you are doing but this feels like the
> kind of case where a new si_code has been defined as well as additional
> fields in siginfo.

There is no new si_code for this, the information will be exposed for
several existing si_code types (BUS_ADRERR, BUS_ADRALN, BUS_MCEERR_AR,
SEGV_ACCERR, SEGV_MAPERR), and possibly others in the future
(particularly SEGV_MTESERR, which is part of the proposed MTE patch
set). Note that we already have a union field for BUS_MCEERR_AR, and
we may want to expose it for the other si_codes that already have
union fields as well.

That being said, taking a closer look at siginfo, I think we are in
luck and we might be able to make this work in a reasonable way by
reusing padding (see below).

> In your patchset I really hate that you were going back to
> force_sig_info, and filling out struct siginfo by hand.  That is an
> error prone pattern, and I have fixed enough bugs in the kernel to prove
> that.

To be fair, most of the callers are in helper functions that take
explicit parameters similar to force_sig_fault et al, and the SIGILL
one could easily be made that way as well.

> I take exception to the idea that including the full address might break
> userspace.  That means typically means someone has been too lazy to look
> and see what userspace is doing.  When that userspace that might break
> is the same userspace you are changing the kernel to serve that makes me
> nervous.  AKA the userspace that cares about this signal and how it is
> represented in siginfo.

It's not a matter of being lazy. This behaviour isn't just an accident
but has been explicitly documented for years (see the
tagged-pointers.rst file that I changed: "Non-zero tags are not
preserved when delivering signals."), so users can reasonably rely on
it. Furthermore we simply don't have visibility into the majority of
userspace. For example, there are a lot of closed source Android apps
out there, and who knows what signal handlers they're installing and
how they're making use of the si_addr field on e.g. SEGV_MAPERR. We
can't just change the documented semantics under their feet.

It's also not the same userspace either. The userspace that's
initially going to be consuming the new fields is in a part of the
Android system that handles and reports crashes, and that's something
that we control unlike all the apps.

Finally, the userspace may need to know whether the tag bits were
actually zero or whether they were just unavailable, otherwise
userspace could for example produce a misleading crash report. Simply
having the kernel set the top bits of si_addr wouldn't accomplish that
due to the kernel's previous behaviour, hence the mask to let
userspace know which bits are accurate.

> A fix of one instance of SIGILL should not be included with a patch that
> does something else, and really should come before everything else if
> possible.

Fair point. I can see if I can split that part out.

> If this information really belongs in struct siginfo (as it sounds like)
> please actually put the information in siginfo, and let userspace look
> in siginfo to find it.  struct siginfo is a union with plenty of space,
> and plenty of si_codes.
>
> If this applies to multiple cases then it might be trickier but please
> dig into the details, don't toss things into sigcontext just because
> you can't figure out a clean design for reporting this.

If we wanted this in siginfo, one idea that I had was to revert commit
b68a68d3dcc15ebbf23cbe91af1abf57591bd96b and add unsigned char fields
_addr_top_byte and _addr_top_byte_mask in the padding between
_addr_lsb and the union (with comments on all the fields of course to
say when they are filled in). I think that would work since we are
already clearing padding in siginfo, one nice property of the new
fields is that the zero values are correct in the case where the
information isn't being exposed (so old kernels would already have the
correct behaviour). That would only work on certain architectures
(i.e. at least alignof(void*) >= 4) so I suppose it could have an
#ifdef __aarch64__ around it.

Peter





Peter
>
> Eric
>
>
> > Peter
> >
> > [1] https://github.com/torvalds/linux/blob/b85051e755b0e9d6dd8f17ef1da083851b83287d/kernel/signal.c#L222

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH 2/4] remoteproc: introduce version element into resource type field
From: Bjorn Andersson @ 2020-05-21 17:54 UTC (permalink / raw)
  To: Suman Anna
  Cc: devicetree, Mathieu Poirier, Loic Pallardy, Lokesh Vutla,
	linux-remoteproc, Arnaud Pouliquen, linux-kernel, Clement Leger,
	Rob Herring, linux-arm-kernel
In-Reply-To: <20200325204701.16862-3-s-anna@ti.com>

On Wed 25 Mar 13:46 PDT 2020, Suman Anna wrote:

> The current remoteproc core has supported only 32-bit remote
> processors and as such some of the current resource structures
> may not scale well for 64-bit remote processors, and would
> require new versions of resource types. Each resource is currently
> identified by a 32-bit type field. Introduce the concept of version
> for these resource types by overloading this 32-bit type field
> into two 16-bit version and type fields with the existing resources
> behaving as version 0 thereby providing backward compatibility.
> 
> The version field is passed as an additional argument to each of
> the handler functions, and all the existing handlers are updated
> accordingly. Each specific handler will be updated on a need basis
> when a new version of the resource type is added.
> 

I really would prefer that we add additional types for the new
structures, neither side will be compatible with new versions without
enhancements to their respective implementations anyways.

> An alternate way would be to introduce the new types as completely
> new resource types which would require additional customization of
> the resource handlers based on the 32-bit or 64-bit mode of a remote
> processor, and introduction of an additional mode flag to the rproc
> structure.
> 

What would this "mode" indicate? If it's version 0 or 1?

> Signed-off-by: Suman Anna <s-anna@ti.com>
> ---
>  drivers/remoteproc/remoteproc_core.c    | 25 +++++++++++++++----------
>  drivers/remoteproc/remoteproc_debugfs.c | 17 ++++++++++-------
>  include/linux/remoteproc.h              |  8 +++++++-
>  3 files changed, 32 insertions(+), 18 deletions(-)
> 
[..]
> diff --git a/include/linux/remoteproc.h b/include/linux/remoteproc.h
> index 77788a4bb94e..526d3cb45e37 100644
> --- a/include/linux/remoteproc.h
> +++ b/include/linux/remoteproc.h
> @@ -86,7 +86,13 @@ struct resource_table {
>   * this header, and it should be parsed according to the resource type.
>   */
>  struct fw_rsc_hdr {
> -	u32 type;
> +	union {
> +		u32 type;
> +		struct {
> +			u16 t;
> +			u16 v;
> +		} st;

I see your "type" is little endian...

Regards,
Bjorn

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH] arch/{mips,sparc,microblaze,powerpc}: Don't enable pagefault/preempt twice
From: Ira Weiny @ 2020-05-21 17:42 UTC (permalink / raw)
  To: Guenter Roeck
  Cc: Peter Zijlstra, Benjamin Herrenschmidt, Dave Hansen, dri-devel,
	linux-mips, James E.J. Bottomley, Max Filippov, Paul Mackerras,
	H. Peter Anvin, sparclinux, Dan Williams, Helge Deller, x86,
	linux-csky, Christoph Hellwig, Ingo Molnar, linux-snps-arc,
	linux-xtensa, Borislav Petkov, Al Viro, Andy Lutomirski,
	Thomas Gleixner, linux-arm-kernel, Chris Zankel,
	Thomas Bogendoerfer, linux-parisc, linux-kernel, Christian Koenig,
	Andrew Morton, linuxppc-dev, David S. Miller
In-Reply-To: <d86dba19-4f4b-061e-a2c7-4f037e9e2de2@roeck-us.net>

On Thu, May 21, 2020 at 09:05:41AM -0700, Guenter Roeck wrote:
> On 5/19/20 10:13 PM, Ira Weiny wrote:
> > On Tue, May 19, 2020 at 12:42:15PM -0700, Guenter Roeck wrote:
> >> On Tue, May 19, 2020 at 11:40:32AM -0700, Ira Weiny wrote:
> >>> On Tue, May 19, 2020 at 09:54:22AM -0700, Guenter Roeck wrote:
> >>>> On Mon, May 18, 2020 at 11:48:43AM -0700, ira.weiny@intel.com wrote:
> >>>>> From: Ira Weiny <ira.weiny@intel.com>
> >>>>>
> >>>>> The kunmap_atomic clean up failed to remove one set of pagefault/preempt
> >>>>> enables when vaddr is not in the fixmap.
> >>>>>
> >>>>> Fixes: bee2128a09e6 ("arch/kunmap_atomic: consolidate duplicate code")
> >>>>> Signed-off-by: Ira Weiny <ira.weiny@intel.com>
> >>>>
> >>>> microblazeel works with this patch,
> >>>
> >>> Awesome...  Andrew in my rush yesterday I should have put a reported by on the
> >>> patch for Guenter as well.
> >>>
> >>> Sorry about that Guenter,
> >>
> >> No worries.
> >>
> >>> Ira
> >>>
> >>>> as do the nosmp sparc32 boot tests,
> >>>> but sparc32 boot tests with SMP enabled still fail with lots of messages
> >>>> such as:
> >>>>
> >>>> BUG: Bad page state in process swapper/0  pfn:006a1
> >>>> page:f0933420 refcount:0 mapcount:1 mapping:(ptrval) index:0x1
> >>>> flags: 0x0()
> >>>> raw: 00000000 00000100 00000122 00000000 00000001 00000000 00000000 00000000
> >>>> page dumped because: nonzero mapcount
> >>>> Modules linked in:
> >>>> CPU: 0 PID: 1 Comm: swapper/0 Tainted: G    B             5.7.0-rc6-next-20200518-00002-gb178d2d56f29 #1
> >>>> [f00e7ab8 :
> >>>> bad_page+0xa8/0x108 ]
> >>>> [f00e8b54 :
> >>>> free_pcppages_bulk+0x154/0x52c ]
> >>>> [f00ea024 :
> >>>> free_unref_page+0x54/0x6c ]
> >>>> [f00ed864 :
> >>>> free_reserved_area+0x58/0xec ]
> >>>> [f0527104 :
> >>>> kernel_init+0x14/0x110 ]
> >>>> [f000b77c :
> >>>> ret_from_kernel_thread+0xc/0x38 ]
> >>>> [00000000 :
> >>>> 0x0 ]
> >>>>
> >>>> Code path leading to that message is different but always the same
> >>>> from free_unref_page().
> > 
> > Actually it occurs to me that the patch consolidating kmap_prot is odd for
> > sparc 32 bit...
> > 
> > Its a long shot but could you try reverting this patch?
> > 
> > 4ea7d2419e3f kmap: consolidate kmap_prot definitions
> > 
> 
> That is not easy to revert, unfortunately, due to several follow-up patches.

I have gotten your sparc tests to run and they all pass...

08:10:34 > ../linux-build-test/rootfs/sparc/run-qemu-sparc.sh 
Build reference: v5.7-rc4-17-g852b6f2edc0f

Building sparc32:SPARCClassic:nosmp:scsi:hd ... running ......... passed
Building sparc32:SPARCbook:nosmp:scsi:cd ... running ......... passed
Building sparc32:LX:nosmp:noapc:scsi:hd ... running ......... passed
Building sparc32:SS-4:nosmp:initrd ... running ......... passed
Building sparc32:SS-5:nosmp:scsi:hd ... running ......... passed
Building sparc32:SS-10:nosmp:scsi:cd ... running ......... passed
Building sparc32:SS-20:nosmp:scsi:hd ... running ......... passed
Building sparc32:SS-600MP:nosmp:scsi:hd ... running ......... passed
Building sparc32:Voyager:nosmp:noapc:scsi:hd ... running ......... passed
Building sparc32:SS-4:smp:scsi:hd ... running ......... passed
Building sparc32:SS-5:smp:scsi:cd ... running ......... passed
Building sparc32:SS-10:smp:scsi:hd ... running ......... passed
Building sparc32:SS-20:smp:scsi:hd ... running ......... passed
Building sparc32:SS-600MP:smp:scsi:hd ... running ......... passed
Building sparc32:Voyager:smp:noapc:scsi:hd ... running ......... passed

Is there another test I need to run?

Ira


> 
> Guenter
> 
> > Alternately I will need to figure out how to run the sparc on qemu here...
> > 
> > Thanks very much for all the testing though!  :-D
> > 
> > Ira
> > 
> >>>>
> >>>> Still testing ppc images.
> >>>>
> >>
> >> ppc image tests are passing with this patch.
> >>
> >> Guenter
> 

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* [GIT PULL] iommu/arm-smmu: Updates for 5.8
From: Will Deacon @ 2020-05-21 17:39 UTC (permalink / raw)
  To: joro; +Cc: kernel-team, iommu, robin.murphy, linux-kernel, linux-arm-kernel

Hi Joerg,

Please pull these Arm SMMU updates for 5.8. The branch is based on your
'core' branch from a little while ago.

Summary in the tag.

Cheers,

Will

--->8

The following changes since commit 1b032ec1ecbce6047af7d11c9db432e237cb17d8:

  iommu: Unexport iommu_group_get_for_dev() (2020-05-05 14:36:14 +0200)

are available in the Git repository at:

  git://git.kernel.org/pub/scm/linux/kernel/git/will/linux.git tags/arm-smmu-updates

for you to fetch changes up to 0299a1a81ca056e79c1a7fb751f936ec0d5c7afe:

  iommu/arm-smmu-v3: Manage ASIDs with xarray (2020-05-21 14:54:06 +0100)

----------------------------------------------------------------
Arm SMMU updates for 5.8

- Avoid mapping reserved MMIO space on SMMUv3, so that it can be claimed
  by the PMU driver

- Use xarray to manage ASIDs on SMMUv3

- Reword confusing shutdown message

- DT compatible string updates

- Allow implementations to override the default domain type

----------------------------------------------------------------
Andre Przywara (1):
      dt-bindings: arm-smmu: Allow mmu-400, smmu-v1 compatible

Chen Zhou (1):
      iommu/arm-smmu-v3: remove set but not used variable 'smmu'

Jean-Philippe Brucker (2):
      iommu/arm-smmu-v3: Don't reserve implementation defined register space
      iommu/arm-smmu-v3: Manage ASIDs with xarray

Jordan Crouse (1):
      iommu/arm-smmu: Allow client devices to select direct mapping

Sai Prakash Ranjan (3):
      iommu/arm-smmu: Make remove callback message more informative
      iommu: arm-smmu-impl: Convert to a generic reset implementation
      iommu/arm-smmu: Implement iommu_ops->def_domain_type call-back

Sibi Sankar (3):
      dt-bindings: remoteproc: qcom: Add iommus property
      arm64: dts: qcom: sdm845-cheza: Add iommus property
      iommu/arm-smmu-qcom: Request direct mapping for modem device

 .../devicetree/bindings/iommu/arm,smmu.yaml        |  4 +-
 .../devicetree/bindings/remoteproc/qcom,q6v5.txt   |  3 +
 arch/arm64/boot/dts/qcom/sdm845-cheza.dtsi         |  5 ++
 drivers/iommu/arm-smmu-impl.c                      |  8 ++-
 drivers/iommu/arm-smmu-qcom.c                      | 37 ++++++++++++-
 drivers/iommu/arm-smmu-v3.c                        | 64 +++++++++++++++++-----
 drivers/iommu/arm-smmu.c                           | 14 ++++-
 drivers/iommu/arm-smmu.h                           |  1 +
 8 files changed, 113 insertions(+), 23 deletions(-)

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: arm64/acpi: NULL dereference reports from UBSAN at boot
From: Lorenzo Pieralisi @ 2020-05-21 17:37 UTC (permalink / raw)
  To: Will Deacon; +Cc: mark.rutland, rjw, linux-kernel, linux-arm-kernel, guohanjun
In-Reply-To: <20200521100952.GA5360@willie-the-truck>

On Thu, May 21, 2020 at 11:09:53AM +0100, Will Deacon wrote:
> Hi folks,
> 
> I just tried booting the arm64 for-kernelci branch under QEMU (version
> 4.2.50 (v4.2.0-779-g4354edb6dcc7)) with UBSAN enabled, and I see a
> couple of NULL pointer dereferences reported at boot. I think they're
> both GIC related (log below). I don't see a panic with UBSAN disabled,
> so something's fishy here.

May I ask you the QEMU command line please - just to make sure I can
replicate it.

> Please can you take a look when you get a chance? I haven't had time to see
> if this is a regression or not, but I don't think it's particularly serious
> as I have all sorts of horrible stuff enabled in my .config, since I'm
> trying to chase down another bug:
> 
> https://git.kernel.org/pub/scm/linux/kernel/git/mark/linux.git/plain/arch/arm64/configs/fuzzing.config?h=fuzzing/arm64-kernelci-20200519&id=c149cf6a51aa4f72d53fc681c6661094e93ef660
> 
> (on top of defconfig)
> 
> CONFIG_FAIL_PAGE_ALLOC may be to blame.

Not sure about that, they are both quite cryptic, I wonder if UBSAN
is not tricked by the ACPI_OFFSET macro - need to debug it further
to understand what's going on here.

Thanks,
Lorenzo

> Cheers,
> 
> Will
> 
> --->8
> 
> [    0.000000][    T0] ================================================================================
> [    0.000000][    T0] UBSAN: null-ptr-deref in drivers/acpi/acpica/tbfadt.c:459:37
> [    0.000000][    T0] member access within null pointer of type 'struct acpi_table_fadt'
> [    0.000000][    T0] CPU: 0 PID: 0 Comm: swapper Not tainted 5.7.0-rc6-00124-g96bc42ff0a82 #1
> [    0.000000][    T0] Call trace:
> [    0.000000][    T0]  dump_backtrace+0x0/0x384
> [    0.000000][    T0]  show_stack+0x28/0x38
> [    0.000000][    T0]  dump_stack+0xec/0x174
> [    0.000000][    T0]  handle_null_ptr_deref+0x134/0x174
> [    0.000000][    T0]  __ubsan_handle_type_mismatch_v1+0x84/0xa4
> [    0.000000][    T0]  acpi_tb_create_local_fadt+0x1d4/0x1418
> [    0.000000][    T0]  acpi_tb_parse_fadt+0x108/0x4b8
> [    0.000000][    T0]  acpi_tb_parse_root_table+0x380/0x578
> [    0.000000][    T0]  acpi_initialize_tables+0x140/0x194
> [    0.000000][    T0]  acpi_table_init+0x90/0xcc
> [    0.000000][    T0]  acpi_boot_table_init+0xfc/0x1c8
> [    0.000000][    T0]  setup_arch+0x2b4/0x3ec
> [    0.000000][    T0]  start_kernel+0x98/0x6f4
> [    0.000000][    T0] ================================================================================
> 
> [    0.000000][    T0] ================================================================================
> [    0.000000][    T0] UBSAN: null-ptr-deref in arch/arm64/kernel/smp.c:596:6
> [    0.000000][    T0] member access within null pointer of type 'struct acpi_madt_generic_interrupt'
> [    0.000000][    T0] CPU: 0 PID: 0 Comm: swapper Not tainted 5.7.0-rc6-00124-g96bc42ff0a82 #1
> [    0.000000][    T0] Call trace:
> [    0.000000][    T0]  dump_backtrace+0x0/0x384
> [    0.000000][    T0]  show_stack+0x28/0x38
> [    0.000000][    T0]  dump_stack+0xec/0x174
> [    0.000000][    T0]  handle_null_ptr_deref+0x134/0x174
> [    0.000000][    T0]  __ubsan_handle_type_mismatch_v1+0x84/0xa4
> [    0.000000][    T0]  acpi_parse_gic_cpu_interface+0x60/0xe8
> [    0.000000][    T0]  acpi_parse_entries_array+0x288/0x498
> [    0.000000][    T0]  acpi_table_parse_entries_array+0x178/0x1b4
> [    0.000000][    T0]  acpi_table_parse_madt+0xa4/0x110
> [    0.000000][    T0]  acpi_parse_and_init_cpus+0x38/0x100
> [    0.000000][    T0]  smp_init_cpus+0x74/0x258
> [    0.000000][    T0]  setup_arch+0x350/0x3ec
> [    0.000000][    T0]  start_kernel+0x98/0x6f4
> [    0.000000][    T0] ================================================================================

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH] arch/{mips,sparc,microblaze,powerpc}: Don't enable pagefault/preempt twice
From: Al Viro @ 2020-05-21 17:27 UTC (permalink / raw)
  To: Guenter Roeck
  Cc: Peter Zijlstra, Benjamin Herrenschmidt, Dave Hansen, dri-devel,
	linux-mips, James E.J. Bottomley, Max Filippov, Paul Mackerras,
	H. Peter Anvin, sparclinux, ira.weiny, Dan Williams, Helge Deller,
	x86, linux-csky, Christoph Hellwig, Ingo Molnar, linux-snps-arc,
	linux-xtensa, Borislav Petkov, Andy Lutomirski, Thomas Gleixner,
	linux-arm-kernel, Chris Zankel, Thomas Bogendoerfer, linux-parisc,
	linux-kernel, Christian Koenig, Andrew Morton, linuxppc-dev,
	David S. Miller
In-Reply-To: <20200519165422.GA5838@roeck-us.net>

On Tue, May 19, 2020 at 09:54:22AM -0700, Guenter Roeck wrote:
> On Mon, May 18, 2020 at 11:48:43AM -0700, ira.weiny@intel.com wrote:
> > From: Ira Weiny <ira.weiny@intel.com>
> > 
> > The kunmap_atomic clean up failed to remove one set of pagefault/preempt
> > enables when vaddr is not in the fixmap.
> > 
> > Fixes: bee2128a09e6 ("arch/kunmap_atomic: consolidate duplicate code")
> > Signed-off-by: Ira Weiny <ira.weiny@intel.com>
> 
> microblazeel works with this patch, as do the nosmp sparc32 boot tests,
> but sparc32 boot tests with SMP enabled still fail with lots of messages
> such as:

BTW, what's your setup for sparc32 boot tests?  IOW, how do you manage to
shrink the damn thing enough to have the loader cope with it?  I hadn't
been able to do that for the current mainline ;-/

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [RFC PATCH V4 1/4] media: v4l2-mem2mem: add v4l2_m2m_suspend, v4l2_m2m_resume
From: Tomasz Figa @ 2020-05-21 17:11 UTC (permalink / raw)
  To: Jerry-ch Chen, Hans Verkuil
  Cc: devicetree, Sean.Cheng, laurent.pinchart+renesas, Rynn.Wu,
	zwisler, srv_heupstream, Jerry-ch Chen, Hans Verkuil, jungo.lin,
	sj.huang, yuzhao, linux-mediatek, pihsun, frederic.chen,
	matthias.bgg, christie.yu, mchehab, linux-arm-kernel, linux-media
In-Reply-To: <20191204124732.10932-2-Jerry-Ch.chen@mediatek.com>

Hi Jerry,

On Wed, Dec 04, 2019 at 08:47:29PM +0800, Jerry-ch Chen wrote:
> From: Pi-Hsun Shih <pihsun@chromium.org>
> 
> Add two functions that can be used to stop new jobs from being queued /
> continue running queued job. This can be used while a driver using m2m
> helper is going to suspend / wake up from resume, and can ensure that
> there's no job running in suspend process.
> 
> BUG=b:143046833
> TEST=build
> 
> Signed-off-by: Pi-Hsun Shih <pihsun@chromium.org>
> Signed-off-by: Jerry-ch Chen <jerry-ch.chen@mediatek.corp-partner.google.com>
> ---
>  drivers/media/v4l2-core/v4l2-mem2mem.c | 40 ++++++++++++++++++++++++++
>  include/media/v4l2-mem2mem.h           | 22 ++++++++++++++
>  2 files changed, 62 insertions(+)
> 
> diff --git a/drivers/media/v4l2-core/v4l2-mem2mem.c b/drivers/media/v4l2-core/v4l2-mem2mem.c
> index 5bbdec55b7d7..76ba203e0035 100644
> --- a/drivers/media/v4l2-core/v4l2-mem2mem.c
> +++ b/drivers/media/v4l2-core/v4l2-mem2mem.c
> @@ -47,6 +47,10 @@ module_param(debug, bool, 0644);
>  #define TRANS_ABORT		(1 << 2)
>  
>  
> +/* The job queue is not running new jobs */
> +#define QUEUE_PAUSED		(1 << 0)
> +
> +
>  /* Offset base for buffers on the destination queue - used to distinguish
>   * between source and destination buffers when mmapping - they receive the same
>   * offsets but for different queues */
> @@ -88,6 +92,7 @@ static const char * const m2m_entity_name[] = {
>   * @job_queue:		instances queued to run
>   * @job_spinlock:	protects job_queue
>   * @job_work:		worker to run queued jobs.
> + * @job_queue_flags:	flags of the queue status, %QUEUE_PAUSED.
>   * @m2m_ops:		driver callbacks
>   */
>  struct v4l2_m2m_dev {
> @@ -105,6 +110,7 @@ struct v4l2_m2m_dev {
>  	struct list_head	job_queue;
>  	spinlock_t		job_spinlock;
>  	struct work_struct	job_work;
> +	unsigned long		job_queue_flags;
>  
>  	const struct v4l2_m2m_ops *m2m_ops;
>  };
> @@ -267,6 +273,12 @@ static void v4l2_m2m_try_run(struct v4l2_m2m_dev *m2m_dev)
>  		return;
>  	}
>  
> +	if (m2m_dev->job_queue_flags & QUEUE_PAUSED) {
> +		spin_unlock_irqrestore(&m2m_dev->job_spinlock, flags);
> +		dprintk("Running new jobs is paused\n");
> +		return;
> +	}
> +
>  	m2m_dev->curr_ctx = list_first_entry(&m2m_dev->job_queue,
>  				   struct v4l2_m2m_ctx, queue);
>  	m2m_dev->curr_ctx->job_flags |= TRANS_RUNNING;
> @@ -447,6 +459,34 @@ void v4l2_m2m_job_finish(struct v4l2_m2m_dev *m2m_dev,
>  }
>  EXPORT_SYMBOL(v4l2_m2m_job_finish);
>  
> +void v4l2_m2m_suspend(struct v4l2_m2m_dev *m2m_dev)
> +{
> +	unsigned long flags;
> +	struct v4l2_m2m_ctx *curr_ctx;
> +
> +	spin_lock_irqsave(&m2m_dev->job_spinlock, flags);
> +	m2m_dev->job_queue_flags |= QUEUE_PAUSED;
> +	curr_ctx = m2m_dev->curr_ctx;
> +	spin_unlock_irqrestore(&m2m_dev->job_spinlock, flags);
> +
> +	if (curr_ctx)
> +		wait_event(curr_ctx->finished,
> +			   !(curr_ctx->job_flags & TRANS_RUNNING));
> +}
> +EXPORT_SYMBOL(v4l2_m2m_suspend);
> +
> +void v4l2_m2m_resume(struct v4l2_m2m_dev *m2m_dev)
> +{
> +	unsigned long flags;
> +
> +	spin_lock_irqsave(&m2m_dev->job_spinlock, flags);
> +	m2m_dev->job_queue_flags &= ~QUEUE_PAUSED;
> +	spin_unlock_irqrestore(&m2m_dev->job_spinlock, flags);
> +
> +	v4l2_m2m_try_run(m2m_dev);
> +}
> +EXPORT_SYMBOL(v4l2_m2m_resume);
> +
>  int v4l2_m2m_reqbufs(struct file *file, struct v4l2_m2m_ctx *m2m_ctx,
>  		     struct v4l2_requestbuffers *reqbufs)
>  {
> diff --git a/include/media/v4l2-mem2mem.h b/include/media/v4l2-mem2mem.h
> index 5467264771ec..119a195da390 100644
> --- a/include/media/v4l2-mem2mem.h
> +++ b/include/media/v4l2-mem2mem.h
> @@ -183,6 +183,28 @@ v4l2_m2m_buf_done(struct vb2_v4l2_buffer *buf, enum vb2_buffer_state state)
>  	vb2_buffer_done(&buf->vb2_buf, state);
>  }
>  
> +/**
> + * v4l2_m2m_suspend() - stop new jobs from being run and wait for current job
> + * to finish
> + *
> + * @m2m_dev: opaque pointer to the internal data to handle M2M context
> + *
> + * Called by a driver in the suspend hook. Stop new jobs from being run, and
> + * wait for current running job to finish.
> + */
> +void v4l2_m2m_suspend(struct v4l2_m2m_dev *m2m_dev);
> +
> +/**
> + * v4l2_m2m_resume() - resume job running and try to run a queued job
> + *
> + * @m2m_dev: opaque pointer to the internal data to handle M2M context
> + *
> + * Called by a driver in the resume hook. This reverts the operation of
> + * v4l2_m2m_suspend() and allows job to be run. Also try to run a queued job if
> + * there is any.
> + */
> +void v4l2_m2m_resume(struct v4l2_m2m_dev *m2m_dev);
> +
>  /**
>   * v4l2_m2m_reqbufs() - multi-queue-aware REQBUFS multiplexer
>   *
> -- 
> 2.18.0

Reviewed-by: Tomasz Figa <tfiga@chromium.org>

[Corrected Hans's email address.]
Hans, does this look good to you?

Best regards,
Tomasz


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply

* Re: [PATCH] arm64/cpufeature: Move BUG_ON() inside get_arm64_ftr_reg()
From: Catalin Marinas @ 2020-05-21 16:59 UTC (permalink / raw)
  To: Will Deacon
  Cc: mark.rutland, Suzuki K Poulose, Anshuman Khandual, linux-kernel,
	Mark Brown, linux-arm-kernel
In-Reply-To: <20200521162212.GK6608@willie-the-truck>

On Thu, May 21, 2020 at 05:22:15PM +0100, Will Deacon wrote:
> On Thu, May 21, 2020 at 08:45:38AM +0530, Anshuman Khandual wrote:
> > On 05/20/2020 11:09 PM, Will Deacon wrote:
> > > On Wed, May 20, 2020 at 04:47:11PM +0100, Catalin Marinas wrote:
> > >> On Wed, May 20, 2020 at 01:20:13PM +0100, Will Deacon wrote:
> > >>> On Wed, May 20, 2020 at 06:52:54AM +0530, Anshuman Khandual wrote:
> > >>>> There is no way to proceed when requested register could not be searched in
> > >>>> arm64_ftr_reg[]. Requesting for a non present register would be an error as
> > >>>> well. Hence lets just BUG_ON() when the search fails in get_arm64_ftr_reg()
> > >>>> rather than checking for return value and doing the same in some individual
> > >>>> callers.
> > >>>>
> > >>>> But there are some callers that dont BUG_ON() upon search failure. It adds
> > >>>> an argument 'failsafe' that provides required switch between callers based
> > >>>> on whether they could proceed or not.
> > >>>>
> > >>>> Cc: Catalin Marinas <catalin.marinas@arm.com>
> > >>>> Cc: Will Deacon <will@kernel.org>
> > >>>> Cc: Suzuki K Poulose <suzuki.poulose@arm.com>
> > >>>> Cc: Mark Brown <broonie@kernel.org>
> > >>>> Cc: linux-arm-kernel@lists.infradead.org
> > >>>> Cc: linux-kernel@vger.kernel.org
> > >>>>
> > >>>> Signed-off-by: Anshuman Khandual <anshuman.khandual@arm.com>
> > >>>> ---
> > >>>> Applies on next-20200518 that has recent cpufeature changes from Will.
> > >>>>
> > >>>>  arch/arm64/kernel/cpufeature.c | 26 +++++++++++++-------------
> > >>>>  1 file changed, 13 insertions(+), 13 deletions(-)
> > >>>>
> > >>>> diff --git a/arch/arm64/kernel/cpufeature.c b/arch/arm64/kernel/cpufeature.c
> > >>>> index bc5048f152c1..62767cc540c3 100644
> > >>>> --- a/arch/arm64/kernel/cpufeature.c
> > >>>> +++ b/arch/arm64/kernel/cpufeature.c
> > >>>> @@ -557,7 +557,7 @@ static int search_cmp_ftr_reg(const void *id, const void *regp)
> > >>>>   *         - NULL on failure. It is upto the caller to decide
> > >>>>   *	     the impact of a failure.
> > >>>>   */
> > >>>> -static struct arm64_ftr_reg *get_arm64_ftr_reg(u32 sys_id)
> > >>>> +static struct arm64_ftr_reg *get_arm64_ftr_reg(u32 sys_id, bool failsafe)
> > >>>
> > >>> Generally, I'm not a big fan of boolean arguments because they are really
> > >>> opaque at the callsite. It also seems bogus to me that we don't trust the
> > >>> caller to pass a valid sys_id, but we trust it to get "failsafe" right,
> > >>> which seems to mean "I promise to check the result isn't NULL before
> > >>> dereferencing it."
> > >>>
> > >>> So I don't see how this patch improves anything. I'd actually be more
> > >>> inclined to stick a WARN() in get_arm64_ftr_reg() when it returns NULL and
> > >>> have the callers handle NULL by returning early, getting rid of all the
> > >>> BUG_ONs in here. Sure, the system might end up in a funny state, but we
> > >>> WARN()d about it and tried to keep going (and Linus has some strong opinions
> > >>> on this too).
> > >>
> > >> Such WARN can be triggered by the user via emulate_sys_reg(), so we
> > >> can't really have it in get_arm64_ftr_reg() without a 'failsafe' option.
> > > 
> > > Ah yes, that would be bad. In which case, I don't think the existing code
> > > should change.
> > 
> > The existing code has BUG_ON() in three different callers doing exactly the
> > same thing that can easily be taken care in get_arm64_ftr_reg() itself. As
> > mentioned before an enum variable (as preferred - over a bool) can still
> > preserve the existing behavior for emulate_sys_reg().
> > 
> > IMHO these are very good reasons for us to change the code which will make
> > it cleaner while also removing three redundant BUG_ON() instances. Hence I
> > will request you to please reconsider this proposal.
> 
> Hmm, then how about trying my proposal with the WARN_ON(), but having a
> get_arm64_ftr_reg_nowarn() variant for the user emulation case?

That works for me, get_arm64_ftr_reg() would be a wrapper over the
_nowarn function with the added WARN_ON.

read_sanitised_ftr_reg() would need to return something though. Would
all 0s be ok? I think it works as long as we don't have negative CPUID
fields.

-- 
Catalin

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply


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