linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8
@ 2012-10-16  1:32 Paul Walmsley
  2012-10-16  1:32 ` [PATCH 1/7] ARM: OMAP2+: PRM: prepare for use of prm_ll_data function pointers Paul Walmsley
                   ` (7 more replies)
  0 siblings, 8 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-16  1:32 UTC (permalink / raw)
  To: linux-arm-kernel

This series removes the omap_prcm_get_reset_sources() function.  This
was exported from arch/arm/mach-omap2/prcm.c for use by the OMAP
watchdog driver to report the "boot reason".  This series reimplements
this using a platform_data function pointer for the time being, but
after the upcoming PRM/CM drivers are merged, the watchdog driver can be
patched to use an exported function from the drivers.

This series will also be used as a base for other PRM/CM cleanup during the
3.8 time frame, since it adds the prm_register() and prm_unregister() functions.
These are called by SoC-specific PRM IP block drivers to register function
pointers with the PRM subsystem.

This series changes the format of the watchdog's boot reason data to conform
with the watchdog subsystem standard (the WDIOF_* flags).  If users need
more detail than that interface provides, either the watchdog interface can
be patched, or those users can get that information from the upcoming PRM
drivers.


- Paul

---

prcm_cleanup_b_3.8
   text	   data	    bss	    dec	    hex	filename
7519295	 696796	5613996	13830087	 d307c7	vmlinux.omap2plus_defconfig.orig
7520203	 696868	5613996	13831067	 d30b9b	vmlinux.omap2plus_defconfig

Paul Walmsley (7):
      ARM: OMAP2+: PRM: prepare for use of prm_ll_data function pointers
      ARM: OMAP2+: CM: prepare for use of cm_ll_data function pointers
      ARM: OMAP1: create read_reset_sources() function (for initial use by watchdog)
      ARM: OMAP2+: PRM: create PRM reset source API for the watchdog timer driver
      ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
      watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr
      ARM: OMAP2+: PRCM: remove omap_prcm_get_reset_sources()


 arch/arm/mach-omap1/common.h                |    2 +
 arch/arm/mach-omap1/devices.c               |   21 ++++++-
 arch/arm/mach-omap1/reset.c                 |   39 +++++++++++++
 arch/arm/mach-omap2/Makefile                |    2 -
 arch/arm/mach-omap2/cm.h                    |   12 ++++
 arch/arm/mach-omap2/cm_common.c             |   71 +++++++++++++++++++++++
 arch/arm/mach-omap2/devices.c               |   26 --------
 arch/arm/mach-omap2/prcm.c                  |   12 ----
 arch/arm/mach-omap2/prm-regbits-24xx.h      |    4 +
 arch/arm/mach-omap2/prm-regbits-34xx.h      |   10 +++
 arch/arm/mach-omap2/prm.h                   |   53 +++++++++++++++++
 arch/arm/mach-omap2/prm2xxx.c               |   68 ++++++++++++++++++++++
 arch/arm/mach-omap2/prm2xxx.h               |    4 +
 arch/arm/mach-omap2/prm2xxx_3xxx.h          |    2 +
 arch/arm/mach-omap2/prm3xxx.c               |   65 +++++++++++++++++++++
 arch/arm/mach-omap2/prm3xxx.h               |    2 +
 arch/arm/mach-omap2/prm44xx.c               |   83 ++++++++++++++++++++++++++-
 arch/arm/mach-omap2/prm44xx.h               |    2 +
 arch/arm/mach-omap2/prm_common.c            |   78 +++++++++++++++++++++++++
 arch/arm/mach-omap2/wd_timer.c              |   33 +++++++++++
 arch/arm/plat-omap/include/plat/prcm.h      |    1 
 drivers/watchdog/omap_wdt.c                 |   26 ++++----
 include/linux/platform_data/omap-wd-timer.h |   38 ++++++++++++
 23 files changed, 594 insertions(+), 60 deletions(-)
 create mode 100644 arch/arm/mach-omap2/cm_common.c
 create mode 100644 include/linux/platform_data/omap-wd-timer.h

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 1/7] ARM: OMAP2+: PRM: prepare for use of prm_ll_data function pointers
  2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
@ 2012-10-16  1:32 ` Paul Walmsley
  2012-10-16  1:32 ` [PATCH 2/7] ARM: OMAP2+: CM: prepare for use of cm_ll_data " Paul Walmsley
                   ` (6 subsequent siblings)
  7 siblings, 0 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-16  1:32 UTC (permalink / raw)
  To: linux-arm-kernel

There are several PRM operations which behave similarly across OMAP2+
SoCs, but which have slight differences in their underlying
implementations.  For example, to fetch the SoC's last reset sources,
different registers are read across OMAP2xxx, 3xxx, and 44xx, and
different bits are used on each SoC.  But the information returned is
so similar that a single, common interface for drivers is useful.

This patch creates the support code for this function pointer
registration process.  No function pointers are included yet, but a
subsequent patch will create one for the reset source API.

To illustrate the end goal with the above reset source example, each
per-SoC driver will use its own low-level implementation function --
e.g., prm2xxx.c would contain omap2xxx_prm_read_reset_sources().  This
function would read the appropriate register and remap the register
bits to a standard set of reset source bits.  When the prm2xxx.c
driver is loaded, it would register this function with the common PRM
driver, prm.c.  prm.c would then export a common function,
omap_prm_read_reset_sources().  Calling it would call through to the
function pointer for the currently-registered SoC PRM driver.  This
will allow other drivers to use PRM-provided data and operations
without needing to know which SoC is currently in use.

Signed-off-by: Paul Walmsley <paul@pwsan.com>
---
 arch/arm/mach-omap2/prm.h        |   11 ++++++++
 arch/arm/mach-omap2/prm_common.c |   52 ++++++++++++++++++++++++++++++++++++++
 2 files changed, 63 insertions(+)

diff --git a/arch/arm/mach-omap2/prm.h b/arch/arm/mach-omap2/prm.h
index 39d5621..3e51c1d 100644
--- a/arch/arm/mach-omap2/prm.h
+++ b/arch/arm/mach-omap2/prm.h
@@ -52,5 +52,16 @@
 #define OMAP_POWERSTATE_SHIFT				0
 #define OMAP_POWERSTATE_MASK				(0x3 << 0)
 
+#ifndef __ASSEMBLER__
+
+/**
+ * struct prm_ll_data - fn ptrs to per-SoC PRM function implementations
+ */
+struct prm_ll_data {};
+
+extern int prm_register(struct prm_ll_data *pld);
+extern int prm_unregister(struct prm_ll_data *pld);
+
+#endif
 
 #endif
diff --git a/arch/arm/mach-omap2/prm_common.c b/arch/arm/mach-omap2/prm_common.c
index 0a100d9..8670a3c 100644
--- a/arch/arm/mach-omap2/prm_common.c
+++ b/arch/arm/mach-omap2/prm_common.c
@@ -53,6 +53,13 @@ static struct irq_chip_generic **prcm_irq_chips;
  */
 static struct omap_prcm_irq_setup *prcm_irq_setup;
 
+/*
+ * prm_ll_data: function pointers to SoC-specific implementations of
+ * common PRM functions
+ */
+static struct prm_ll_data null_prm_ll_data;
+static struct prm_ll_data *prm_ll_data = &null_prm_ll_data;
+
 /* Private functions */
 
 /*
@@ -318,3 +325,48 @@ err:
 	omap_prcm_irq_cleanup();
 	return -ENOMEM;
 }
+
+/**
+ * prm_register - register per-SoC low-level data with the PRM
+ * @pld: low-level per-SoC OMAP PRM data & function pointers to register
+ *
+ * Register per-SoC low-level OMAP PRM data and function pointers with
+ * the OMAP PRM common interface.  The caller must keep the data
+ * pointed to by @pld valid until it calls prm_unregister() and
+ * it returns successfully.  Returns 0 upon success, -EINVAL if @pld
+ * is NULL, or -EEXIST if prm_register() has already been called
+ * without an intervening prm_unregister().
+ */
+int prm_register(struct prm_ll_data *pld)
+{
+	if (!pld)
+		return -EINVAL;
+
+	if (prm_ll_data != &null_prm_ll_data)
+		return -EEXIST;
+
+	prm_ll_data = pld;
+
+	return 0;
+}
+
+/**
+ * prm_unregister - unregister per-SoC low-level data & function pointers
+ * @pld: low-level per-SoC OMAP PRM data & function pointers to unregister
+ *
+ * Unregister per-SoC low-level OMAP PRM data and function pointers
+ * that were previously registered with prm_register().  The
+ * caller may not destroy any of the data pointed to by @pld until
+ * this function returns successfully.  Returns 0 upon success, or
+ * -EINVAL if @pld is NULL or if @pld does not match the struct
+ * prm_ll_data * previously registered by prm_register().
+ */
+int prm_unregister(struct prm_ll_data *pld)
+{
+	if (!pld || prm_ll_data != pld)
+		return -EINVAL;
+
+	prm_ll_data = &null_prm_ll_data;
+
+	return 0;
+}

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [PATCH 2/7] ARM: OMAP2+: CM: prepare for use of cm_ll_data function pointers
  2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
  2012-10-16  1:32 ` [PATCH 1/7] ARM: OMAP2+: PRM: prepare for use of prm_ll_data function pointers Paul Walmsley
@ 2012-10-16  1:32 ` Paul Walmsley
  2012-10-16  1:32 ` [PATCH 3/7] ARM: OMAP1: create read_reset_sources() function (for initial use by watchdog) Paul Walmsley
                   ` (5 subsequent siblings)
  7 siblings, 0 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-16  1:32 UTC (permalink / raw)
  To: linux-arm-kernel

There are several CM operations which behave similarly across OMAP2+
SoCs, but which have slight differences in their underlying
implementations.

This patch creates the support code for this function pointer
registration process.  No function pointers are included yet, but a
subsequent patch will create these for the module IDLEST registers.

This patch allows other code to use CM-provided data and operations
without needing to know which SoC is currently in use.  A further
description of the concept is provided in the patch entitled
"ARM: OMAP2+: PRM: prepare for use of prm_ll_data function pointers".

Signed-off-by: Paul Walmsley <paul@pwsan.com>
---
 arch/arm/mach-omap2/Makefile    |    2 +
 arch/arm/mach-omap2/cm.h        |   12 +++++++
 arch/arm/mach-omap2/cm_common.c |   71 +++++++++++++++++++++++++++++++++++++++
 3 files changed, 84 insertions(+), 1 deletion(-)
 create mode 100644 arch/arm/mach-omap2/cm_common.c

diff --git a/arch/arm/mach-omap2/Makefile b/arch/arm/mach-omap2/Makefile
index 3751d56..f7cf382 100644
--- a/arch/arm/mach-omap2/Makefile
+++ b/arch/arm/mach-omap2/Makefile
@@ -93,7 +93,7 @@ obj-$(CONFIG_ARCH_OMAP4)                += cpuidle44xx.o
 endif
 
 # PRCM
-obj-y					+= prcm.o prm_common.o
+obj-y					+= prcm.o prm_common.o cm_common.o
 obj-$(CONFIG_ARCH_OMAP2)		+= prm2xxx_3xxx.o prm2xxx.o cm2xxx.o
 obj-$(CONFIG_ARCH_OMAP3)		+= prm2xxx_3xxx.o prm3xxx.o cm3xxx.o
 obj-$(CONFIG_ARCH_OMAP3)		+= vc3xxx_data.o vp3xxx_data.o
diff --git a/arch/arm/mach-omap2/cm.h b/arch/arm/mach-omap2/cm.h
index f24e3f7..b3cee91 100644
--- a/arch/arm/mach-omap2/cm.h
+++ b/arch/arm/mach-omap2/cm.h
@@ -33,4 +33,16 @@
  */
 #define MAX_MODULE_DISABLE_TIME		5000
 
+# ifndef __ASSEMBLER__
+
+/**
+ * struct cm_ll_data - fn ptrs to per-SoC CM function implementations
+ */
+struct cm_ll_data {};
+
+extern int cm_register(struct cm_ll_data *cld);
+extern int cm_unregister(struct cm_ll_data *cld);
+
+# endif
+
 #endif
diff --git a/arch/arm/mach-omap2/cm_common.c b/arch/arm/mach-omap2/cm_common.c
new file mode 100644
index 0000000..3246cef
--- /dev/null
+++ b/arch/arm/mach-omap2/cm_common.c
@@ -0,0 +1,71 @@
+/*
+ * OMAP2+ common Clock Management (CM) IP block functions
+ *
+ * Copyright (C) 2012 Texas Instruments, Inc.
+ * Paul Walmsley <paul@pwsan.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ * XXX This code should eventually be moved to a CM driver.
+ */
+
+#include <linux/kernel.h>
+#include <linux/init.h>
+
+#include "cm2xxx.h"
+#include "cm3xxx.h"
+#include "cm44xx.h"
+
+/*
+ * cm_ll_data: function pointers to SoC-specific implementations of
+ * common CM functions
+ */
+static struct cm_ll_data null_cm_ll_data;
+static struct cm_ll_data *cm_ll_data = &null_cm_ll_data;
+
+/**
+ * cm_register - register per-SoC low-level data with the CM
+ * @cld: low-level per-SoC OMAP CM data & function pointers to register
+ *
+ * Register per-SoC low-level OMAP CM data and function pointers with
+ * the OMAP CM common interface.  The caller must keep the data
+ * pointed to by @cld valid until it calls cm_unregister() and
+ * it returns successfully.  Returns 0 upon success, -EINVAL if @cld
+ * is NULL, or -EEXIST if cm_register() has already been called
+ * without an intervening cm_unregister().
+ */
+int cm_register(struct cm_ll_data *cld)
+{
+	if (!cld)
+		return -EINVAL;
+
+	if (cm_ll_data != &null_cm_ll_data)
+		return -EEXIST;
+
+	cm_ll_data = cld;
+
+	return 0;
+}
+
+/**
+ * cm_unregister - unregister per-SoC low-level data & function pointers
+ * @cld: low-level per-SoC OMAP CM data & function pointers to unregister
+ *
+ * Unregister per-SoC low-level OMAP CM data and function pointers
+ * that were previously registered with cm_register().  The
+ * caller may not destroy any of the data pointed to by @cld until
+ * this function returns successfully.  Returns 0 upon success, or
+ * -EINVAL if @cld is NULL or if @cld does not match the struct
+ * cm_ll_data * previously registered by cm_register().
+ */
+int cm_unregister(struct cm_ll_data *cld)
+{
+	if (!cld || cm_ll_data != cld)
+		return -EINVAL;
+
+	cm_ll_data = &null_cm_ll_data;
+
+	return 0;
+}

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [PATCH 3/7] ARM: OMAP1: create read_reset_sources() function (for initial use by watchdog)
  2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
  2012-10-16  1:32 ` [PATCH 1/7] ARM: OMAP2+: PRM: prepare for use of prm_ll_data function pointers Paul Walmsley
  2012-10-16  1:32 ` [PATCH 2/7] ARM: OMAP2+: CM: prepare for use of cm_ll_data " Paul Walmsley
@ 2012-10-16  1:32 ` Paul Walmsley
  2012-10-16  1:32 ` [PATCH 4/7] ARM: OMAP2+: PRM: create PRM reset source API for the watchdog timer driver Paul Walmsley
                   ` (4 subsequent siblings)
  7 siblings, 0 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-16  1:32 UTC (permalink / raw)
  To: linux-arm-kernel

