Skip to contentSkip to conversation

x86/platform/intel-mid: Fix RTC / WDT handling

PATCH New Andy Shevchenko 2 participants 9 messages Jan 19, 2017 – Jan 20, 2017

Subsystems (2)
lore
Share & tools
lore
#0 lore raw

v4 cover x86/platform/intel-mid: Fix RTC / WDT handling

Current RTC approach breaks some platforms. Rewrite it completely and make avaiable only for intended platforms.

Tested on Intel Merrifield, ASuS T100TA (normal and acpi=off cases).

Since v3:
- move to arch_initcall()
- do the same for watchdog registration code (new patch 4)

Since v2:
- add mp_map_gsi_to_irq() fix to the series as patch 1
- add patch 3
- rewrite RTC approach as another platform code for Intel MID

Andy Shevchenko (4):
x86/ioapic: Return suitable error code in mp_map_gsi_to_irq() x86/platform/intel-mid: Allocate RTC interrupt for Merrifield x86/platform/intel-mid: Don't shadow error code of mp_map_gsi_to_irq() x86/platform/intel-mid: Move watchdog registration to arch_initcall()

 arch/x86/kernel/apic/io_apic.c                     |  4 +-
 arch/x86/platform/intel-mid/device_libs/Makefile   |  1 +
 .../intel-mid/device_libs/platform_mrfld_rtc.c     | 48 ++++++++++++++++++++++
 .../intel-mid/device_libs/platform_mrfld_wdt.c     | 12 +++---
 arch/x86/platform/intel-mid/sfi.c                  | 14 -------
 5 files changed, 57 insertions(+), 22 deletions(-)
 create mode 100644 arch/x86/platform/intel-mid/device_libs/platform_mrfld_rtc.c
Signature · 1 line
2.11.0
#1 lore raw

PATCH v4 1/4 x86/ioapic: Return suitable error code in mp_map_gsi_to_irq()

mp_map_gsi_to_irq() in some cases might return legacy -1, which would be wrongly interpreted as -EPERM.

Correct those cases to return proper error code.

---
 arch/x86/kernel/apic/io_apic.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)
arch/x86/kernel/apic/io_apic.c +2 -2
index 945e512a112a..f62c38d325da 100644
@@ -1107,12 +1107,12 @@ int mp_map_gsi_to_irq(u32 gsi, unsigned int flags, struct irq_alloc_info *info)
 
 	ioapic = mp_find_ioapic(gsi);
 	if (ioapic < 0)
-		return -1;
+		return -ENODEV;
 
 	pin = mp_find_ioapic_pin(ioapic, gsi);
 	idx = find_irq_entry(ioapic, pin, mp_INT);
 	if ((flags & IOAPIC_MAP_CHECK) && idx < 0)
-		return -1;
+		return -ENODEV;
 
 	return mp_map_pin_to_irq(gsi, idx, ioapic, pin, flags, info);
 }
Signature · 1 line
2.11.0
#2 lore raw

[tip:x86/platform] x86/ioapic: Return suitable error code in mp_map_gsi_to_irq()

x86/ioapic: Return suitable error code in mp_map_gsi_to_irq()
Commit-ID:  358e96deaed3330a59d9dd6a7e419f4da08d6497
Gitweb:     http://git.kernel.org/tip/358e96deaed3330a59d9dd6a7e419f4da08d6497
Author:     Andy Shevchenko <[email protected]>
AuthorDate: Thu, 19 Jan 2017 21:24:22 +0200
Committer:  Thomas Gleixner <[email protected]>
CommitDate: Fri, 20 Jan 2017 10:07:41 +0100

x86/ioapic: Return suitable error code in mp_map_gsi_to_irq()

mp_map_gsi_to_irq() in some cases might return legacy -1, which would be wrongly interpreted as -EPERM.

Correct those cases to return proper error code.

---
 arch/x86/kernel/apic/io_apic.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)
arch/x86/kernel/apic/io_apic.c +2 -2
index 945e512..f62c38d 100644
@@ -1107,12 +1107,12 @@ int mp_map_gsi_to_irq(u32 gsi, unsigned int flags, struct irq_alloc_info *info)
 
 	ioapic = mp_find_ioapic(gsi);
 	if (ioapic < 0)
-		return -1;
+		return -ENODEV;
 
 	pin = mp_find_ioapic_pin(ioapic, gsi);
 	idx = find_irq_entry(ioapic, pin, mp_INT);
 	if ((flags & IOAPIC_MAP_CHECK) && idx < 0)
-		return -1;
+		return -ENODEV;
 
 	return mp_map_pin_to_irq(gsi, idx, ioapic, pin, flags, info);
 }
