Commit 0417a5c6 authored by Arnd Bergmann's avatar Arnd Bergmann
Browse files

Merge tag 'reset-for-v5.8' of git://git.pengutronix.de/pza/linux into arm/drivers

Reset controller updates for v5.8

This tag adds support for i.MX8MP and i.MX8MN SoCs to the i.MX7 reset
controller driver, extends the Hi6220 reset driver to support the AO
reset controller used to bring the Mali450 GPU out of reset, and adds
a define for the internal DAC reset line on Amlogic GXL SoCs.

* tag 'reset-for-v5.8' of git://git.pengutronix.de/pza/linux:
  reset: hi6220: Add support for AO reset controller
  reset: imx7: Add support for i.MX8MP SoC
  dt-bindings: reset: imx7: Document usage on i.MX8MP SoC
  dt-bindings: reset: imx7: Add support for i.MX8MN
  dt-bindings: reset: meson: add gxl internal dac reset

Link: https://lore.kernel.org/r/20200515143844.GA17201@pengutronix.de


Signed-off-by: default avatarArnd Bergmann <arnd@arndb.de>
parents 93f9fb1e 697fa27d
Loading
Loading
Loading
Loading
+5 −1
Original line number Diff line number Diff line
@@ -9,6 +9,8 @@ Required properties:
	- For i.MX7 SoCs should be "fsl,imx7d-src", "syscon"
	- For i.MX8MQ SoCs should be "fsl,imx8mq-src", "syscon"
	- For i.MX8MM SoCs should be "fsl,imx8mm-src", "fsl,imx8mq-src", "syscon"
	- For i.MX8MN SoCs should be "fsl,imx8mn-src", "fsl,imx8mq-src", "syscon"
	- For i.MX8MP SoCs should be "fsl,imx8mp-src", "syscon"
- reg: should be register base and length as documented in the
  datasheet
- interrupts: Should contain SRC interrupt
@@ -49,4 +51,6 @@ Example:
For list of all valid reset indices see
<dt-bindings/reset/imx7-reset.h> for i.MX7,
<dt-bindings/reset/imx8mq-reset.h> for i.MX8MQ and
<dt-bindings/reset/imx8mq-reset.h> for i.MX8MM
<dt-bindings/reset/imx8mq-reset.h> for i.MX8MM and
<dt-bindings/reset/imx8mq-reset.h> for i.MX8MN and
<dt-bindings/reset/imx8mp-reset.h> for i.MX8MP
+68 −1
Original line number Diff line number Diff line
@@ -33,6 +33,7 @@
enum hi6220_reset_ctrl_type {
	PERIPHERAL,
	MEDIA,
	AO,
};