On OMAP1, the existing OMAP watchdog driver reads a register directly
from a non-watchdog IP block.  It also does not convert the register's
contents into the standard WDIOF_* bits expected from the
GETBOOTSTATUS ioctl().

To move towards fixing these problems, create an function in
arch/arm/mach-omap1 to return the reset source data.  A subsequent
patch will provide this function to the watchdog driver via
platform_data.

In the long term, the best approach would be to move this function
to a new OMAP1 driver that handles access to the OMAP1 Clock
Generation and Reset Management IP block.  Then no platform_data would
be needed.

Signed-off-by: Paul Walmsley <paul@pwsan.com>
---
 arch/arm/mach-omap1/common.h |    2 ++
 arch/arm/mach-omap1/reset.c  |   39 +++++++++++++++++++++++++++++++++++++++
 2 files changed, 41 insertions(+)

diff --git a/arch/arm/mach-omap1/common.h b/arch/arm/mach-omap1/common.h
index c2552b2..e83fd70 100644
--- a/arch/arm/mach-omap1/common.h
+++ b/arch/arm/mach-omap1/common.h
@@ -90,4 +90,6 @@ extern int ocpi_enable(void);
 static inline int ocpi_enable(void) { return 0; }
 #endif
 
+extern u32 omap1_read_reset_sources(void);
+
 #endif /* __ARCH_ARM_MACH_OMAP1_COMMON_H */
diff --git a/arch/arm/mach-omap1/reset.c b/arch/arm/mach-omap1/reset.c
index b177091..3e894fb 100644
--- a/arch/arm/mach-omap1/reset.c
+++ b/arch/arm/mach-omap1/reset.c
@@ -8,8 +8,22 @@
 
 #include <mach/hardware.h>
 
+#include "iomap.h"
 #include "common.h"
 