#3 lore raw

PATCH v4 2/4 x86/platform/intel-mid: Allocate RTC interrupt for Merrifield

In reply to Andy Shevchenko

Legacy RTC requires interrupt line 8 to be dedicated for it. On Intel MID platforms the legacy PIC is absent and in order to make RTC work we need to allocate interrupt separately.

Current solution brought by the commit:

de1c2540aa4f ("x86/platform/intel-mid: Enable RTC on Intel Merrifield")

does it in a wrong place, and since it's done unconditionally for all x86 devices, some of them, e.g. PNP based, might get it wrong -- at the beginning x86_platform.legacy.rtc flag is set for all x86 devices.

Move intel_mid_legacy_rtc_init() to its own module and call it before x86 RTC CMOS initialization.

Cc Luis R. Rodriguez <[email protected]>
---
 arch/x86/platform/intel-mid/device_libs/Makefile   |  1 +
 .../intel-mid/device_libs/platform_mrfld_rtc.c     | 48 ++++++++++++++++++++++
 arch/x86/platform/intel-mid/sfi.c                  | 14 -------
 3 files changed, 49 insertions(+), 14 deletions(-)
 create mode 100644 arch/x86/platform/intel-mid/device_libs/platform_mrfld_rtc.c
arch/x86/platform/intel-mid/device_libs/Makefile +1 -0
index d4af7785844e..a7dbec4dce27 100644
@@ -26,4 +26,5 @@ obj-$(subst m,y,$(CONFIG_GPIO_PCA953X)) += platform_pcal9555a.o
 obj-$(subst m,y,$(CONFIG_GPIO_PCA953X)) += platform_tca6416.o
 # MISC Devices
 obj-$(subst m,y,$(CONFIG_KEYBOARD_GPIO)) += platform_gpio_keys.o
+obj-$(subst m,y,$(CONFIG_RTC_DRV_CMOS)) += platform_mrfld_rtc.o
 obj-$(subst m,y,$(CONFIG_INTEL_MID_WATCHDOG)) += platform_mrfld_wdt.o
arch/x86/platform/intel-mid/device_libs/platform_mrfld_rtc.c new file +48 -0

48 lines not on this page · raw message

arch/x86/platform/intel-mid/sfi.c +0 -14
index e4d4cabbb370..19b43e3a9f0f 100644
@@ -41,7 +41,6 @@
 #include <asm/intel_scu_ipc.h>
 #include <asm/apb_timer.h>
 #include <asm/reboot.h>
-#include <asm/time.h>
 
 #define	SFI_SIG_OEM0	"OEM0"
 #define MAX_IPCDEVS	24
@@ -540,21 +539,8 @@ static int __init sfi_parse_devs(struct sfi_table_header *table)
 	return 0;
 }
 
