Skip to content

Commit

Permalink
Merge tag 'tegra-for-4.12-soc' of git://git.kernel.org/pub/scm/linux/…
Browse files Browse the repository at this point in the history
…kernel/git/tegra/linux into next/drivers

soc/tegra: Core SoC changes for v4.12-rc1

This contains PMC support for Tegra186 as well as a proper driver for
the flow controller found on SoCs up to Tegra210. This also turns the
fuse driver into an explicitly non-modular driver.

* tag 'tegra-for-4.12-soc' of git://git.kernel.org/pub/scm/linux/kernel/git/tegra/linux:
  soc/tegra: Add initial flowctrl support for Tegra132/210
  soc/tegra: flowctrl: Add basic platform driver
  soc/tegra: Move Tegra flowctrl driver
  ARM: tegra: Remove unnecessary inclusion of flowctrl header
  soc: tegra: make fuse-tegra explicitly non-modular
  soc/tegra: Fix link errors with PMC disabled
  soc/tegra: Implement Tegra186 PMC support

Signed-off-by: Olof Johansson <olof@lixom.net>
  • Loading branch information
Olof Johansson committed Apr 19, 2017
2 parents fe8fee6 + 1fd09e5 commit 55de807
Show file tree
Hide file tree
Showing 17 changed files with 353 additions and 47 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
NVIDIA Tegra Power Management Controller (PMC)

Required properties:
- compatible: Should contain one of the following:
- "nvidia,tegra186-pmc": for Tegra186
- reg: Must contain an (offset, length) pair of the register set for each
entry in reg-names.
- reg-names: Must include the following entries:
- "pmc"
- "wake"
- "aotag"
- "scratch"

Optional properties:
- nvidia,invert-interrupt: If present, inverts the PMU interrupt signal.

Example:

SoC DTSI:

pmc@c3600000 {
compatible = "nvidia,tegra186-pmc";
reg = <0 0x0c360000 0 0x10000>,
<0 0x0c370000 0 0x10000>,
<0 0x0c380000 0 0x10000>,
<0 0x0c390000 0 0x10000>;
reg-names = "pmc", "wake", "aotag", "scratch";
};

Board DTS:

pmc@c360000 {
nvidia,invert-interrupt;
};
1 change: 0 additions & 1 deletion arch/arm/mach-tegra/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ asflags-y += -march=armv7-a

obj-y += io.o
obj-y += irq.o
obj-y += flowctrl.o
obj-y += pm.o
obj-y += reset.o
obj-y += reset-handler.o
Expand Down
3 changes: 2 additions & 1 deletion arch/arm/mach-tegra/cpuidle-tegra20.c
Original file line number Diff line number Diff line change
Expand Up @@ -26,12 +26,13 @@
#include <linux/kernel.h>
#include <linux/module.h>

#include <soc/tegra/flowctrl.h>

#include <asm/cpuidle.h>
#include <asm/smp_plat.h>
#include <asm/suspend.h>

#include "cpuidle.h"
#include "flowctrl.h"
#include "iomap.h"
#include "irq.h"
#include "pm.h"
Expand Down
2 changes: 1 addition & 1 deletion arch/arm/mach-tegra/platsmp.c
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
#include <linux/jiffies.h>
#include <linux/smp.h>

#include <soc/tegra/flowctrl.h>
#include <soc/tegra/fuse.h>
#include <soc/tegra/pmc.h>

Expand All @@ -30,7 +31,6 @@
#include <asm/smp_scu.h>

#include "common.h"
#include "flowctrl.h"
#include "iomap.h"
#include "reset.h"

Expand Down
2 changes: 1 addition & 1 deletion arch/arm/mach-tegra/pm.c
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
#include <linux/spinlock.h>
#include <linux/suspend.h>

#include <soc/tegra/flowctrl.h>
#include <soc/tegra/fuse.h>
#include <soc/tegra/pm.h>
#include <soc/tegra/pmc.h>
Expand All @@ -38,7 +39,6 @@
#include <asm/suspend.h>
#include <asm/tlbflush.h>