+/* ARM_SYSST bit shifts related to SoC reset sources */
+#define ARM_SYSST_POR_SHIFT				5
+#define ARM_SYSST_EXT_RST_SHIFT				4
+#define ARM_SYSST_ARM_WDRST_SHIFT			2
+#define ARM_SYSST_GLOB_SWRST_SHIFT			1
+
+/* Standardized reset source bits (across all OMAP SoCs) */
+#define OMAP_GLOBAL_COLD_RST_SRC_ID_SHIFT		0
+#define OMAP_GLOBAL_WARM_RST_SRC_ID_SHIFT		1
+#define OMAP_MPU_WD_RST_SRC_ID_SHIFT			3
+#define OMAP_EXTWARM_RST_SRC_ID_SHIFT			5
+
+
 void omap1_restart(char mode, const char *cmd)
 {
 	/*
@@ -23,3 +37,28 @@ void omap1_restart(char mode, const char *cmd)
 
 	omap_writew(1, ARM_RSTCT1);
 }
+
+/**
+ * omap1_read_reset_sources - return the source of the SoC's last reset
+ *
+ * Returns bits that represent the last reset source for the SoC.  The
+ * format is standardized across OMAPs for use by the OMAP watchdog.
+ */
+u32 omap1_read_reset_sources(void)
+{
+	int ret = 0;
+	u16 rs;
+
+	rs = __raw_readw(OMAP1_IO_ADDRESS(ARM_SYSST));
+
+	if (rs & (1 << ARM_SYSST_POR_SHIFT))
+		ret |= 1 << OMAP_GLOBAL_COLD_RST_SRC_ID_SHIFT;
+	if (rs & (1 << ARM_SYSST_EXT_RST_SHIFT))
+		ret |= 1 << OMAP_EXTWARM_RST_SRC_ID_SHIFT;
+	if (rs & (1 << ARM_SYSST_ARM_WDRST_SHIFT))
+		ret |= 1 << OMAP_MPU_WD_RST_SRC_ID_SHIFT;
+	if (rs & (1 << ARM_SYSST_GLOB_SWRST_SHIFT))
+		ret |= 1 << OMAP_GLOBAL_WARM_RST_SRC_ID_SHIFT;
+
+	return ret;
+}

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [PATCH 4/7] ARM: OMAP2+: PRM: create PRM reset source API for the watchdog timer driver
  2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
                   ` (2 preceding siblings ...)
  2012-10-16  1:32 ` [PATCH 3/7] ARM: OMAP1: create read_reset_sources() function (for initial use by watchdog) Paul Walmsley
@ 2012-10-16  1:32 ` Paul Walmsley
  2012-10-16  1:32 ` [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer Paul Walmsley
                   ` (3 subsequent siblings)
  7 siblings, 0 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-16  1:32 UTC (permalink / raw)
  To: linux-arm-kernel

The OMAP watchdog timer driver needs to determine what caused the SoC
to reset for its GETBOOTSTATUS ioctl.  So, define a set of standard
reset sources across OMAP SoCs.  For OMAP2xxx, 3xxx, and 4xxx SoCs,
define mappings from the SoC-specific reset source register bits to
the standardized reset source IDs.  Create SoC-specific PRM functions
that read the appropriate per-SoC register and use the mapping to
return the standardized reset bits.  Register the SoC-specific PRM
functions with the common PRM code via prm_register().  Create a
function in the common PRM code, prm_read_reset_sources(), that
calls the SoC-specific function, registered during boot.

This patch does not yet handle some SoCs, such as AM33xx.  Those SoCs
were not handled by the code this will replace.

Signed-off-by: Paul Walmsley <paul@pwsan.com>
---
 arch/arm/mach-omap2/prm-regbits-24xx.h |    4 ++
 arch/arm/mach-omap2/prm-regbits-34xx.h |   10 ++++
 arch/arm/mach-omap2/prm.h              |   44 +++++++++++++++++
 arch/arm/mach-omap2/prm2xxx.c          |   68 ++++++++++++++++++++++++++
 arch/arm/mach-omap2/prm2xxx.h          |    4 ++
 arch/arm/mach-omap2/prm2xxx_3xxx.h     |    2 +
 arch/arm/mach-omap2/prm3xxx.c          |   65 +++++++++++++++++++++++++
 arch/arm/mach-omap2/prm3xxx.h          |    2 +
 arch/arm/mach-omap2/prm44xx.c          |   83 +++++++++++++++++++++++++++++++-
 arch/arm/mach-omap2/prm44xx.h          |    2 +
 arch/arm/mach-omap2/prm_common.c       |   26 ++++++++++
 11 files changed, 306 insertions(+), 4 deletions(-)

diff --git a/arch/arm/mach-omap2/prm-regbits-24xx.h b/arch/arm/mach-omap2/prm-regbits-24xx.h
index bd70a5a..638da6d 100644
--- a/arch/arm/mach-omap2/prm-regbits-24xx.h
+++ b/arch/arm/mach-omap2/prm-regbits-24xx.h
@@ -209,9 +209,13 @@
 
 /* RM_RSTST_WKUP specific bits */
 /* 2430 calls EXTWMPU_RST "EXTWARM_RST" and GLOBALWMPU_RST "GLOBALWARM_RST" */
+#define OMAP24XX_EXTWMPU_RST_SHIFT			6
 #define OMAP24XX_EXTWMPU_RST_MASK			(1 << 6)
+#define OMAP24XX_SECU_WD_RST_SHIFT			5
 #define OMAP24XX_SECU_WD_RST_MASK			(1 << 5)
+#define OMAP24XX_MPU_WD_RST_SHIFT			4
 #define OMAP24XX_MPU_WD_RST_MASK			(1 << 4)
+#define OMAP24XX_SECU_VIOL_RST_SHIFT			3
 #define OMAP24XX_SECU_VIOL_RST_MASK			(1 << 3)
 
 /* PM_WKEN_WKUP specific bits */
diff --git a/arch/arm/mach-omap2/prm-regbits-34xx.h b/arch/arm/mach-omap2/prm-regbits-34xx.h
index 073d4db..838b594 100644
--- a/arch/arm/mach-omap2/prm-regbits-34xx.h
+++ b/arch/arm/mach-omap2/prm-regbits-34xx.h
@@ -509,15 +509,25 @@
 #define OMAP3430_RSTTIME1_MASK				(0xff << 0)
 
 /* PRM_RSTST */
+#define OMAP3430_ICECRUSHER_RST_SHIFT			10
 #define OMAP3430_ICECRUSHER_RST_MASK			(1 << 10)
+#define OMAP3430_ICEPICK_RST_SHIFT			9
 #define OMAP3430_ICEPICK_RST_MASK			(1 << 9)
+#define OMAP3430_VDD2_VOLTAGE_MANAGER_RST_SHIFT		8
 #define OMAP3430_VDD2_VOLTAGE_MANAGER_RST_MASK		(1 << 8)
+#define OMAP3430_VDD1_VOLTAGE_MANAGER_RST_SHIFT		7
 #define OMAP3430_VDD1_VOLTAGE_MANAGER_RST_MASK		(1 << 7)
+#define OMAP3430_EXTERNAL_WARM_RST_SHIFT		6
 #define OMAP3430_EXTERNAL_WARM_RST_MASK			(1 << 6)
+#define OMAP3430_SECURE_WD_RST_SHIFT			5
 #define OMAP3430_SECURE_WD_RST_MASK			(1 << 5)
+#define OMAP3430_MPU_WD_RST_SHIFT			4
 #define OMAP3430_MPU_WD_RST_MASK			(1 << 4)
+#define OMAP3430_SECURITY_VIOL_RST_SHIFT		3
 #define OMAP3430_SECURITY_VIOL_RST_MASK			(1 << 3)
+#define OMAP3430_GLOBAL_SW_RST_SHIFT			1
 #define OMAP3430_GLOBAL_SW_RST_MASK			(1 << 1)
+#define OMAP3430_GLOBAL_COLD_RST_SHIFT			0
 #define OMAP3430_GLOBAL_COLD_RST_MASK			(1 << 0)
 
 /* PRM_VOLTCTRL */
diff --git a/arch/arm/mach-omap2/prm.h b/arch/arm/mach-omap2/prm.h
index 3e51c1d..c30ab5d 100644
--- a/arch/arm/mach-omap2/prm.h
+++ b/arch/arm/mach-omap2/prm.h
@@ -52,16 +52,58 @@
 #define OMAP_POWERSTATE_SHIFT				0
 #define OMAP_POWERSTATE_MASK				(0x3 << 0)
 
+/*
+ * Standardized OMAP reset source bits
+ *
+ * To the extent these happen to match the hardware register bit
+ * shifts, it's purely coincidental.  Used by omap-wdt.c.
+ * OMAP_UNKNOWN_RST_SRC_ID_SHIFT is a special value, used whenever
+ * there are any bits remaining in the global PRM_RSTST register that
+ * haven't been identified, or when the PRM code for the current SoC
+ * doesn't know how to interpret the register.
+ */
+#define OMAP_GLOBAL_COLD_RST_SRC_ID_SHIFT			0
+#define OMAP_GLOBAL_WARM_RST_SRC_ID_SHIFT			1
+#define OMAP_SECU_VIOL_RST_SRC_ID_SHIFT				2
+#define OMAP_MPU_WD_RST_SRC_ID_SHIFT				3
+#define OMAP_SECU_WD_RST_SRC_ID_SHIFT				4
+#define OMAP_EXTWARM_RST_SRC_ID_SHIFT				5
+#define OMAP_VDD_MPU_VM_RST_SRC_ID_SHIFT			6
+#define OMAP_VDD_IVA_VM_RST_SRC_ID_SHIFT			7
+#define OMAP_VDD_CORE_VM_RST_SRC_ID_SHIFT			8
+#define OMAP_ICEPICK_RST_SRC_ID_SHIFT				9
+#define OMAP_ICECRUSHER_RST_SRC_ID_SHIFT			10
+#define OMAP_C2C_RST_SRC_ID_SHIFT				11
+#define OMAP_UNKNOWN_RST_SRC_ID_SHIFT				12
+
 #ifndef __ASSEMBLER__
 
 /**
+ * struct prm_reset_src_map - map register bitshifts to standard bitshifts
+ * @reg_shift: bitshift in the PRM reset source register
+ * @std_shift: bitshift equivalent in the standard reset source list
+ *
+ * The fields are signed because -1 is used as a terminator.
+ */
+struct prm_reset_src_map {
+	s8 reg_shift;
+	s8 std_shift;
+};
+
+/**
  * struct prm_ll_data - fn ptrs to per-SoC PRM function implementations
+ * @read_reset_sources: ptr to the Soc PRM-specific get_reset_source impl
  */
-struct prm_ll_data {};
+struct prm_ll_data {
+	u32 (*read_reset_sources)(void);
+};
 
 extern int prm_register(struct prm_ll_data *pld);
 extern int prm_unregister(struct prm_ll_data *pld);
 
+extern u32 prm_read_reset_sources(void);
+
 #endif
 
+
 #endif
diff --git a/arch/arm/mach-omap2/prm2xxx.c b/arch/arm/mach-omap2/prm2xxx.c
index d08a2b9..1fc06b0 100644
--- a/arch/arm/mach-omap2/prm2xxx.c
+++ b/arch/arm/mach-omap2/prm2xxx.c
@@ -28,6 +28,46 @@
 #include "cm2xxx_3xxx.h"
 #include "prm-regbits-24xx.h"
 
+/*
+ * omap2xxx_prm_reset_src_map - map from bits in the PRM_RSTST_WKUP
+ *   hardware register (which are specific to the OMAP2xxx SoCs) to
+ *   reset source ID bit shifts (which is an OMAP SoC-independent
+ *   enumeration)
+ */
+static struct prm_reset_src_map omap2xxx_prm_reset_src_map[] = {
+	{ OMAP_GLOBALCOLD_RST_SHIFT, OMAP_GLOBAL_COLD_RST_SRC_ID_SHIFT },
+	{ OMAP_GLOBALWARM_RST_SHIFT, OMAP_GLOBAL_WARM_RST_SRC_ID_SHIFT },
+	{ OMAP24XX_SECU_VIOL_RST_SHIFT, OMAP_SECU_VIOL_RST_SRC_ID_SHIFT },
+	{ OMAP24XX_MPU_WD_RST_SHIFT, OMAP_MPU_WD_RST_SRC_ID_SHIFT },
+	{ OMAP24XX_SECU_WD_RST_SHIFT, OMAP_SECU_WD_RST_SRC_ID_SHIFT },
+	{ OMAP24XX_EXTWMPU_RST_SHIFT, OMAP_EXTWARM_RST_SRC_ID_SHIFT },
+	{ -1, -1 },
+};
+
+/**
+ * omap2xxx_prm_read_reset_sources - return the last SoC reset source
+ *
+ * Return a u32 representing the last reset sources of the SoC.  The
+ * returned reset source bits are standardized across OMAP SoCs.
+ */
+static u32 omap2xxx_prm_read_reset_sources(void)
+{
+	struct prm_reset_src_map *p;
+	u32 r = 0;
+	u32 v;
+
+	v = omap2_prm_read_mod_reg(WKUP_MOD, OMAP2_RM_RSTST);
+
+	p = omap2xxx_prm_reset_src_map;
+	while (p->reg_shift >= 0 && p->std_shift >= 0) {
+		if (v & (1 << p->reg_shift))
+			r |= 1 << p->std_shift;
+		p++;
+	}
+
+	return r;
+}
+
 int omap2xxx_clkdm_sleep(struct clockdomain *clkdm)
 {
 	omap2_prm_set_mod_reg_bits(OMAP24XX_FORCESTATE_MASK,
@@ -55,3 +95,31 @@ struct pwrdm_ops omap2_pwrdm_operations = {
 	.pwrdm_read_mem_retst	= omap2_pwrdm_read_mem_retst,
 	.pwrdm_wait_transition	= omap2_pwrdm_wait_transition,
 };
+
+/*
+ *
+ */
+
+static struct prm_ll_data omap2xxx_prm_ll_data = {
+	.read_reset_sources = &omap2xxx_prm_read_reset_sources,
+};
+
+static int __init omap2xxx_prm_init(void)
+{
+	if (!cpu_is_omap24xx())
+		return 0;
+
+	return prm_register(&omap2xxx_prm_ll_data);
+}
+subsys_initcall(omap2xxx_prm_init);
+
+static void __exit omap2xxx_prm_exit(void)
+{
+	if (!cpu_is_omap24xx())
+		return;
+
+	/* Should never happen */
+	WARN(prm_unregister(&omap2xxx_prm_ll_data),
+	     "%s: prm_ll_data function pointer mismatch\n", __func__);
+}
+__exitcall(omap2xxx_prm_exit);
diff --git a/arch/arm/mach-omap2/prm2xxx.h b/arch/arm/mach-omap2/prm2xxx.h
index 6d76716..1d97112 100644
--- a/arch/arm/mach-omap2/prm2xxx.h
+++ b/arch/arm/mach-omap2/prm2xxx.h
@@ -123,6 +123,10 @@
 /* Function prototypes */
 extern int omap2xxx_clkdm_sleep(struct clockdomain *clkdm);
 extern int omap2xxx_clkdm_wakeup(struct clockdomain *clkdm);
+
+extern int __init prm2xxx_init(void);
+extern int __exit prm2xxx_exit(void);
+
 #endif
 
 #endif
diff --git a/arch/arm/mach-omap2/prm2xxx_3xxx.h b/arch/arm/mach-omap2/prm2xxx_3xxx.h
index 22a405a..3330b1b 100644
--- a/arch/arm/mach-omap2/prm2xxx_3xxx.h
+++ b/arch/arm/mach-omap2/prm2xxx_3xxx.h
@@ -211,7 +211,9 @@ extern int omap2_clkdm_clear_all_wkdeps(struct clockdomain *clkdm);
  *
  * 3430: RM_RSTST_CORE, RM_RSTST_EMU
  */
+#define OMAP_GLOBALWARM_RST_SHIFT			1
 #define OMAP_GLOBALWARM_RST_MASK			(1 << 1)
+#define OMAP_GLOBALCOLD_RST_SHIFT			0
 #define OMAP_GLOBALCOLD_RST_MASK			(1 << 0)
 
 /*
diff --git a/arch/arm/mach-omap2/prm3xxx.c b/arch/arm/mach-omap2/prm3xxx.c
index b2c5fd9..e96446c 100644
--- a/arch/arm/mach-omap2/prm3xxx.c
+++ b/arch/arm/mach-omap2/prm3xxx.c
@@ -46,6 +46,27 @@ static struct omap_prcm_irq_setup omap3_prcm_irq_setup = {
 	.restore_irqen		= &omap3xxx_prm_restore_irqen,
 };
 
+/*
+ * omap3_prm_reset_src_map - map from bits in the PRM_RSTST hardware
+ *   register (which are specific to OMAP3xxx SoCs) to reset source ID
+ *   bit shifts (which is an OMAP SoC-independent enumeration)
+ */
+static struct prm_reset_src_map omap3xxx_prm_reset_src_map[] = {
+	{ OMAP3430_GLOBAL_COLD_RST_SHIFT, OMAP_GLOBAL_COLD_RST_SRC_ID_SHIFT },
+	{ OMAP3430_GLOBAL_SW_RST_SHIFT, OMAP_GLOBAL_WARM_RST_SRC_ID_SHIFT },
+	{ OMAP3430_SECURITY_VIOL_RST_SHIFT, OMAP_SECU_VIOL_RST_SRC_ID_SHIFT },
+	{ OMAP3430_MPU_WD_RST_SHIFT, OMAP_MPU_WD_RST_SRC_ID_SHIFT },
+	{ OMAP3430_SECURE_WD_RST_SHIFT, OMAP_MPU_WD_RST_SRC_ID_SHIFT },
+	{ OMAP3430_EXTERNAL_WARM_RST_SHIFT, OMAP_EXTWARM_RST_SRC_ID_SHIFT },
+	{ OMAP3430_VDD1_VOLTAGE_MANAGER_RST_SHIFT,
+	  OMAP_VDD_MPU_VM_RST_SRC_ID_SHIFT },
+	{ OMAP3430_VDD2_VOLTAGE_MANAGER_RST_SHIFT,
+	  OMAP_VDD_CORE_VM_RST_SRC_ID_SHIFT },
+	{ OMAP3430_ICEPICK_RST_SHIFT, OMAP_ICEPICK_RST_SRC_ID_SHIFT },
+	{ OMAP3430_ICECRUSHER_RST_SHIFT, OMAP_ICECRUSHER_RST_SRC_ID_SHIFT },
+	{ -1, -1 },
+};
+
 /* PRM VP */
 
 /*
@@ -216,6 +237,30 @@ static void __init omap3xxx_prm_enable_io_wakeup(void)
 					   PM_WKEN);
 }
 
+/**
+ * omap3xxx_prm_read_reset_sources - return the last SoC reset source
+ *
+ * Return a u32 representing the last reset sources of the SoC.  The
+ * returned reset source bits are standardized across OMAP SoCs.
+ */
+static u32 omap3xxx_prm_read_reset_sources(void)
+{
+	struct prm_reset_src_map *p;
+	u32 r = 0;
+	u32 v;
+
+	v = omap2_prm_read_mod_reg(WKUP_MOD, OMAP2_RM_RSTST);
+
+	p = omap3xxx_prm_reset_src_map;
+	while (p->reg_shift >= 0 && p->std_shift >= 0) {
+		if (v & (1 << p->reg_shift))
+			r |= 1 << p->std_shift;
+		p++;
+	}
+
+	return r;
+}
+
 /* Powerdomain low-level functions */
 
 /* Applicable only for OMAP3. Not supported on OMAP2 */
@@ -319,6 +364,10 @@ struct pwrdm_ops omap3_pwrdm_operations = {
  *
  */
 
+static struct prm_ll_data omap3xxx_prm_ll_data = {
+	.read_reset_sources = &omap3xxx_prm_read_reset_sources,
+};
+
 static int __init omap3xxx_prm_init(void)
 {
 	int ret;
@@ -326,12 +375,28 @@ static int __init omap3xxx_prm_init(void)
 	if (!cpu_is_omap34xx())
 		return 0;
 
+	ret = prm_register(&omap3xxx_prm_ll_data);
+	if (ret)
+		return ret;
+
 	omap3xxx_prm_enable_io_wakeup();
 	ret = omap_prcm_register_chain_handler(&omap3_prcm_irq_setup);
 	if (!ret)
 		irq_set_status_flags(omap_prcm_event_to_irq("io"),
 				     IRQ_NOAUTOEN);
 
+
 	return ret;
 }
 subsys_initcall(omap3xxx_prm_init);
+
+static void __exit omap3xxx_prm_exit(void)
+{
+	if (!cpu_is_omap34xx())
+		return;
+
+	/* Should never happen */
+	WARN(prm_unregister(&omap3xxx_prm_ll_data),
+	     "%s: prm_ll_data function pointer mismatch\n", __func__);
+}
+__exitcall(omap3xxx_prm_exit);
diff --git a/arch/arm/mach-omap2/prm3xxx.h b/arch/arm/mach-omap2/prm3xxx.h
index 6821e83..a3c28a8 100644
--- a/arch/arm/mach-omap2/prm3xxx.h
+++ b/arch/arm/mach-omap2/prm3xxx.h
@@ -152,6 +152,8 @@ extern void omap3xxx_prm_ocp_barrier(void);
 extern void omap3xxx_prm_save_and_clear_irqen(u32 *saved_mask);
 extern void omap3xxx_prm_restore_irqen(u32 *saved_mask);
 
+extern u32 omap3xxx_prm_get_reset_sources(void);
+
 #endif /* __ASSEMBLER */
 
 
diff --git a/arch/arm/mach-omap2/prm44xx.c b/arch/arm/mach-omap2/prm44xx.c
index 9231fe5..beb4502 100644
--- a/arch/arm/mach-omap2/prm44xx.c
+++ b/arch/arm/mach-omap2/prm44xx.c
@@ -1,7 +1,7 @@
 /*
  * OMAP4 PRM module functions
  *
- * Copyright (C) 2011 Texas Instruments, Inc.
+ * Copyright (C) 2011-2012 Texas Instruments, Inc.
  * Copyright (C) 2010 Nokia Corporation
  * Beno?t Cousson
  * Paul Walmsley
@@ -29,6 +29,8 @@
 #include "prminst44xx.h"
 #include "powerdomain.h"
 
+/* Static data */
+
 static const struct omap_prcm_irq omap4_prcm_irqs[] = {
 	OMAP_PRCM_IRQ("wkup",   0,      0),
 	OMAP_PRCM_IRQ("io",     9,      1),
@@ -47,6 +49,33 @@ static struct omap_prcm_irq_setup omap4_prcm_irq_setup = {
 	.restore_irqen		= &omap44xx_prm_restore_irqen,
 };
 
+/*
+ * omap44xx_prm_reset_src_map - map from bits in the PRM_RSTST
+ *   hardware register (which are specific to OMAP44xx SoCs) to reset
+ *   source ID bit shifts (which is an OMAP SoC-independent
+ *   enumeration)
+ */
+static struct prm_reset_src_map omap44xx_prm_reset_src_map[] = {
+	{ OMAP4430_RST_GLOBAL_WARM_SW_SHIFT,
+	  OMAP_GLOBAL_WARM_RST_SRC_ID_SHIFT },
+	{ OMAP4430_RST_GLOBAL_COLD_SW_SHIFT,
+	  OMAP_GLOBAL_COLD_RST_SRC_ID_SHIFT },
+	{ OMAP4430_MPU_SECURITY_VIOL_RST_SHIFT,
+	  OMAP_SECU_VIOL_RST_SRC_ID_SHIFT },
+	{ OMAP4430_MPU_WDT_RST_SHIFT, OMAP_MPU_WD_RST_SRC_ID_SHIFT },
+	{ OMAP4430_SECURE_WDT_RST_SHIFT, OMAP_SECU_WD_RST_SRC_ID_SHIFT },
+	{ OMAP4430_EXTERNAL_WARM_RST_SHIFT, OMAP_EXTWARM_RST_SRC_ID_SHIFT },
+	{ OMAP4430_VDD_MPU_VOLT_MGR_RST_SHIFT,
+	  OMAP_VDD_MPU_VM_RST_SRC_ID_SHIFT },
+	{ OMAP4430_VDD_IVA_VOLT_MGR_RST_SHIFT,
+	  OMAP_VDD_IVA_VM_RST_SRC_ID_SHIFT },
+	{ OMAP4430_VDD_CORE_VOLT_MGR_RST_SHIFT,
+	  OMAP_VDD_CORE_VM_RST_SRC_ID_SHIFT },
+	{ OMAP4430_ICEPICK_RST_SHIFT, OMAP_ICEPICK_RST_SRC_ID_SHIFT },
+	{ OMAP4430_C2C_RST_SHIFT, OMAP_C2C_RST_SRC_ID_SHIFT },
+	{ -1, -1 },
+};
+
 /* PRM low-level functions */
 
 /* Read a register in a CM/PRM instance in the PRM module */
@@ -292,6 +321,31 @@ static void __init omap44xx_prm_enable_io_wakeup(void)
 				    OMAP4_PRM_IO_PMCTRL_OFFSET);
 }
 
+/**
+ * omap44xx_prm_read_reset_sources - return the last SoC reset source
+ *
+ * Return a u32 representing the last reset sources of the SoC.  The
+ * returned reset source bits are standardized across OMAP SoCs.
+ */
+static u32 omap44xx_prm_read_reset_sources(void)
+{
+	struct prm_reset_src_map *p;
+	u32 r = 0;
+	u32 v;
+
+	v = omap4_prm_read_inst_reg(OMAP4430_PRM_OCP_SOCKET_INST,
+				    OMAP4_RM_RSTST);
+
+	p = omap44xx_prm_reset_src_map;
+	while (p->reg_shift >= 0 && p->std_shift >= 0) {
+		if (v & (1 << p->reg_shift))
+			r |= 1 << p->std_shift;
+		p++;
+	}
+
+	return r;
+}
+
 /* Powerdomain low-level functions */
 
 static int omap4_pwrdm_set_next_pwrst(struct powerdomain *pwrdm, u8 pwrst)
@@ -554,14 +608,37 @@ struct pwrdm_ops omap4_pwrdm_operations = {
 	.pwrdm_wait_transition	= omap4_pwrdm_wait_transition,
 };
 
+/*
+ * XXX document
+ */
+static struct prm_ll_data omap44xx_prm_ll_data = {
+	.read_reset_sources = &omap44xx_prm_read_reset_sources,
+};
 
-static int __init omap4xxx_prm_init(void)
+static int __init omap44xx_prm_init(void)
 {
+	int ret;
+
 	if (!cpu_is_omap44xx())
 		return 0;
 
+	ret = prm_register(&omap44xx_prm_ll_data);
+	if (ret)
+		return ret;
+
 	omap44xx_prm_enable_io_wakeup();
 
 	return omap_prcm_register_chain_handler(&omap4_prcm_irq_setup);
 }
-subsys_initcall(omap4xxx_prm_init);
+subsys_initcall(omap44xx_prm_init);
+
+static void __exit omap44xx_prm_exit(void)
+{
+	if (!cpu_is_omap44xx())
+		return;
+
+	/* Should never happen */
+	WARN(prm_unregister(&omap44xx_prm_ll_data),
+	     "%s: prm_ll_data function pointer mismatch\n", __func__);
+}
+__exitcall(omap44xx_prm_exit);
diff --git a/arch/arm/mach-omap2/prm44xx.h b/arch/arm/mach-omap2/prm44xx.h
index ee72ae6..c8e1acc 100644
--- a/arch/arm/mach-omap2/prm44xx.h
+++ b/arch/arm/mach-omap2/prm44xx.h
@@ -771,6 +771,8 @@ extern void omap44xx_prm_ocp_barrier(void);
 extern void omap44xx_prm_save_and_clear_irqen(u32 *saved_mask);
 extern void omap44xx_prm_restore_irqen(u32 *saved_mask);
 
+extern u32 omap44xx_prm_get_reset_sources(void);
+
 # endif
 
 #endif
diff --git a/arch/arm/mach-omap2/prm_common.c b/arch/arm/mach-omap2/prm_common.c
index 8670a3c..e200e4f 100644
--- a/arch/arm/mach-omap2/prm_common.c
+++ b/arch/arm/mach-omap2/prm_common.c
@@ -28,6 +28,8 @@
 #include <plat/prcm.h>
 
 #include "prm2xxx_3xxx.h"
+#include "prm2xxx.h"
+#include "prm3xxx.h"
 #include "prm44xx.h"
 
 /*
@@ -327,6 +329,30 @@ err:
 }
 
 /**
+ * prm_read_reset_sources - return the sources of the SoC's last reset
+ *
+ * Return a u32 bitmask representing the reset sources that caused the
+ * SoC to reset.  The low-level per-SoC functions called by this
+ * function remap the SoC-specific reset source bits into an
+ * OMAP-common set of reset source bits, defined in
+ * arch/arm/mach-omap2/prm.h.  Returns the standardized reset source
+ * u32 bitmask from the hardware upon success, or returns (1 <<
+ * OMAP_UNKNOWN_RST_SRC_ID_SHIFT) if no low-level read_reset_sources()
+ * function was registered.
+ */
+u32 prm_read_reset_sources(void)
+{
+	u32 ret = 1 << OMAP_UNKNOWN_RST_SRC_ID_SHIFT;
+
+	if (prm_ll_data->read_reset_sources)
+		ret = prm_ll_data->read_reset_sources();
+	else
+		WARN_ONCE(1, "prm: %s: no mapping function defined for reset sources\n", __func__);
+
+	return ret;
+}
+
+/**
  * prm_register - register per-SoC low-level data with the PRM
  * @pld: low-level per-SoC OMAP PRM data & function pointers to register
  *

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
                   ` (3 preceding siblings ...)
  2012-10-16  1:32 ` [PATCH 4/7] ARM: OMAP2+: PRM: create PRM reset source API for the watchdog timer driver Paul Walmsley
@ 2012-10-16  1:32 ` Paul Walmsley
  2012-10-25 15:38   ` Aaro Koskinen
  2012-11-08 19:26   ` Paul Walmsley
  2012-10-16  1:32 ` [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr Paul Walmsley
                   ` (2 subsequent siblings)
  7 siblings, 2 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-16  1:32 UTC (permalink / raw)
  To: linux-arm-kernel

The OMAP watchdog timer driver directly calls a function exported by
code in arch/arm/mach-omap2.  This is not good; it tightly couples
this driver to the mach-omap2 integration code.  Instead, add a
temporary platform_data function pointer to abstract this function
call.  A subsequent patch will convert the watchdog driver to use this
function pointer.

This patch also moves the device creation code out of
arch/arm/mach-omap2/devices.c and into arch/arm/mach-omap2/wd_timer.c.
This is another step towards the removal of
arch/arm/mach-omap2/devices.c.

Signed-off-by: Paul Walmsley <paul@pwsan.com>
Cc: Wim Van Sebroeck <wim@iguana.be>
---
 arch/arm/mach-omap1/devices.c               |   21 +++++++++++++--
 arch/arm/mach-omap2/devices.c               |   26 ------------------
 arch/arm/mach-omap2/wd_timer.c              |   33 +++++++++++++++++++++++
 include/linux/platform_data/omap-wd-timer.h |   38 +++++++++++++++++++++++++++
 4 files changed, 89 insertions(+), 29 deletions(-)
 create mode 100644 include/linux/platform_data/omap-wd-timer.h

diff --git a/arch/arm/mach-omap1/devices.c b/arch/arm/mach-omap1/devices.c
index d3fec92..c3408e7 100644
--- a/arch/arm/mach-omap1/devices.c
+++ b/arch/arm/mach-omap1/devices.c
@@ -17,6 +17,8 @@
 #include <linux/platform_device.h>
 #include <linux/spi/spi.h>
 
+#include <linux/platform_data/omap-wd-timer.h>
+
 #include <asm/mach/map.h>
 
 #include <plat/tc.h>
@@ -439,18 +441,31 @@ static struct resource wdt_resources[] = {
 };
 
 static struct platform_device omap_wdt_device = {
-	.name	   = "omap_wdt",
-	.id	     = -1,
+	.name		= "omap_wdt",
+	.id		= -1,
 	.num_resources	= ARRAY_SIZE(wdt_resources),
 	.resource	= wdt_resources,
 };
 
 static int __init omap_init_wdt(void)
 {
+	struct omap_wd_timer_platform_data pdata;
+	int ret;
+
 	if (!cpu_is_omap16xx())
 		return -ENODEV;
 
-	return platform_device_register(&omap_wdt_device);
+	pdata.read_reset_sources = omap1_read_reset_sources;
+
+	ret = platform_device_register(&omap_wdt_device);
+	if (!ret) {
+		ret = platform_device_add_data(&omap_wdt_device, &pdata,
+					       sizeof(pdata));
+		if (ret)
+			platform_device_del(&omap_wdt_device);
+	}
+
+	return ret;
 }
 subsys_initcall(omap_init_wdt);
 #endif
diff --git a/arch/arm/mach-omap2/devices.c b/arch/arm/mach-omap2/devices.c
index c8c2117..2ab2c99 100644
--- a/arch/arm/mach-omap2/devices.c
+++ b/arch/arm/mach-omap2/devices.c
@@ -644,29 +644,3 @@ static int __init omap2_init_devices(void)
 	return 0;
 }
 arch_initcall(omap2_init_devices);
-
-#if defined(CONFIG_OMAP_WATCHDOG) || defined(CONFIG_OMAP_WATCHDOG_MODULE)
-static int __init omap_init_wdt(void)
-{
-	int id = -1;
-	struct platform_device *pdev;
-	struct omap_hwmod *oh;
-	char *oh_name = "wd_timer2";
-	char *dev_name = "omap_wdt";
-
-	if (!cpu_class_is_omap2() || of_have_populated_dt())
-		return 0;
-
-	oh = omap_hwmod_lookup(oh_name);
-	if (!oh) {
-		pr_err("Could not look up wd_timer%d hwmod\n", id);
-		return -EINVAL;
-	}
-
-	pdev = omap_device_build(dev_name, id, oh, NULL, 0, NULL, 0, 0);
-	WARN(IS_ERR(pdev), "Can't build omap_device for %s:%s.\n",
-				dev_name, oh->name);
-	return 0;
-}
-subsys_initcall(omap_init_wdt);
-#endif
diff --git a/arch/arm/mach-omap2/wd_timer.c b/arch/arm/mach-omap2/wd_timer.c
index b2f1c67..00ef54c 100644
--- a/arch/arm/mach-omap2/wd_timer.c
+++ b/arch/arm/mach-omap2/wd_timer.c
@@ -11,10 +11,14 @@
 #include <linux/io.h>
 #include <linux/err.h>
 
+#include <linux/platform_data/omap-wd-timer.h>
+
 #include <plat/omap_hwmod.h>
+#include <plat/omap_device.h>
 
 #include "wd_timer.h"
 #include "common.h"
+#include "prm.h"
 
 /*
  * In order to avoid any assumptions from bootloader regarding WDT
@@ -99,3 +103,32 @@ int omap2_wd_timer_reset(struct omap_hwmod *oh)
 	return (c == MAX_MODULE_SOFTRESET_WAIT) ? -ETIMEDOUT :
 		omap2_wd_timer_disable(oh);
 }
+
+static int __init omap_init_wdt(void)
+{
+	int id = -1;
+	struct platform_device *pdev;
+	struct omap_hwmod *oh;
+	char *oh_name = "wd_timer2";
+	char *dev_name = "omap_wdt";
+	struct omap_wd_timer_platform_data pdata;
+
+	if (!cpu_class_is_omap2())
+		return 0;
+
+	oh = omap_hwmod_lookup(oh_name);
+	if (!oh) {
+		pr_err("Could not look up wd_timer%d hwmod\n", id);
+		return -EINVAL;
+	}
+
+	pdata.read_reset_sources = prm_read_reset_sources;
+
+	pdev = omap_device_build(dev_name, id, oh, &pdata,
+				 sizeof(struct omap_wd_timer_platform_data),
+				 NULL, 0, 0);
+	WARN(IS_ERR(pdev), "Can't build omap_device for %s:%s.\n",
+	     dev_name, oh->name);
+	return 0;
+}
+subsys_initcall(omap_init_wdt);
diff --git a/include/linux/platform_data/omap-wd-timer.h b/include/linux/platform_data/omap-wd-timer.h
new file mode 100644
index 0000000..d75f5f8
--- /dev/null
+++ b/include/linux/platform_data/omap-wd-timer.h
@@ -0,0 +1,38 @@
+/*
+ * OMAP2+ WDTIMER-specific function prototypes
+ *
+ * Copyright (C) 2012 Texas Instruments, Inc.
+ * Paul Walmsley
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+
+#ifndef __LINUX_PLATFORM_DATA_OMAP_WD_TIMER_H
+#define __LINUX_PLATFORM_DATA_OMAP_WD_TIMER_H
+
+#include <linux/types.h>
+
+/*
+ * Standardized OMAP reset source bits
+ *
+ * This is a subset of the ones listed in arch/arm/mach-omap2/prm.h
+ * and are the only ones needed in the watchdog driver.
+ */
+#define OMAP_MPU_WD_RST_SRC_ID_SHIFT				3
+
+/**
+ * struct omap_wd_timer_platform_data - WDTIMER integration to the host SoC
+ * @read_reset_sources - fn ptr for the SoC to indicate the last reset cause
+ *
+ * The function pointed to by @read_reset_sources must return its data
+ * in a standard format - search for RST_SRC_ID_SHIFT in
+ * arch/arm/mach-omap2
+ */
+struct omap_wd_timer_platform_data {
+	u32 (*read_reset_sources)(void);
+};
+
+#endif

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr
  2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
                   ` (4 preceding siblings ...)
  2012-10-16  1:32 ` [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer Paul Walmsley
@ 2012-10-16  1:32 ` Paul Walmsley
  2012-10-25 20:14   ` Jon Hunter
  2012-10-16  1:32 ` [PATCH 7/7] ARM: OMAP2+: PRCM: remove omap_prcm_get_reset_sources() Paul Walmsley
  2012-10-22 12:14 ` [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Benoit Cousson
  7 siblings, 1 reply; 28+ messages in thread
From: Paul Walmsley @ 2012-10-16  1:32 UTC (permalink / raw)
  To: linux-arm-kernel

Previously the OMAP watchdog driver used a non-standard way to report
the chip reset source via the GETBOOTSTATUS ioctl.  This patch
converts the driver to use the standard WDIOF_* flags for this
purpose.

This patch may break existing userspace code that uses the existing
non-standard data format returned by the OMAP watchdog driver's
GETBOOTSTATUS ioctl.  To fetch detailed reset source information,
userspace code will need to retrieve it directly from the CGRM or PRM
drivers when those are completed.

Previously, to fetch the reset source, the driver either read a
register outside the watchdog IP block (OMAP1), or called a function
exported directly from arch/arm/mach-omap2.  Both approaches are
broken.  This patch also converts the driver to use a platform_data
function pointer.  This approach is temporary, and is due to the lack
of drivers for the OMAP16xx+ Clock Generation and Reset Management IP
block and the OMAP2+ Power and Reset Management IP block.  Once
drivers are available for those IP blocks, the watchdog driver can be
converted to call exported drivers from those functions directly.
At that point, the platform_data function pointer can be removed.

In the short term, this patch is needed to allow the PRM code to be
removed from arch/arm/mach-omap2 (it is being moved to a driver).

Signed-off-by: Paul Walmsley <paul@pwsan.com>
Cc: Wim Van Sebroeck <wim@iguana.be>
---
 drivers/watchdog/omap_wdt.c |   26 ++++++++++++--------------
 1 file changed, 12 insertions(+), 14 deletions(-)

diff --git a/drivers/watchdog/omap_wdt.c b/drivers/watchdog/omap_wdt.c
index f5db18db..5d33bc0 100644
--- a/drivers/watchdog/omap_wdt.c
+++ b/drivers/watchdog/omap_wdt.c
@@ -46,8 +46,8 @@
 #include <linux/slab.h>
 #include <linux/pm_runtime.h>
 #include <mach/hardware.h>
-#include <plat/cpu.h>
-#include <plat/prcm.h>
+
+#include <linux/platform_data/omap-wd-timer.h>
 
 #include "omap_wdt.h"
 
@@ -202,8 +202,10 @@ static ssize_t omap_wdt_write(struct file *file, const char __user *data,
 static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
 						unsigned long arg)
 {
+	struct omap_wd_timer_platform_data *pdata;
 	struct omap_wdt_dev *wdev;
-	int new_margin;
+	u32 rs;
+	int new_margin, bs;
 	static const struct watchdog_info ident = {
 		.identity = "OMAP Watchdog",
 		.options = WDIOF_SETTIMEOUT,
@@ -211,6 +213,7 @@ static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
 	};
 
 	wdev = file->private_data;
+	pdata = wdev->dev->platform_data;
 
 	switch (cmd) {
 	case WDIOC_GETSUPPORT:
@@ -219,17 +222,12 @@ static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
 	case WDIOC_GETSTATUS:
 		return put_user(0, (int __user *)arg);
 	case WDIOC_GETBOOTSTATUS:
-#ifdef CONFIG_ARCH_OMAP1
-		if (cpu_is_omap16xx())
-			return put_user(__raw_readw(ARM_SYSST),
-					(int __user *)arg);
-#endif
-#ifdef CONFIG_ARCH_OMAP2PLUS
-		if (cpu_is_omap24xx())
-			return put_user(omap_prcm_get_reset_sources(),
-					(int __user *)arg);
-#endif
-		return put_user(0, (int __user *)arg);
+		if (!pdata->read_reset_sources)
+			return put_user(0, (int __user *)arg);
+		rs = pdata->read_reset_sources();
+		bs = (rs & (1 << OMAP_MPU_WD_RST_SRC_ID_SHIFT)) ?
+			WDIOF_CARDRESET : 0;
+		return put_user(bs, (int __user *)arg);
 	case WDIOC_KEEPALIVE:
 		spin_lock(&wdt_lock);
 		omap_wdt_ping(wdev);

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [PATCH 7/7] ARM: OMAP2+: PRCM: remove omap_prcm_get_reset_sources()
  2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
                   ` (5 preceding siblings ...)
  2012-10-16  1:32 ` [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr Paul Walmsley
@ 2012-10-16  1:32 ` Paul Walmsley
  2012-10-22 12:14 ` [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Benoit Cousson
  7 siblings, 0 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-16  1:32 UTC (permalink / raw)
  To: linux-arm-kernel

omap_prcm_get_reset_sources() is now unused; so, remove it.

Signed-off-by: Paul Walmsley <paul@pwsan.com>
---
 arch/arm/mach-omap2/prcm.c             |   12 ------------
 arch/arm/plat-omap/include/plat/prcm.h |    1 -
 2 files changed, 13 deletions(-)

diff --git a/arch/arm/mach-omap2/prcm.c b/arch/arm/mach-omap2/prcm.c
index 0f51e03..0a2c33b 100644
--- a/arch/arm/mach-omap2/prcm.c
+++ b/arch/arm/mach-omap2/prcm.c
@@ -46,18 +46,6 @@ void __iomem *prcm_mpu_base;
 
 #define MAX_MODULE_ENABLE_WAIT		100000
 
-u32 omap_prcm_get_reset_sources(void)
-{
-	/* XXX This presumably needs modification for 34XX */
-	if (cpu_is_omap24xx() || cpu_is_omap34xx())
-		return omap2_prm_read_mod_reg(WKUP_MOD, OMAP2_RM_RSTST) & 0x7f;
-	if (cpu_is_omap44xx())
-		return omap2_prm_read_mod_reg(WKUP_MOD, OMAP4_RM_RSTST) & 0x7f;
-
-	return 0;
-}
-EXPORT_SYMBOL(omap_prcm_get_reset_sources);
-
 /* Resets clock rates and reboots the system. Only called from system.h */
 void omap_prcm_restart(char mode, const char *cmd)
 {
diff --git a/arch/arm/plat-omap/include/plat/prcm.h b/arch/arm/plat-omap/include/plat/prcm.h
index 267f43b..a76cbd4 100644
--- a/arch/arm/plat-omap/include/plat/prcm.h
+++ b/arch/arm/plat-omap/include/plat/prcm.h
@@ -27,7 +27,6 @@
 #ifndef __ASM_ARM_ARCH_OMAP_PRCM_H
 #define __ASM_ARM_ARCH_OMAP_PRCM_H
 
-u32 omap_prcm_get_reset_sources(void);
 int omap2_cm_wait_idlest(void __iomem *reg, u32 mask, u8 idlest,
 			 const char *name);
 

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8
  2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
                   ` (6 preceding siblings ...)
  2012-10-16  1:32 ` [PATCH 7/7] ARM: OMAP2+: PRCM: remove omap_prcm_get_reset_sources() Paul Walmsley
@ 2012-10-22 12:14 ` Benoit Cousson
  2012-10-22 17:06   ` Paul Walmsley
  7 siblings, 1 reply; 28+ messages in thread
From: Benoit Cousson @ 2012-10-22 12:14 UTC (permalink / raw)
  To: linux-arm-kernel


Hi Paul,

What is CGRM? Is it a typo?

Regards,
Benoit


On 10/16/2012 03:32 AM, Paul Walmsley wrote:
> This series removes the omap_prcm_get_reset_sources() function.  This
> was exported from arch/arm/mach-omap2/prcm.c for use by the OMAP
> watchdog driver to report the "boot reason".  This series reimplements
> this using a platform_data function pointer for the time being, but
> after the upcoming PRM/CM drivers are merged, the watchdog driver can be
> patched to use an exported function from the drivers.
> 
> This series will also be used as a base for other PRM/CM cleanup during the
> 3.8 time frame, since it adds the prm_register() and prm_unregister() functions.
> These are called by SoC-specific PRM IP block drivers to register function
> pointers with the PRM subsystem.
> 
> This series changes the format of the watchdog's boot reason data to conform
> with the watchdog subsystem standard (the WDIOF_* flags).  If users need
> more detail than that interface provides, either the watchdog interface can
> be patched, or those users can get that information from the upcoming PRM
> drivers.
> 
> 
> - Paul
> 
> ---
> 
> prcm_cleanup_b_3.8
>    text	   data	    bss	    dec	    hex	filename
> 7519295	 696796	5613996	13830087	 d307c7	vmlinux.omap2plus_defconfig.orig
> 7520203	 696868	5613996	13831067	 d30b9b	vmlinux.omap2plus_defconfig
> 
> Paul Walmsley (7):
>       ARM: OMAP2+: PRM: prepare for use of prm_ll_data function pointers
>       ARM: OMAP2+: CM: prepare for use of cm_ll_data function pointers
>       ARM: OMAP1: create read_reset_sources() function (for initial use by watchdog)
>       ARM: OMAP2+: PRM: create PRM reset source API for the watchdog timer driver
>       ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
>       watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr
>       ARM: OMAP2+: PRCM: remove omap_prcm_get_reset_sources()
> 
> 
>  arch/arm/mach-omap1/common.h                |    2 +
>  arch/arm/mach-omap1/devices.c               |   21 ++++++-
>  arch/arm/mach-omap1/reset.c                 |   39 +++++++++++++
>  arch/arm/mach-omap2/Makefile                |    2 -
>  arch/arm/mach-omap2/cm.h                    |   12 ++++
>  arch/arm/mach-omap2/cm_common.c             |   71 +++++++++++++++++++++++
>  arch/arm/mach-omap2/devices.c               |   26 --------
>  arch/arm/mach-omap2/prcm.c                  |   12 ----
>  arch/arm/mach-omap2/prm-regbits-24xx.h      |    4 +
>  arch/arm/mach-omap2/prm-regbits-34xx.h      |   10 +++
>  arch/arm/mach-omap2/prm.h                   |   53 +++++++++++++++++
>  arch/arm/mach-omap2/prm2xxx.c               |   68 ++++++++++++++++++++++
>  arch/arm/mach-omap2/prm2xxx.h               |    4 +
>  arch/arm/mach-omap2/prm2xxx_3xxx.h          |    2 +
>  arch/arm/mach-omap2/prm3xxx.c               |   65 +++++++++++++++++++++
>  arch/arm/mach-omap2/prm3xxx.h               |    2 +
>  arch/arm/mach-omap2/prm44xx.c               |   83 ++++++++++++++++++++++++++-
>  arch/arm/mach-omap2/prm44xx.h               |    2 +
>  arch/arm/mach-omap2/prm_common.c            |   78 +++++++++++++++++++++++++
>  arch/arm/mach-omap2/wd_timer.c              |   33 +++++++++++
>  arch/arm/plat-omap/include/plat/prcm.h      |    1 
>  drivers/watchdog/omap_wdt.c                 |   26 ++++----
>  include/linux/platform_data/omap-wd-timer.h |   38 ++++++++++++
>  23 files changed, 594 insertions(+), 60 deletions(-)
>  create mode 100644 arch/arm/mach-omap2/cm_common.c
>  create mode 100644 include/linux/platform_data/omap-wd-timer.h
> 
> --
> To unsubscribe from this list: send the line "unsubscribe linux-omap" in
> the body of a message to majordomo at vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html
> 

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8
  2012-10-22 12:14 ` [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Benoit Cousson
@ 2012-10-22 17:06   ` Paul Walmsley
  2012-10-22 17:29     ` Benoit Cousson
  0 siblings, 1 reply; 28+ messages in thread
From: Paul Walmsley @ 2012-10-22 17:06 UTC (permalink / raw)
  To: linux-arm-kernel

On Mon, 22 Oct 2012, Benoit Cousson wrote:

> What is CGRM? Is it a typo?

That's the OMAP1 Clock Generation and Reset Module that contains the 
ARM_SYSST register:

http://www.ti.com/lit/ug/spru678a/spru678a.pdf

- Paul

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8
  2012-10-22 17:06   ` Paul Walmsley
@ 2012-10-22 17:29     ` Benoit Cousson
  0 siblings, 0 replies; 28+ messages in thread
From: Benoit Cousson @ 2012-10-22 17:29 UTC (permalink / raw)
  To: linux-arm-kernel

On 10/22/2012 07:06 PM, Paul Walmsley wrote:
> On Mon, 22 Oct 2012, Benoit Cousson wrote:
> 
>> What is CGRM? Is it a typo?
> 
> That's the OMAP1 Clock Generation and Reset Module that contains the 
> ARM_SYSST register:

Outch, that's pretty old stuff. Thanks for the clarification.

Regards,
Benoit

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-16  1:32 ` [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer Paul Walmsley
@ 2012-10-25 15:38   ` Aaro Koskinen
  2012-10-25 18:51     ` Paul Walmsley
  2012-11-08 19:26   ` Paul Walmsley
  1 sibling, 1 reply; 28+ messages in thread
From: Aaro Koskinen @ 2012-10-25 15:38 UTC (permalink / raw)
  To: linux-arm-kernel

Hi,

On Mon, Oct 15, 2012 at 07:32:33PM -0600, Paul Walmsley wrote:
> The OMAP watchdog timer driver directly calls a function exported by
> code in arch/arm/mach-omap2.  This is not good; it tightly couples
> this driver to the mach-omap2 integration code.  Instead, add a
> temporary platform_data function pointer to abstract this function
> call.  A subsequent patch will convert the watchdog driver to use this
> function pointer.

Why a function is needed? Reset cause won't change until the next reset,
so it should be enough to read it once during the init and store it into
the platform data.

A.

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 15:38   ` Aaro Koskinen
@ 2012-10-25 18:51     ` Paul Walmsley
  2012-10-25 18:57       ` Tony Lindgren
  0 siblings, 1 reply; 28+ messages in thread
From: Paul Walmsley @ 2012-10-25 18:51 UTC (permalink / raw)
  To: linux-arm-kernel

Terve,

On Thu, 25 Oct 2012, Aaro Koskinen wrote:

> On Mon, Oct 15, 2012 at 07:32:33PM -0600, Paul Walmsley wrote:
> > The OMAP watchdog timer driver directly calls a function exported by
> > code in arch/arm/mach-omap2.  This is not good; it tightly couples
> > this driver to the mach-omap2 integration code.  Instead, add a
> > temporary platform_data function pointer to abstract this function
> > call.  A subsequent patch will convert the watchdog driver to use this
> > function pointer.
> 
> Why a function is needed? Reset cause won't change until the next reset,
> so it should be enough to read it once during the init and store it into
> the platform data.

Once the PRM/CM drivers and DT conversion is complete, this driver won't 
have any platform_data.  There won't be any watchdog driver initialization 
code in arch/arm/mach-omap2.  At that point in time, the driver will just 
call a function from the PRM driver that provides the reset source data.  

As you say, the watchdog can certainly do this from its probe code; it 
would be more efficient.  Just didn't want to make that change now; seems 
like it would be best done as a separate optimization patch.


- Paul

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 18:51     ` Paul Walmsley
@ 2012-10-25 18:57       ` Tony Lindgren
  2012-10-25 19:09         ` Paul Walmsley
  0 siblings, 1 reply; 28+ messages in thread
From: Tony Lindgren @ 2012-10-25 18:57 UTC (permalink / raw)
  To: linux-arm-kernel

* Paul Walmsley <paul@pwsan.com> [121025 11:53]:
> Terve,
> 
> On Thu, 25 Oct 2012, Aaro Koskinen wrote:
> 
> > On Mon, Oct 15, 2012 at 07:32:33PM -0600, Paul Walmsley wrote:
> > > The OMAP watchdog timer driver directly calls a function exported by
> > > code in arch/arm/mach-omap2.  This is not good; it tightly couples
> > > this driver to the mach-omap2 integration code.  Instead, add a
> > > temporary platform_data function pointer to abstract this function
> > > call.  A subsequent patch will convert the watchdog driver to use this
> > > function pointer.
> > 
> > Why a function is needed? Reset cause won't change until the next reset,
> > so it should be enough to read it once during the init and store it into
> > the platform data.
> 
> Once the PRM/CM drivers and DT conversion is complete, this driver won't 
> have any platform_data.  There won't be any watchdog driver initialization 
> code in arch/arm/mach-omap2.  At that point in time, the driver will just 
> call a function from the PRM driver that provides the reset source data.  
> 
> As you say, the watchdog can certainly do this from its probe code; it 
> would be more efficient.  Just didn't want to make that change now; seems 
> like it would be best done as a separate optimization patch.

Ideally we'd have some Linux generic function to implement in the PRM/CM
drivers for getting the bootreason. But I guess we don't?

Regards,

Tony

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 18:57       ` Tony Lindgren
@ 2012-10-25 19:09         ` Paul Walmsley
  2012-10-25 19:19           ` Tony Lindgren
  0 siblings, 1 reply; 28+ messages in thread
From: Paul Walmsley @ 2012-10-25 19:09 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, 25 Oct 2012, Tony Lindgren wrote:

> Ideally we'd have some Linux generic function to implement in the PRM/CM
> drivers for getting the bootreason. But I guess we don't?

Do you know of one, apart from WDIOC_GETBOOTSTATUS?


- Paul

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 19:09         ` Paul Walmsley
@ 2012-10-25 19:19           ` Tony Lindgren
  2012-10-25 19:31             ` Paul Walmsley
  0 siblings, 1 reply; 28+ messages in thread
From: Tony Lindgren @ 2012-10-25 19:19 UTC (permalink / raw)
  To: linux-arm-kernel

* Paul Walmsley <paul@pwsan.com> [121025 12:11]:
> On Thu, 25 Oct 2012, Tony Lindgren wrote:
> 
> > Ideally we'd have some Linux generic function to implement in the PRM/CM
> > drivers for getting the bootreason. But I guess we don't?
> 
> Do you know of one, apart from WDIOC_GETBOOTSTATUS?

I wonder if we can now with multiple watchdogs supported to
have also PRM/CM implement omap_prcm_wdt_ioctl() that just
handles WDIOC_GETBOOTSTATUS and then just remove that handling
from the other omap watchdog drivers?

Regards,

Tony

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 19:19           ` Tony Lindgren
@ 2012-10-25 19:31             ` Paul Walmsley
  2012-10-25 19:34               ` Tony Lindgren
  0 siblings, 1 reply; 28+ messages in thread
From: Paul Walmsley @ 2012-10-25 19:31 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, 25 Oct 2012, Tony Lindgren wrote:

> I wonder if we can now with multiple watchdogs supported to
> have also PRM/CM implement omap_prcm_wdt_ioctl() that just
> handles WDIOC_GETBOOTSTATUS and then just remove that handling
> from the other omap watchdog drivers?

The watchdog ioctl code needs access to internal watchdog state and 
functions, for example  WDIOC_KEEPALIVE and  WDIOC_SETTIMEOUT.  How would 
the approach you're thinking of implement those operations?



- Paul

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 19:31             ` Paul Walmsley
@ 2012-10-25 19:34               ` Tony Lindgren
  2012-10-25 19:42                 ` Tony Lindgren
  2012-10-25 19:57                 ` Paul Walmsley
  0 siblings, 2 replies; 28+ messages in thread
From: Tony Lindgren @ 2012-10-25 19:34 UTC (permalink / raw)
  To: linux-arm-kernel

* Paul Walmsley <paul@pwsan.com> [121025 12:32]:
> On Thu, 25 Oct 2012, Tony Lindgren wrote:
> 
> > I wonder if we can now with multiple watchdogs supported to
> > have also PRM/CM implement omap_prcm_wdt_ioctl() that just
> > handles WDIOC_GETBOOTSTATUS and then just remove that handling
> > from the other omap watchdog drivers?
> 
> The watchdog ioctl code needs access to internal watchdog state and 
> functions, for example  WDIOC_KEEPALIVE and  WDIOC_SETTIMEOUT.  How would 
> the approach you're thinking of implement those operations?

I have not looked how the watchdog subsystem handles multiple
watchdogs, but.. Can't we have the omap watchdog and twl watchdog
return -ENOTSUPP for WDIOC_GETBOOTSTATUS and have the watchdog
core fail over to the third wathcdog omap_prcm_wdt_ioctl() that
only implements WDIOC_GETBOOTSTATUS? Or something like that.

Regards,

Tony

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 19:34               ` Tony Lindgren
@ 2012-10-25 19:42                 ` Tony Lindgren
  2012-10-25 19:57                 ` Paul Walmsley
  1 sibling, 0 replies; 28+ messages in thread
From: Tony Lindgren @ 2012-10-25 19:42 UTC (permalink / raw)
  To: linux-arm-kernel

* Tony Lindgren <tony@atomide.com> [121025 12:35]:
> * Paul Walmsley <paul@pwsan.com> [121025 12:32]:
> > On Thu, 25 Oct 2012, Tony Lindgren wrote:
> > 
> > > I wonder if we can now with multiple watchdogs supported to
> > > have also PRM/CM implement omap_prcm_wdt_ioctl() that just
> > > handles WDIOC_GETBOOTSTATUS and then just remove that handling
> > > from the other omap watchdog drivers?
> > 
> > The watchdog ioctl code needs access to internal watchdog state and 
> > functions, for example  WDIOC_KEEPALIVE and  WDIOC_SETTIMEOUT.  How would 
> > the approach you're thinking of implement those operations?
> 
> I have not looked how the watchdog subsystem handles multiple
> watchdogs, but.. Can't we have the omap watchdog and twl watchdog
> return -ENOTSUPP for WDIOC_GETBOOTSTATUS and have the watchdog
> core fail over to the third wathcdog omap_prcm_wdt_ioctl() that
> only implements WDIOC_GETBOOTSTATUS? Or something like that.

After poking around a bit, probably the way to do this would
be to have watchdog core bootstatus in addition to the
bootstatus in struct watchdog_device?

Then the omap_prcm watchdog could just initialize the
watchdog core bootstatus, and the other omap watchdog drivers
would just return the watchdog core bootstatus.

Not that it's related to this patchset, just trying to figure
out how it could be done in a generic way :)

Regards,

Tony 

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 19:34               ` Tony Lindgren
  2012-10-25 19:42                 ` Tony Lindgren
@ 2012-10-25 19:57                 ` Paul Walmsley
  2012-10-25 20:08                   ` Aaro Koskinen
  1 sibling, 1 reply; 28+ messages in thread
From: Paul Walmsley @ 2012-10-25 19:57 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, 25 Oct 2012, Tony Lindgren wrote:

> I have not looked how the watchdog subsystem handles multiple
> watchdogs, but..

In the new watchdog core code, each watchdog driver gets a separate 
/dev/watchdog* character device.  The ioctls are called on those device 
nodes.

[ As an aside, neither the OMAP watchdog driver, nor the TWL watchdog 
driver have been updated to use the new watchdog core code.  So they both 
can't be loaded at the same time until one or both are fixed. ]

> Can't we have the omap watchdog and twl watchdog return -ENOTSUPP for 
> WDIOC_GETBOOTSTATUS and have the watchdog core fail over to the third 
> wathcdog omap_prcm_wdt_ioctl() that only implements WDIOC_GETBOOTSTATUS? 
> Or something like that.

Sounds like a question better asked of Alan Cox and Wim, who wrote the 
watchdog core code.

Two other observations:

- It's possible that two different watchdogs could report different boot 
reasons.  The TWL might store its own watchdog boot reason which could be 
different from what's reported via the OMAP PRM.  For example, the TWL can 
record a thermal shutdown reset event, STS_BOOT.TS, which wouldn't be 
reflected in the PRM reset source data, which would just see some kind of 
external reset or power-off event.

- The PRM doesn't contain a hardware watchdog, so not sure it makes sense 
to create a watchdog driver for it.


- Paul

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 19:57                 ` Paul Walmsley
@ 2012-10-25 20:08                   ` Aaro Koskinen
  2012-10-25 20:09                     ` Paul Walmsley
  0 siblings, 1 reply; 28+ messages in thread
From: Aaro Koskinen @ 2012-10-25 20:08 UTC (permalink / raw)
  To: linux-arm-kernel

Hi,

On Thu, Oct 25, 2012 at 07:57:31PM +0000, Paul Walmsley wrote:
> [ As an aside, neither the OMAP watchdog driver, nor the TWL watchdog 
> driver have been updated to use the new watchdog core code.  So they both 
> can't be loaded at the same time until one or both are fixed. ]

FYI, this is being done currently:

	- OMAP wdt: https://lkml.org/lkml/2012/10/10/402
	- TWL wdt: http://marc.info/?l=linux-omap&m=134734329319385&w=2

A.

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-25 20:08                   ` Aaro Koskinen
@ 2012-10-25 20:09                     ` Paul Walmsley
  0 siblings, 0 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-25 20:09 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, 25 Oct 2012, Aaro Koskinen wrote:

> On Thu, Oct 25, 2012 at 07:57:31PM +0000, Paul Walmsley wrote:
> > [ As an aside, neither the OMAP watchdog driver, nor the TWL watchdog 
> > driver have been updated to use the new watchdog core code.  So they both 
> > can't be loaded at the same time until one or both are fixed. ]
> 
> FYI, this is being done currently:
> 
> 	- OMAP wdt: https://lkml.org/lkml/2012/10/10/402
> 	- TWL wdt: http://marc.info/?l=linux-omap&m=134734329319385&w=2

Thanks, that's good news.


- Paul

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr
  2012-10-16  1:32 ` [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr Paul Walmsley
@ 2012-10-25 20:14   ` Jon Hunter
  2012-10-25 20:16     ` Paul Walmsley
  0 siblings, 1 reply; 28+ messages in thread
From: Jon Hunter @ 2012-10-25 20:14 UTC (permalink / raw)
  To: linux-arm-kernel

Hi Paul,

On 10/15/2012 08:32 PM, Paul Walmsley wrote:
> Previously the OMAP watchdog driver used a non-standard way to report
> the chip reset source via the GETBOOTSTATUS ioctl.  This patch
> converts the driver to use the standard WDIOF_* flags for this
> purpose.
> 
> This patch may break existing userspace code that uses the existing
> non-standard data format returned by the OMAP watchdog driver's
> GETBOOTSTATUS ioctl.  To fetch detailed reset source information,
> userspace code will need to retrieve it directly from the CGRM or PRM
> drivers when those are completed.
> 
> Previously, to fetch the reset source, the driver either read a
> register outside the watchdog IP block (OMAP1), or called a function
> exported directly from arch/arm/mach-omap2.  Both approaches are
> broken.  This patch also converts the driver to use a platform_data
> function pointer.  This approach is temporary, and is due to the lack
> of drivers for the OMAP16xx+ Clock Generation and Reset Management IP
> block and the OMAP2+ Power and Reset Management IP block.  Once
> drivers are available for those IP blocks, the watchdog driver can be
> converted to call exported drivers from those functions directly.
> At that point, the platform_data function pointer can be removed.
> 
> In the short term, this patch is needed to allow the PRM code to be
> removed from arch/arm/mach-omap2 (it is being moved to a driver).
> 
> Signed-off-by: Paul Walmsley <paul@pwsan.com>
> Cc: Wim Van Sebroeck <wim@iguana.be>
> ---
>  drivers/watchdog/omap_wdt.c |   26 ++++++++++++--------------
>  1 file changed, 12 insertions(+), 14 deletions(-)
> 
> diff --git a/drivers/watchdog/omap_wdt.c b/drivers/watchdog/omap_wdt.c
> index f5db18db..5d33bc0 100644
> --- a/drivers/watchdog/omap_wdt.c
> +++ b/drivers/watchdog/omap_wdt.c
> @@ -46,8 +46,8 @@
>  #include <linux/slab.h>
>  #include <linux/pm_runtime.h>
>  #include <mach/hardware.h>
> -#include <plat/cpu.h>
> -#include <plat/prcm.h>
> +
> +#include <linux/platform_data/omap-wd-timer.h>
>  
>  #include "omap_wdt.h"
>  
> @@ -202,8 +202,10 @@ static ssize_t omap_wdt_write(struct file *file, const char __user *data,
>  static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
>  						unsigned long arg)
>  {
> +	struct omap_wd_timer_platform_data *pdata;
>  	struct omap_wdt_dev *wdev;
> -	int new_margin;
> +	u32 rs;
> +	int new_margin, bs;
>  	static const struct watchdog_info ident = {
>  		.identity = "OMAP Watchdog",
>  		.options = WDIOF_SETTIMEOUT,
> @@ -211,6 +213,7 @@ static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
>  	};
>  
>  	wdev = file->private_data;
> +	pdata = wdev->dev->platform_data;
>  
>  	switch (cmd) {
>  	case WDIOC_GETSUPPORT:
> @@ -219,17 +222,12 @@ static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
>  	case WDIOC_GETSTATUS:
>  		return put_user(0, (int __user *)arg);
>  	case WDIOC_GETBOOTSTATUS:
> -#ifdef CONFIG_ARCH_OMAP1
> -		if (cpu_is_omap16xx())
> -			return put_user(__raw_readw(ARM_SYSST),
> -					(int __user *)arg);
> -#endif
> -#ifdef CONFIG_ARCH_OMAP2PLUS
> -		if (cpu_is_omap24xx())
> -			return put_user(omap_prcm_get_reset_sources(),
> -					(int __user *)arg);
> -#endif
> -		return put_user(0, (int __user *)arg);
> +		if (!pdata->read_reset_sources)
> +			return put_user(0, (int __user *)arg);

In the case of booting with device-tree, pdata could be null and so
should we check for this too? In other words ...

+		if (!pdata || !pdata->read_reset_sources)
+			return put_user(0, (int __user *)arg);

Cheers
Jon

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr
  2012-10-25 20:14   ` Jon Hunter
@ 2012-10-25 20:16     ` Paul Walmsley
  2012-10-25 20:29       ` Paul Walmsley
  0 siblings, 1 reply; 28+ messages in thread
From: Paul Walmsley @ 2012-10-25 20:16 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, 25 Oct 2012, Jon Hunter wrote:

> > +		if (!pdata->read_reset_sources)
> > +			return put_user(0, (int __user *)arg);
> 
> In the case of booting with device-tree, pdata could be null and so
> should we check for this too? In other words ...
> 
> +		if (!pdata || !pdata->read_reset_sources)
> +			return put_user(0, (int __user *)arg);

Thanks, good catch, will integrate that fix.


- Paul

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr
  2012-10-25 20:16     ` Paul Walmsley
@ 2012-10-25 20:29       ` Paul Walmsley
  2012-10-25 20:59         ` Felipe Balbi
  0 siblings, 1 reply; 28+ messages in thread
From: Paul Walmsley @ 2012-10-25 20:29 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, 25 Oct 2012, Paul Walmsley wrote:

> On Thu, 25 Oct 2012, Jon Hunter wrote:
> 
> > In the case of booting with device-tree, pdata could be null and so
> > should we check for this too? In other words ...
> > 
> > +		if (!pdata || !pdata->read_reset_sources)
> > +			return put_user(0, (int __user *)arg);
> 
> Thanks, good catch, will integrate that fix.

Here's the updated patch.

- Paul

From: Paul Walmsley <paul@pwsan.com>
Date: Sun, 7 Oct 2012 20:13:26 -0600
Subject: [PATCH] watchdog: OMAP: use standard GETBOOTSTATUS interface; use
 platform_data fn ptr

Previously the OMAP watchdog driver used a non-standard way to report
the chip reset source via the GETBOOTSTATUS ioctl.  This patch
converts the driver to use the standard WDIOF_* flags for this
purpose.

This patch may break existing userspace code that uses the existing
non-standard data format returned by the OMAP watchdog driver's
GETBOOTSTATUS ioctl.  To fetch detailed reset source information,
userspace code will need to retrieve it directly from the CGRM or PRM
drivers when those are completed.

Previously, to fetch the reset source, the driver either read a
register outside the watchdog IP block (OMAP1), or called a function
exported directly from arch/arm/mach-omap2.  Both approaches are
broken.  This patch also converts the driver to use a platform_data
function pointer.  This approach is temporary, and is due to the lack
of drivers for the OMAP16xx+ Clock Generation and Reset Management IP
block and the OMAP2+ Power and Reset Management IP block.  Once
drivers are available for those IP blocks, the watchdog driver can be
converted to call exported drivers from those functions directly.
At that point, the platform_data function pointer can be removed.

In the short term, this patch is needed to allow the PRM code to be
removed from arch/arm/mach-omap2 (it is being moved to a driver).

This version integrates a fix from Jon Hunter <jon-hunter@ti.com>
that avoids a NULL pointer dereference in a DT-only boot.

Signed-off-by: Paul Walmsley <paul@pwsan.com>
Cc: Wim Van Sebroeck <wim@iguana.be>
Cc: Jon Hunter <jon-hunter@ti.com>
---
 drivers/watchdog/omap_wdt.c |   26 ++++++++++++--------------
 1 file changed, 12 insertions(+), 14 deletions(-)

diff --git a/drivers/watchdog/omap_wdt.c b/drivers/watchdog/omap_wdt.c
index f5db18db..477a1d4 100644
--- a/drivers/watchdog/omap_wdt.c
+++ b/drivers/watchdog/omap_wdt.c
@@ -46,8 +46,8 @@
 #include <linux/slab.h>
 #include <linux/pm_runtime.h>
 #include <mach/hardware.h>
-#include <plat/cpu.h>
-#include <plat/prcm.h>
+
+#include <linux/platform_data/omap-wd-timer.h>
 
 #include "omap_wdt.h"
 
@@ -202,8 +202,10 @@ static ssize_t omap_wdt_write(struct file *file, const char __user *data,
 static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
 						unsigned long arg)
 {
+	struct omap_wd_timer_platform_data *pdata;
 	struct omap_wdt_dev *wdev;
-	int new_margin;
+	u32 rs;
+	int new_margin, bs;
 	static const struct watchdog_info ident = {
 		.identity = "OMAP Watchdog",
 		.options = WDIOF_SETTIMEOUT,
@@ -211,6 +213,7 @@ static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
 	};
 
 	wdev = file->private_data;
+	pdata = wdev->dev->platform_data;
 
 	switch (cmd) {
 	case WDIOC_GETSUPPORT:
@@ -219,17 +222,12 @@ static long omap_wdt_ioctl(struct file *file, unsigned int cmd,
 	case WDIOC_GETSTATUS:
 		return put_user(0, (int __user *)arg);
 	case WDIOC_GETBOOTSTATUS:
-#ifdef CONFIG_ARCH_OMAP1
-		if (cpu_is_omap16xx())
-			return put_user(__raw_readw(ARM_SYSST),
-					(int __user *)arg);
-#endif
-#ifdef CONFIG_ARCH_OMAP2PLUS
-		if (cpu_is_omap24xx())
-			return put_user(omap_prcm_get_reset_sources(),
-					(int __user *)arg);
-#endif
-		return put_user(0, (int __user *)arg);
+		if (!pdata || !pdata->read_reset_sources)
+			return put_user(0, (int __user *)arg);
+		rs = pdata->read_reset_sources();
+		bs = (rs & (1 << OMAP_MPU_WD_RST_SRC_ID_SHIFT)) ?
+			WDIOF_CARDRESET : 0;
+		return put_user(bs, (int __user *)arg);
 	case WDIOC_KEEPALIVE:
 		spin_lock(&wdt_lock);
 		omap_wdt_ping(wdev);
-- 
1.7.10.4

^ permalink raw reply related	[flat|nested] 28+ messages in thread

* [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr
  2012-10-25 20:29       ` Paul Walmsley
@ 2012-10-25 20:59         ` Felipe Balbi
  2012-10-25 21:09           ` Paul Walmsley
  0 siblings, 1 reply; 28+ messages in thread
From: Felipe Balbi @ 2012-10-25 20:59 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, Oct 25, 2012 at 08:29:26PM +0000, Paul Walmsley wrote:
> On Thu, 25 Oct 2012, Paul Walmsley wrote:
> 
> > On Thu, 25 Oct 2012, Jon Hunter wrote:
> > 
> > > In the case of booting with device-tree, pdata could be null and so
> > > should we check for this too? In other words ...
> > > 
> > > +		if (!pdata || !pdata->read_reset_sources)
> > > +			return put_user(0, (int __user *)arg);
> > 
> > Thanks, good catch, will integrate that fix.
> 
> Here's the updated patch.
> 
> - Paul
> 
> From: Paul Walmsley <paul@pwsan.com>
> Date: Sun, 7 Oct 2012 20:13:26 -0600
> Subject: [PATCH] watchdog: OMAP: use standard GETBOOTSTATUS interface; use
>  platform_data fn ptr
> 
> Previously the OMAP watchdog driver used a non-standard way to report
> the chip reset source via the GETBOOTSTATUS ioctl.  This patch
> converts the driver to use the standard WDIOF_* flags for this
> purpose.
> 
> This patch may break existing userspace code that uses the existing
> non-standard data format returned by the OMAP watchdog driver's
> GETBOOTSTATUS ioctl.  To fetch detailed reset source information,
> userspace code will need to retrieve it directly from the CGRM or PRM
> drivers when those are completed.
> 
> Previously, to fetch the reset source, the driver either read a
> register outside the watchdog IP block (OMAP1), or called a function
> exported directly from arch/arm/mach-omap2.  Both approaches are
> broken.  This patch also converts the driver to use a platform_data
> function pointer.  This approach is temporary, and is due to the lack
> of drivers for the OMAP16xx+ Clock Generation and Reset Management IP
> block and the OMAP2+ Power and Reset Management IP block.  Once
> drivers are available for those IP blocks, the watchdog driver can be
> converted to call exported drivers from those functions directly.

should be "exported functions from those drivers directly."

-- 
balbi
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 836 bytes
Desc: Digital signature
URL: <http://lists.infradead.org/pipermail/linux-arm-kernel/attachments/20121025/83e5922c/attachment-0001.sig>

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr
  2012-10-25 20:59         ` Felipe Balbi
@ 2012-10-25 21:09           ` Paul Walmsley
  0 siblings, 0 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-10-25 21:09 UTC (permalink / raw)
  To: linux-arm-kernel

On Thu, 25 Oct 2012, Felipe Balbi wrote:

> should be "exported functions from those drivers directly."

Thanks, will update the patch description.


- Paul

^ permalink raw reply	[flat|nested] 28+ messages in thread

* [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer
  2012-10-16  1:32 ` [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer Paul Walmsley
  2012-10-25 15:38   ` Aaro Koskinen
@ 2012-11-08 19:26   ` Paul Walmsley
  1 sibling, 0 replies; 28+ messages in thread
From: Paul Walmsley @ 2012-11-08 19:26 UTC (permalink / raw)
  To: linux-arm-kernel

On Mon, 15 Oct 2012, Paul Walmsley wrote:

> The OMAP watchdog timer driver directly calls a function exported by
> code in arch/arm/mach-omap2.  This is not good; it tightly couples
> this driver to the mach-omap2 integration code.  Instead, add a
> temporary platform_data function pointer to abstract this function
> call.  A subsequent patch will convert the watchdog driver to use this
> function pointer.
> 
> This patch also moves the device creation code out of
> arch/arm/mach-omap2/devices.c and into arch/arm/mach-omap2/wd_timer.c.
> This is another step towards the removal of
> arch/arm/mach-omap2/devices.c.
> 
> Signed-off-by: Paul Walmsley <paul@pwsan.com>
> Cc: Wim Van Sebroeck <wim@iguana.be>

This patch missed the change from commit 
6e152231995aa4ed5eafd87a6a8348563248f843 ("ARM: OMAP: avoid build wdt 
platform device if with dt support") to skip the mach-omap2/ device build 
if the DT blob was present.  This resulted in the watchdog getting 
probed twice.  This didn't result in any problems, aside from a 
message in the kernel log.  

Anyway, here's an update with that change added.


- Paul

From: Paul Walmsley <paul@pwsan.com>
Date: Mon, 29 Oct 2012 20:49:44 -0600
Subject: [PATCH] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata
 function pointer

The OMAP watchdog timer driver directly calls a function exported by
code in arch/arm/mach-omap2.  This is not good; it tightly couples
this driver to the mach-omap2 integration code.  Instead, add a
temporary platform_data function pointer to abstract this function
call.  A subsequent patch will convert the watchdog driver to use this
function pointer.

This patch also moves the device creation code out of
arch/arm/mach-omap2/devices.c and into arch/arm/mach-omap2/wd_timer.c.
This is another step towards the removal of
arch/arm/mach-omap2/devices.c.

Cc: Wim Van Sebroeck <wim@iguana.be>
Acked-by: Wim Van Sebroeck <wim@iguana.be>
[paul at pwsan.com: skip wd_timer device creation when DT blob is present]
Signed-off-by: Paul Walmsley <paul@pwsan.com>
---
 arch/arm/mach-omap1/devices.c               |   21 ++++++++++++---
 arch/arm/mach-omap2/devices.c               |   26 ------------------
 arch/arm/mach-omap2/wd_timer.c              |   35 +++++++++++++++++++++++-
 include/linux/platform_data/omap-wd-timer.h |   38 +++++++++++++++++++++++++++
 4 files changed, 90 insertions(+), 30 deletions(-)
 create mode 100644 include/linux/platform_data/omap-wd-timer.h

diff --git a/arch/arm/mach-omap1/devices.c b/arch/arm/mach-omap1/devices.c
index 645668e..7450318 100644
--- a/arch/arm/mach-omap1/devices.c
+++ b/arch/arm/mach-omap1/devices.c
@@ -17,6 +17,8 @@
 #include <linux/platform_device.h>
 #include <linux/spi/spi.h>
 
+#include <linux/platform_data/omap-wd-timer.h>
+
 #include <asm/mach/map.h>
 
 #include <mach/tc.h>
@@ -448,18 +450,31 @@ static struct resource wdt_resources[] = {
 };
 
 static struct platform_device omap_wdt_device = {
-	.name	   = "omap_wdt",
-	.id	     = -1,
+	.name		= "omap_wdt",
+	.id		= -1,
 	.num_resources	= ARRAY_SIZE(wdt_resources),
 	.resource	= wdt_resources,
 };
 
 static int __init omap_init_wdt(void)
 {
+	struct omap_wd_timer_platform_data pdata;
+	int ret;
+
 	if (!cpu_is_omap16xx())
 		return -ENODEV;
 
-	return platform_device_register(&omap_wdt_device);
+	pdata.read_reset_sources = omap1_get_reset_sources;
+
+	ret = platform_device_register(&omap_wdt_device);
+	if (!ret) {
+		ret = platform_device_add_data(&omap_wdt_device, &pdata,
+					       sizeof(pdata));
+		if (ret)
+			platform_device_del(&omap_wdt_device);
+	}
+
+	return ret;
 }
 subsys_initcall(omap_init_wdt);
 #endif
diff --git a/arch/arm/mach-omap2/devices.c b/arch/arm/mach-omap2/devices.c
index 2ad491d..cf365c3 100644
--- a/arch/arm/mach-omap2/devices.c
+++ b/arch/arm/mach-omap2/devices.c
@@ -646,29 +646,3 @@ static int __init omap2_init_devices(void)
 	return 0;
 }
 arch_initcall(omap2_init_devices);
-
-#if defined(CONFIG_OMAP_WATCHDOG) || defined(CONFIG_OMAP_WATCHDOG_MODULE)
-static int __init omap_init_wdt(void)
-{
-	int id = -1;
-	struct platform_device *pdev;
-	struct omap_hwmod *oh;
-	char *oh_name = "wd_timer2";
-	char *dev_name = "omap_wdt";
-
-	if (!cpu_class_is_omap2() || of_have_populated_dt())
-		return 0;
-
-	oh = omap_hwmod_lookup(oh_name);
-	if (!oh) {
-		pr_err("Could not look up wd_timer%d hwmod\n", id);
-		return -EINVAL;
-	}
-
-	pdev = omap_device_build(dev_name, id, oh, NULL, 0, NULL, 0, 0);
-	WARN(IS_ERR(pdev), "Can't build omap_device for %s:%s.\n",
-				dev_name, oh->name);
-	return 0;
-}
-subsys_initcall(omap_init_wdt);
-#endif
diff --git a/arch/arm/mach-omap2/wd_timer.c b/arch/arm/mach-omap2/wd_timer.c
index f6b6c37..5a8629f 100644
--- a/arch/arm/mach-omap2/wd_timer.c
+++ b/arch/arm/mach-omap2/wd_timer.c
@@ -11,10 +11,14 @@
 #include <linux/io.h>
 #include <linux/err.h>
 
-#include "omap_hwmod.h"
+#include <linux/platform_data/omap-wd-timer.h>
 
+#include "omap_hwmod.h"
+#include "omap_device.h"
 #include "wd_timer.h"
 #include "common.h"
+#include "prm.h"
+#include "soc.h"
 
 /*
  * In order to avoid any assumptions from bootloader regarding WDT
@@ -99,3 +103,32 @@ int omap2_wd_timer_reset(struct omap_hwmod *oh)
 	return (c == MAX_MODULE_SOFTRESET_WAIT) ? -ETIMEDOUT :
 		omap2_wd_timer_disable(oh);
 }
+
+static int __init omap_init_wdt(void)
+{
+	int id = -1;
+	struct platform_device *pdev;
+	struct omap_hwmod *oh;
+	char *oh_name = "wd_timer2";
+	char *dev_name = "omap_wdt";
+	struct omap_wd_timer_platform_data pdata;
+
+	if (!cpu_class_is_omap2() || of_have_populated_dt())
+		return 0;
+
+	oh = omap_hwmod_lookup(oh_name);
+	if (!oh) {
+		pr_err("Could not look up wd_timer%d hwmod\n", id);
+		return -EINVAL;
+	}
+
+	pdata.read_reset_sources = prm_read_reset_sources;
+
+	pdev = omap_device_build(dev_name, id, oh, &pdata,
+				 sizeof(struct omap_wd_timer_platform_data),
+				 NULL, 0, 0);
+	WARN(IS_ERR(pdev), "Can't build omap_device for %s:%s.\n",
+	     dev_name, oh->name);
+	return 0;
+}
+subsys_initcall(omap_init_wdt);
diff --git a/include/linux/platform_data/omap-wd-timer.h b/include/linux/platform_data/omap-wd-timer.h
new file mode 100644
index 0000000..d75f5f8
--- /dev/null
+++ b/include/linux/platform_data/omap-wd-timer.h
@@ -0,0 +1,38 @@
+/*
+ * OMAP2+ WDTIMER-specific function prototypes
+ *
+ * Copyright (C) 2012 Texas Instruments, Inc.
+ * Paul Walmsley
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+
+#ifndef __LINUX_PLATFORM_DATA_OMAP_WD_TIMER_H
+#define __LINUX_PLATFORM_DATA_OMAP_WD_TIMER_H
+
+#include <linux/types.h>
+
+/*
+ * Standardized OMAP reset source bits
+ *
+ * This is a subset of the ones listed in arch/arm/mach-omap2/prm.h
+ * and are the only ones needed in the watchdog driver.
+ */
+#define OMAP_MPU_WD_RST_SRC_ID_SHIFT				3
+
+/**
+ * struct omap_wd_timer_platform_data - WDTIMER integration to the host SoC
+ * @read_reset_sources - fn ptr for the SoC to indicate the last reset cause
+ *
+ * The function pointed to by @read_reset_sources must return its data
+ * in a standard format - search for RST_SRC_ID_SHIFT in
+ * arch/arm/mach-omap2
+ */
+struct omap_wd_timer_platform_data {
+	u32 (*read_reset_sources)(void);
+};
+
+#endif
-- 
1.7.10.4

^ permalink raw reply related	[flat|nested] 28+ messages in thread

end of thread, other threads:[~2012-11-08 19:26 UTC | newest]

Thread overview: 28+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2012-10-16  1:32 [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Paul Walmsley
2012-10-16  1:32 ` [PATCH 1/7] ARM: OMAP2+: PRM: prepare for use of prm_ll_data function pointers Paul Walmsley
2012-10-16  1:32 ` [PATCH 2/7] ARM: OMAP2+: CM: prepare for use of cm_ll_data " Paul Walmsley
2012-10-16  1:32 ` [PATCH 3/7] ARM: OMAP1: create read_reset_sources() function (for initial use by watchdog) Paul Walmsley
2012-10-16  1:32 ` [PATCH 4/7] ARM: OMAP2+: PRM: create PRM reset source API for the watchdog timer driver Paul Walmsley
2012-10-16  1:32 ` [PATCH 5/7] ARM: OMAP2+: WDT: move init; add read_reset_sources pdata function pointer Paul Walmsley
2012-10-25 15:38   ` Aaro Koskinen
2012-10-25 18:51     ` Paul Walmsley
2012-10-25 18:57       ` Tony Lindgren
2012-10-25 19:09         ` Paul Walmsley
2012-10-25 19:19           ` Tony Lindgren
2012-10-25 19:31             ` Paul Walmsley
2012-10-25 19:34               ` Tony Lindgren
2012-10-25 19:42                 ` Tony Lindgren
2012-10-25 19:57                 ` Paul Walmsley
2012-10-25 20:08                   ` Aaro Koskinen
2012-10-25 20:09                     ` Paul Walmsley
2012-11-08 19:26   ` Paul Walmsley
2012-10-16  1:32 ` [PATCH 6/7] watchdog: OMAP: use standard GETBOOTSTATUS interface; use platform_data fn ptr Paul Walmsley
2012-10-25 20:14   ` Jon Hunter
2012-10-25 20:16     ` Paul Walmsley
2012-10-25 20:29       ` Paul Walmsley
2012-10-25 20:59         ` Felipe Balbi
2012-10-25 21:09           ` Paul Walmsley
2012-10-16  1:32 ` [PATCH 7/7] ARM: OMAP2+: PRCM: remove omap_prcm_get_reset_sources() Paul Walmsley
2012-10-22 12:14 ` [PATCH 0/7] ARM: OMAP: second set of PRM/CM/CGRM cleanup patches for 3.8 Benoit Cousson
2012-10-22 17:06   ` Paul Walmsley
2012-10-22 17:29     ` Benoit Cousson

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).