-static int __init intel_mid_legacy_rtc_init(void)
-{
-	struct irq_alloc_info info;
-
-	if (!x86_platform.legacy.rtc)
-		return -ENODEV;
-
-	ioapic_set_alloc_attr(&info, NUMA_NO_NODE, 1, 0);
-	return mp_map_gsi_to_irq(RTC_IRQ, IOAPIC_MAP_ALLOC, &info);
-}
-
 static int __init intel_mid_platform_init(void)
 {
-	intel_mid_legacy_rtc_init();
-
 	sfi_table_parse(SFI_SIG_GPIO, NULL, NULL, sfi_parse_gpio);
 	sfi_table_parse(SFI_SIG_DEVS, NULL, NULL, sfi_parse_devs);
 	return 0;
Signature · 1 line
2.11.0
#4 lore raw

[tip:x86/platform] x86/platform/intel-mid: Allocate RTC interrupt for Merrifield

x86/platform/intel-mid: Allocate RTC interrupt for Merrifield
Commit-ID:  910a26f6e952148a0c8815281737aaead640626c
Gitweb:     http://git.kernel.org/tip/910a26f6e952148a0c8815281737aaead640626c
Author:     Andy Shevchenko <[email protected]>
AuthorDate: Thu, 19 Jan 2017 21:24:23 +0200
Committer:  Thomas Gleixner <[email protected]>
CommitDate: Fri, 20 Jan 2017 10:07:41 +0100

x86/platform/intel-mid: Allocate RTC interrupt for Merrifield

Legacy RTC requires interrupt line 8 to be dedicated for it. On Intel MID platforms the legacy PIC is absent and in order to make RTC work we need to allocate interrupt separately.

Current solution brought by commit de1c2540aa4f does it in a wrong place, and since it's done unconditionally for all x86 devices, some of them, e.g. PNP based, might get it wrong because they execute the MID specific code due to x86_platform.legacy.rtc flag being set.

Move intel_mid_legacy_rtc_init() to its own module and call it before x86 RTC CMOS initialization.

Fixes de1c2540aa4f ("x86/platform/intel-mid: Enable RTC on Intel Merrifield")
Cc "Luis R . Rodriguez" <[email protected]>
---
 arch/x86/platform/intel-mid/device_libs/Makefile   |  1 +
 .../intel-mid/device_libs/platform_mrfld_rtc.c     | 48 ++++++++++++++++++++++
 arch/x86/platform/intel-mid/sfi.c                  | 14 -------
 3 files changed, 49 insertions(+), 14 deletions(-)
arch/x86/platform/intel-mid/device_libs/Makefile +1 -0
index d4af778..a7dbec4 100644
@@ -26,4 +26,5 @@ obj-$(subst m,y,$(CONFIG_GPIO_PCA953X)) += platform_pcal9555a.o
 obj-$(subst m,y,$(CONFIG_GPIO_PCA953X)) += platform_tca6416.o
 # MISC Devices
 obj-$(subst m,y,$(CONFIG_KEYBOARD_GPIO)) += platform_gpio_keys.o
+obj-$(subst m,y,$(CONFIG_RTC_DRV_CMOS)) += platform_mrfld_rtc.o
 obj-$(subst m,y,$(CONFIG_INTEL_MID_WATCHDOG)) += platform_mrfld_wdt.o
arch/x86/platform/intel-mid/device_libs/platform_mrfld_rtc.c new file +48 -0

48 lines not on this page · raw message

arch/x86/platform/intel-mid/sfi.c +0 -14
index e4d4cab..19b43e3 100644
@@ -41,7 +41,6 @@
 #include <asm/intel_scu_ipc.h>
 #include <asm/apb_timer.h>
 #include <asm/reboot.h>
-#include <asm/time.h>
 
 #define	SFI_SIG_OEM0	"OEM0"
 #define MAX_IPCDEVS	24
@@ -540,21 +539,8 @@ static int __init sfi_parse_devs(struct sfi_table_header *table)
 	return 0;
 }
 
-static int __init intel_mid_legacy_rtc_init(void)
-{
-	struct irq_alloc_info info;
-
-	if (!x86_platform.legacy.rtc)
-		return -ENODEV;
-
-	ioapic_set_alloc_attr(&info, NUMA_NO_NODE, 1, 0);
-	return mp_map_gsi_to_irq(RTC_IRQ, IOAPIC_MAP_ALLOC, &info);
-}
-
 static int __init intel_mid_platform_init(void)
 {
-	intel_mid_legacy_rtc_init();
-
 	sfi_table_parse(SFI_SIG_GPIO, NULL, NULL, sfi_parse_gpio);
 	sfi_table_parse(SFI_SIG_DEVS, NULL, NULL, sfi_parse_devs);
 	return 0;
#5 lore raw

PATCH v4 3/4 x86/platform/intel-mid: Don't shadow error code of mp_map_gsi_to_irq()

In reply to Andy Shevchenko

When call mp_map_gsi_to_irq() and return its error code do not shadow it. Note that 0 is not an error.

---
 arch/x86/platform/intel-mid/device_libs/platform_mrfld_wdt.c | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)