#include "flowctrl.h"
#include "iomap.h"
#include "pm.h"
#include "reset.h"
Expand Down
2 changes: 1 addition & 1 deletion arch/arm/mach-tegra/reset-handler.S
Original file line number Diff line number Diff line change
Expand Up @@ -17,12 +17,12 @@
#include <linux/init.h>
#include <linux/linkage.h>

#include <soc/tegra/flowctrl.h>
#include <soc/tegra/fuse.h>

#include <asm/asm-offsets.h>
#include <asm/cache.h>

#include "flowctrl.h"
#include "iomap.h"
#include "reset.h"
#include "sleep.h"
Expand Down
3 changes: 2 additions & 1 deletion arch/arm/mach-tegra/sleep-tegra20.S
Original file line number Diff line number Diff line change
Expand Up @@ -20,14 +20,15 @@

#include <linux/linkage.h>

#include <soc/tegra/flowctrl.h>

#include <asm/assembler.h>
#include <asm/proc-fns.h>
#include <asm/cp15.h>
#include <asm/cache.h>

#include "irammap.h"
#include "sleep.h"
#include "flowctrl.h"

#define EMC_CFG 0xc
#define EMC_ADR_CFG 0x10
Expand Down
2 changes: 1 addition & 1 deletion arch/arm/mach-tegra/sleep-tegra30.S
Original file line number Diff line number Diff line change
Expand Up @@ -16,13 +16,13 @@

#include <linux/linkage.h>

#include <soc/tegra/flowctrl.h>
#include <soc/tegra/fuse.h>

#include <asm/asm-offsets.h>
#include <asm/assembler.h>
#include <asm/cache.h>

#include "flowctrl.h"
#include "irammap.h"
#include "sleep.h"

Expand Down
2 changes: 0 additions & 2 deletions arch/arm/mach-tegra/sleep.S
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,6 @@
#include <asm/hardware/cache-l2x0.h>

#include "iomap.h"

#include "flowctrl.h"
#include "sleep.h"

#define CLK_RESET_CCLK_BURST 0x20
Expand Down
2 changes: 0 additions & 2 deletions arch/arm/mach-tegra/tegra.c
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,6 @@
#include "board.h"
#include "common.h"
#include "cpuidle.h"
#include "flowctrl.h"
#include "iomap.h"
#include "irq.h"
#include "pm.h"
Expand All @@ -75,7 +74,6 @@ static void __init tegra_init_early(void)
{
of_register_trusted_foundations();
tegra_cpu_reset_handler_init();
tegra_flowctrl_init();
}