struct hi6220_reset_data {
@@ -92,6 +93,65 @@ static const struct reset_control_ops hi6220_media_reset_ops = {
	.deassert = hi6220_media_deassert,
};

#define AO_SCTRL_SC_PW_CLKEN0     0x800
#define AO_SCTRL_SC_PW_CLKDIS0    0x804

#define AO_SCTRL_SC_PW_RSTEN0     0x810
#define AO_SCTRL_SC_PW_RSTDIS0    0x814

#define AO_SCTRL_SC_PW_ISOEN0     0x820
#define AO_SCTRL_SC_PW_ISODIS0    0x824
#define AO_MAX_INDEX              12

static int hi6220_ao_assert(struct reset_controller_dev *rc_dev,
			       unsigned long idx)
{
	struct hi6220_reset_data *data = to_reset_data(rc_dev);
	struct regmap *regmap = data->regmap;
	int ret;

	ret = regmap_write(regmap, AO_SCTRL_SC_PW_RSTEN0, BIT(idx));
	if (ret)
		return ret;

	ret = regmap_write(regmap, AO_SCTRL_SC_PW_ISOEN0, BIT(idx));
	if (ret)
		return ret;

	ret = regmap_write(regmap, AO_SCTRL_SC_PW_CLKDIS0, BIT(idx));
	return ret;
}

static int hi6220_ao_deassert(struct reset_controller_dev *rc_dev,
				 unsigned long idx)
{
	struct hi6220_reset_data *data = to_reset_data(rc_dev);
	struct regmap *regmap = data->regmap;
	int ret;

	/*
	 * It was suggested to disable isolation before enabling
	 * the clocks and deasserting reset, to avoid glitches.
	 * But this order is preserved to keep it matching the
	 * vendor code.
	 */
	ret = regmap_write(regmap, AO_SCTRL_SC_PW_RSTDIS0, BIT(idx));
	if (ret)
		return ret;

	ret = regmap_write(regmap, AO_SCTRL_SC_PW_ISODIS0, BIT(idx));
	if (ret)
		return ret;

	ret = regmap_write(regmap, AO_SCTRL_SC_PW_CLKEN0, BIT(idx));
	return ret;
}

static const struct reset_control_ops hi6220_ao_reset_ops = {
	.assert = hi6220_ao_assert,
	.deassert = hi6220_ao_deassert,
};

static int hi6220_reset_probe(struct platform_device *pdev)
{
	struct device_node *np = pdev->dev.of_node;
@@ -117,9 +177,12 @@ static int hi6220_reset_probe(struct platform_device *pdev)
	if (type == MEDIA) {
		data->rc_dev.ops = &hi6220_media_reset_ops;
		data->rc_dev.nr_resets = MEDIA_MAX_INDEX;
	} else {
	} else if (type == PERIPHERAL) {
		data->rc_dev.ops = &hi6220_peripheral_reset_ops;
		data->rc_dev.nr_resets = PERIPH_MAX_INDEX;
	} else {
		data->rc_dev.ops = &hi6220_ao_reset_ops;
		data->rc_dev.nr_resets = AO_MAX_INDEX;
	}

	return reset_controller_register(&data->rc_dev);
@@ -134,6 +197,10 @@ static const struct of_device_id hi6220_reset_match[] = {
		.compatible = "hisilicon,hi6220-mediactrl",
		.data = (void *)MEDIA,
	},
	{
		.compatible = "hisilicon,hi6220-aoctrl",
		.data = (void *)AO,
	},
	{ /* sentinel */ },
};
MODULE_DEVICE_TABLE(of, hi6220_reset_match);
+101 −0
Original line number Diff line number Diff line
@@ -15,6 +15,7 @@
#include <linux/regmap.h>
#include <dt-bindings/reset/imx7-reset.h>
#include <dt-bindings/reset/imx8mq-reset.h>
#include <dt-bindings/reset/imx8mp-reset.h>

struct imx7_src_signal {
	unsigned int offset, bit;
@@ -145,6 +146,18 @@ enum imx8mq_src_registers {
	SRC_DDRC2_RCR		= 0x1004,
};

enum imx8mp_src_registers {
	SRC_SUPERMIX_RCR	= 0x0018,
	SRC_AUDIOMIX_RCR	= 0x001c,
	SRC_MLMIX_RCR		= 0x0028,
	SRC_GPU2D_RCR		= 0x0038,
	SRC_GPU3D_RCR		= 0x003c,
	SRC_VPU_G1_RCR		= 0x0048,
	SRC_VPU_G2_RCR		= 0x004c,
	SRC_VPUVC8KE_RCR	= 0x0050,
	SRC_NOC_RCR		= 0x0054,
};

static const struct imx7_src_signal imx8mq_src_signals[IMX8MQ_RESET_NUM] = {
	[IMX8MQ_RESET_A53_CORE_POR_RESET0]	= { SRC_A53RCR0, BIT(0) },
	[IMX8MQ_RESET_A53_CORE_POR_RESET1]	= { SRC_A53RCR0, BIT(1) },
@@ -253,6 +266,93 @@ static const struct imx7_src_variant variant_imx8mq = {
	},
};

static const struct imx7_src_signal imx8mp_src_signals[IMX8MP_RESET_NUM] = {
	[IMX8MP_RESET_A53_CORE_POR_RESET0]	= { SRC_A53RCR0, BIT(0) },
	[IMX8MP_RESET_A53_CORE_POR_RESET1]	= { SRC_A53RCR0, BIT(1) },
	[IMX8MP_RESET_A53_CORE_POR_RESET2]	= { SRC_A53RCR0, BIT(2) },
	[IMX8MP_RESET_A53_CORE_POR_RESET3]	= { SRC_A53RCR0, BIT(3) },
	[IMX8MP_RESET_A53_CORE_RESET0]		= { SRC_A53RCR0, BIT(4) },
	[IMX8MP_RESET_A53_CORE_RESET1]		= { SRC_A53RCR0, BIT(5) },
	[IMX8MP_RESET_A53_CORE_RESET2]		= { SRC_A53RCR0, BIT(6) },
	[IMX8MP_RESET_A53_CORE_RESET3]		= { SRC_A53RCR0, BIT(7) },
	[IMX8MP_RESET_A53_DBG_RESET0]		= { SRC_A53RCR0, BIT(8) },
	[IMX8MP_RESET_A53_DBG_RESET1]		= { SRC_A53RCR0, BIT(9) },
	[IMX8MP_RESET_A53_DBG_RESET2]		= { SRC_A53RCR0, BIT(10) },
	[IMX8MP_RESET_A53_DBG_RESET3]		= { SRC_A53RCR0, BIT(11) },
	[IMX8MP_RESET_A53_ETM_RESET0]		= { SRC_A53RCR0, BIT(12) },
	[IMX8MP_RESET_A53_ETM_RESET1]		= { SRC_A53RCR0, BIT(13) },
	[IMX8MP_RESET_A53_ETM_RESET2]		= { SRC_A53RCR0, BIT(14) },
	[IMX8MP_RESET_A53_ETM_RESET3]		= { SRC_A53RCR0, BIT(15) },
	[IMX8MP_RESET_A53_SOC_DBG_RESET]	= { SRC_A53RCR0, BIT(20) },
	[IMX8MP_RESET_A53_L2RESET]		= { SRC_A53RCR0, BIT(21) },
	[IMX8MP_RESET_SW_NON_SCLR_M7C_RST]	= { SRC_M4RCR, BIT(0) },
	[IMX8MP_RESET_OTG1_PHY_RESET]		= { SRC_USBOPHY1_RCR, BIT(0) },
	[IMX8MP_RESET_OTG2_PHY_RESET]		= { SRC_USBOPHY2_RCR, BIT(0) },
	[IMX8MP_RESET_SUPERMIX_RESET]		= { SRC_SUPERMIX_RCR, BIT(0) },
	[IMX8MP_RESET_AUDIOMIX_RESET]		= { SRC_AUDIOMIX_RCR, BIT(0) },
	[IMX8MP_RESET_MLMIX_RESET]		= { SRC_MLMIX_RCR, BIT(0) },
	[IMX8MP_RESET_PCIEPHY]			= { SRC_PCIEPHY_RCR, BIT(2) },
	[IMX8MP_RESET_PCIEPHY_PERST]		= { SRC_PCIEPHY_RCR, BIT(3) },
	[IMX8MP_RESET_PCIE_CTRL_APPS_EN]	= { SRC_PCIEPHY_RCR, BIT(6) },
	[IMX8MP_RESET_PCIE_CTRL_APPS_TURNOFF]	= { SRC_PCIEPHY_RCR, BIT(11) },
	[IMX8MP_RESET_HDMI_PHY_APB_RESET]	= { SRC_HDMI_RCR, BIT(0) },
	[IMX8MP_RESET_MEDIA_RESET]		= { SRC_DISP_RCR, BIT(0) },
	[IMX8MP_RESET_GPU2D_RESET]		= { SRC_GPU2D_RCR, BIT(0) },
	[IMX8MP_RESET_GPU3D_RESET]		= { SRC_GPU3D_RCR, BIT(0) },
	[IMX8MP_RESET_GPU_RESET]		= { SRC_GPU_RCR, BIT(0) },
	[IMX8MP_RESET_VPU_RESET]		= { SRC_VPU_RCR, BIT(0) },
	[IMX8MP_RESET_VPU_G1_RESET]		= { SRC_VPU_G1_RCR, BIT(0) },
	[IMX8MP_RESET_VPU_G2_RESET]		= { SRC_VPU_G2_RCR, BIT(0) },
	[IMX8MP_RESET_VPUVC8KE_RESET]		= { SRC_VPUVC8KE_RCR, BIT(0) },
	[IMX8MP_RESET_NOC_RESET]		= { SRC_NOC_RCR, BIT(0) },
};

static int imx8mp_reset_set(struct reset_controller_dev *rcdev,
			    unsigned long id, bool assert)
{
	struct imx7_src *imx7src = to_imx7_src(rcdev);
	const unsigned int bit = imx7src->signals[id].bit;
	unsigned int value = assert ? bit : 0;

	switch (id) {
	case IMX8MP_RESET_PCIEPHY:
		/*
		 * wait for more than 10us to release phy g_rst and
		 * btnrst
		 */
		if (!assert)
			udelay(10);
		break;

	case IMX8MP_RESET_PCIE_CTRL_APPS_EN:
		value = assert ? 0 : bit;
		break;
	}

	return imx7_reset_update(imx7src, id, value);
}

static int imx8mp_reset_assert(struct reset_controller_dev *rcdev,
			       unsigned long id)
{
	return imx8mp_reset_set(rcdev, id, true);
}

static int imx8mp_reset_deassert(struct reset_controller_dev *rcdev,
				 unsigned long id)
{
	return imx8mp_reset_set(rcdev, id, false);
}

static const struct imx7_src_variant variant_imx8mp = {
	.signals = imx8mp_src_signals,
	.signals_num = ARRAY_SIZE(imx8mp_src_signals),
	.ops = {
		.assert   = imx8mp_reset_assert,
		.deassert = imx8mp_reset_deassert,
	},
};

static int imx7_reset_probe(struct platform_device *pdev)
{
	struct imx7_src *imx7src;
@@ -283,6 +383,7 @@ static int imx7_reset_probe(struct platform_device *pdev)
static const struct of_device_id imx7_reset_dt_ids[] = {
	{ .compatible = "fsl,imx7d-src", .data = &variant_imx7 },
	{ .compatible = "fsl,imx8mq-src", .data = &variant_imx8mq },
	{ .compatible = "fsl,imx8mp-src", .data = &variant_imx8mp },
	{ /* sentinel */ },
};

+1 −1
Original line number Diff line number Diff line
@@ -69,7 +69,7 @@
#define RESET_SYS_CPU_L2		58
#define RESET_SYS_CPU_P			59
#define RESET_SYS_CPU_MBIST		60
/*					61	*/
#define RESET_ACODEC			61
/*					62	*/
/*					63	*/
/*	RESET2					*/
+50 −0
Original line number Diff line number Diff line
/* SPDX-License-Identifier: GPL-2.0-only */
/*
 * Copyright 2020 NXP
 */

#ifndef DT_BINDING_RESET_IMX8MP_H
#define DT_BINDING_RESET_IMX8MP_H

#define IMX8MP_RESET_A53_CORE_POR_RESET0	0
#define IMX8MP_RESET_A53_CORE_POR_RESET1	1
#define IMX8MP_RESET_A53_CORE_POR_RESET2	2
#define IMX8MP_RESET_A53_CORE_POR_RESET3	3
#define IMX8MP_RESET_A53_CORE_RESET0		4
#define IMX8MP_RESET_A53_CORE_RESET1		5
#define IMX8MP_RESET_A53_CORE_RESET2		6
#define IMX8MP_RESET_A53_CORE_RESET3		7
#define IMX8MP_RESET_A53_DBG_RESET0		8
#define IMX8MP_RESET_A53_DBG_RESET1		9
#define IMX8MP_RESET_A53_DBG_RESET2		10
#define IMX8MP_RESET_A53_DBG_RESET3		11
#define IMX8MP_RESET_A53_ETM_RESET0		12
#define IMX8MP_RESET_A53_ETM_RESET1		13
#define IMX8MP_RESET_A53_ETM_RESET2		14
#define IMX8MP_RESET_A53_ETM_RESET3		15
#define IMX8MP_RESET_A53_SOC_DBG_RESET		16
#define IMX8MP_RESET_A53_L2RESET		17
#define IMX8MP_RESET_SW_NON_SCLR_M7C_RST	18
#define IMX8MP_RESET_OTG1_PHY_RESET		19
#define IMX8MP_RESET_OTG2_PHY_RESET		20
#define IMX8MP_RESET_SUPERMIX_RESET		21
#define IMX8MP_RESET_AUDIOMIX_RESET		22
#define IMX8MP_RESET_MLMIX_RESET		23
#define IMX8MP_RESET_PCIEPHY			24
#define IMX8MP_RESET_PCIEPHY_PERST		25
#define IMX8MP_RESET_PCIE_CTRL_APPS_EN		26
#define IMX8MP_RESET_PCIE_CTRL_APPS_TURNOFF	27
#define IMX8MP_RESET_HDMI_PHY_APB_RESET		28
#define IMX8MP_RESET_MEDIA_RESET		29
#define IMX8MP_RESET_GPU2D_RESET		30
#define IMX8MP_RESET_GPU3D_RESET		31
#define IMX8MP_RESET_GPU_RESET			32
#define IMX8MP_RESET_VPU_RESET			33
#define IMX8MP_RESET_VPU_G1_RESET		34
#define IMX8MP_RESET_VPU_G2_RESET		35
#define IMX8MP_RESET_VPUVC8KE_RESET		36
#define IMX8MP_RESET_NOC_RESET			37

#define IMX8MP_RESET_NUM			38

#endif
Loading