arch/x86/platform/intel-mid/device_libs/platform_mrfld_wdt.c +5 -5
index 3f1f1c77d090..8a10a56f2840 100644
@@ -28,9 +28,9 @@ static struct platform_device wdt_dev = {
 
 static int tangier_probe(struct platform_device *pdev)
 {
-	int gsi;
 	struct irq_alloc_info info;
 	struct intel_mid_wdt_pdata *pdata = pdev->dev.platform_data;
+	int gsi, irq;
 
 	if (!pdata)
 		return -EINVAL;
@@ -38,10 +38,10 @@ static int tangier_probe(struct platform_device *pdev)
 	/* IOAPIC builds identity mapping between GSI and IRQ on MID */
 	gsi = pdata->irq;
 	ioapic_set_alloc_attr(&info, cpu_to_node(0), 1, 0);
-	if (mp_map_gsi_to_irq(gsi, IOAPIC_MAP_ALLOC, &info) <= 0) {
-		dev_warn(&pdev->dev, "cannot find interrupt %d in ioapic\n",
-			 gsi);
-		return -EINVAL;
+	irq = mp_map_gsi_to_irq(gsi, IOAPIC_MAP_ALLOC, &info);
+	if (irq < 0) {
+		dev_warn(&pdev->dev, "cannot find interrupt %d in ioapic\n", gsi);
+		return irq;
 	}
 
 	return 0;
Signature · 1 line
2.11.0
#6 lore raw

[tip:x86/platform] x86/platform/intel-mid: Don't shadow error code of mp_map_gsi_to_irq()

x86/platform/intel-mid: Don't shadow error code of mp_map_gsi_to_irq()
Commit-ID:  939533955d1f1d51e8e37d7d675646ce9d55534b
Gitweb:     http://git.kernel.org/tip/939533955d1f1d51e8e37d7d675646ce9d55534b
Author:     Andy Shevchenko <[email protected]>
AuthorDate: Thu, 19 Jan 2017 21:24:24 +0200
Committer:  Thomas Gleixner <[email protected]>
CommitDate: Fri, 20 Jan 2017 10:07:41 +0100

x86/platform/intel-mid: Don't shadow error code of mp_map_gsi_to_irq()

When call mp_map_gsi_to_irq() and return its error code do not shadow it. Note that 0 is not an error.

---
 arch/x86/platform/intel-mid/device_libs/platform_mrfld_wdt.c | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)
arch/x86/platform/intel-mid/device_libs/platform_mrfld_wdt.c +5 -5
index 3f1f1c7..8a10a56 100644
@@ -28,9 +28,9 @@ static struct platform_device wdt_dev = {
 
 static int tangier_probe(struct platform_device *pdev)
 {
-	int gsi;
 	struct irq_alloc_info info;
 	struct intel_mid_wdt_pdata *pdata = pdev->dev.platform_data;
+	int gsi, irq;
 
 	if (!pdata)
 		return -EINVAL;
@@ -38,10 +38,10 @@ static int tangier_probe(struct platform_device *pdev)
 	/* IOAPIC builds identity mapping between GSI and IRQ on MID */
 	gsi = pdata->irq;
 	ioapic_set_alloc_attr(&info, cpu_to_node(0), 1, 0);
-	if (mp_map_gsi_to_irq(gsi, IOAPIC_MAP_ALLOC, &info) <= 0) {
-		dev_warn(&pdev->dev, "cannot find interrupt %d in ioapic\n",
-			 gsi);
-		return -EINVAL;
+	irq = mp_map_gsi_to_irq(gsi, IOAPIC_MAP_ALLOC, &info);
+	if (irq < 0) {
+		dev_warn(&pdev->dev, "cannot find interrupt %d in ioapic\n", gsi);
+		return irq;
 	}
 
 	return 0;
#7 lore raw

PATCH v4 4/4 x86/platform/intel-mid: Move watchdog registration to arch_initcall()

In reply to Andy Shevchenko

There is no need to choose a random initcall level for certainly architecture dependent code.

Move watchdog registration to arch_initcall() from rootfs_initcall().

---
 arch/x86/platform/intel-mid/device_libs/platform_mrfld_wdt.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
arch/x86/platform/intel-mid/device_libs/platform_mrfld_wdt.c +1 -1
index 8a10a56f2840..86edd1e941eb 100644
@@ -82,4 +82,4 @@ static int __init register_mid_wdt(void)
 
 	return 0;
 }
-rootfs_initcall(register_mid_wdt);
+arch_initcall(register_mid_wdt);
Signature · 1 line
2.11.0
#8 lore raw

[tip:x86/platform] x86/platform/intel-mid: Move watchdog registration to arch_initcall()

x86/platform/intel-mid: Move watchdog registration to arch_initcall()
Commit-ID:  e2e2eabb68dfd00502bf8501b015862eb8b3f392
Gitweb:     http://git.kernel.org/tip/e2e2eabb68dfd00502bf8501b015862eb8b3f392
Author:     Andy Shevchenko <[email protected]>
AuthorDate: Thu, 19 Jan 2017 21:24:25 +0200
Committer:  Thomas Gleixner <[email protected]>
CommitDate: Fri, 20 Jan 2017 10:07:42 +0100

x86/platform/intel-mid: Move watchdog registration to arch_initcall()

There is no need to choose a random initcall level for certainly architecture dependent code.

Move watchdog registration to arch_initcall() from rootfs_initcall().

---
 arch/x86/platform/intel-mid/device_libs/platform_mrfld_wdt.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
arch/x86/platform/intel-mid/device_libs/platform_mrfld_wdt.c +1 -1
index 8a10a56..86edd1e9 100644
@@ -82,4 +82,4 @@ static int __init register_mid_wdt(void)
 
 	return 0;
 }
-rootfs_initcall(register_mid_wdt);
+arch_initcall(register_mid_wdt);