static void __init tegra_dt_init_irq(void)
Expand Down
22 changes: 22 additions & 0 deletions drivers/soc/tegra/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@ config ARCH_TEGRA_2x_SOC
select PINCTRL_TEGRA20
select PL310_ERRATA_727915 if CACHE_L2X0
select PL310_ERRATA_769419 if CACHE_L2X0
select SOC_TEGRA_FLOWCTRL
select SOC_TEGRA_PMC
select TEGRA_TIMER
help
Support for NVIDIA Tegra AP20 and T20 processors, based on the
Expand All @@ -23,6 +25,8 @@ config ARCH_TEGRA_3x_SOC
select ARM_ERRATA_764369 if SMP
select PINCTRL_TEGRA30
select PL310_ERRATA_769419 if CACHE_L2X0
select SOC_TEGRA_FLOWCTRL
select SOC_TEGRA_PMC
select TEGRA_TIMER
help
Support for NVIDIA Tegra T30 processor family, based on the
Expand All @@ -33,6 +37,8 @@ config ARCH_TEGRA_114_SOC
select ARM_ERRATA_798181 if SMP
select HAVE_ARM_ARCH_TIMER
select PINCTRL_TEGRA114
select SOC_TEGRA_FLOWCTRL
select SOC_TEGRA_PMC
select TEGRA_TIMER
help
Support for NVIDIA Tegra T114 processor family, based on the
Expand All @@ -42,6 +48,8 @@ config ARCH_TEGRA_124_SOC
bool "Enable support for Tegra124 family"
select HAVE_ARM_ARCH_TIMER
select PINCTRL_TEGRA124
select SOC_TEGRA_FLOWCTRL
select SOC_TEGRA_PMC
select TEGRA_TIMER
help
Support for NVIDIA Tegra T124 processor family, based on the
Expand All @@ -55,6 +63,8 @@ if ARM64
config ARCH_TEGRA_132_SOC
bool "NVIDIA Tegra132 SoC"
select PINCTRL_TEGRA124
select SOC_TEGRA_FLOWCTRL
select SOC_TEGRA_PMC
help
Enable support for NVIDIA Tegra132 SoC, based on the Denver
ARMv8 CPU. The Tegra132 SoC is similar to the Tegra124 SoC,
Expand All @@ -64,6 +74,8 @@ config ARCH_TEGRA_132_SOC
config ARCH_TEGRA_210_SOC
bool "NVIDIA Tegra210 SoC"
select PINCTRL_TEGRA210
select SOC_TEGRA_FLOWCTRL
select SOC_TEGRA_PMC
help
Enable support for the NVIDIA Tegra210 SoC. Also known as Tegra X1,
the Tegra210 has four Cortex-A57 cores paired with four Cortex-A53
Expand All @@ -83,6 +95,7 @@ config ARCH_TEGRA_186_SOC
select TEGRA_BPMP
select TEGRA_HSP_MBOX
select TEGRA_IVC
select SOC_TEGRA_PMC_TEGRA186
help
Enable support for the NVIDIA Tegar186 SoC. The Tegra186 features a
combination of Denver and Cortex-A57 CPU cores and a GPU based on
Expand All @@ -93,3 +106,12 @@ config ARCH_TEGRA_186_SOC

endif
endif

config SOC_TEGRA_FLOWCTRL
bool

config SOC_TEGRA_PMC
bool

config SOC_TEGRA_PMC_TEGRA186
bool
4 changes: 3 additions & 1 deletion drivers/soc/tegra/Makefile
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
obj-y += fuse/

obj-y += common.o
obj-y += pmc.o
obj-$(CONFIG_SOC_TEGRA_FLOWCTRL) += flowctrl.o
obj-$(CONFIG_SOC_TEGRA_PMC) += pmc.o
obj-$(CONFIG_SOC_TEGRA_PMC_TEGRA186) += pmc-tegra186.o
87 changes: 70 additions & 17 deletions arch/arm/mach-tegra/flowctrl.c → drivers/soc/tegra/flowctrl.c
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
/*
* arch/arm/mach-tegra/flowctrl.c
* drivers/soc/tegra/flowctrl.c
*
* functions and macros to control the flowcontroller
* Functions and macros to control the flowcontroller
*
* Copyright (c) 2010-2012, NVIDIA Corporation. All rights reserved.
*
Expand All @@ -24,11 +24,12 @@
#include <linux/kernel.h>
#include <linux/of.h>
#include <linux/of_address.h>
#include <linux/platform_device.h>

#include <soc/tegra/common.h>
#include <soc/tegra/flowctrl.h>
#include <soc/tegra/fuse.h>

#include "flowctrl.h"

static u8 flowctrl_offset_halt_cpu[] = {
FLOW_CTRL_HALT_CPU0_EVENTS,
FLOW_CTRL_HALT_CPU1_EVENTS,
Expand All @@ -47,6 +48,10 @@ static void __iomem *tegra_flowctrl_base;

static void flowctrl_update(u8 offset, u32 value)
{
if (WARN_ONCE(IS_ERR_OR_NULL(tegra_flowctrl_base),
"Tegra flowctrl not initialised!\n"))
return;

writel(value, tegra_flowctrl_base + offset);

/* ensure the update has reached the flow controller */
Expand All @@ -58,6 +63,10 @@ u32 flowctrl_read_cpu_csr(unsigned int cpuid)
{
u8 offset = flowctrl_offset_cpu_csr[cpuid];

if (WARN_ONCE(IS_ERR_OR_NULL(tegra_flowctrl_base),
"Tegra flowctrl not initialised!\n"))
return 0;

return readl(tegra_flowctrl_base + offset);
}

Expand Down Expand Up @@ -140,32 +149,76 @@ void flowctrl_cpu_suspend_exit(unsigned int cpuid)
flowctrl_write_cpu_csr(cpuid, reg);
}

static const struct of_device_id matches[] __initconst = {
static int tegra_flowctrl_probe(struct platform_device *pdev)
{
void __iomem *base = tegra_flowctrl_base;
struct resource *res;

res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
tegra_flowctrl_base = devm_ioremap_resource(&pdev->dev, res);
if (IS_ERR(tegra_flowctrl_base))
return PTR_ERR(base);

iounmap(base);

return 0;
}

static const struct of_device_id tegra_flowctrl_match[] = {
{ .compatible = "nvidia,tegra210-flowctrl" },
{ .compatible = "nvidia,tegra124-flowctrl" },
{ .compatible = "nvidia,tegra114-flowctrl" },
{ .compatible = "nvidia,tegra30-flowctrl" },
{ .compatible = "nvidia,tegra20-flowctrl" },
{ }
};

void __init tegra_flowctrl_init(void)
static struct platform_driver tegra_flowctrl_driver = {
.driver = {
.name = "tegra-flowctrl",
.suppress_bind_attrs = true,
.of_match_table = tegra_flowctrl_match,
},
.probe = tegra_flowctrl_probe,
};
builtin_platform_driver(tegra_flowctrl_driver);

static int __init tegra_flowctrl_init(void)
{
/* hardcoded fallback if device tree node is missing */
unsigned long base = 0x60007000;
unsigned long size = SZ_4K;
struct resource res;
struct device_node *np;

np = of_find_matching_node(NULL, matches);
if (np) {
struct resource res;
if (!soc_is_tegra())
return 0;

if (of_address_to_resource(np, 0, &res) == 0) {
size = resource_size(&res);
base = res.start;
np = of_find_matching_node(NULL, tegra_flowctrl_match);
if (np) {
if (of_address_to_resource(np, 0, &res) < 0) {
pr_err("failed to get flowctrl register\n");
return -ENXIO;
}

of_node_put(np);
} else if (IS_ENABLED(CONFIG_ARM)) {
/*
* Hardcoded fallback for 32-bit Tegra
* devices if device tree node is missing.
*/
res.start = 0x60007000;
res.end = 0x60007fff;
res.flags = IORESOURCE_MEM;
} else {
/*
* At this point we're running on a Tegra,
* that doesn't support the flow controller
* (eg. Tegra186), so just return.
*/
return 0;
}

tegra_flowctrl_base = ioremap_nocache(base, size);
tegra_flowctrl_base = ioremap_nocache(res.start, resource_size(&res));
if (!tegra_flowctrl_base)
return -ENXIO;

return 0;
}
early_initcall(tegra_flowctrl_init);
4 changes: 2 additions & 2 deletions drivers/soc/tegra/fuse/fuse-tegra.c
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
#include <linux/clk.h>
#include <linux/device.h>
#include <linux/kobject.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/platform_device.h>
#include <linux/of.h>
#include <linux/of_address.h>
Expand Down Expand Up @@ -168,7 +168,7 @@ static struct platform_driver tegra_fuse_driver = {
},
.probe = tegra_fuse_probe,
};
module_platform_driver(tegra_fuse_driver);
builtin_platform_driver(tegra_fuse_driver);

bool __init tegra_fuse_read_spare(unsigned int spare)
{
Expand Down
Loading

0 comments on commit 55de807

Please sign in to comment.