Merge branch 'rcar-3.5.1/dts-rcar-gen3.rc2' into v4.9/rcar-3.5.2.pt3

* rcar-3.5.1/dts-rcar-gen3.rc2: (80 commits)
  arm64: dts: r8a7795-salvator-xs: Add Media Clock Recovery Handler device node
  arm64: dts: r8a7795-salvator-xs: Add ADSP support
  arm64: dts: r8a7795-salvator-xs: Add VSPM I/F driver support
  arm64: dts: r8a7795-salvator-xs: Add MMNGRBUF driver support
  arm64: dts: r8a7795-salvator-xs: Add MMNGR driver support
  arm64: dts: r8a7795-salvator-xs: Add cpu-supply property in a57_0 node
  arm64: dts: r8a7795-salvator-xs: Add regulator for DVFS
  arm64: dts: r8a7795-salvator-xs: Add I2C for DVFS device support
  arm64: dts: r8a7795-salvator-xs: Enable EXTALR clock
  arm64: dts: r8a7795-salvator-xs: Add RCLK watchdog timer support
  arm64: dts: r8a7795-salvator-xs: Add SATA device support
  arm64: dts: r8a7795-salvator-xs: Add PCIe device support
  arm64: dts: r8a7795-salvator-xs: Enable HS400 for SDHI2
  arm64: dts: r8a7795-salvator-xs: Enable HS200 for SDHI2
  arm64: dts: r8a7795-salvator-xs: Add SDHI2 device support as MMC interface
  arm64: dts: r8a7795-salvator-xs: Enable UHS-I SDR-104 for SDHI0 and SDHI3
  arm64: dts: r8a7795-salvator-xs: Enable UHS for SDHI0 and SDHI3
  arm64: dts: r8a7795-salvator-xs: Add SDHI0 and SDHI3 device supports
  arm64: dts: r8a7795-salvator-xs: Add sound MIX support
  arm64: dts: r8a7795-salvator-xs: Add sound CTU support
  arm64: dts: r8a7795-salvator-xs: Add AUDIO-CLKOUTn synchronous with L/R clock
  arm64: dts: r8a7795-salvator-xs: Add ak4613 In/Out pin as single-end
  arm64: dts: r8a7795-salvator-xs: Add CS2000 as AUDIO_CLK_B
  arm64: dts: r8a7795-salvator-xs: Add Sound DVC support
  arm64: dts: r8a7795-salvator-xs: Add Sound SRC support
  arm64: dts: r8a7795-salvator-xs: Add Sound SSI support
  arm64: dts: r8a7795-salvator-xs: Add ADV7482 video decoder devices support
  arm64: dts: r8a7795-salvator-xs: Add CSI2 device support
  arm64: dts: r8a7795-salvator-xs: Add VIN device support
  arm64: dts: r8a7795-salvator-xs: Add PWM device support
  ...
diff --git a/Documentation/devicetree/bindings/cpufreq/avs/rcar-avs.txt b/Documentation/devicetree/bindings/cpufreq/avs/rcar-avs.txt
new file mode 100644
index 0000000..1fd80e7
--- /dev/null
+++ b/Documentation/devicetree/bindings/cpufreq/avs/rcar-avs.txt
@@ -0,0 +1,26 @@
+R-Car AVS driver
+
+It is a simple driver that checks AVS (Adaptive Voltage Scaling) value of
+chip. It helps to cpufreq select the best opp table (appropriate table with
+avs value) to apply for the chip at runtime.
+
+Required properties:
+ - reg: address and offset for registers of AVS.
+
+Optional properties:
+ - None
+
+Examples:
+ - Below is device tree definition for R-Car H3 and M3:
+
+  For H3:
+	avs_sensor: avs {
+		compatible = "renesas,r8a7795-avs", "renesas,rcar-gen3-avs";
+		reg = <0 0xe60a013c 0 0x04>;
+	};
+
+  For M3:
+	avs_sensor: avs {
+		compatible = "renesas,r8a7796-avs", "renesas,rcar-gen3-avs";
+		reg = <0 0xe60a013c 0 0x04>;
+	};
diff --git a/drivers/clk/clk-cs2000-cp.c b/drivers/clk/clk-cs2000-cp.c
index 0a04b05..3fca052 100644
--- a/drivers/clk/clk-cs2000-cp.c
+++ b/drivers/clk/clk-cs2000-cp.c
@@ -59,6 +59,10 @@
 	struct i2c_client *client;
 	struct clk *clk_in;
 	struct clk *ref_clk;
+
+	/* suspend/resume */
+	unsigned long saved_rate;
+	unsigned long saved_parent_rate;
 };
 
 static const struct of_device_id cs2000_of_match[] = {
@@ -286,6 +290,9 @@
 	if (ret < 0)
 		return ret;
 
+	priv->saved_rate	= rate;
+	priv->saved_parent_rate	= parent_rate;
+
 	return 0;
 }
 
@@ -489,42 +496,24 @@
 	return ret;
 }
 
-#ifdef CONFIG_PM_SLEEP
-static int cs2000_suspend(struct device *dev)
-{
-	/* Empty function for now */
-	return 0;
-}
-
 static int cs2000_resume(struct device *dev)
 {
 	struct cs2000_priv *priv = dev_get_drvdata(dev);
-	int rate;
-	int ret;
+	int ch = 0; /* it uses ch0 only at this point */
 
-	/* Setting is referred from cs2000_clk_register */
-	rate = clk_get_rate(priv->ref_clk);
-	ret = __cs2000_set_rate(priv, 0, rate, rate);
-
-	if (ret < 0)
-		return ret;
-
-	return 0;
+	return __cs2000_set_rate(priv, ch,
+				 priv->saved_rate,
+				 priv->saved_parent_rate);
 }
 
 static const struct dev_pm_ops cs2000_pm_ops = {
-	.suspend = cs2000_suspend,
-	.resume_early = cs2000_resume,
+	.resume_early	= cs2000_resume,
 };
-#define DEV_PM_OPS (&cs2000_pm_ops)
-#else
-#define DEV_PM_OPS NULL
-#endif /* CONFIG_PM_SLEEP */
 
 static struct i2c_driver cs2000_driver = {
 	.driver = {
 		.name = "cs2000-cp",
-		.pm	= DEV_PM_OPS,
+		.pm	= &cs2000_pm_ops,
 		.of_match_table = cs2000_of_match,
 	},
 	.probe		= cs2000_probe,
diff --git a/drivers/clk/renesas/r8a7795-cpg-mssr.c b/drivers/clk/renesas/r8a7795-cpg-mssr.c
index 41a1a79..e0a7233 100644
--- a/drivers/clk/renesas/r8a7795-cpg-mssr.c
+++ b/drivers/clk/renesas/r8a7795-cpg-mssr.c
@@ -1,6 +1,7 @@
 /*
  * r8a7795 Clock Pulse Generator / Module Standby and Software Reset
  *
+ * Copyright (C) 2017 Renesas Electronics Corp.
  * Copyright (C) 2015 Glider bvba
  *
  * Based on clk-rcar-gen3.c
@@ -136,7 +137,6 @@
 	DEF_MOD("msiof2",		 209,	R8A7795_CLK_MSO),
 	DEF_MOD("msiof1",		 210,	R8A7795_CLK_MSO),
 	DEF_MOD("msiof0",		 211,	R8A7795_CLK_MSO),
-	DEF_MOD("mfis",			 213,	R8A7795_CLK_S3D2),
 	DEF_MOD("sys-dmac2",		 217,	R8A7795_CLK_S0D3),
 	DEF_MOD("sys-dmac1",		 218,	R8A7795_CLK_S0D3),
 	DEF_MOD("sys-dmac0",		 219,	R8A7795_CLK_S0D3),
@@ -242,6 +242,7 @@
 	DEF_MOD("can-if0",		 916,	R8A7795_CLK_S3D4),
 	DEF_MOD("i2c6",			 918,	R8A7795_CLK_S3D2),
 	DEF_MOD("i2c5",			 919,	R8A7795_CLK_S3D2),
+	DEF_MOD("adg",                   922,   R8A7795_CLK_S0D1),
 	DEF_MOD("i2c-dvfs",		 926,	R8A7795_CLK_CP),
 	DEF_MOD("i2c4",			 927,	R8A7795_CLK_S3D2),
 	DEF_MOD("i2c3",			 928,	R8A7795_CLK_S3D2),
diff --git a/drivers/clk/renesas/r8a7796-cpg-mssr.c b/drivers/clk/renesas/r8a7796-cpg-mssr.c
index 8c96083..0fbb024 100644
--- a/drivers/clk/renesas/r8a7796-cpg-mssr.c
+++ b/drivers/clk/renesas/r8a7796-cpg-mssr.c
@@ -1,6 +1,7 @@
 /*
  * r8a7796 Clock Pulse Generator / Module Standby and Software Reset
  *
+ * Copyright (C) 2017 Renesas Electronics Corp.
  * Copyright (C) 2016 Glider bvba
  *
  * Based on r8a7795-cpg-mssr.c
@@ -132,7 +133,6 @@
 	DEF_MOD("msiof2",		 209,	R8A7796_CLK_MSO),
 	DEF_MOD("msiof1",		 210,	R8A7796_CLK_MSO),
 	DEF_MOD("msiof0",		 211,	R8A7796_CLK_MSO),
-	DEF_MOD("mfis",			 213,	R8A7796_CLK_S0D6),
 	DEF_MOD("sys-dmac2",		 217,	R8A7796_CLK_S0D3),
 	DEF_MOD("sys-dmac1",		 218,	R8A7796_CLK_S0D3),
 	DEF_MOD("sys-dmac0",		 219,	R8A7796_CLK_S0D3),
@@ -216,6 +216,7 @@
 	DEF_MOD("can-if0",		 916,	R8A7796_CLK_S3D4),
 	DEF_MOD("i2c6",			 918,	R8A7796_CLK_S0D6),
 	DEF_MOD("i2c5",			 919,	R8A7796_CLK_S0D6),
+	DEF_MOD("adg",			 922,	R8A7796_CLK_S0D1),
 	DEF_MOD("i2c-dvfs",		 926,	R8A7796_CLK_CP),
 	DEF_MOD("i2c4",			 927,	R8A7796_CLK_S0D6),
 	DEF_MOD("i2c3",			 928,	R8A7796_CLK_S0D6),
diff --git a/drivers/clk/renesas/rcar-gen3-cpg.c b/drivers/clk/renesas/rcar-gen3-cpg.c
index 31246ab..f49046e 100644
--- a/drivers/clk/renesas/rcar-gen3-cpg.c
+++ b/drivers/clk/renesas/rcar-gen3-cpg.c
@@ -1,6 +1,7 @@
 /*
  * R-Car Gen3 Clock Pulse Generator
  *
+ * Copyright (C) 2017 Renesas Electronics Corp.
  * Copyright (C) 2015-2016 Glider bvba
  *
  * Based on clk-rcar-gen3.c
@@ -494,12 +495,12 @@
  *                     sd_srcfc   sd_fc   div
  * stp_hck   stp_ck    (div)      (div)     = sd_srcfc x sd_fc
  *-------------------------------------------------------------------
- *  0         0         1 (2)      0 (2)      4 : SDR104 / HS400 / HS200
+ *  0         0         1 (2)      0 (-)      2 : HS400
+ *  0         0         0 (1)      1 (4)      4 : SDR104 / HS200
  *  0         0         1 (2)      1 (4)      8 : SDR50
  *  1         0         2 (4)      1 (4)     16 : HS / SDR25
  *  1         0         3 (8)      1 (4)     32 : NS / SDR12
  *  0         0         0 (1)      0 (2)      2 : (no case)
- *  0         0         0 (1)      1 (4)      4 : (no case)
  *  1         0         2 (4)      0 (2)      8 : (no case)
  *  1         0         3 (8)      0 (2)     16 : (no case)
  *  1         0         4 (16)     0 (2)     32 : (no case)
@@ -507,12 +508,12 @@
  */
 static const struct sd_div_table cpg_sd_div_table[] = {
 /*	CPG_SD_DIV_TABLE_DATA(stp_hck,  stp_ck,   sd_srcfc,   sd_fc,  sd_div) */
-	CPG_SD_DIV_TABLE_DATA(0,	0,	  1,	      0,        4),
+	CPG_SD_DIV_TABLE_DATA(0,	0,	  1,	      0,        2),
+	CPG_SD_DIV_TABLE_DATA(0,	0,	  0,	      1,        4),
 	CPG_SD_DIV_TABLE_DATA(0,	0,	  1,	      1,        8),
 	CPG_SD_DIV_TABLE_DATA(1,	0,	  2,	      1,       16),
 	CPG_SD_DIV_TABLE_DATA(1,	0,	  3,	      1,       32),
 	CPG_SD_DIV_TABLE_DATA(0,	0,	  0,	      0,        2),
-	CPG_SD_DIV_TABLE_DATA(0,	0,	  0,	      1,        4),
 	CPG_SD_DIV_TABLE_DATA(1,	0,	  2,	      0,        8),
 	CPG_SD_DIV_TABLE_DATA(1,	0,	  3,	      0,       16),
 	CPG_SD_DIV_TABLE_DATA(1,	0,	  4,	      0,       32),
diff --git a/drivers/clk/renesas/renesas-cpg-mssr.c b/drivers/clk/renesas/renesas-cpg-mssr.c
index 1c0609d..494e4e8 100644
--- a/drivers/clk/renesas/renesas-cpg-mssr.c
+++ b/drivers/clk/renesas/renesas-cpg-mssr.c
@@ -462,8 +462,6 @@
 
 	switch (clkspec->args[0]) {
 	case CPG_CORE:
-		if (!pd->num_core_pm_clks)
-			return true;
 		for (i = 0; i < pd->num_core_pm_clks; i++)
 			if (clkspec->args[1] == pd->core_pm_clks[i])
 				return true;
@@ -485,7 +483,6 @@
 	struct clk *clk;
 	int i = 0;
 	int error;
-	bool had_clk = false;
 
 	if (!pd) {
 		dev_dbg(dev, "CPG/MSSR clock domain not yet available\n");
@@ -494,40 +491,40 @@
 
 	while (!of_parse_phandle_with_args(np, "clocks", "#clock-cells", i,
 					   &clkspec)) {
-		i++;
-		if (!cpg_mssr_is_pm_clk(&clkspec, pd))
-			continue;
+		if (cpg_mssr_is_pm_clk(&clkspec, pd))
+			goto found;
 
-		if (!had_clk) {
-			error = pm_clk_create(dev);
-			if (error) {
-				dev_err(dev, "pm_clk_create failed %d\n",
-					error);
-				return error;
-			}
-			had_clk = true;
-		}
-
-		clk = of_clk_get_from_provider(&clkspec);
 		of_node_put(clkspec.np);
-
-		if (IS_ERR(clk))
-			goto fail_destroy;
-
-		error = pm_clk_add_clk(dev, clk);
-		if (error) {
-			dev_err(dev, "pm_clk_add_clk %pC failed %d\n",
-				clk, error);
-			goto fail_put;
-		}
+		i++;
 	}
 
 	return 0;
 
-fail_put:
-	clk_put(clk);
+found:
+	clk = of_clk_get_from_provider(&clkspec);
+	of_node_put(clkspec.np);
+
+	if (IS_ERR(clk))
+		return PTR_ERR(clk);
+
+	error = pm_clk_create(dev);
+	if (error) {
+		dev_err(dev, "pm_clk_create failed %d\n", error);
+		goto fail_put;
+	}
+
+	error = pm_clk_add_clk(dev, clk);
+	if (error) {
+		dev_err(dev, "pm_clk_add_clk %pC failed %d\n", clk, error);
+		goto fail_destroy;
+	}
+
+	return 0;
+
 fail_destroy:
 	pm_clk_destroy(dev);
+fail_put:
+	clk_put(clk);
 	return error;
 }
 
diff --git a/drivers/dma/sh/rcar-dmac.c b/drivers/dma/sh/rcar-dmac.c
index e9d79d7..f0849cc 100644
--- a/drivers/dma/sh/rcar-dmac.c
+++ b/drivers/dma/sh/rcar-dmac.c
@@ -1647,6 +1647,13 @@
 
 		spin_lock(&dmac->channels[i].lock);
 		pm_runtime_get_sync(dev);
+
+		if (rcar_dmac_chan_is_busy(&dmac->channels[i])) {
+			pm_runtime_put(dev);
+			spin_unlock(&dmac->channels[i].lock);
+			return -EBUSY;
+		}
+
 		rcar_dmac_chan_halt(&dmac->channels[i]);
 		pm_runtime_put(dev);
 		spin_unlock(&dmac->channels[i].lock);
diff --git a/drivers/dma/sh/usb-dmac.c b/drivers/dma/sh/usb-dmac.c
index 52bc399..c574d15 100644
--- a/drivers/dma/sh/usb-dmac.c
+++ b/drivers/dma/sh/usb-dmac.c
@@ -1,7 +1,7 @@
 /*
  * Renesas USB DMA Controller Driver
  *
- * Copyright (C) 2015 Renesas Electronics Corporation
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  *
  * based on rcar-dmac.c
  * Copyright (C) 2014 Renesas Electronics Inc.
@@ -117,7 +117,7 @@
 #define USB_DMASWR			0x0008
 #define USB_DMASWR_SWR			(1 << 0)
 #define USB_DMAOR			0x0060
-#define USB_DMAOR_AE			(1 << 2)
+#define USB_DMAOR_AE			(1 << 1)
 #define USB_DMAOR_DME			(1 << 0)
 
 #define USB_DMASAR			0x0000
@@ -685,6 +685,10 @@
 	for (i = 0; i < dmac->n_channels; ++i) {
 		if (!dmac->channels[i].iomem)
 			break;
+
+		if (usb_dmac_chan_is_busy(&dmac->channels[i]))
+			return -EBUSY;
+
 		usb_dmac_chan_halt(&dmac->channels[i]);
 	}
 
diff --git a/drivers/gpu/drm/bridge/dw-hdmi.c b/drivers/gpu/drm/bridge/dw-hdmi.c
index 2b776ec..19a8c58 100644
--- a/drivers/gpu/drm/bridge/dw-hdmi.c
+++ b/drivers/gpu/drm/bridge/dw-hdmi.c
@@ -1,7 +1,7 @@
 /*
  * DesignWare High-Definition Multimedia Interface (HDMI) driver
  *
- * Copyright (C) 2015 Renesas Electronics Corporation
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  * Copyright (C) 2013-2015 Mentor Graphics Inc.
  * Copyright (C) 2011-2013 Freescale Semiconductor, Inc.
  * Copyright (C) 2010, Guennadi Liakhovetski <g.liakhovetski@gmx.de>
@@ -878,7 +878,12 @@
 static void __hdmi_phy_i2c_write(struct dw_hdmi *hdmi, unsigned short data,
 				 unsigned char addr)
 {
-	hdmi_writeb(hdmi, 0xFF, HDMI_IH_I2CMPHY_STAT0);
+	if (hdmi->dev_type == RCAR_HDMI)
+		hdmi_writeb(hdmi, HDMI_IH_I2CMPHY_STAT0_I2CMPHYDONE |
+				HDMI_IH_I2CMPHY_STAT0_I2CMPHYERROR,
+				HDMI_IH_I2CMPHY_STAT0);
+	else
+		hdmi_writeb(hdmi, 0xFF, HDMI_IH_I2CMPHY_STAT0);
 	hdmi_writeb(hdmi, addr, HDMI_PHY_I2CM_ADDRESS_ADDR);
 	hdmi_writeb(hdmi, (unsigned char)(data >> 8),
 		    HDMI_PHY_I2CM_DATAO_1_ADDR);
@@ -1051,15 +1056,14 @@
 		hdmi_phy_i2c_write(hdmi, 0x0000, 0x13);	/* PLLPHBYCTRL */
 		hdmi_phy_i2c_write(hdmi, 0x0006, 0x17);
 
-		hdmi_phy_i2c_write(hdmi, phy_config->term,
-				   0x19);		/* TXTERM */
-		hdmi_phy_i2c_write(hdmi, phy_config->sym_ctr,
-				   0x09);		/* CKSYMTXCTRL */
-		hdmi_phy_i2c_write(hdmi, phy_config->vlev_ctr,
-				   0x0e);		/* VLEVCTRL */
 		/* REMOVE CLK TERM */
 		hdmi_phy_i2c_write(hdmi, 0x8000, 0x05);	/* CKCALCTRL */
 	}
+
+	hdmi_phy_i2c_write(hdmi, phy_config->term, 0x19);     /* TXTERM */
+	hdmi_phy_i2c_write(hdmi, phy_config->sym_ctr, 0x09);  /* CKSYMTXCTRL */
+	hdmi_phy_i2c_write(hdmi, phy_config->vlev_ctr, 0x0e); /* VLEVCTRL */
+
 	dw_hdmi_phy_enable_powerdown(hdmi, false);
 
 	/* toggle TMDS enable */
@@ -1384,7 +1388,13 @@
 	u8 val;
 
 	/* TMDS software reset */
-	hdmi_writeb(hdmi, (u8)~HDMI_MC_SWRSTZ_TMDSSWRST_REQ, HDMI_MC_SWRSTZ);
+	if (hdmi->dev_type == RCAR_HDMI)
+		hdmi_writeb(hdmi, (HDMI_MC_SWRSTZ_TMDSSWRST_MASK &
+				  (u8)~HDMI_MC_SWRSTZ_TMDSSWRST_REQ),
+				  HDMI_MC_SWRSTZ);
+	else
+		hdmi_writeb(hdmi, (u8)~HDMI_MC_SWRSTZ_TMDSSWRST_REQ,
+				  HDMI_MC_SWRSTZ);
 
 	val = hdmi_readb(hdmi, HDMI_FC_INVIDCONF);
 	if (hdmi->dev_type == IMX6DL_HDMI) {
@@ -1503,6 +1513,52 @@
 
 	return 0;
 }
+static void initialize_hdmi_rcar_ih_mutes(struct dw_hdmi *hdmi)
+{
+	u8 ih_mute;
+	/*
+	 * Boot up defaults are:
+	 * HDMI_IH_MUTE   = 0x03 (disabled)
+	 * HDMI_IH_MUTE_* = 0x00 (enabled)
+	 *
+	 * Disable top level interrupt bits in HDMI block
+	 */
+	ih_mute = hdmi_readb(hdmi, HDMI_IH_MUTE) |
+		  HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT |
+		  HDMI_IH_MUTE_MUTE_ALL_INTERRUPT;
+
+	hdmi_writeb(hdmi, ih_mute, HDMI_IH_MUTE);
+
+	/* by default mask all interrupts */
+	hdmi_writeb(hdmi, 0xff, HDMI_VP_MASK);
+	hdmi_writeb(hdmi, 0xff, HDMI_FC_MASK0);
+	hdmi_writeb(hdmi, 0xff, HDMI_FC_MASK1);
+	hdmi_writeb(hdmi, 0x03, HDMI_FC_MASK2);
+	hdmi_writeb(hdmi, 0xf3, HDMI_PHY_MASK0);
+	hdmi_writeb(hdmi, 0x0c, HDMI_PHY_I2CM_INT_ADDR);
+	hdmi_writeb(hdmi, 0xcc, HDMI_PHY_I2CM_CTLINT_ADDR);
+	hdmi_writeb(hdmi, 0x0c, HDMI_AUD_INT);
+	hdmi_writeb(hdmi, 0xff, HDMI_A_APIINTMSK);
+	hdmi_writeb(hdmi, 0x7f, HDMI_CEC_MASK);
+	hdmi_writeb(hdmi, 0x44, HDMI_I2CM_INT);
+	hdmi_writeb(hdmi, 0x44, HDMI_I2CM_CTLINT);
+
+	/* Disable interrupts in the IH_MUTE_* registers */
+	hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_FC_STAT0);
+	hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_FC_STAT1);
+	hdmi_writeb(hdmi, 0x03, HDMI_IH_MUTE_FC_STAT2);
+	hdmi_writeb(hdmi, 0x1f, HDMI_IH_MUTE_AS_STAT0);
+	hdmi_writeb(hdmi, 0x3f, HDMI_IH_MUTE_PHY_STAT0);
+	hdmi_writeb(hdmi, 0x0f, HDMI_IH_MUTE_I2CM_STAT0);
+	hdmi_writeb(hdmi, 0x7f, HDMI_IH_MUTE_CEC_STAT0);
+	hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_VP_STAT0);
+	hdmi_writeb(hdmi, 0x03, HDMI_IH_MUTE_I2CMPHY_STAT0);
+
+	/* Enable top level interrupt bits in HDMI block */
+	ih_mute &= ~(HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT |
+		    HDMI_IH_MUTE_MUTE_ALL_INTERRUPT);
+	hdmi_writeb(hdmi, ih_mute, HDMI_IH_MUTE);
+}
 
 static void initialize_hdmi_ih_mutes(struct dw_hdmi *hdmi)
 {
@@ -1639,7 +1695,7 @@
 	dw_hdmi_update_phy_mask(hdmi);
 
 	if (hdmi->dev_type == RCAR_HDMI) {
-		hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
+		hdmi_writeb(hdmi, 0x3f, HDMI_IH_MUTE_PHY_STAT0);
 		hdmi_writeb(hdmi, HDMI_PHY_HPD | HDMI_PHY_RX_SENSE,
 					 HDMI_PHY_POL0);
 	}
@@ -1655,19 +1711,21 @@
 
 	if (hdmi->dev_type == RCAR_HDMI) {
 		/* Reinitialization for resume */
-		initialize_hdmi_ih_mutes(hdmi);
+		initialize_hdmi_rcar_ih_mutes(hdmi);
 		hdmi_init_clk_regenerator(hdmi);
 		hdmi_writeb(hdmi, HDMI_PHY_HPD | HDMI_PHY_RX_SENSE,
 					HDMI_PHY_POL0);
 		hdmi_writeb(hdmi, HDMI_IH_PHY_STAT0_HPD |
 					HDMI_IH_PHY_STAT0_RX_SENSE,
 					HDMI_IH_PHY_STAT0);
-		hdmi_writeb(hdmi, ~(HDMI_IH_PHY_STAT0_HPD |
-					HDMI_IH_PHY_STAT0_RX_SENSE),
+		hdmi_writeb(hdmi, (HDMI_IH_MUTE_PHY_STAT0_MASK &
+					~(HDMI_IH_PHY_STAT0_HPD |
+					HDMI_IH_PHY_STAT0_RX_SENSE)),
 					HDMI_IH_MUTE_PHY_STAT0);
 		dw_hdmi_fb_registered(hdmi);
-		hdmi_writeb(hdmi, ~(HDMI_IH_PHY_STAT0_HPD |
-					HDMI_IH_PHY_STAT0_RX_SENSE),
+		hdmi_writeb(hdmi, (HDMI_IH_MUTE_PHY_STAT0_MASK &
+					~(HDMI_IH_PHY_STAT0_HPD |
+					HDMI_IH_PHY_STAT0_RX_SENSE)),
 					HDMI_IH_MUTE_PHY_STAT0);
 		dw_hdmi_i2c_init(hdmi);
 	}
@@ -1821,7 +1879,10 @@
 
 	intr_stat = hdmi_readb(hdmi, HDMI_IH_PHY_STAT0);
 	if (intr_stat) {
-		hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
+		if (hdmi->dev_type == RCAR_HDMI)
+			hdmi_writeb(hdmi, 0x3f, HDMI_IH_MUTE_PHY_STAT0);
+		else
+			hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
 		return IRQ_WAKE_THREAD;
 	}
 
@@ -1892,8 +1953,14 @@
 	}
 
 	hdmi_writeb(hdmi, intr_stat, HDMI_IH_PHY_STAT0);
-	hdmi_writeb(hdmi, ~(HDMI_IH_PHY_STAT0_HPD | HDMI_IH_PHY_STAT0_RX_SENSE),
-		    HDMI_IH_MUTE_PHY_STAT0);
+	if (hdmi->dev_type == RCAR_HDMI)
+		hdmi_writeb(hdmi, (HDMI_IH_MUTE_PHY_STAT0_MASK &
+				 ~(HDMI_IH_PHY_STAT0_HPD |
+				  HDMI_IH_PHY_STAT0_RX_SENSE)),
+				  HDMI_IH_MUTE_PHY_STAT0);
+	else
+		hdmi_writeb(hdmi, ~(HDMI_IH_PHY_STAT0_HPD |
+			 HDMI_IH_PHY_STAT0_RX_SENSE), HDMI_IH_MUTE_PHY_STAT0);
 
 	return IRQ_HANDLED;
 }
@@ -1943,6 +2010,7 @@
 		 const struct dw_hdmi_plat_data *plat_data)
 {
 	struct drm_device *drm = data;
+	struct device *dev_master;
 	struct device_node *np = dev->of_node;
 	struct platform_device_info pdevinfo;
 	struct device_node *ddc_node;
@@ -1964,7 +2032,11 @@
 	hdmi->encoder = encoder;
 	hdmi->disabled = true;
 	hdmi->rxsense = true;
-	hdmi->phy_mask = (u8)~(HDMI_PHY_HPD | HDMI_PHY_RX_SENSE);
+	if (hdmi->dev_type == RCAR_HDMI)
+		hdmi->phy_mask = (u8)~(BIT(3) | BIT(2) | HDMI_PHY_HPD |
+					 HDMI_PHY_RX_SENSE);
+	else
+		hdmi->phy_mask = (u8)~(HDMI_PHY_HPD | HDMI_PHY_RX_SENSE);
 
 	mutex_init(&hdmi->mutex);
 	mutex_init(&hdmi->audio_mutex);
@@ -2004,7 +2076,12 @@
 		dev_dbg(hdmi->dev, "no ddc property found\n");
 	}
 
-	hdmi->regs = devm_ioremap_resource(dev, iores);
+	if (hdmi->dev_type == RCAR_HDMI)
+		dev_master = master;
+	else
+		dev_master = dev;
+
+	hdmi->regs = devm_ioremap_resource(dev_master, iores);
 	if (IS_ERR(hdmi->regs))
 		return PTR_ERR(hdmi->regs);
 
@@ -2040,9 +2117,12 @@
 		 hdmi_readb(hdmi, HDMI_PRODUCT_ID0),
 		 hdmi_readb(hdmi, HDMI_PRODUCT_ID1));
 
-	initialize_hdmi_ih_mutes(hdmi);
+	if (hdmi->dev_type == RCAR_HDMI)
+		initialize_hdmi_rcar_ih_mutes(hdmi);
+	else
+		initialize_hdmi_ih_mutes(hdmi);
 
-	ret = devm_request_threaded_irq(dev, irq, dw_hdmi_hardirq,
+	ret = devm_request_threaded_irq(dev_master, irq, dw_hdmi_hardirq,
 					dw_hdmi_irq, IRQF_SHARED,
 					dev_name(dev), hdmi);
 	if (ret)
@@ -2080,8 +2160,14 @@
 		goto err_iahb;
 
 	/* Unmute interrupts */
-	hdmi_writeb(hdmi, ~(HDMI_IH_PHY_STAT0_HPD | HDMI_IH_PHY_STAT0_RX_SENSE),
-		    HDMI_IH_MUTE_PHY_STAT0);
+	if (hdmi->dev_type == RCAR_HDMI)
+		hdmi_writeb(hdmi, (HDMI_IH_MUTE_PHY_STAT0_MASK &
+				 ~(HDMI_IH_PHY_STAT0_HPD |
+				  HDMI_IH_PHY_STAT0_RX_SENSE)),
+				  HDMI_IH_MUTE_PHY_STAT0);
+	else
+		hdmi_writeb(hdmi, ~(HDMI_IH_PHY_STAT0_HPD |
+			 HDMI_IH_PHY_STAT0_RX_SENSE), HDMI_IH_MUTE_PHY_STAT0);
 
 	memset(&pdevinfo, 0, sizeof(pdevinfo));
 	pdevinfo.parent = dev;
@@ -2133,7 +2219,10 @@
 		platform_device_unregister(hdmi->audio);
 
 	/* Disable all interrupts */
-	hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
+	if (hdmi->dev_type == RCAR_HDMI)
+		hdmi_writeb(hdmi, 0x3f, HDMI_IH_MUTE_PHY_STAT0);
+	else
+		hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
 
 	hdmi->connector.funcs->destroy(&hdmi->connector);
 	hdmi->encoder->funcs->destroy(hdmi->encoder);
diff --git a/drivers/gpu/drm/bridge/dw-hdmi.h b/drivers/gpu/drm/bridge/dw-hdmi.h
index 6aadc84..00ac86a 100644
--- a/drivers/gpu/drm/bridge/dw-hdmi.h
+++ b/drivers/gpu/drm/bridge/dw-hdmi.h
@@ -566,6 +566,10 @@
 	HDMI_IH_PHY_STAT0_TX_PHY_LOCK = 0x2,
 	HDMI_IH_PHY_STAT0_HPD = 0x1,
 
+/* IH_I2CMPHY_STAT0 field values */
+	HDMI_IH_I2CMPHY_STAT0_I2CMPHYDONE = 0x2,
+	HDMI_IH_I2CMPHY_STAT0_I2CMPHYERROR = 0x1,
+
 /* IH_I2CM_STAT0 and IH_MUTE_I2CM_STAT0 field values */
 	HDMI_IH_I2CM_STAT0_DONE = 0x2,
 	HDMI_IH_I2CM_STAT0_ERROR = 0x1,
@@ -595,6 +599,9 @@
 	HDMI_IH_MUTE_AHBDMAAUD_STAT0_BUFFFULL = 0x02,
 	HDMI_IH_MUTE_AHBDMAAUD_STAT0_BUFFEMPTY = 0x01,
 
+/* IH_MUTE_PHY_STAT0 field values */
+	HDMI_IH_MUTE_PHY_STAT0_MASK = 0x3f,
+
 /* IH_MUTE field values */
 	HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT = 0x2,
 	HDMI_IH_MUTE_MUTE_ALL_INTERRUPT = 0x1,
@@ -950,6 +957,7 @@
 
 /* MC_SWRSTZ field values */
 	HDMI_MC_SWRSTZ_TMDSSWRST_REQ = 0x02,
+	HDMI_MC_SWRSTZ_TMDSSWRST_MASK = 0xdf,	/* R-Car only */
 
 /* MC_FLOWCTRL field values */
 	HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_MASK = 0x1,
diff --git a/drivers/gpu/drm/rcar-du/rcar_du_hdmienc.c b/drivers/gpu/drm/rcar-du/rcar_du_hdmienc.c
index cd79c39..ef3e87f 100644
--- a/drivers/gpu/drm/rcar-du/rcar_du_hdmienc.c
+++ b/drivers/gpu/drm/rcar-du/rcar_du_hdmienc.c
@@ -1,7 +1,7 @@
 /*
  * R-Car Display Unit HDMI Encoder
  *
- * Copyright (C) 2014-2015 Renesas Electronics Corporation
+ * Copyright (C) 2014-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -174,22 +174,25 @@
 		},
 	}
 };
+
 static const struct dw_hdmi_curr_ctrl rcar_du_hdmienc_cur_ctr[] = {
 	/*      pixelclk    bpp8    bpp10   bpp12 */
 	{
-		35500000,  { 0x0344, 0x0000, 0x0000 },
+		35500000,  { 0x0283, 0x0000, 0x0000 },
 	}, {
 		44900000,  { 0x0285, 0x0000, 0x0000 },
 	}, {
-		71000000,  { 0x1184, 0x0000, 0x0000 },
+		71000000,  { 0x1183, 0x0000, 0x0000 },
 	}, {
-		90000000,  { 0x1144, 0x0000, 0x0000 },
+		90000000,  { 0x1142, 0x0000, 0x0000 },
 	}, {
-		140250000, { 0x20c4, 0x0000, 0x0000 },
+		140250000, { 0x20c0, 0x0000, 0x0000 },
 	}, {
-		182750000, { 0x2084, 0x0000, 0x0000 },
+		182750000, { 0x2080, 0x0000, 0x0000 },
 	}, {
-		297000000, { 0x0084, 0x0000, 0x0000 },
+		281250000, { 0x3040, 0x0000, 0x0000 },
+	}, {
+		297000000, { 0x3041, 0x0000, 0x0000 },
 	}, {
 		~0UL,      { 0x0000, 0x0000, 0x0000 },
 	}
@@ -198,21 +201,21 @@
 static const struct dw_hdmi_multi_div rcar_du_hdmienc_multi_div[] = {
 	/*      pixelclk    bpp8    bpp10   bpp12 */
 	{
-		35500000,  { 0x0328, 0x0000, 0x0000 },
+		35500000,  { 0x0628, 0x0000, 0x0000 },
 	}, {
-		44900000,  { 0x0128, 0x0000, 0x0000 },
+		44900000,  { 0x0228, 0x0000, 0x0000 },
 	}, {
-		71000000,  { 0x0314, 0x0000, 0x0000 },
+		71000000,  { 0x0614, 0x0000, 0x0000 },
 	}, {
-		90000000,  { 0x0114, 0x0000, 0x0000 },
+		90000000,  { 0x0214, 0x0000, 0x0000 },
 	}, {
-		140250000, { 0x030a, 0x0000, 0x0000 },
+		140250000, { 0x060a, 0x0000, 0x0000 },
 	}, {
-		182750000, { 0x010a, 0x0000, 0x0000 },
+		182750000, { 0x020a, 0x0000, 0x0000 },
 	}, {
-		281250000, { 0x0305, 0x0000, 0x0000 },
+		281250000, { 0x0605, 0x0000, 0x0000 },
 	}, {
-		297000000, { 0x0105, 0x0000, 0x0000 },
+		297000000, { 0x0405, 0x0000, 0x0000 },
 	}, {
 		~0UL,      { 0x0000, 0x0000, 0x0000 },
 	}
@@ -220,9 +223,8 @@
 
 static const struct dw_hdmi_phy_config rcar_du_hdmienc_phy_config[] = {
 	/*pixelclk   symbol   term   vlev*/
-	{ 74250000,  0x8009, 0x0004, 0x0272},
-	{ 148500000, 0x802b, 0x0004, 0x028d},
-	{ 297000000, 0x8039, 0x0005, 0x028d},
+	{ 165000000, 0x0c88, 0x0007, 0x000c},
+	{ 297000000, 0x03c8, 0x0004, 0x000c},
 	{ ~0UL,	     0x0000, 0x0000, 0x0000}
 };
 
@@ -340,8 +342,8 @@
 	}
 
 	if (dw_hdmi_use)
-		ret = dw_hdmi_bind(hdmienc->dev, NULL, rcdu->ddev, encoder,
-				iores, irq, plat_data);
+		ret = dw_hdmi_bind(hdmienc->dev, rcdu->dev, rcdu->ddev,
+				   encoder, iores, irq, plat_data);
 
 	if (bridge) {
 		ret = drm_bridge_attach(rcdu->ddev, bridge);
diff --git a/drivers/gpu/drm/rcar-du/rcar_lvds_regs.h b/drivers/gpu/drm/rcar-du/rcar_lvds_regs.h
index 3c019d1..2ce9277 100644
--- a/drivers/gpu/drm/rcar-du/rcar_lvds_regs.h
+++ b/drivers/gpu/drm/rcar-du/rcar_lvds_regs.h
@@ -1,7 +1,7 @@
 /*
  * rcar_lvds_regs.h  --  R-Car LVDS Interface Registers Definitions
  *
- * Copyright (C) 2013-2016 Renesas Electronics Corporation
+ * Copyright (C) 2013-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -27,9 +27,9 @@
 #define LVDCR1				0x0004
 #define LVDCR1_CKSEL			(1 << 15)		/* Gen2 only */
 #define LVDCR1_CHSTBY_GEN2(n)		(3 << (2 + (n) * 2))	/* Gen2 only */
-#define LVDCR1_CHSTBY_GEN3(n)		(1 << (2 + (n) * 2))	/* Gen3 only */
+#define LVDCR1_CHSTBY_GEN3(n)		(3 << (2 + (n) * 2))	/* Gen3 only */
 #define LVDCR1_CLKSTBY_GEN2		(3 << 0)		/* Gen2 only */
-#define LVDCR1_CLKSTBY_GEN3		(1 << 0)		/* Gen3 only */
+#define LVDCR1_CLKSTBY_GEN3		(3 << 0)		/* Gen3 only */
 
 #define LVDPLLCR			0x0008
 #define LVDPLLCR_CEEN			(1 << 14)
diff --git a/drivers/hwspinlock/rcar_hwspinlock.c b/drivers/hwspinlock/rcar_hwspinlock.c
index 35ba8c1..b92db1b 100644
--- a/drivers/hwspinlock/rcar_hwspinlock.c
+++ b/drivers/hwspinlock/rcar_hwspinlock.c
@@ -1,7 +1,7 @@
 /*
  * rcar_hwspinlock.c
  *
- * Copyright (C) 2016 Renesas Electronics Corporation
+ * Copyright (C) 2016-2017 Renesas Electronics Corporation
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2
@@ -13,7 +13,6 @@
  * GNU General Public License for more details.
  */
 #include <linux/hwspinlock.h>
-#include <linux/clk.h>
 #include <linux/kernel.h>
 #include <linux/module.h>
 #include <linux/pm_runtime.h>
@@ -60,18 +59,6 @@
 	struct hwspinlock_device	*bank;
 	struct hwspinlock		*lock;
 	struct resource			*res = NULL;
-	struct clk			*clock;
-
-	/* enable MFIS clock */
-	clock = of_clk_get(pdev->dev.of_node, 0);
-	if (!clock) {
-		dev_err(&pdev->dev, "Failed to get clock.\n");
-		ret = PTR_ERR(clock);
-		goto out;
-	}
-	clk_prepare_enable(clock);
-
-	pm_runtime_enable(&pdev->dev);
 
 	/* map MFIS register */
 	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
@@ -80,7 +67,7 @@
 	if (IS_ERR(addr)) {
 		dev_err(&pdev->dev, "Failed to remap MFIS Lock register.\n");
 		ret = PTR_ERR(addr);
-		goto clk_disable;
+		goto out;
 	}
 
 	/* create hwspinlock control info */
@@ -90,7 +77,7 @@
 	if (!bank) {
 		dev_err(&pdev->dev, "Failed to allocate memory.\n");
 		ret = PTR_ERR(bank);
-		goto clk_disable;
+		goto out;
 	}
 
 	for (idx = 0; idx < RCAR_HWSPINLOCK_NUM; idx++) {
@@ -99,15 +86,13 @@
 	}
 	platform_set_drvdata(pdev, bank);
 
+	pm_runtime_enable(&pdev->dev);
+
 	/* register hwspinlock */
 	ret = hwspin_lock_register(bank, &pdev->dev, &rcar_hwspinlock_ops,
 				   0, RCAR_HWSPINLOCK_NUM);
-	if (!ret)
-		goto out;
-
-clk_disable:
-	if (clock)
-		clk_disable_unprepare(clock);
+	if (ret)
+		pm_runtime_disable(&pdev->dev);
 
 out:
 	return ret;
@@ -116,7 +101,6 @@
 static int rcar_hwspinlock_remove(struct platform_device *pdev)
 {
 	int		ret;
-	struct clk	*clock = NULL;
 
 	ret = hwspin_lock_unregister(platform_get_drvdata(pdev));
 	if (ret) {
@@ -125,9 +109,6 @@
 	}
 
 	pm_runtime_disable(&pdev->dev);
-	clock = of_clk_get(pdev->dev.of_node, 0);
-	if (clock)
-		clk_disable_unprepare(clock);
 
 	return 0;
 }
diff --git a/drivers/i2c/busses/i2c-rcar.c b/drivers/i2c/busses/i2c-rcar.c
index b4dde6a..4989496 100644
--- a/drivers/i2c/busses/i2c-rcar.c
+++ b/drivers/i2c/busses/i2c-rcar.c
@@ -141,6 +141,7 @@
 	struct dma_chan *dma_rx;
 	struct scatterlist sg;
 	enum dma_data_direction dma_direction;
+	int suspended;
 };
 
 #define rcar_i2c_priv_to_dev(p)		((p)->adap.dev.parent)
@@ -919,6 +920,9 @@
 	int i, ret;
 	long time_left;
 
+	if (priv->suspended)
+		return -EBUSY;
+
 	pm_runtime_get_sync(dev);
 
 	ret = rcar_i2c_bus_barrier(priv);
@@ -1129,9 +1133,11 @@
 static int rcar_i2c_suspend(struct device *dev)
 {
 	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
 	struct platform_device *pdev = to_platform_device(dev);
+	struct rcar_i2c_priv *priv = platform_get_drvdata(pdev);
 
+	priv->suspended = 1;
+#ifdef CONFIG_RCAR_DDR_BACKUP
 	pm_runtime_get_sync(dev);
 	ret = rcar_i2c_save_regs(pdev);
 	pm_runtime_put(dev);
@@ -1142,19 +1148,20 @@
 static int rcar_i2c_resume(struct device *dev)
 {
 	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
 	struct platform_device *pdev = to_platform_device(dev);
+	struct rcar_i2c_priv *priv = platform_get_drvdata(pdev);
 
+#ifdef CONFIG_RCAR_DDR_BACKUP
 	pm_runtime_get_sync(dev);
 	ret = rcar_i2c_restore_regs(pdev);
 	pm_runtime_put(dev);
 #endif /* CONFIG_RCAR_DDR_BACKUP */
+	priv->suspended = 0;
 	return ret;
 }
 
 static const struct dev_pm_ops rcar_i2c_pm_ops = {
-	.suspend = rcar_i2c_suspend,
-	.resume_early = rcar_i2c_resume,
+	SET_LATE_SYSTEM_SLEEP_PM_OPS(rcar_i2c_suspend,rcar_i2c_resume)
 };
 
 #define DEV_PM_OPS (&rcar_i2c_pm_ops)
diff --git a/drivers/media/i2c/adv7482.c b/drivers/media/i2c/adv7482.c
index 6e5dddb..f59d0ca 100644
--- a/drivers/media/i2c/adv7482.c
+++ b/drivers/media/i2c/adv7482.c
@@ -2,7 +2,7 @@
  * drivers/media/i2c/adv7482.c
  *     This file is Analog Devices ADV7482 HDMI receiver driver.
  *
- * Copyright (C) 2015-2016 Renesas Electronics Corporation
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2
@@ -2349,41 +2349,63 @@
 	struct adv7482_link_config link_config;
 	int ret;
 
-	ret = adv7482_write_register(client, ADV7482_I2C_IO,
-				ADV7482_IO_PWR_MAN_REG, ADV7482_IO_PWR_ON);
-	if (ret < 0)
-		return ret;
-
 	ret = adv7482_parse_dt(dev->of_node, &link_config);
 	if (ret)
 		return ret;
 
-	/* Initializes ADV7482 to its default values */
-	ret = adv7482_write_registers(client, link_config.regs);
+	/* SW reset ADV7482 to its default values */
+	if (link_config.sw_reset) {
+		ret = adv7482_write_registers(client, adv7482_sw_reset);
 
-	/* Power down */
-	ret = adv7482_write_registers(client, link_config.power_down);
+		/* check rd_info */
+		{
+			u8 msb;
+			u8 lsb;
+
+			ret = adv7482_read_register(client, ADV7482_I2C_IO,
+					ADV7482_IO_RD_INFO1_REG, &lsb);
+			if (ret < 0)
+				return ret;
+
+			ret = adv7482_read_register(client, ADV7482_I2C_IO,
+					ADV7482_IO_RD_INFO2_REG, &msb);
+			if (ret < 0)
+				return ret;
+		}
+	}
+
+	if (link_config.hdmi_in) {
+		ret = adv7482_write_registers(client,
+				adv7482_init_txa_4lane);
+		/* Power down */
+		ret = adv7482_write_registers(client,
+				adv7482_power_down_txa_4lane);
+	}
+
+	/* Initializes ADV7482 to its default values */
+	if (link_config.sdp_in) {
+		ret = adv7482_write_registers(client,
+						adv7482_init_txb_1lane);
+		/* Power down */
+		ret = adv7482_write_registers(client,
+						adv7482_power_down_txb_1lane);
+	}
 
 	if (link_config.sdp_in && link_config.hdmi_in) {
 		/* Power up hdmi rx */
 		ret = adv7482_write_registers(client,
 						adv7482_power_up_hdmi_rx);
-		if (ret < 0)
-			return ret;
-
 		/* Enable csi4 and sci1 */
 		ret = adv7482_write_registers(client,
 						adv7482_enable_csi4_csi1);
-		if (ret < 0)
-			return ret;
 	}
 
 	return ret;
 }
 
-static SIMPLE_DEV_PM_OPS(adv7482_pm_ops, adv7482_suspend, adv7482_resume);
-#define ADV7482_PM_OPS (&adv7482_pm_ops)
-
+const struct dev_pm_ops adv7482_pm_ops = {
+	SET_LATE_SYSTEM_SLEEP_PM_OPS(adv7482_suspend, adv7482_resume)
+};
 #else
 #define ADV7482_PM_OPS NULL
 #endif
@@ -2399,7 +2421,7 @@
 static struct i2c_driver adv7482_driver = {
 	.driver = {
 		.name	= DRIVER_NAME,
-		.pm = ADV7482_PM_OPS,
+		.pm = &adv7482_pm_ops,
 		.of_match_table = adv7482_of_ids,
 	},
 	.probe		= adv7482_probe,
diff --git a/drivers/media/platform/rcar-vin/rcar-core.c b/drivers/media/platform/rcar-vin/rcar-core.c
index 05d5485..287917c 100644
--- a/drivers/media/platform/rcar-vin/rcar-core.c
+++ b/drivers/media/platform/rcar-vin/rcar-core.c
@@ -1,7 +1,7 @@
 /*
  * Driver for Renesas R-Car VIN
  *
- * Copyright (C) 2016 Renesas Electronics Corp.
+ * Copyright (C) 2016-2017 Renesas Electronics Corp.
  * Copyright (C) 2011-2013 Renesas Solutions Corp.
  * Copyright (C) 2013 Cogent Embedded, Inc., <source@cogentembedded.com>
  * Copyright (C) 2008 Magnus Damm
@@ -838,6 +838,9 @@
 	struct rvin_dev *vin = notifier_to_vin(notifier);
 	unsigned int i;
 
+	if (!subdev->dev)
+		return;
+
 	mutex_lock(&vin->group->lock);
 	for (i = 0; i < RVIN_CSI_MAX; i++) {
 		struct device_node *del = subdev->dev->of_node;
@@ -1445,12 +1448,12 @@
 
 	vin->dev = &pdev->dev;
 
-	if (soc_device_match(r8a7795es1))
-		vin->info = &rcar_info_r8a7795_es1x;
-
 	vin->info = match->data;
 	vin->last_input = NULL;
 
+	if (soc_device_match(r8a7795es1))
+		vin->info = &rcar_info_r8a7795_es1x;
+
 	mem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
 	if (mem == NULL)
 		return -EINVAL;
@@ -1495,11 +1498,11 @@
 
 	rvin_v4l2_remove(vin);
 
+	v4l2_async_notifier_unregister(&vin->notifier);
+
 	if (vin->group)
 		rvin_group_delete(vin);
 
-	v4l2_async_notifier_unregister(&vin->notifier);
-
 	rvin_dma_remove(vin);
 
 	return 0;
@@ -1509,23 +1512,38 @@
 static int rcar_vin_suspend(struct device *dev)
 {
 	struct rvin_dev *vin = dev_get_drvdata(dev);
+	int ret;
 
 	if ((vin->info->chip == RCAR_GEN3) &&
 		((vin->index == 0) || (vin->index == 4)))
 		vin->chsel = rvin_get_chsel(vin);
 
-	return 0;
+	if (vin->state != STALLED)
+		return 0;
+
+	ret = rvin_suspend_stop_streaming(vin);
+
+	pm_runtime_put(vin->dev);
+
+	return ret;
 }
 
 static int rcar_vin_resume(struct device *dev)
 {
 	struct rvin_dev *vin = dev_get_drvdata(dev);
+	int ret;
 
 	if ((vin->info->chip == RCAR_GEN3) &&
 		((vin->index == 0) || (vin->index == 4)))
 		rvin_set_chsel(vin, vin->chsel);
 
-	return 0;
+	if (vin->state != STALLED)
+		return 0;
+
+	pm_runtime_get_sync(vin->dev);
+	ret = rvin_resume_start_streaming(vin);
+
+	return ret;
 }
 
 static SIMPLE_DEV_PM_OPS(rcar_vin_pm_ops,
diff --git a/drivers/media/platform/rcar-vin/rcar-csi2.c b/drivers/media/platform/rcar-vin/rcar-csi2.c
index 7440cfc..529e845 100644
--- a/drivers/media/platform/rcar-vin/rcar-csi2.c
+++ b/drivers/media/platform/rcar-vin/rcar-csi2.c
@@ -1,7 +1,7 @@
 /*
  * Driver for Renesas R-Car MIPI CSI-2
  *
- * Copyright (C) 2016 Renesas Electronics Corp.
+ * Copyright (C) 2016-2017 Renesas Electronics Corp.
  *
  * 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
@@ -13,6 +13,7 @@
 #include <linux/interrupt.h>
 #include <linux/module.h>
 #include <linux/of.h>
+#include <linux/of_device.h>
 #include <linux/platform_device.h>
 #include <linux/pm_runtime.h>
 #include <linux/sys_soc.h>
@@ -98,50 +99,90 @@
 /* PHY Test Interface Clear bits */
 #define PHTC_TESTCLR			(1 << 0)
 
-/* PHY Frequency Control bits */
-#define PHYPLL_HSFREQRANGE_80MBPS	(0x00 << 16)
-#define PHYPLL_HSFREQRANGE_90MBPS	(0x10 << 16)
-#define PHYPLL_HSFREQRANGE_100MBPS	(0x20 << 16)
-#define PHYPLL_HSFREQRANGE_110MBPS	(0x30 << 16)
-#define PHYPLL_HSFREQRANGE_120MBPS	(0x01 << 16)
-#define PHYPLL_HSFREQRANGE_130MBPS	(0x11 << 16)
-#define PHYPLL_HSFREQRANGE_140MBPS	(0x21 << 16)
-#define PHYPLL_HSFREQRANGE_150MBPS	(0x31 << 16)
-#define PHYPLL_HSFREQRANGE_160MBPS	(0x02 << 16)
-#define PHYPLL_HSFREQRANGE_170MBPS	(0x12 << 16)
-#define PHYPLL_HSFREQRANGE_180MBPS	(0x22 << 16)
-#define PHYPLL_HSFREQRANGE_190MBPS	(0x32 << 16)
-#define PHYPLL_HSFREQRANGE_205MBPS	(0x03 << 16)
-#define PHYPLL_HSFREQRANGE_220MBPS	(0x13 << 16)
-#define PHYPLL_HSFREQRANGE_235MBPS	(0x23 << 16)
-#define PHYPLL_HSFREQRANGE_250MBPS	(0x33 << 16)
-#define PHYPLL_HSFREQRANGE_275MBPS	(0x04 << 16)
-#define PHYPLL_HSFREQRANGE_300MBPS	(0x14 << 16)
-#define PHYPLL_HSFREQRANGE_325MBPS	(0x05 << 16)
-#define PHYPLL_HSFREQRANGE_350MBPS	(0x15 << 16)
-#define PHYPLL_HSFREQRANGE_400MBPS	(0x25 << 16)
-#define PHYPLL_HSFREQRANGE_450MBPS	(0x06 << 16)
-#define PHYPLL_HSFREQRANGE_500MBPS	(0x16 << 16)
-#define PHYPLL_HSFREQRANGE_550MBPS	(0x07 << 16)
-#define PHYPLL_HSFREQRANGE_600MBPS	(0x17 << 16)
-#define PHYPLL_HSFREQRANGE_650MBPS	(0x08 << 16)
-#define PHYPLL_HSFREQRANGE_700MBPS	(0x18 << 16)
-#define PHYPLL_HSFREQRANGE_750MBPS	(0x09 << 16)
-#define PHYPLL_HSFREQRANGE_800MBPS	(0x19 << 16)
-#define PHYPLL_HSFREQRANGE_850MBPS	(0x29 << 16)
-#define PHYPLL_HSFREQRANGE_900MBPS	(0x39 << 16)
-#define PHYPLL_HSFREQRANGE_950MBPS	(0x0A << 16)
-#define PHYPLL_HSFREQRANGE_1000MBPS	(0x1A << 16)
-#define PHYPLL_HSFREQRANGE_1050MBPS	(0x2A << 16)
-#define PHYPLL_HSFREQRANGE_1100MBPS	(0x3A << 16)
-#define PHYPLL_HSFREQRANGE_1150MBPS	(0x0B << 16)
-#define PHYPLL_HSFREQRANGE_1200MBPS	(0x1B << 16)
-#define PHYPLL_HSFREQRANGE_1250MBPS	(0x2B << 16)
-#define PHYPLL_HSFREQRANGE_1300MBPS	(0x3B << 16)
-#define PHYPLL_HSFREQRANGE_1350MBPS	(0x0C << 16)
-#define PHYPLL_HSFREQRANGE_1400MBPS	(0x1C << 16)
-#define PHYPLL_HSFREQRANGE_1450MBPS	(0x2C << 16)
-#define PHYPLL_HSFREQRANGE_1500MBPS	(0x3C << 16)
+/* PHY Frequency Control */
+#define CSI2_FRE_NUM	43
+
+enum fre_range {
+	BPS_80M,
+	BPS_90M,
+	BPS_100M,
+	BPS_110M,
+	BPS_120M,
+	BPS_130M,
+	BPS_140M,
+	BPS_150M,
+	BPS_160M,
+	BPS_170M,
+	BPS_180M,
+	BPS_190M,
+	BPS_205M,
+	BPS_220M,
+	BPS_235M,
+	BPS_250M,
+	BPS_275M,
+	BPS_300M,
+	BPS_325M,
+	BPS_350M,
+	BPS_400M,
+	BPS_450M,
+	BPS_500M,
+	BPS_550M,
+	BPS_600M,
+	BPS_650M,
+	BPS_700M,
+	BPS_750M,
+	BPS_800M,
+	BPS_850M,
+	BPS_900M,
+	BPS_950M,
+	BPS_1000M,
+	BPS_1050M,
+	BPS_1100M,
+	BPS_1150M,
+	BPS_1200M,
+	BPS_1250M,
+	BPS_1300M,
+	BPS_1350M,
+	BPS_1400M,
+	BPS_1450M,
+	BPS_1500M,
+};
+
+struct rcar_csi2_info {
+	int fre_range[CSI2_FRE_NUM];
+};
+
+static const struct rcar_csi2_info rcar_csi2_info_r8a7795 = {
+	.fre_range = {
+		(0x00 << 16), (0x10 << 16), (0x20 << 16), (0x30 << 16),
+		(0x01 << 16), (0x11 << 16), (0x21 << 16), (0x31 << 16),
+		(0x02 << 16), (0x12 << 16), (0x22 << 16), (0x32 << 16),
+		(0x03 << 16), (0x13 << 16), (0x23 << 16), (0x33 << 16),
+		(0x04 << 16), (0x14 << 16), (0x25 << 16), (0x35 << 16),
+		(0x05 << 16), (0x26 << 16), (0x36 << 16), (0x37 << 16),
+		(0x07 << 16), (0x18 << 16), (0x28 << 16), (0x39 << 16),
+		(0x09 << 16), (0x19 << 16), (0x29 << 16), (0x3a << 16),
+		(0x0a << 16), (0x1a << 16), (0x2a << 16), (0x3b << 16),
+		(0x0b << 16), (0x1b << 16), (0x2b << 16), (0x3c << 16),
+		(0x0c << 16), (0x1c << 16), (0x2c << 16),
+	},
+};
+
+static const struct rcar_csi2_info rcar_csi2_info_r8a7796 = {
+	.fre_range = {
+		(0x00 << 16), (0x10 << 16), (0x20 << 16), (0x30 << 16),
+		(0x01 << 16), (0x11 << 16), (0x21 << 16), (0x31 << 16),
+		(0x02 << 16), (0x12 << 16), (0x22 << 16), (0x32 << 16),
+		(0x03 << 16), (0x13 << 16), (0x23 << 16), (0x33 << 16),
+		(0x04 << 16), (0x14 << 16), (0x05 << 16), (0x15 << 16),
+		(0x25 << 16), (0x06 << 16), (0x16 << 16), (0x07 << 16),
+		(0x17 << 16), (0x08 << 16), (0x18 << 16), (0x09 << 16),
+		(0x19 << 16), (0x29 << 16), (0x39 << 16), (0x0a << 16),
+		(0x1a << 16), (0x2a << 16), (0x3a << 16), (0x0b << 16),
+		(0x1b << 16), (0x2b << 16), (0x3b << 16), (0x0c << 16),
+		(0x1c << 16), (0x2c << 16), (0x3c << 16),
+	},
+};
 
 enum rcar_csi2_pads {
 	RCAR_CSI2_SINK,
@@ -159,6 +200,7 @@
 	struct device *dev;
 	void __iomem *base;
 	spinlock_t lock;
+	const struct rcar_csi2_info *info;
 
 	unsigned short lanes;
 	unsigned char swap[4];
@@ -286,7 +328,7 @@
 	case 1:
 		fld = FLD_FLD_NUM(1) | FLD_FLD_EN;
 		phycnt = PHYCNT_ENABLECLK | PHYCNT_ENABLE_0;
-		phypll = PHYPLL_HSFREQRANGE_400MBPS;
+		phypll = priv->info->fre_range[BPS_205M];
 		break;
 	case 4:
 		fld = FLD_FLD_NUM(2) | FLD_FLD_EN4 | FLD_FLD_EN3 |
@@ -297,18 +339,17 @@
 		/* Calculate MBPS per lane, assume 32 bits per pixel at 60Hz */
 		pixels = (priv->mf.width * priv->mf.height);
 		if (pixels <= 640 * 480)
-			phypll = PHYPLL_HSFREQRANGE_100MBPS;
+			phypll = priv->info->fre_range[BPS_100M];
 		else if (pixels <= 720 * 576)
-			phypll = PHYPLL_HSFREQRANGE_190MBPS;
+			phypll = priv->info->fre_range[BPS_190M];
 		else if (pixels <= 1280 * 720)
-			phypll = PHYPLL_HSFREQRANGE_450MBPS;
+			phypll = priv->info->fre_range[BPS_450M];
 		else if (pixels <= 1920 * 1080) {
 			if (priv->mf.field == V4L2_FIELD_NONE)
-				phypll = PHYPLL_HSFREQRANGE_900MBPS;
+				phypll = priv->info->fre_range[BPS_900M];
 			else
-				phypll = PHYPLL_HSFREQRANGE_450MBPS;
-			}
-		else
+				phypll = priv->info->fre_range[BPS_450M];
+		} else
 			goto error;
 
 		break;
@@ -316,6 +357,8 @@
 		goto error;
 	}
 
+	csi_dbg(priv, "PHYPLL:0x%x\n", phypll);
+
 	/* Init */
 	iowrite32(TREF_TREF, priv->base + TREF_REG);
 	rcar_csi2_reset(priv);
@@ -330,20 +373,20 @@
 		  priv->base + LSWAP_REG);
 
 	if (!soc_device_match(r8a7795es1x) && !soc_device_match(r8a7796)) {
-		/* Set PHY Test Interface Write Register for external
-		 * reference resistor is unnecessary in R-Car H3(WS2.0)
-		 */
-		iowrite32(0x012701e2, priv->base + PHTW_REG);
+		/* Set PHY Test Interface Write Register in R-Car H3(ES2.0) */
+		iowrite32(0x01cc01e2, priv->base + PHTW_REG);
 		iowrite32(0x010101e3, priv->base + PHTW_REG);
 		iowrite32(0x010101e4, priv->base + PHTW_REG);
 		iowrite32(0x01100104, priv->base + PHTW_REG);
+		iowrite32(0x01030100, priv->base + PHTW_REG);
+		iowrite32(0x01800107, priv->base + PHTW_REG);
 	}
 
 	/* Start */
 	iowrite32(phypll, priv->base + PHYPLL_REG);
 
-	/* Set CSI0CLK Frequency Configuration Preset Register for external
-	 * reference resistor is unnecessary in R-Car H3(WS2.0)
+	/* Set CSI0CLK Frequency Configuration Preset Register
+	 * in R-Car H3(ES2.0)
 	 */
 	if (!soc_device_match(r8a7795es1x) && !soc_device_match(r8a7796))
 		iowrite32(CSI0CLKFREQRANGE(32), priv->base + CSI0CLKFCPR_REG);
@@ -450,9 +493,14 @@
  */
 
 static const struct of_device_id rcar_csi2_of_table[] = {
-	{ .compatible = "renesas,r8a7795-csi2" },
-	{ .compatible = "renesas,r8a7796-csi2" },
-	{ .compatible = "renesas,rcar-gen3-csi2" },
+	{
+		.compatible = "renesas,r8a7795-csi2",
+		.data = &rcar_csi2_info_r8a7795,
+	},
+	{
+		.compatible = "renesas,r8a7796-csi2",
+		.data = &rcar_csi2_info_r8a7796,
+	},
 	{ },
 };
 MODULE_DEVICE_TABLE(of, rcar_csi2_of_table);
@@ -550,6 +598,7 @@
 static int rcar_csi2_probe(struct platform_device *pdev)
 {
 	struct rcar_csi2 *priv;
+	const struct of_device_id *match;
 	unsigned int i;
 	int ret;
 	u32 vc_num;
@@ -558,6 +607,14 @@
 	if (!priv)
 		return -ENOMEM;
 
+	match = of_match_device(of_match_ptr(rcar_csi2_of_table), &pdev->dev);
+	if (!match)
+		return -ENODEV;
+	priv->info = match->data;
+
+	/* HSFREQRANGE bit information of H3(ES1.x) and M3(WS1.0) are same. */
+	if (soc_device_match(r8a7795es1x))
+		priv->info = &rcar_csi2_info_r8a7796;
 
 	priv->dev = &pdev->dev;
 	spin_lock_init(&priv->lock);
@@ -577,7 +634,6 @@
 	vc_num = priv->vc_num;
 	platform_set_drvdata(pdev, priv);
 
-retry:
 	priv->subdev.owner = THIS_MODULE;
 	priv->subdev.dev = &pdev->dev;
 	v4l2_subdev_init(&priv->subdev, &rcar_csi2_subdev_ops);
@@ -602,10 +658,6 @@
 	if (ret < 0)
 		return ret;
 
-	vc_num--;
-	if (vc_num > 0)
-		goto retry;
-
 	pm_runtime_enable(&pdev->dev);
 
 	csi_info(priv, "%d lanes found. virtual channel number %d use\n",
@@ -625,11 +677,34 @@
 	return 0;
 }
 
+static int rcar_csi2_suspend(struct device *dev)
+{
+	struct rcar_csi2 *priv = dev_get_drvdata(dev);
+
+	pm_runtime_put_sync(priv->dev);
+
+	return 0;
+}
+
+static int rcar_csi2_resume(struct device *dev)
+{
+	struct rcar_csi2 *priv = dev_get_drvdata(dev);
+
+	pm_runtime_get_sync(priv->dev);
+
+	return 0;
+}
+
+const struct dev_pm_ops rcar_csi2_pm_ops = {
+	SET_LATE_SYSTEM_SLEEP_PM_OPS(rcar_csi2_suspend, rcar_csi2_resume)
+};
+
 static struct platform_driver __refdata rcar_csi2_pdrv = {
 	.remove	= rcar_csi2_remove,
 	.probe	= rcar_csi2_probe,
 	.driver	= {
 		.name	= "rcar-csi2",
+		.pm = &rcar_csi2_pm_ops,
 		.of_match_table	= of_match_ptr(rcar_csi2_of_table),
 	},
 };
diff --git a/drivers/media/platform/rcar-vin/rcar-dma.c b/drivers/media/platform/rcar-vin/rcar-dma.c
index 3e7fb7d..667b162 100644
--- a/drivers/media/platform/rcar-vin/rcar-dma.c
+++ b/drivers/media/platform/rcar-vin/rcar-dma.c
@@ -1,7 +1,7 @@
 /*
  * Driver for Renesas R-Car VIN
  *
- * Copyright (C) 2016 Renesas Electronics Corp.
+ * Copyright (C) 2016-2017 Renesas Electronics Corp.
  * Copyright (C) 2011-2013 Renesas Solutions Corp.
  * Copyright (C) 2013 Cogent Embedded, Inc., <source@cogentembedded.com>
  * Copyright (C) 2008 Magnus Damm
@@ -1249,9 +1249,12 @@
 	 * If capture is stalled add buffer to HW and restart
 	 * capturing if HW is ready to continue.
 	 */
-	if (vin->state == STALLED)
-		if (rvin_fill_hw(vin))
+	if (vin->state == STALLED) {
+		if (rvin_fill_hw(vin)) {
 			rvin_capture_on(vin);
+			vin->state = RUNNING;
+		}
+	}
 
 	spin_unlock_irqrestore(&vin->qlock, flags);
 }
@@ -1416,6 +1419,66 @@
 	rvin_disable_interrupts(vin);
 }
 
+int rvin_resume_start_streaming(struct rvin_dev *vin)
+{
+	unsigned long flags;
+	int ret;
+
+	ret = __rvin_start_streaming(vin);
+	if (ret)
+		return ret;
+
+	spin_lock_irqsave(&vin->qlock, flags);
+
+	vin->sequence = 0;
+
+	rvin_crop_scale_comp(vin);
+	ret = rvin_setup(vin);
+
+	/* Return all buffers if something went wrong */
+	if (ret) {
+		return_all_buffers(vin, VB2_BUF_STATE_QUEUED);
+		__rvin_stop_streaming(vin);
+	}
+
+	spin_unlock_irqrestore(&vin->qlock, flags);
+
+	return ret;
+}
+
+int rvin_suspend_stop_streaming(struct rvin_dev *vin)
+{
+	unsigned long flags;
+	struct v4l2_subdev *source, *bridge = NULL;
+
+	/* Release all active buffers */
+	spin_lock_irqsave(&vin->qlock, flags);
+	return_all_buffers(vin, VB2_BUF_STATE_ERROR);
+	spin_unlock_irqrestore(&vin->qlock, flags);
+
+	__rvin_stop_streaming(vin);
+	source = vin_to_source(vin);
+	if (!source)
+		return -EINVAL;
+
+	if (vin_have_bridge(vin)) {
+		bridge = vin_to_bridge(vin);
+
+		if (!bridge)
+			return -EINVAL;
+
+		mutex_lock(&vin->group->lock);
+		bridge->entity.stream_count = 0;
+		source->entity.stream_count = 0;
+		mutex_unlock(&vin->group->lock);
+	}
+
+	/* disable interrupts */
+	rvin_disable_interrupts(vin);
+
+	return 0;
+}
+
 static const struct vb2_ops rvin_qops = {
 	.queue_setup		= rvin_queue_setup,
 	.buf_prepare		= rvin_buffer_prepare,
diff --git a/drivers/media/platform/rcar-vin/rcar-v4l2.c b/drivers/media/platform/rcar-vin/rcar-v4l2.c
index a0ad84c..ade1f8b 100644
--- a/drivers/media/platform/rcar-vin/rcar-v4l2.c
+++ b/drivers/media/platform/rcar-vin/rcar-v4l2.c
@@ -1,7 +1,7 @@
 /*
  * Driver for Renesas R-Car VIN
  *
- * Copyright (C) 2016 Renesas Electronics Corp.
+ * Copyright (C) 2016-2017 Renesas Electronics Corp.
  * Copyright (C) 2011-2013 Renesas Solutions Corp.
  * Copyright (C) 2013 Cogent Embedded, Inc., <source@cogentembedded.com>
  * Copyright (C) 2008 Magnus Damm
@@ -530,10 +530,17 @@
 {
 	struct rvin_dev *vin = video_drvdata(file);
 	struct v4l2_subdev *sd = vin_to_source(vin);
+	struct rvin_source_fmt source;
 
 	if (crop->type != V4L2_BUF_TYPE_VIDEO_CAPTURE)
 		return -EINVAL;
 
+	__rvin_try_format_source(vin, V4L2_SUBDEV_FORMAT_TRY,
+				 &vin->format, &source);
+
+	vin->source.width = source.width;
+	vin->source.height = source.height;
+
 	return v4l2_subdev_call(sd, video, g_pixelaspect, &crop->pixelaspect);
 }
 
diff --git a/drivers/media/platform/rcar-vin/rcar-vin.h b/drivers/media/platform/rcar-vin/rcar-vin.h
index d85d0ab..1f9a8dd 100644
--- a/drivers/media/platform/rcar-vin/rcar-vin.h
+++ b/drivers/media/platform/rcar-vin/rcar-vin.h
@@ -1,7 +1,7 @@
 /*
  * Driver for Renesas R-Car VIN
  *
- * Copyright (C) 2016 Renesas Electronics Corp.
+ * Copyright (C) 2016-2017 Renesas Electronics Corp.
  * Copyright (C) 2011-2013 Renesas Solutions Corp.
  * Copyright (C) 2013 Cogent Embedded, Inc., <source@cogentembedded.com>
  * Copyright (C) 2008 Magnus Damm
@@ -274,4 +274,7 @@
 int rvin_set_chsel(struct rvin_dev *vin, u8 chsel);
 int rvin_get_chsel(struct rvin_dev *vin);
 
+int rvin_resume_start_streaming(struct rvin_dev *vin);
+int rvin_suspend_stop_streaming(struct rvin_dev *vin);
+
 #endif
diff --git a/drivers/media/platform/vsp1/vsp1.h b/drivers/media/platform/vsp1/vsp1.h
index 665772f..8a95c7f 100644
--- a/drivers/media/platform/vsp1/vsp1.h
+++ b/drivers/media/platform/vsp1/vsp1.h
@@ -114,7 +114,7 @@
 };
 
 int vsp1_gen3_vspdl_check(struct vsp1_device *vsp1);
-int vsp1_device_get(struct vsp1_device *vsp1);
+int vsp1_device_get(struct vsp1_device *vsp1, unsigned int index);
 void vsp1_device_put(struct vsp1_device *vsp1);
 void vsp1_underrun_workaround(struct vsp1_device *vsp1, bool reset);
 
diff --git a/drivers/media/platform/vsp1/vsp1_brs.c b/drivers/media/platform/vsp1/vsp1_brs.c
index e9811a7..6a4079f 100644
--- a/drivers/media/platform/vsp1/vsp1_brs.c
+++ b/drivers/media/platform/vsp1/vsp1_brs.c
@@ -1,7 +1,7 @@
 /*
  * vsp1_brs.c  --  R-Car VSP1 Blend ROP Sub Unit
  *
- * Copyright (C) 2016 Renesas Electronics Corporation
+ * Copyright (C) 2016-2017 Renesas Electronics Corporation
  *
  * This file is based on the drivers/media/platform/vsp1/vsp1_bru.c
  *
@@ -112,23 +112,27 @@
 			   unsigned int pad, struct v4l2_mbus_framefmt *fmt)
 {
 	struct v4l2_mbus_framefmt *format;
+	struct vsp1_device *vsp1 = brs->entity.vsp1;
+	int brs_base;
 
-	switch (pad) {
-	case BRS_PAD_SINK(0):
+	brs_base = vsp1->info->rpf_count - vsp1->num_brs_inputs;
+
+	if (!pad)
+		goto not_set_code;
+
+	if (pad == brs_base) {
 		/* Default to YUV if the requested format is not supported. */
 		if (fmt->code != MEDIA_BUS_FMT_ARGB8888_1X32 &&
 		    fmt->code != MEDIA_BUS_FMT_AYUV8_1X32)
 			fmt->code = MEDIA_BUS_FMT_AYUV8_1X32;
-		break;
-
-	default:
+	} else {
 		/* The BRS can't perform format conversion. */
 		format = vsp1_entity_get_pad_format(&brs->entity, config,
-						    BRS_PAD_SINK(0));
+						    BRS_PAD_SINK(brs_base));
 		fmt->code = format->code;
-		break;
 	}
 
+not_set_code:
 	fmt->width = clamp(fmt->width, BRS_MIN_SIZE, BRS_MAX_SIZE);
 	fmt->height = clamp(fmt->height, BRS_MIN_SIZE, BRS_MAX_SIZE);
 	fmt->field = V4L2_FIELD_NONE;
@@ -140,9 +144,11 @@
 			  struct v4l2_subdev_format *fmt)
 {
 	struct vsp1_brs *brs = to_brs(subdev);
+	struct vsp1_device *vsp1 = brs->entity.vsp1;
 	struct v4l2_subdev_pad_config *config;
 	struct v4l2_mbus_framefmt *format;
 	int ret = 0;
+	int brs_base;
 
 	mutex_lock(&brs->entity.lock);
 
@@ -168,11 +174,13 @@
 		compose->height = format->height;
 	}
 
+	brs_base = vsp1->info->rpf_count - vsp1->num_brs_inputs;
+
 	/* Propagate the format code to all pads */
-	if (fmt->pad == BRS_PAD_SINK(0)) {
+	if (fmt->pad == BRS_PAD_SINK(brs_base)) {
 		unsigned int i;
 
-		for (i = 0; i <= brs->entity.source_pad; ++i) {
+		for (i = brs_base; i <= brs->entity.source_pad; ++i) {
 			format = vsp1_entity_get_pad_format(&brs->entity,
 							    config, i);
 			format->code = fmt->format.code;
@@ -290,9 +298,14 @@
 			  enum vsp1_entity_params params)
 {
 	struct vsp1_brs *brs = to_brs(&entity->subdev);
+	struct vsp1_device *vsp1 = brs->entity.vsp1;
 	struct v4l2_mbus_framefmt *format;
 	unsigned int flags;
 	unsigned int i;
+	unsigned int reg_offset = 3;	/* for use from RPF3 */
+	unsigned int brs_base;
+
+	brs_base = vsp1->info->rpf_count - vsp1->num_brs_inputs;
 
 	if (params != VSP1_ENTITY_PARAMS_INIT)
 		return;
@@ -303,18 +316,27 @@
 	if (pipe->vmute_flag) {
 		vsp1_brs_write(brs, dl, VI6_BRS_INCTRL, 0);
 		vsp1_brs_write(brs, dl, VI6_BRS_VIRRPF_SIZE,
-		  (format->width << VI6_BRS_VIRRPF_SIZE_HSIZE_SHIFT) |
-		  (format->height << VI6_BRS_VIRRPF_SIZE_VSIZE_SHIFT));
+			(format->width << VI6_BRS_VIRRPF_SIZE_HSIZE_SHIFT) |
+			(format->height << VI6_BRS_VIRRPF_SIZE_VSIZE_SHIFT));
 		vsp1_brs_write(brs, dl, VI6_BRS_VIRRPF_LOC, 0);
 		vsp1_brs_write(brs, dl, VI6_BRS_VIRRPF_COL, (0xFF << 24));
 
-		for (i = 0; i < brs->entity.source_pad; ++i) {
-			vsp1_brs_write(brs, dl, VI6_BRS_BLD(i),
-			VI6_BRS_BLD_CCMDX_255_SRC_A |
-			VI6_BRS_BLD_CCMDY_SRC_A |
-			VI6_BRS_BLD_ACMDX_255_SRC_A |
-			VI6_BRS_BLD_ACMDY_COEFY |
-			VI6_BRS_BLD_COEFY_MASK);
+		for (i = brs_base; i < brs->entity.source_pad; ++i) {
+			u32 ctrl = 0;
+
+			if (i == brs_base)
+				ctrl |= VI6_BRS_CTRL_DSTSEL_VRPF;
+
+			ctrl |= VI6_BRS_CTRL_SRCSEL_BRSIN(i - reg_offset);
+			vsp1_brs_write(brs, dl, VI6_BRS_CTRL(i - reg_offset),
+								ctrl);
+
+			vsp1_brs_write(brs, dl, VI6_BRS_BLD(i - reg_offset),
+						VI6_BRS_BLD_CCMDX_255_SRC_A |
+						VI6_BRS_BLD_CCMDY_SRC_A |
+						VI6_BRS_BLD_ACMDX_255_SRC_A |
+						VI6_BRS_BLD_ACMDY_COEFY |
+						VI6_BRS_BLD_COEFY_MASK);
 		}
 
 		return;
@@ -345,7 +367,7 @@
 	vsp1_brs_write(brs, dl, VI6_BRS_VIRRPF_COL, brs->bgcolor |
 		       (0xff << VI6_BRS_VIRRPF_COL_A_SHIFT));
 
-	for (i = 0; i < brs->entity.source_pad; ++i) {
+	for (i = reg_offset; i < brs->entity.source_pad; ++i) {
 		bool premultiplied = false;
 		u32 ctrl = 0;
 
@@ -367,18 +389,12 @@
 		/* Select the virtual RPF as the Blend/ROP unit A DST input to
 		 * serve as a background color.
 		 */
-		if (i == 0)
+		if (i == brs_base)
 			ctrl |= VI6_BRS_CTRL_DSTSEL_VRPF;
 
-		/* Route BRS inputs 0 to 3 as SRC inputs to Blend/ROP units A to
-		 * D in that order. The Blend/ROP unit B SRC is hardwired to the
-		 * ROP unit output, the corresponding register bits must be set
-		 * to 0.
-		 */
-		if (i != 1)
-			ctrl |= VI6_BRS_CTRL_SRCSEL_BRSIN(i);
+		ctrl |= VI6_BRS_CTRL_SRCSEL_BRSIN(i - reg_offset);
 
-		vsp1_brs_write(brs, dl, VI6_BRS_CTRL(i), ctrl);
+		vsp1_brs_write(brs, dl, VI6_BRS_CTRL(i - reg_offset), ctrl);
 
 		/* Harcode the blending formula to
 		 *
@@ -392,7 +408,7 @@
 		 *
 		 * otherwise.
 		 */
-		vsp1_brs_write(brs, dl, VI6_BRS_BLD(i),
+		vsp1_brs_write(brs, dl, VI6_BRS_BLD(i - reg_offset),
 			       VI6_BRS_BLD_CCMDX_255_SRC_A |
 			       (premultiplied ? VI6_BRS_BLD_CCMDY_COEFY :
 						VI6_BRS_BLD_CCMDY_SRC_A) |
diff --git a/drivers/media/platform/vsp1/vsp1_dl.c b/drivers/media/platform/vsp1/vsp1_dl.c
index 988f2b7..019ae2b 100644
--- a/drivers/media/platform/vsp1/vsp1_dl.c
+++ b/drivers/media/platform/vsp1/vsp1_dl.c
@@ -1,7 +1,7 @@
 /*
  * vsp1_dl.h  --  R-Car VSP1 Display List
  *
- * Copyright (C) 2015-2016 Renesas Corporation
+ * Copyright (C) 2015-2017 Renesas Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -583,11 +583,16 @@
 	return 0;
 }
 
-static void vsp1_dl_list_fill_header(struct vsp1_dl_list *dl, bool is_last)
+static void vsp1_dl_list_fill_header(struct vsp1_dl_list *dl, bool is_last,
+				     unsigned int lif_index)
 {
 	struct vsp1_dl_header_list *hdr = dl->header->lists;
 	struct vsp1_dl_body *dlb;
+	struct vsp1_device *vsp1 = dl->dlm->vsp1;
 	unsigned int num_lists = 0;
+	unsigned int init_bru_num, end_bru_num;
+	unsigned int init_brs_num, end_brs_num;
+	unsigned int i, rpf_update = 0;
 
 	/*
 	 * Fill the header with the display list bodies addresses and sizes. The
@@ -609,6 +614,28 @@
 
 	dl->header->num_lists = num_lists;
 
+	if (vsp1_gen3_vspdl_check(vsp1)) {
+		if (!vsp1->brs || !vsp1->lif[1])
+			return;
+
+		init_bru_num = 0;
+		init_brs_num = vsp1->info->rpf_count - vsp1->num_brs_inputs;
+		end_bru_num = vsp1->info->rpf_count - vsp1->num_brs_inputs;
+		end_brs_num = vsp1->info->rpf_count;
+	} else {
+		init_bru_num = 0;
+		init_brs_num = 0;
+		end_bru_num = vsp1->info->rpf_count;
+		end_brs_num = 0;
+	}
+
+	if (lif_index == 1) {
+		for (i = init_brs_num; i < end_brs_num; ++i)
+			rpf_update |= (0x01 << (16 + i));
+	} else {
+		for (i = init_bru_num; i < end_bru_num; ++i)
+			rpf_update |= (0x01 << (16 + i));
+	}
 	/*
 	 * If this display list's chain is not empty, we are on a list, where
 	 * the next item in the list is the display list entity which should be
@@ -638,7 +665,7 @@
 			/* Set opecode */
 			dl->ext_body->ext_dl_cmd[0] = 0x00000003;
 			/* RPF[0]-[4] address is updated */
-			dl->ext_body->ext_dl_cmd[1] = 0x001f0001;
+			dl->ext_body->ext_dl_cmd[1] = 0x00000001 | rpf_update;
 
 			/* Set pointer of source/destination address */
 			dl->ext_body->ext_dl_data[0] = dl->ext_addr_dma;
@@ -648,7 +675,7 @@
 	}
 }
 
-void vsp1_dl_list_commit(struct vsp1_dl_list *dl)
+void vsp1_dl_list_commit(struct vsp1_dl_list *dl, unsigned int lif_index)
 {
 	struct vsp1_dl_manager *dlm = dl->dlm;
 	struct vsp1_device *vsp1 = dlm->vsp1;
@@ -666,12 +693,13 @@
 		 */
 
 		/* Fill the header for the head and chained display lists. */
-		vsp1_dl_list_fill_header(dl, list_empty(&dl->chain));
+		vsp1_dl_list_fill_header(dl, list_empty(&dl->chain),
+							 lif_index);
 
 		list_for_each_entry(dl_child, &dl->chain, chain) {
 			bool last = list_is_last(&dl_child->chain, &dl->chain);
 
-			vsp1_dl_list_fill_header(dl_child, last);
+			vsp1_dl_list_fill_header(dl_child, last, lif_index);
 		}
 
 		/*
@@ -802,8 +830,7 @@
 void vsp1_dlm_setup(struct vsp1_device *vsp1, unsigned int lif_index)
 {
 	u32 ctrl = (256 << VI6_DL_CTRL_AR_WAIT_SHIFT)
-		 | VI6_DL_CTRL_DC2 | VI6_DL_CTRL_DC1 | VI6_DL_CTRL_DC0
-		 | VI6_DL_CTRL_DLE;
+		 | VI6_DL_CTRL_DLE(lif_index);
 
 	if ((vsp1->info->header_mode) && (vsp1->auto_fld_mode)) {
 		vsp1_write(vsp1, VI6_DL_EXT_CTRL(lif_index),
@@ -817,8 +844,9 @@
 	if ((vsp1->drm) && (!vsp1->info->header_mode))
 		ctrl |= VI6_DL_CTRL_CFM0 | VI6_DL_CTRL_NH0;
 
-	vsp1_write(vsp1, VI6_DL_CTRL, ctrl);
-	vsp1_write(vsp1, VI6_DL_SWAP(lif_index), VI6_DL_SWAP_LWS);
+	vsp1_write(vsp1, VI6_DL_CTRL, (vsp1_read(vsp1, VI6_DL_CTRL) | ctrl));
+	vsp1_write(vsp1, VI6_DL_SWAP(lif_index), VI6_DL_SWAP_LWS |
+				    (lif_index == 1 ? VI6_DL_SWAP_IND : 0));
 }
 
 void vsp1_dlm_reset(struct vsp1_dl_manager *dlm)
diff --git a/drivers/media/platform/vsp1/vsp1_dl.h b/drivers/media/platform/vsp1/vsp1_dl.h
index 39c084a..9b38139 100644
--- a/drivers/media/platform/vsp1/vsp1_dl.h
+++ b/drivers/media/platform/vsp1/vsp1_dl.h
@@ -1,7 +1,7 @@
 /*
  * vsp1_dl.h  --  R-Car VSP1 Display List
  *
- * Copyright (C) 2015-2016 Renesas Corporation
+ * Copyright (C) 2015-2017 Renesas Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -34,7 +34,7 @@
 void vsp1_dl_set_addr_auto_fld(struct vsp1_dl_list *dl, struct vsp1_rwpf *rpf);
 void vsp1_dl_list_put(struct vsp1_dl_list *dl);
 void vsp1_dl_list_write(struct vsp1_dl_list *dl, u32 reg, u32 data);
-void vsp1_dl_list_commit(struct vsp1_dl_list *dl);
+void vsp1_dl_list_commit(struct vsp1_dl_list *dl, unsigned int lif_index);
 
 struct vsp1_dl_body *vsp1_dl_fragment_alloc(struct vsp1_device *vsp1,
 					    unsigned int num_entries);
diff --git a/drivers/media/platform/vsp1/vsp1_drm.c b/drivers/media/platform/vsp1/vsp1_drm.c
index 1d46636..f9e0ef8 100644
--- a/drivers/media/platform/vsp1/vsp1_drm.c
+++ b/drivers/media/platform/vsp1/vsp1_drm.c
@@ -1,7 +1,7 @@
 /*
  * vsp1_drm.c  --  R-Car VSP1 DRM API
  *
- * Copyright (C) 2015-2016 Renesas Electronics Corporation
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -283,7 +283,7 @@
 	 * as there's no plane configured yet, so we can't start processing
 	 * buffers.
 	 */
-	ret = vsp1_device_get(vsp1);
+	ret = vsp1_device_get(vsp1, lif_index);
 	if (ret < 0)
 		return ret;
 
@@ -310,7 +310,7 @@
 	struct vsp1_device *vsp1 = dev_get_drvdata(dev);
 	struct vsp1_pipeline *pipe = &vsp1->drm->pipe[lif_index];
 
-	vsp1->drm->num_inputs = pipe->num_inputs;
+	vsp1->drm->num_inputs[lif_index] = pipe->num_inputs;
 
 	/* Prepare the display list. */
 	pipe->dl = vsp1_dl_list_get(pipe->output->dlm);
@@ -604,13 +604,14 @@
 			continue;
 		}
 
-		vsp1->bru->inputs[i].rpf = rpf;
 		if ((lif_index == 1) && (vsp1->brs)) {
 			vsp1->brs->inputs[i].rpf = rpf;
-			rpf->brs_input = 2;
+			rpf->brs_input = i;
 			brs_use = true;
+		} else {
+			vsp1->bru->inputs[i].rpf = rpf;
+			rpf->bru_input = i;
 		}
-		rpf->bru_input = i;
 		rpf->entity.sink_pad = i;
 
 		dev_dbg(vsp1->dev, "%s: connecting RPF.%u to %s:%u\n",
@@ -656,18 +657,18 @@
 		}
 	}
 
-	vsp1_dl_list_commit(pipe->dl);
+	vsp1_dl_list_commit(pipe->dl, lif_index);
 	pipe->dl = NULL;
 
 	/* Start or stop the pipeline if needed. */
-	if (!vsp1->drm->num_inputs && pipe->num_inputs) {
+	if (!vsp1->drm->num_inputs[lif_index] && pipe->num_inputs) {
 		vsp1_write(vsp1, VI6_DISP_IRQ_STA(lif_index), 0);
 		vsp1_write(vsp1, VI6_DISP_IRQ_ENB(lif_index),
 					 VI6_DISP_IRQ_ENB_DSTE);
 		spin_lock_irqsave(&pipe->irqlock, flags);
 		vsp1_pipeline_run(pipe);
 		spin_unlock_irqrestore(&pipe->irqlock, flags);
-	} else if (vsp1->drm->num_inputs && !pipe->num_inputs) {
+	} else if (vsp1->drm->num_inputs[lif_index] && !pipe->num_inputs) {
 		vsp1_write(vsp1, VI6_DISP_IRQ_ENB(lif_index), 0);
 		vsp1_pipeline_stop(pipe);
 	}
@@ -703,9 +704,15 @@
 	struct vsp1_pipeline *pipe = &vsp1->drm->pipe[lif_index];
 	struct vsp1_rwpf *wpf = pipe->output;
 	const struct vsp1_format_info *fmtinfo;
-	struct vsp1_rwpf *rpf = pipe->inputs[0];
+	struct vsp1_rwpf *rpf;
 	unsigned long flags;
 	int i;
+	u32 rpf_num = 0;
+
+	if (pipe->brs)
+		rpf_num = vsp1->info->rpf_count - vsp1->num_brs_inputs;
+
+	rpf = pipe->inputs[rpf_num];
 
 	fmtinfo = vsp1_get_format_info(vsp1, pixelformat);
 	if (!fmtinfo) {
@@ -739,11 +746,10 @@
 
 void vsp1_du_wait_wb(struct device *dev, u32 count, unsigned int lif_index)
 {
-	int ret;
 	struct vsp1_device *vsp1 = dev_get_drvdata(dev);
 	struct vsp1_pipeline *pipe = &vsp1->drm->pipe[lif_index];
 
-	ret = wait_event_interruptible(pipe->event_wait,
+	wait_event_interruptible(pipe->event_wait,
 				       (pipe->output->write_back == count));
 }
 EXPORT_SYMBOL_GPL(vsp1_du_wait_wb);
diff --git a/drivers/media/platform/vsp1/vsp1_drm.h b/drivers/media/platform/vsp1/vsp1_drm.h
index 1bcee33..8ad4f44 100644
--- a/drivers/media/platform/vsp1/vsp1_drm.h
+++ b/drivers/media/platform/vsp1/vsp1_drm.h
@@ -1,7 +1,7 @@
 /*
  * vsp1_drm.h  --  R-Car VSP1 DRM/KMS Interface
  *
- * Copyright (C) 2015-2016 Renesas Electronics Corporation
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -26,7 +26,7 @@
  */
 struct vsp1_drm {
 	struct vsp1_pipeline pipe[VSP1_MAX_LIF];
-	unsigned int num_inputs;
+	unsigned int num_inputs[VSP1_MAX_LIF];
 	struct {
 		bool enabled;
 		struct v4l2_rect crop;
diff --git a/drivers/media/platform/vsp1/vsp1_drv.c b/drivers/media/platform/vsp1/vsp1_drv.c
index 4286d9f..8f04573 100644
--- a/drivers/media/platform/vsp1/vsp1_drv.c
+++ b/drivers/media/platform/vsp1/vsp1_drv.c
@@ -78,7 +78,6 @@
 	va_end(args);
 }
 
-#define SRCR7_REG		0xe61501cc
 #define	FCPVD0_REG		0xfea27000
 #define	FCPVD1_REG		0xfea2f000
 #define	FCPVD2_REG		0xfea37000
@@ -679,17 +678,15 @@
 	return 0;
 }
 
-static int vsp1_device_init(struct vsp1_device *vsp1)
+static int vsp1_device_init(struct vsp1_device *vsp1, unsigned int index)
 {
 	unsigned int i;
 	int ret;
 
 	/* Reset any channel that might be running. */
-	for (i = 0; i < vsp1->info->wpf_count; ++i) {
-		ret = vsp1_reset_wpf(vsp1, i);
-		if (ret < 0)
-			return ret;
-	}
+	ret = vsp1_reset_wpf(vsp1, index);
+	if (ret < 0)
+		return ret;
 
 	vsp1_write(vsp1, VI6_CLK_DCSWT, (8 << VI6_CLK_DCSWT_CSTPW_SHIFT) |
 		   (8 << VI6_CLK_DCSWT_CSTRW_SHIFT));
@@ -713,12 +710,7 @@
 	vsp1_write(vsp1, VI6_DPR_HGT_SMPPT, (7 << VI6_DPR_SMPPT_TGW_SHIFT) |
 		   (VI6_DPR_NODE_UNUSED << VI6_DPR_SMPPT_PT_SHIFT));
 
-	for (i = 0; i < vsp1->info->wpf_count; ++i) {
-		if ((i == 1) && (!vsp1_gen3_vspdl_check(vsp1)))
-			break;
-
-		vsp1_dlm_setup(vsp1, i);
-	}
+	vsp1_dlm_setup(vsp1, index);
 
 	return 0;
 }
@@ -730,7 +722,7 @@
  *
  * Return 0 on success or a negative error code otherwise.
  */
-int vsp1_device_get(struct vsp1_device *vsp1)
+int vsp1_device_get(struct vsp1_device *vsp1, unsigned int index)
 {
 	int ret = 0;
 
@@ -743,7 +735,7 @@
 		return ret;
 
 	if (vsp1->info) {
-		ret = vsp1_device_init(vsp1);
+		ret = vsp1_device_init(vsp1, index);
 		if (ret < 0)
 			return ret;
 	}
@@ -1007,10 +999,17 @@
 static int vsp1_remove(struct platform_device *pdev)
 {
 	struct vsp1_device *vsp1 = platform_get_drvdata(pdev);
+	u32 i, lif_num = 1;
 
-	vsp1_device_put(vsp1);
+	if (vsp1_gen3_vspdl_check(vsp1))
+		lif_num = 2;
+
 	vsp1_destroy_entities(vsp1);
-	rcar_fcp_put(vsp1->fcp);
+
+	for (i = 0; i < lif_num; i++) {
+		vsp1_device_put(vsp1);
+		rcar_fcp_put(vsp1->fcp);
+	}
 
 	pm_runtime_disable(&pdev->dev);
 
diff --git a/drivers/media/platform/vsp1/vsp1_lif.c b/drivers/media/platform/vsp1/vsp1_lif.c
index 69bcf7e..b442d14 100644
--- a/drivers/media/platform/vsp1/vsp1_lif.c
+++ b/drivers/media/platform/vsp1/vsp1_lif.c
@@ -1,7 +1,7 @@
 /*
  * vsp1_lif.c  --  R-Car VSP1 LCD Controller Interface
  *
- * Copyright (C) 2013-2016 Renesas Electronics Corporation
+ * Copyright (C) 2013-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -134,8 +134,9 @@
 {
 	const struct v4l2_mbus_framefmt *format;
 	struct vsp1_lif *lif = to_lif(&entity->subdev);
+	struct vsp1_device *vsp1 = entity->vsp1;
 	unsigned int hbth = 0;
-	unsigned int obth = 3000;
+	unsigned int obth;
 	unsigned int lbth = 0;
 
 	if (params != VSP1_ENTITY_PARAMS_INIT)
@@ -144,7 +145,10 @@
 	format = vsp1_entity_get_pad_format(&lif->entity, lif->entity.config,
 					    LIF_PAD_SOURCE);
 
-	obth = min(obth, (format->width + 1) / 2 * format->height - 4);
+	if (vsp1_gen3_vspdl_check(vsp1))
+		obth = 1500;
+	else
+		obth = 3000;
 
 	vsp1_lif_write(lif, dl, VI6_LIF_CSBTH(lif->entity.index),
 			(hbth << VI6_LIF_CSBTH_HBTH_SHIFT) |
diff --git a/drivers/media/platform/vsp1/vsp1_regs.h b/drivers/media/platform/vsp1/vsp1_regs.h
index 7dcbd63..ec7e107 100644
--- a/drivers/media/platform/vsp1/vsp1_regs.h
+++ b/drivers/media/platform/vsp1/vsp1_regs.h
@@ -1,7 +1,7 @@
 /*
  * vsp1_regs.h  --  R-Car VSP1 Registers Definitions
  *
- * Copyright (C) 2013-2016 Renesas Electronics Corporation
+ * Copyright (C) 2013-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -86,16 +86,14 @@
 #define VI6_DL_CTRL			0x0100
 #define VI6_DL_CTRL_AR_WAIT_MASK	(0xffff << 16)
 #define VI6_DL_CTRL_AR_WAIT_SHIFT	16
-#define VI6_DL_CTRL_DC2			(1 << 12)
-#define VI6_DL_CTRL_DC1			(1 << 8)
-#define VI6_DL_CTRL_DC0			(1 << 4)
 #define VI6_DL_CTRL_CFM0		(1 << 2)
 #define VI6_DL_CTRL_NH0			(1 << 1)
-#define VI6_DL_CTRL_DLE			(1 << 0)
+#define VI6_DL_CTRL_DLE(n)		(1 << (4 * n))
 
 #define VI6_DL_HDR_ADDR(n)		(0x0104 + (n) * 4)
 
 #define VI6_DL_SWAP(n)			(0x0114 + (n) * 56)
+#define VI6_DL_SWAP_IND			(1 << 31)
 #define VI6_DL_SWAP_LWS			(1 << 2)
 #define VI6_DL_SWAP_WDS			(1 << 1)
 #define VI6_DL_SWAP_BTS			(1 << 0)
@@ -264,6 +262,10 @@
 #define VI6_WPF_SRCRPF_VIRACT_SUB	(1 << 28)
 #define VI6_WPF_SRCRPF_VIRACT_MST	(2 << 28)
 #define VI6_WPF_SRCRPF_VIRACT_MASK	(3 << 28)
+#define VI6_WPF_SRCRPF_VIRACT2_DIS	(0 << 24)
+#define VI6_WPF_SRCRPF_VIRACT2_SUB	(1 << 24)
+#define VI6_WPF_SRCRPF_VIRACT2_MST	(2 << 24)
+#define VI6_WPF_SRCRPF_VIRACT2_MASK	(3 << 24)
 #define VI6_WPF_SRCRPF_RPF_ACT_DIS(n)	(0 << ((n) * 2))
 #define VI6_WPF_SRCRPF_RPF_ACT_SUB(n)	(1 << ((n) * 2))
 #define VI6_WPF_SRCRPF_RPF_ACT_MST(n)	(2 << ((n) * 2))
diff --git a/drivers/media/platform/vsp1/vsp1_rpf.c b/drivers/media/platform/vsp1/vsp1_rpf.c
index a12d6f9..483dc91 100644
--- a/drivers/media/platform/vsp1/vsp1_rpf.c
+++ b/drivers/media/platform/vsp1/vsp1_rpf.c
@@ -1,7 +1,7 @@
 /*
  * vsp1_rpf.c  --  R-Car VSP1 Read Pixel Formatter
  *
- * Copyright (C) 2013-2016 Renesas Electronics Corporation
+ * Copyright (C) 2013-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -64,9 +64,25 @@
 	u32 alph_sel = 0;
 	u32 i;
 	u32 crop_width, crop_height, crop_x, crop_y;
+	unsigned int sta_rpf = 0, end_rpf = 0;
+
+	if (vsp1_gen3_vspdl_check(vsp1)) {
+		if (pipe->brs) {
+			sta_rpf = vsp1->info->rpf_count -
+					 vsp1->num_brs_inputs;
+			end_rpf = vsp1->info->rpf_count;
+		} else if (pipe->bru) {
+			sta_rpf = 0;
+			end_rpf = vsp1->info->rpf_count -
+					 vsp1->num_brs_inputs;
+		}
+	} else {
+		sta_rpf = 0;
+		end_rpf = vsp1->info->rpf_count;
+	}
 
 	if (pipe->vmute_flag) {
-		for (i = 0; i < vsp1->info->rpf_count; ++i)
+		for (i = sta_rpf; i < end_rpf; ++i)
 			vsp1_rpf_write(rpf, dl, VI6_DPR_RPF_ROUTE(i),
 						VI6_DPR_NODE_UNUSED);
 		return;
diff --git a/drivers/media/platform/vsp1/vsp1_video.c b/drivers/media/platform/vsp1/vsp1_video.c
index f4ada40..ecca021 100644
--- a/drivers/media/platform/vsp1/vsp1_video.c
+++ b/drivers/media/platform/vsp1/vsp1_video.c
@@ -1,7 +1,7 @@
 /*
  * vsp1_video.c  --  R-Car VSP1 Video Node
  *
- * Copyright (C) 2013-2016 Renesas Electronics Corporation
+ * Copyright (C) 2013-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -413,7 +413,7 @@
 	}
 
 	/* Complete, and commit the head display list. */
-	vsp1_dl_list_commit(pipe->dl);
+	vsp1_dl_list_commit(pipe->dl, 0);
 	pipe->dl = NULL;
 
 	vsp1_pipeline_run(pipe);
@@ -1216,7 +1216,7 @@
 
 	file->private_data = vfh;
 
-	ret = vsp1_device_get(video->vsp1);
+	ret = vsp1_device_get(video->vsp1, 0);
 	if (ret < 0) {
 		v4l2_fh_del(vfh);
 		kfree(vfh);
diff --git a/drivers/media/platform/vsp1/vsp1_wpf.c b/drivers/media/platform/vsp1/vsp1_wpf.c
index d41eed9..f490ae4 100644
--- a/drivers/media/platform/vsp1/vsp1_wpf.c
+++ b/drivers/media/platform/vsp1/vsp1_wpf.c
@@ -1,7 +1,7 @@
 /*
  * vsp1_wpf.c  --  R-Car VSP1 Write Pixel Formatter
  *
- * Copyright (C) 2013-2016 Renesas Electronics Corporation
+ * Copyright (C) 2013-2017 Renesas Electronics Corporation
  *
  * Contact: Laurent Pinchart (laurent.pinchart@ideasonboard.com)
  *
@@ -189,16 +189,16 @@
 	bool writeback = pipe->lif && wpf->mem.addr[0];
 
 	if (pipe->vmute_flag) {
-		vsp1_wpf_write(wpf, dl, VI6_WPF_SRCRPF +
-			(0x100 * wpf->entity.index),
-			 VI6_WPF_SRCRPF_VIRACT_MST);
-		vsp1_wpf_write(wpf, dl, VI6_WPF_HSZCLIP +
-			(0x100 * wpf->entity.index), 0);
-		vsp1_wpf_write(wpf, dl, VI6_WPF_VSZCLIP +
-			(0x100 * wpf->entity.index), 0);
-		vsp1_wpf_write(wpf, dl, VI6_DPR_WPF_FPORCH(wpf->entity.index),
-			VI6_DPR_WPF_FPORCH_FP_WPFN);
-
+		if (pipe->bru)
+			vsp1_wpf_write(wpf, dl, VI6_WPF_SRCRPF,
+					 VI6_WPF_SRCRPF_VIRACT_MST);
+		else if (pipe->brs)
+			vsp1_wpf_write(wpf, dl, VI6_WPF_SRCRPF,
+					 VI6_WPF_SRCRPF_VIRACT2_MST);
+		vsp1_wpf_write(wpf, dl, VI6_WPF_HSZCLIP, 0);
+		vsp1_wpf_write(wpf, dl, VI6_WPF_VSZCLIP, 0);
+		vsp1_dl_list_write(dl, VI6_DPR_WPF_FPORCH(wpf->entity.index),
+					   VI6_DPR_WPF_FPORCH_FP_WPFN);
 		return;
 	}
 
@@ -386,12 +386,29 @@
 	if (pipe->bru || pipe->num_inputs > 1)
 		srcrpf |= VI6_WPF_SRCRPF_VIRACT_MST;
 
+	/* When using multiple BRS module, layer is allocated as follows.
+	 * When one BRS is used, RPF4 is master layer.
+	 * When two BRS is used, RPF3 is master layer and RPF4 is sub layer.
+	 */
+	if (pipe->brs) {
+		if (vsp1->num_brs_inputs == 1)
+			srcrpf = VI6_WPF_SRCRPF_VIRACT2_MST |
+				 VI6_WPF_SRCRPF_RPF_ACT_MST(4);
+		else if (pipe->num_inputs > 1)
+			srcrpf = VI6_WPF_SRCRPF_VIRACT2_MST |
+				 VI6_WPF_SRCRPF_RPF_ACT_MST(3) |
+				 VI6_WPF_SRCRPF_RPF_ACT_SUB(4);
+		else if (pipe->num_inputs == 1)
+			srcrpf = VI6_WPF_SRCRPF_VIRACT2_MST |
+				 VI6_WPF_SRCRPF_RPF_ACT_MST(3);
+	}
+
 	vsp1_wpf_write(wpf, dl, VI6_WPF_SRCRPF, srcrpf);
 
 	/* Enable interrupts */
 	vsp1_dl_list_write(dl, VI6_WPF_IRQ_STA(wpf->entity.index), 0);
 	vsp1_dl_list_write(dl, VI6_WPF_IRQ_ENB(wpf->entity.index),
-			   VI6_WFP_IRQ_ENB_FREE | VI6_WFP_IRQ_ENB_UNDE);
+			   VI6_WFP_IRQ_ENB_DFEE | VI6_WFP_IRQ_ENB_UNDE);
 }
 
 static const struct vsp1_entity_operations wpf_entity_ops = {
diff --git a/drivers/mmc/host/sh_mobile_sdhi.c b/drivers/mmc/host/sh_mobile_sdhi.c
index 643ce2f..83aabfe 100644
--- a/drivers/mmc/host/sh_mobile_sdhi.c
+++ b/drivers/mmc/host/sh_mobile_sdhi.c
@@ -1,8 +1,8 @@
 /*
  * SuperH Mobile SDHI
  *
- * Copyright (C) 2016 Renesas Electronics Corporation
  * Copyright (C) 2016 Sang Engineering, Wolfram Sang
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  * Copyright (C) 2009 Magnus Damm
  *
  * This program is free software; you can redistribute it and/or modify
@@ -110,8 +110,7 @@
 
 static const struct sh_mobile_sdhi_of_data of_rcar_gen3_compatible = {
 	.tmio_flags	= TMIO_MMC_HAS_IDLE_WAIT | TMIO_MMC_WRPROTECT_DISABLE |
-			  TMIO_MMC_CLK_ACTUAL | TMIO_MMC_MIN_RCAR2 |
-			  TMIO_MMC_CLK_NO_SLEEP,
+			  TMIO_MMC_CLK_ACTUAL | TMIO_MMC_MIN_RCAR2,
 	.capabilities	= MMC_CAP_SD_HIGHSPEED | MMC_CAP_SDIO_IRQ |
 			  MMC_CAP_CMD23,
 	.bus_shift	= 2,
@@ -349,33 +348,30 @@
 
 	priv = host_to_priv(host);
 
-	/* set sampling clock selection range */
-	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_DTCNTL,
-		       0x8 << SH_MOBILE_SDHI_SCC_DTCNTL_TAPNUM_SHIFT);
-
 	/* Initialize SCC */
 	sd_ctrl_write32_as_16_and_16(host, CTL_STATUS, 0x0);
 
-	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_DTCNTL,
-		       SH_MOBILE_SDHI_SCC_DTCNTL_TAPEN |
-		       sd_scc_read32(host, priv, SH_MOBILE_SDHI_SCC_DTCNTL));
-
 	sd_ctrl_write16(host, CTL_SD_CARD_CLK_CTL, ~CLK_CTL_SCLKEN &
 			sd_ctrl_read16(host, CTL_SD_CARD_CLK_CTL));
 
+	/* set sampling clock selection range */
+	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_DTCNTL,
+		       SH_MOBILE_SDHI_SCC_DTCNTL_TAPEN |
+		       0x8 << SH_MOBILE_SDHI_SCC_DTCNTL_TAPNUM_SHIFT);
+
 	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_CKSEL,
 		       SH_MOBILE_SDHI_SCC_CKSEL_DTSEL |
 		       sd_scc_read32(host, priv, SH_MOBILE_SDHI_SCC_CKSEL));
 
-	sd_ctrl_write16(host, CTL_SD_CARD_CLK_CTL, CLK_CTL_SCLKEN |
-			sd_ctrl_read16(host, CTL_SD_CARD_CLK_CTL));
-
 	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_RVSCNTL,
 		       ~SH_MOBILE_SDHI_SCC_RVSCNTL_RVSEN &
 		       sd_scc_read32(host, priv, SH_MOBILE_SDHI_SCC_RVSCNTL));
 
 	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_DT2FF, host->scc_tappos);
 
+	sd_ctrl_write16(host, CTL_SD_CARD_CLK_CTL, CLK_CTL_SCLKEN |
+			sd_ctrl_read16(host, CTL_SD_CARD_CLK_CTL));
+
 	/* Read TAPNUM */
 	return (sd_scc_read32(host, priv, SH_MOBILE_SDHI_SCC_DTCNTL) >>
 		SH_MOBILE_SDHI_SCC_DTCNTL_TAPNUM_SHIFT) &
@@ -416,17 +412,46 @@
 		SH_MOBILE_SDHI_SCC_TMPPORT2_HS400OSEL) |
 		sd_scc_read32(host, priv, SH_MOBILE_SDHI_SCC_TMPPORT2));
 
+	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_TAPSET, host->tap_set/2);
+
 	sd_ctrl_write16(host, CTL_SD_CARD_CLK_CTL, CLK_CTL_SCLKEN |
 		sd_ctrl_read16(host, CTL_SD_CARD_CLK_CTL));
 }
 
+static void sh_mobile_sdhi_reset_hs400_mode(struct mmc_host *mmc)
+{
+	struct tmio_mmc_host *host = mmc_priv(mmc);
+	struct sh_mobile_sdhi *priv = host_to_priv(host);
+
+	if (!(host->mmc->caps2 & MMC_CAP2_HS200_1_8V_SDR) &&
+	    !(host->mmc->caps2 & (MMC_CAP2_HS400_1_8V |
+					MMC_CAP2_HS200_1_8V_SDR)))
+		return;
+
+	if (!priv->scc_ctl)
+		return;
+
+	sd_ctrl_write16(host, CTL_SD_CARD_CLK_CTL, ~CLK_CTL_SCLKEN &
+		sd_ctrl_read16(host, CTL_SD_CARD_CLK_CTL));
+
+	/* Reset HS400 mode */
+	sd_ctrl_write16(host, CTL_SDIF_MODE, ~0x0001 &
+			sd_ctrl_read16(host, CTL_SDIF_MODE));
+	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_TMPPORT2,
+			~(SH_MOBILE_SDHI_SCC_TMPPORT2_HS400EN |
+			SH_MOBILE_SDHI_SCC_TMPPORT2_HS400OSEL) &
+			sd_scc_read32(host, priv, SH_MOBILE_SDHI_SCC_TMPPORT2));
+
+	sd_ctrl_write16(host, CTL_SD_CARD_CLK_CTL, CLK_CTL_SCLKEN |
+			sd_ctrl_read16(host, CTL_SD_CARD_CLK_CTL));
+}
+
 #define SH_MOBILE_SDHI_MAX_TAP 3
 
 static int sh_mobile_sdhi_select_tuning(struct tmio_mmc_host *host)
 {
 	struct sh_mobile_sdhi *priv = host_to_priv(host);
 	unsigned long tap_cnt;  /* counter of tuning success */
-	unsigned long tap_set;  /* tap position */
 	unsigned long tap_start;/* start position of tuning success */
 	unsigned long tap_end;  /* end position of tuning success */
 	unsigned long ntap;     /* temporary counter of tuning success */
@@ -511,12 +536,12 @@
 		select = true;
 
 	if (select)
-		tap_set = (tap_start + tap_end) / 2 % host->tap_num;
+		host->tap_set = (tap_start + tap_end) / 2 % host->tap_num;
 	else
 		return -EIO;
 
 	/* Set SCC */
-	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_TAPSET, tap_set);
+	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_TAPSET, host->tap_set);
 
 	/* Enable auto re-tuning */
 	sd_scc_write32(host, priv, SH_MOBILE_SDHI_SCC_RVSCNTL,
@@ -733,6 +758,7 @@
 		host->hw_reset		= sh_mobile_sdhi_hw_reset;
 		host->prepare_hs400_tuning =
 			sh_mobile_sdhi_prepare_hs400_tuning;
+		host->reset_hs400_mode = sh_mobile_sdhi_reset_hs400_mode;
 	}
 
 	/* Orginally registers were 16 bit apart, could be 32 or 64 nowadays */
@@ -850,13 +876,11 @@
 }
 
 static const struct dev_pm_ops tmio_mmc_dev_pm_ops = {
+	SET_LATE_SYSTEM_SLEEP_PM_OPS(pm_runtime_force_suspend,
+			pm_runtime_force_resume)
 	SET_RUNTIME_PM_OPS(tmio_mmc_host_runtime_suspend,
 			tmio_mmc_host_runtime_resume,
 			NULL)
-#ifdef CONFIG_PM_SLEEP
-	.suspend_late = tmio_mmc_host_suspend,
-	.resume_early = tmio_mmc_host_resume,
-#endif
 };
 
 static struct platform_driver sh_mobile_sdhi_driver = {
diff --git a/drivers/mmc/host/tmio_mmc.c b/drivers/mmc/host/tmio_mmc.c
index 17ac517..e897e7f 100644
--- a/drivers/mmc/host/tmio_mmc.c
+++ b/drivers/mmc/host/tmio_mmc.c
@@ -30,7 +30,7 @@
 	const struct mfd_cell *cell = mfd_get_cell(pdev);
 	int ret;
 
-	ret = tmio_mmc_host_suspend(dev);
+	ret = pm_runtime_force_suspend(dev);
 
 	/* Tell MFD core it can disable us now.*/
 	if (!ret && cell->disable)
@@ -50,7 +50,7 @@
 		ret = cell->resume(pdev);
 
 	if (!ret)
-		ret = tmio_mmc_host_resume(dev);
+		ret = pm_runtime_force_resume(dev);
 
 	return ret;
 }
diff --git a/drivers/mmc/host/tmio_mmc.h b/drivers/mmc/host/tmio_mmc.h
index 4c37076..a707292 100644
--- a/drivers/mmc/host/tmio_mmc.h
+++ b/drivers/mmc/host/tmio_mmc.h
@@ -2,7 +2,7 @@
  * linux/drivers/mmc/host/tmio_mmc.h
  *
  * Copyright (C) 2016 Sang Engineering, Wolfram Sang
- * Copyright (C) 2015-16 Renesas Electronics Corporation
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  * Copyright (C) 2007 Ian Molton
  * Copyright (C) 2004 Ian Molton
  *
@@ -101,6 +101,9 @@
 		TMIO_STAT_CARD_REMOVE | TMIO_STAT_CARD_INSERT)
 #define TMIO_MASK_IRQ     (TMIO_MASK_READOP | TMIO_MASK_WRITEOP | TMIO_MASK_CMD)
 
+#define TMIO_TRANSTATE_DEND	0x00000001
+#define TMIO_TRANSTATE_AEND	0x00000002
+
 struct tmio_mmc_data;
 struct tmio_mmc_host;
 
@@ -141,6 +144,7 @@
 	struct tasklet_struct	dma_issue;
 	struct scatterlist	bounce_sg;
 	u8			*bounce_buf;
+	u32			dma_tranend1;
 
 	/* Track lost interrupts */
 	struct delayed_work	delayed_reset_work;
@@ -149,6 +153,7 @@
 	/* Cache */
 	u32			sdcard_irq_mask;
 	u32			sdio_irq_mask;
+	u32			dma_irq_mask;
 	unsigned int		clk_cache;
 
 	spinlock_t		lock;		/* protect host private data */
@@ -159,6 +164,9 @@
 	u32			scc_tappos;
 	struct completion	completion;
 
+	spinlock_t		trans_lock;
+	unsigned int		trans_state;
+
 	/* Mandatory callback */
 	int (*clk_enable)(struct tmio_mmc_host *host);
 
@@ -184,7 +192,9 @@
 	/* Tuning values: 1 for success, 0 for failure */
 	DECLARE_BITMAP(taps, BITS_PER_BYTE * sizeof(long));
 	unsigned int tap_num;
+	unsigned long tap_set;
 	void (*prepare_hs400_tuning)(struct mmc_host *mmc, struct mmc_ios *ios);
+	void (*reset_hs400_mode)(struct mmc_host *mmc);
 
 	/* Sampling data comparison: 1 for match. 0 for mismatch */
 	DECLARE_BITMAP(smpcmp, BITS_PER_BYTE * sizeof(long));
@@ -198,6 +208,9 @@
 void tmio_mmc_host_remove(struct tmio_mmc_host *host);
 void tmio_mmc_do_data_irq(struct tmio_mmc_host *host);
 
+void tmio_set_transtate(struct tmio_mmc_host *host, unsigned int state);
+void tmio_clear_transtate(struct tmio_mmc_host *host);
+
 void tmio_mmc_enable_mmc_irqs(struct tmio_mmc_host *host, u32 i);
 void tmio_mmc_disable_mmc_irqs(struct tmio_mmc_host *host, u32 i);
 irqreturn_t tmio_mmc_irq(int irq, void *devid);
@@ -248,16 +261,21 @@
 }
 #endif
 
+#if (defined(CONFIG_MMC_SDHI) || defined(CONFIG_MMC_SDHI_MODULE)) \
+	&& defined(CONFIG_ARM64)
+bool __tmio_mmc_dma_irq(struct tmio_mmc_host *host);
+#else
+static inline bool __tmio_mmc_dma_irq(struct tmio_mmc_host *host)
+{
+	return false;
+}
+#endif
+
 #ifdef CONFIG_PM
 int tmio_mmc_host_runtime_suspend(struct device *dev);
 int tmio_mmc_host_runtime_resume(struct device *dev);
 #endif
 
-#ifdef CONFIG_PM_SLEEP
-int tmio_mmc_host_suspend(struct device *dev);
-int tmio_mmc_host_resume(struct device *dev);
-#endif
-
 static inline u16 sd_ctrl_read16(struct tmio_mmc_host *host, int addr)
 {
 	return readw(host->ctl + (addr << host->bus_shift));
diff --git a/drivers/mmc/host/tmio_mmc_dma_gen3.c b/drivers/mmc/host/tmio_mmc_dma_gen3.c
index b289dfa..0af3d3c 100644
--- a/drivers/mmc/host/tmio_mmc_dma_gen3.c
+++ b/drivers/mmc/host/tmio_mmc_dma_gen3.c
@@ -1,7 +1,7 @@
 /*
  * linux/drivers/mmc/tmio_mmc_dma_gen3.c
  *
- * Copyright (C) 2015 Renesas Electronics Corporation
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  *
  * 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
@@ -18,6 +18,7 @@
 #include <linux/mmc/host.h>
 #include <linux/pagemap.h>
 #include <linux/scatterlist.h>
+#include <linux/sys_soc.h>
 
 #include "tmio_mmc.h"
 
@@ -46,13 +47,24 @@
 
 /* DM_CM_INFO1 and DM_CM_INFO1_MASK */
 #define INFO1_CLEAR		0
-#define INFO1_DTRANEND1		BIT(17)
+#define INFO1_DTRANEND1_BIT20	BIT(20)
+#define INFO1_DTRANEND1_BIT17	BIT(17)
 #define INFO1_DTRANEND0		BIT(16)
 
 /* DM_CM_INFO2 and DM_CM_INFO2_MASK */
 #define INFO2_DTRANERR1		BIT(17)
 #define INFO2_DTRANERR0		BIT(16)
 
+static const struct soc_device_attribute r8a7795es1x[] = {
+	{ .soc_id = "r8a7795", .revision = "ES1.*" },
+	{ },
+};
+
+static const struct soc_device_attribute r8a7796es10[] = {
+	{ .soc_id = "r8a7796", .revision = "ES1.0" },
+	{ },
+};
+
 /*
  * Specification of this driver:
  * - host->chan_{rx,tx} will be used as a flag of enabling/disabling the dma
@@ -65,6 +77,11 @@
 	writeq(val, host->ctl + addr);
 }
 
+static u32 tmio_dm_read(struct tmio_mmc_host *host, int addr)
+{
+	return readl(host->ctl + addr);
+}
+
 void tmio_mmc_enable_dma(struct tmio_mmc_host *host, bool enable)
 {
 	if (!host->chan_tx || !host->chan_rx)
@@ -73,8 +90,11 @@
 	if (!enable)
 		tmio_dm_write(host, DM_CM_INFO1, INFO1_CLEAR);
 
-	if (host->dma->enable)
+	if (host->dma->enable) {
+		host->dma_irq_mask = ~(host->dma_tranend1 | INFO1_DTRANEND0);
 		host->dma->enable(host, enable);
+		tmio_dm_write(host, DM_CM_INFO1_MASK, host->dma_irq_mask);
+	}
 }
 
 void tmio_mmc_abort_dma(struct tmio_mmc_host *host)
@@ -131,6 +151,7 @@
 		return;
 	}
 
+	tmio_clear_transtate(host);
 	tmio_mmc_enable_dma(host, true);
 
 	/* disable PIO irqs to avoid "PIO IRQ in DMA mode!" */
@@ -175,6 +196,27 @@
 }
 #endif
 
+bool __tmio_mmc_dma_irq(struct tmio_mmc_host *host)
+{
+	unsigned int ireg, status;
+
+	status = tmio_dm_read(host, DM_CM_INFO1);
+	ireg = status & ~host->dma_irq_mask;
+
+	if (ireg & INFO1_DTRANEND0) {
+		tmio_dm_write(host, DM_CM_INFO1, ireg & ~INFO1_DTRANEND0);
+		tmio_set_transtate(host, TMIO_TRANSTATE_DEND);
+		return true;
+	}
+
+	if (ireg & host->dma_tranend1) {
+		tmio_dm_write(host, DM_CM_INFO1, ireg & ~host->dma_tranend1);
+		tmio_set_transtate(host, TMIO_TRANSTATE_DEND);
+		return true;
+	}
+	return false;
+}
+
 void tmio_mmc_request_dma(struct tmio_mmc_host *host,
 			  struct tmio_mmc_data *pdata)
 {
@@ -182,6 +224,11 @@
 	/* Each value is set to non-zero to assume "enabling" each DMA */
 	host->chan_rx = host->chan_tx = (void *)0xdeadbeaf;
 
+	if (soc_device_match(r8a7795es1x) || soc_device_match(r8a7796es10))
+		host->dma_tranend1 = INFO1_DTRANEND1_BIT17;
+	else /* ES 2.0 */
+		host->dma_tranend1 = INFO1_DTRANEND1_BIT20;
+
 	tasklet_init(&host->dma_complete, tmio_mmc_complete_tasklet_fn,
 		     (unsigned long)host);
 	tasklet_init(&host->dma_issue, tmio_mmc_issue_tasklet_fn,
diff --git a/drivers/mmc/host/tmio_mmc_pio.c b/drivers/mmc/host/tmio_mmc_pio.c
index ec14cd9..4b99701 100644
--- a/drivers/mmc/host/tmio_mmc_pio.c
+++ b/drivers/mmc/host/tmio_mmc_pio.c
@@ -1,8 +1,8 @@
 /*
  * linux/drivers/mmc/host/tmio_mmc_pio.c
  *
- * Copyright (C) 2016 Renesas Electronics Corporation
  * Copyright (C) 2016 Sang Engineering, Wolfram Sang
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  * Copyright (C) 2011 Guennadi Liakhovetski
  * Copyright (C) 2007 Ian Molton
  * Copyright (C) 2004 Ian Molton
@@ -65,6 +65,32 @@
 	sd_ctrl_write32_as_16_and_16(host, CTL_IRQ_MASK, host->sdcard_irq_mask);
 }
 
+void tmio_set_transtate(struct tmio_mmc_host *host, unsigned int state)
+{
+	unsigned long flags = 0;
+
+	spin_lock_irqsave(&host->trans_lock, flags);
+	host->trans_state |= state;
+
+	if (host->trans_state == (TMIO_TRANSTATE_DEND | TMIO_TRANSTATE_AEND)) {
+		spin_unlock_irqrestore(&host->trans_lock, flags);
+		tasklet_schedule(&host->dma_complete);
+	} else {
+		spin_unlock_irqrestore(&host->trans_lock, flags);
+	}
+}
+
+void tmio_clear_transtate(struct tmio_mmc_host *host)
+{
+	unsigned long flags = 0;
+
+	spin_lock_irqsave(&host->trans_lock, flags);
+
+	host->trans_state = 0;
+
+	spin_unlock_irqrestore(&host->trans_lock, flags);
+}
+
 static void tmio_mmc_ack_mmc_irqs(struct tmio_mmc_host *host, u32 i)
 {
 	sd_ctrl_write32_as_16_and_16(host, CTL_STATUS, ~i);
@@ -161,9 +187,8 @@
 	msleep(host->pdata->flags & TMIO_MMC_MIN_RCAR2 ? 1 : 10);
 
 	if (host->pdata->flags & TMIO_MMC_HAVE_HIGH_REG) {
-		sd_ctrl_write16(host, CTL_CLK_AND_WAIT_CTL, CLK_CTL_SCLKEN);
-		if (!(host->pdata->flags & TMIO_MMC_CLK_NO_SLEEP))
-			msleep(10);
+		sd_ctrl_write16(host, CTL_CLK_AND_WAIT_CTL, 0x0100);
+		msleep(10);
 	}
 }
 
@@ -171,8 +196,7 @@
 {
 	if (host->pdata->flags & TMIO_MMC_HAVE_HIGH_REG) {
 		sd_ctrl_write16(host, CTL_CLK_AND_WAIT_CTL, 0x0000);
-		if (!(host->pdata->flags & TMIO_MMC_CLK_NO_SLEEP))
-			msleep(10);
+		msleep(10);
 	}
 
 	sd_ctrl_write16(host, CTL_SD_CARD_CLK_CTL, ~CLK_CTL_SCLKEN &
@@ -189,6 +213,13 @@
 		tmio_mmc_clk_stop(host);
 		return;
 	}
+	/*
+	 * Both HS400 and HS200/SD104 set 200MHz, but HS400 sets 400MHz
+	 * to distinguish the CPG settings.
+	 */
+	if (host->mmc->ios.timing == MMC_TIMING_MMC_HS400 &&
+			new_clock == 200000000)
+		new_clock = 400000000;
 
 	if (host->clk_update)
 		clock = host->clk_update(host, new_clock) / 512;
@@ -562,6 +593,17 @@
 	if (!data)
 		goto out;
 
+	/* The response of automatic CMD12 is stored */
+	if (host->pdata->flags & TMIO_MMC_MIN_RCAR2) {
+		if ((sd_ctrl_read16(host, CTL_SD_CMD) &
+			(TRANSFER_MULTI | NO_CMD12_ISSUE)) == TRANSFER_MULTI) {
+			if (data->stop) {
+				data->stop->resp[0] =
+					sd_ctrl_read16_and_16_as_32(host,
+							CTL_RESPONSE);
+			}
+		}
+	}
 	if (stat & TMIO_STAT_CRCFAIL || stat & TMIO_STAT_STOPBIT_ERR ||
 	    stat & TMIO_STAT_TXUNDERRUN)
 		data->error = -EILSEQ;
@@ -587,11 +629,17 @@
 
 		if (done) {
 			tmio_mmc_disable_mmc_irqs(host, TMIO_STAT_DATAEND);
-			tasklet_schedule(&host->dma_complete);
+			if (!data->error)
+				tmio_set_transtate(host, TMIO_TRANSTATE_AEND);
+			else
+				tasklet_schedule(&host->dma_complete);
 		}
 	} else if (host->chan_rx && (data->flags & MMC_DATA_READ) && !host->force_pio) {
 		tmio_mmc_disable_mmc_irqs(host, TMIO_STAT_DATAEND);
-		tasklet_schedule(&host->dma_complete);
+		if (!data->error)
+			tmio_set_transtate(host, TMIO_TRANSTATE_AEND);
+		else
+			tasklet_schedule(&host->dma_complete);
 	} else {
 		tmio_mmc_do_data_irq(host);
 		tmio_mmc_disable_mmc_irqs(host, TMIO_MASK_READOP | TMIO_MASK_WRITEOP);
@@ -641,7 +689,7 @@
 	 * we will ultimatley finish the request in the data_end handler.
 	 * If theres no data or we encountered an error, finish now.
 	 */
-	if (host->data && (!cmd->error || cmd->error == -EILSEQ)) {
+	if (host->data && !cmd->error) {
 		if (host->data->flags & MMC_DATA_READ) {
 			if (host->force_pio || !host->chan_rx)
 				tmio_mmc_enable_mmc_irqs(host, TMIO_MASK_READOP);
@@ -751,6 +799,8 @@
 		return IRQ_HANDLED;
 	if (__tmio_mmc_sdcard_irq(host, ireg, status))
 		return IRQ_HANDLED;
+	if (__tmio_mmc_dma_irq(host))
+		return IRQ_HANDLED;
 
 	tmio_mmc_sdio_irq(irq, devid);
 
@@ -1009,10 +1059,10 @@
 	struct device *dev = &host->pdev->dev;
 	unsigned long flags;
 
-	/* HS400 Register setting */
-	if (ios->timing == MMC_TIMING_MMC_HS400)
-		if (host->prepare_hs400_tuning)
-			host->prepare_hs400_tuning(mmc, ios);
+	/* reset HS400 mode */
+	if (!(ios->timing == MMC_TIMING_MMC_HS400))
+		if (host->reset_hs400_mode)
+			host->reset_hs400_mode(mmc);
 
 	mutex_lock(&host->ios_lock);
 
@@ -1063,6 +1113,12 @@
 			"%s.%d: IOS interrupted: clk %u, mode %u",
 			current->comm, task_pid_nr(current),
 			ios->clock, ios->power_mode);
+
+	/* HS400 Register setting */
+	if (ios->timing == MMC_TIMING_MMC_HS400)
+		if (host->prepare_hs400_tuning)
+			host->prepare_hs400_tuning(mmc, ios);
+
 	host->mrq = NULL;
 
 	host->clk_cache = ios->clock;
@@ -1275,6 +1331,9 @@
 	spin_lock_init(&_host->lock);
 	mutex_init(&_host->ios_lock);
 
+	spin_lock_init(&_host->trans_lock);
+	_host->trans_state = 0;
+
 	/* Init delayed work for request timeouts */
 	INIT_DELAYED_WORK(&_host->delayed_reset_work, tmio_mmc_reset_work);
 	INIT_WORK(&_host->done, tmio_mmc_done_work);
@@ -1376,23 +1435,4 @@
 EXPORT_SYMBOL(tmio_mmc_host_runtime_resume);
 #endif
 
-#ifdef CONFIG_PM_SLEEP
-int tmio_mmc_host_suspend(struct device *dev)
-{
-	struct mmc_host *mmc = dev_get_drvdata(dev);
-
-	tmio_mmc_hw_reset(mmc);
-
-	return 0;
-}
-EXPORT_SYMBOL(tmio_mmc_host_suspend);
-
-int tmio_mmc_host_resume(struct device *dev)
-{
-	/* Empty for now */
-	return 0;
-}
-EXPORT_SYMBOL(tmio_mmc_host_resume);
-#endif /* CONFIG_PM_SLEEP */
-
 MODULE_LICENSE("GPL v2");
diff --git a/drivers/net/ethernet/renesas/ravb.h b/drivers/net/ethernet/renesas/ravb.h
index 9a8dd874..7d35379 100644
--- a/drivers/net/ethernet/renesas/ravb.h
+++ b/drivers/net/ethernet/renesas/ravb.h
@@ -1,6 +1,6 @@
 /* Renesas Ethernet AVB device driver
  *
- * Copyright (C) 2014-2015 Renesas Electronics Corporation
+ * Copyright (C) 2014-2017 Renesas Electronics Corporation
  * Copyright (C) 2015 Renesas Solutions Corp.
  * Copyright (C) 2015-2016 Cogent Embedded, Inc. <source@cogentembedded.com>
  *
@@ -1140,7 +1140,7 @@
 		 u32 set);
 int ravb_wait(struct net_device *ndev, enum ravb_reg reg, u32 mask, u32 value);
 
-void ravb_ptp_interrupt(struct net_device *ndev);
+irqreturn_t ravb_ptp_interrupt(struct net_device *ndev);
 void ravb_ptp_init(struct net_device *ndev, struct platform_device *pdev);
 void ravb_ptp_stop(struct net_device *ndev);
 
diff --git a/drivers/net/ethernet/renesas/ravb_main.c b/drivers/net/ethernet/renesas/ravb_main.c
index 7150f0b..3177789 100644
--- a/drivers/net/ethernet/renesas/ravb_main.c
+++ b/drivers/net/ethernet/renesas/ravb_main.c
@@ -1,6 +1,6 @@
 /* Renesas Ethernet AVB device driver
  *
- * Copyright (C) 2014-2015 Renesas Electronics Corporation
+ * Copyright (C) 2014-2017 Renesas Electronics Corporation
  * Copyright (C) 2015 Renesas Solutions Corp.
  * Copyright (C) 2015-2016 Cogent Embedded, Inc. <source@cogentembedded.com>
  *
@@ -841,10 +841,8 @@
 	}
 
 	/* gPTP interrupt status summary */
-	if (iss & ISS_CGIS) {
-		ravb_ptp_interrupt(ndev);
-		result = IRQ_HANDLED;
-	}
+	if (iss & ISS_CGIS)
+		result = ravb_ptp_interrupt(ndev);
 
 	mmiowb();
 	spin_unlock(&priv->lock);
@@ -874,10 +872,8 @@
 	}
 
 	/* gPTP interrupt status summary */
-	if (iss & ISS_CGIS) {
-		ravb_ptp_interrupt(ndev);
-		result = IRQ_HANDLED;
-	}
+	if (iss & ISS_CGIS)
+		result = ravb_ptp_interrupt(ndev);
 
 	mmiowb();
 	spin_unlock(&priv->lock);
@@ -1379,8 +1375,8 @@
 };
 
 static inline int ravb_hook_irq(unsigned int irq, irq_handler_t handler,
-				struct net_device *ndev, struct device *dev,
-				const char *ch)
+				unsigned long flags, struct net_device *ndev,
+				struct device *dev, const char *ch)
 {
 	char *name;
 	int error;
@@ -1388,7 +1384,7 @@
 	name = devm_kasprintf(dev, GFP_KERNEL, "%s:%s", ndev->name, ch);
 	if (!name)
 		return -ENOMEM;
-	error = request_irq(irq, handler, 0, name, ndev);
+	error = request_irq(irq, handler, flags, name, ndev);
 	if (error)
 		netdev_err(ndev, "cannot request IRQ %s\n", name);
 
@@ -1414,28 +1410,28 @@
 			goto out_napi_off;
 		}
 	} else {
-		error = ravb_hook_irq(ndev->irq, ravb_multi_interrupt, ndev,
-				      dev, "ch22:multi");
+		error = ravb_hook_irq(ndev->irq, ravb_multi_interrupt,
+				      IRQF_SHARED, ndev, dev, "ch22:multi");
 		if (error)
 			goto out_napi_off;
-		error = ravb_hook_irq(priv->emac_irq, ravb_emac_interrupt, ndev,
-				      dev, "ch24:emac");
+		error = ravb_hook_irq(priv->emac_irq, ravb_emac_interrupt,
+				      0, ndev, dev, "ch24:emac");
 		if (error)
 			goto out_free_irq;
 		error = ravb_hook_irq(priv->rx_irqs[RAVB_BE], ravb_be_interrupt,
-				      ndev, dev, "ch0:rx_be");
+				      0, ndev, dev, "ch0:rx_be");
 		if (error)
 			goto out_free_irq_emac;
 		error = ravb_hook_irq(priv->tx_irqs[RAVB_BE], ravb_be_interrupt,
-				      ndev, dev, "ch18:tx_be");
+				      0, ndev, dev, "ch18:tx_be");
 		if (error)
 			goto out_free_irq_be_rx;
 		error = ravb_hook_irq(priv->rx_irqs[RAVB_NC], ravb_nc_interrupt,
-				      ndev, dev, "ch1:rx_nc");
+				      0, ndev, dev, "ch1:rx_nc");
 		if (error)
 			goto out_free_irq_be_tx;
 		error = ravb_hook_irq(priv->tx_irqs[RAVB_NC], ravb_nc_interrupt,
-				      ndev, dev, "ch19:tx_nc");
+				      0, ndev, dev, "ch19:tx_nc");
 		if (error)
 			goto out_free_irq_nc_rx;
 	}
diff --git a/drivers/net/ethernet/renesas/ravb_ptp.c b/drivers/net/ethernet/renesas/ravb_ptp.c
index eede70e..eef70f1 100644
--- a/drivers/net/ethernet/renesas/ravb_ptp.c
+++ b/drivers/net/ethernet/renesas/ravb_ptp.c
@@ -1,6 +1,6 @@
 /* PTP 1588 clock using the Renesas Ethernet AVB
  *
- * Copyright (C) 2013-2015 Renesas Electronics Corporation
+ * Copyright (C) 2013-2017 Renesas Electronics Corporation
  * Copyright (C) 2015 Renesas Solutions Corp.
  * Copyright (C) 2015-2016 Cogent Embedded, Inc. <source@cogentembedded.com>
  *
@@ -296,10 +296,11 @@
 };
 
 /* Caller must hold the lock */
-void ravb_ptp_interrupt(struct net_device *ndev)
+irqreturn_t ravb_ptp_interrupt(struct net_device *ndev)
 {
 	struct ravb_private *priv = netdev_priv(ndev);
 	u32 gis = ravb_read(ndev, GIS);
+	irqreturn_t result = IRQ_NONE;
 
 	gis &= ravb_read(ndev, GIC);
 	if (gis & GIS_PTCF) {
@@ -309,6 +310,9 @@
 		event.index = 0;
 		event.timestamp = ravb_read(ndev, GCPT);
 		ptp_clock_event(priv->ptp.clock, &event);
+
+		result = IRQ_HANDLED;
+		gis &= ~GIS_PTCF;
 	}
 	if (gis & GIS_PTMF) {
 		struct ravb_ptp_perout *perout = priv->ptp.perout;
@@ -317,9 +321,14 @@
 			perout->target += perout->period;
 			ravb_ptp_update_compare(priv, perout->target);
 		}
+
+		result = IRQ_HANDLED;
+		gis &= ~GIS_PTCF;
 	}
 
-	ravb_write(ndev, ~gis, GIS);
+	ravb_write(ndev, gis, GIS);
+
+	return result;
 }
 
 void ravb_ptp_init(struct net_device *ndev, struct platform_device *pdev)
diff --git a/drivers/pci/host/pcie-rcar.c b/drivers/pci/host/pcie-rcar.c
index 5751444..8e24d5f 100644
--- a/drivers/pci/host/pcie-rcar.c
+++ b/drivers/pci/host/pcie-rcar.c
@@ -30,7 +30,6 @@
 #include <linux/platform_device.h>
 #include <linux/pm_runtime.h>
 #include <linux/slab.h>
-#include <linux/soc/renesas/s2ram_ddr_backup.h>
 
 #define PCIECAR			0x000010
 #define PCIECCTLR		0x000018
@@ -148,7 +147,6 @@
 	return container_of(chip, struct rcar_msi, chip);
 }
 
-
 /* Structure representing the PCIe interface */
 struct rcar_pcie {
 	struct device		*dev;
@@ -162,144 +160,6 @@
 
 static int rcar_pcie_wait_for_dl(struct rcar_pcie *pcie);
 
-#ifdef CONFIG_RCAR_DDR_BACKUP
-
-#define PCIE_BACKUP_REGS(pcie_ip_regs)	\
-struct hw_register (pcie_ip_regs)[] = {	\
-/* PCIEC transfer control registers */	\
-	{"PCIETCTLR",	0x2000,	32, 0}, \
-	{"PCIEINTER",	0x200C,	32, 0},	\
-	{"PCIEERRFER",	0x2024,	32, 0},	\
-	{"PCIETIER",	0x2030,	32, 0},	\
-	{"PCIEPMSCIER",	0x2038,	32, 0}, \
-	{"PCIEMSIALR",	0x2048,	32, 0},	\
-	{"PCIEMSIAUR",	0x204C,	32, 0},	\
-	{"PCIEMSIIER",	0x2050,	32, 0},	\
-	{"PCIEPRAR0",	0x2080,	32, 0},	\
-	{"PCIEPRAR1",	0x2084,	32, 0},	\
-	{"PCIEPRAR2",	0x2088,	32, 0},	\
-	{"PCIEPRAR3",	0x208C,	32, 0},	\
-	{"PCIEPRAR4",	0x2090,	32, 0},	\
-	{"PCIEPRAR5",	0x2094,	32, 0},	\
-	\
-	/* Local address registers */	\
-	{"PCIELAR0",	0x2200,	32, 0},	\
-	{"PCIELAMR0",	0x2208,	32, 0},	\
-	{"PCIELAR1",	0x2220,	32, 0},	\
-	{"PCIELAMR1",	0x2228,	32, 0},	\
-	{"PCIELAR2",	0x2240,	32, 0},	\
-	{"PCIELAMR2",	0x2248,	32, 0},	\
-	{"PCIELAR3",	0x2260,	32, 0},	\
-	{"PCIELAMR3",	0x2268,	32, 0},	\
-	{"PCIELAR4",	0x2280,	32, 0},	\
-	{"PCIELAMR4",	0x2288,	32, 0},	\
-	{"PCIELAR5",	0x22A0,	32, 0},	\
-	{"PCIELAMR5",	0x22A8,	32, 0},	\
-	\
-	/* PCIEC address registers */	\
-	{"PCIEPALR0",	0x3400,	32, 0},	\
-	{"PCIEPAUR0",	0x3404,	32, 0},	\
-	{"PCIEPAMR0",	0x3408,	32, 0},	\
-	{"PCIEPTCTLR0",	0x340C,	32, 0},	\
-	{"PCIEPALR1",	0x3420,	32, 0},	\
-	{"PCIEPAUR1",	0x3424,	32, 0},	\
-	{"PCIEPAMR1",	0x3428,	32, 0},	\
-	{"PCIEPTCTLR1",	0x342C,	32, 0},	\
-	{"PCIEPALR2",	0x3440,	32, 0},	\
-	{"PCIEPAUR2",	0x3444,	32, 0},	\
-	{"PCIEPAMR2",	0x3448,	32, 0},	\
-	{"PCIEPTCTLR2",	0x344C,	32, 0},	\
-	{"PCIEPALR3",	0x3460,	32, 0},	\
-	{"PCIEPAUR3",	0x3464,	32, 0},	\
-	{"PCIEPAMR3",	0x3468,	32, 0},	\
-	{"PCIEPTCTLR3",	0x346C,	32, 0},	\
-}
-
-static PCIE_BACKUP_REGS(pcie0_ip_regs);
-static PCIE_BACKUP_REGS(pcie1_ip_regs);
-
-static struct rcar_ip pcie0_ip = {
-	.ip_name = "pcie0",
-	.reg_count = ARRAY_SIZE(pcie0_ip_regs),
-	.ip_reg = pcie0_ip_regs,
-};
-
-static struct rcar_ip pcie1_ip = {
-	.ip_name = "pcie1",
-	.reg_count = ARRAY_SIZE(pcie1_ip_regs),
-	.ip_reg = pcie1_ip_regs,
-};
-
-struct ip_info {
-	const char *name;
-	struct rcar_ip *ip;
-};
-
-static struct ip_info ip_info_tbl[] = {
-	{"fe000000.pcie", &pcie0_ip },
-	{"ee800000.pcie", &pcie1_ip },
-	{NULL, NULL},
-};
-
-static struct rcar_ip *rcar_pcie_get_ip(const char *name)
-{
-	struct ip_info *ip_info = ip_info_tbl;
-	struct rcar_ip *ip = NULL;
-
-	while (ip_info->name) {
-		if (!strcmp(ip_info->name, name)) {
-			ip = ip_info->ip;
-			break;
-		}
-		ip_info++;
-	}
-
-	return ip;
-}
-
-static int rcar_pcie_save_regs(struct device *dev)
-{
-	struct rcar_ip *ip = rcar_pcie_get_ip(dev_name(dev));
-	struct rcar_pcie *pcie = NULL;
-	int ret;
-
-	if (ip) {
-		if (!ip->virt_addr) {
-			pcie = dev_get_drvdata(dev);
-			ip->virt_addr = pcie->base;
-		}
-
-		ret = rcar_handle_registers(ip, DO_BACKUP);
-		if (ret)
-			pr_err("%s: %s: BACKUP failed, ret=%d\n",
-				__func__, dev_name(dev), ret);
-	} else
-		pr_err("%s: Failed to find backup of dev: %s\n\n",
-				__func__, dev_name(dev));
-
-	return 0;
-}
-
-static int rcar_pcie_restore_regs(struct device *dev)
-{
-	struct rcar_ip *ip = rcar_pcie_get_ip(dev_name(dev));
-	int ret = -ENODEV;
-
-	if (ip) {
-		ret = rcar_handle_registers(ip, DO_RESTORE);
-		if (ret)
-			pr_err("%s: %s: RESTORE failed, ret=%d\n",
-				__func__, dev_name(dev), ret);
-
-	} else
-		pr_err("%s: Failed to find backup of dev: %s\n\n",
-				__func__, dev_name(dev));
-
-	return 0;
-}
-
-#endif /* CONFIG_RCAR_DDR_BACKUP */
-
 static void rcar_pci_write_reg(struct rcar_pcie *pcie, unsigned long val,
 			       unsigned long reg)
 {
@@ -391,6 +251,7 @@
 
 	if ((val == 0) || (rcar_pci_read_reg(pcie, PCIETCTLR) & DL_DOWN)) {
 		/* Wait PCI Express link is re-initialized */
+		dev_info(&bus->dev, "Wait PCI Express link is re-initialized\n");
 		rcar_pci_write_reg(pcie, CFINIT, PCIETCTLR);
 		rcar_pcie_wait_for_dl(pcie);
 	}
@@ -621,6 +482,36 @@
 		 (macsr & LINK_SPEED) == LINK_SPEED_5_0GTS ? "5" : "2.5");
 }
 
+static int rcar_pcie_hw_enable(struct rcar_pcie *pcie)
+{
+	struct resource_entry *win;
+	LIST_HEAD(res);
+	int i = 0;
+
+	/* Try setting 5 GT/s link speed */
+	rcar_pcie_force_speedup(pcie);
+
+	/* Setup PCI resources */
+	resource_list_for_each_entry(win, &pcie->resources) {
+		struct resource *res = win->res;
+
+		if (!res->flags)
+			continue;
+
+		switch (resource_type(res)) {
+		case IORESOURCE_IO:
+		case IORESOURCE_MEM:
+			rcar_pcie_setup_window(i, pcie, res);
+			i++;
+			break;
+		default:
+			continue;
+		}
+	}
+
+	return 0;
+}
+
 static int rcar_pcie_enable(struct rcar_pcie *pcie)
 {
 	struct device *dev = pcie->dev;
@@ -710,6 +601,7 @@
 		if ((rcar_pci_read_reg(pcie, PCIETSTR) & DATA_LINK_ACTIVE))
 			return 0;
 
+		/* It sometimes interrupts, I don't use sleep. */
 		mdelay(5);
 	}
 
@@ -1017,6 +909,23 @@
 	.map = rcar_msi_map,
 };
 
+static int rcar_pcie_hw_enable_msi(struct rcar_pcie *pcie)
+{
+	struct rcar_msi *msi = &pcie->msi;
+	unsigned long base;
+
+	/* setup MSI data target */
+	base = virt_to_phys((void *)msi->pages);
+
+	rcar_pci_write_reg(pcie, base | MSIFE, PCIEMSIALR);
+	rcar_pci_write_reg(pcie, 0, PCIEMSIAUR);
+
+	/* enable all MSI interrupts */
+	rcar_pci_write_reg(pcie, 0xffffffff, PCIEMSIIER);
+
+	return 0;
+}
+
 static int rcar_pcie_enable_msi(struct rcar_pcie *pcie)
 {
 	struct device *dev = pcie->dev;
@@ -1364,29 +1273,57 @@
 #ifdef CONFIG_PM_SLEEP
 static int rcar_pcie_suspend(struct device *dev)
 {
-	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
-	ret = rcar_pcie_save_regs(dev);
-#endif /* CONFIG_RCAR_DDR_BACKUP */
-
-	return ret;
+	/* Processing is unnecesary */
+	return 0;
 }
 
 static int rcar_pcie_resume(struct device *dev)
 {
 	struct rcar_pcie *pcie = dev_get_drvdata(dev);
-	int ret = 0;
+	unsigned int data;
+	const struct of_device_id *of_id;
+	int err;
+	int (*hw_init_fn)(struct rcar_pcie *);
 
-	if (pcie) {
-#ifdef CONFIG_RCAR_DDR_BACKUP
-		rcar_pcie_restore_regs(dev);
-#endif /* CONFIG_RCAR_DDR_BACKUP */
-		ret = rcar_pcie_hw_init(pcie);
-		if (ret)
-			pr_debug("%s: %s: re-init hw fail, ret=%d\n",
-			__func__, dev_name(dev), ret);
-	} else
-		pr_warn("%s: %s: pcie NULL\n", __func__, dev_name(dev));
+	/* HW initialize on Resume */
+	if (!pcie) {
+		dev_warn(dev, "%s: %s: pcie NULL\n", __func__, dev_name(dev));
+		return 0; /* resume of the whole system continues */
+	}
+
+	err = rcar_pcie_parse_map_dma_ranges(pcie, dev->of_node);
+	if (err) {
+		dev_err(dev, "%s: %s: parse map dma ranges fail, err=%d\n",
+				 __func__, dev_name(dev), err);
+		return 0; /* resume of the whole system continues */
+	}
+
+	of_id = of_match_device(rcar_pcie_of_match, dev);
+	if (!of_id || !of_id->data) {
+		dev_err(dev, "of_match_device not found.\n");
+		return 0; /* resume of the whole system continues */
+	}
+	hw_init_fn = of_id->data;
+
+	/* Failure to get a link might just be that no cards are inserted */
+	err = hw_init_fn(pcie);
+	if (err) {
+		dev_err(dev, "PCIe link down\n");
+		dev_dbg(dev, "%s: %s: re-init hw fail, err=%d\n",
+				__func__, dev_name(dev), err);
+		pm_runtime_put(dev);
+		return 0; /* resume of the whole system continues */
+	}
+
+	data = rcar_pci_read_reg(pcie, MACSR);
+	dev_info(dev, "PCIe x%d: link up\n", (data >> 20) & 0x3f);
+
+	if (IS_ENABLED(CONFIG_PCI_MSI)) {
+		/* enable MSI */
+		rcar_pcie_hw_enable_msi(pcie);
+		dev_dbg(dev, "%s: %s: enable MSI\n", __func__, dev_name(dev));
+	}
+	rcar_pcie_hw_enable(pcie);
 
 	return 0;
 }
diff --git a/drivers/phy/phy-rcar-gen3-usb2.c b/drivers/phy/phy-rcar-gen3-usb2.c
index 80ee954..f106dee 100644
--- a/drivers/phy/phy-rcar-gen3-usb2.c
+++ b/drivers/phy/phy-rcar-gen3-usb2.c
@@ -1,7 +1,7 @@
 /*
  * Renesas R-Car Gen3 for USB2.0 PHY driver
  *
- * Copyright (C) 2015 Renesas Electronics Corporation
+ * Copyright (C) 2015-2017 Renesas Electronics Corporation
  *
  * This is based on the phy-rcar-gen2 driver:
  * Copyright (C) 2014 Renesas Solutions Corp.
@@ -481,8 +481,15 @@
 #ifdef CONFIG_PM_SLEEP
 static int rcar_gen3_phy_suspend(struct device *dev)
 {
-	/* Empty function for now */
-	return 0;
+	int ret = 0;
+
+	if (to_phy(dev))
+		ret = rcar_gen3_phy_usb2_exit(to_phy(dev));
+	else {
+		pr_warn("%s: No phy dev\n", __func__);
+		ret = -ENODEV;
+	}
+	return ret;
 }
 
 static int rcar_gen3_phy_resume(struct device *dev)
diff --git a/drivers/pwm/pwm-rcar.c b/drivers/pwm/pwm-rcar.c
index 659454a..630f3f08 100644
--- a/drivers/pwm/pwm-rcar.c
+++ b/drivers/pwm/pwm-rcar.c
@@ -17,7 +17,6 @@
 #include <linux/pm_runtime.h>
 #include <linux/pwm.h>
 #include <linux/slab.h>
-#include <linux/soc/renesas/s2ram_ddr_backup.h>
 
 #define RCAR_PWM_MAX_DIVISION	24
 #define RCAR_PWM_MIN_CYCLE	2
@@ -37,124 +36,6 @@
 #define  RCAR_PWMCNT_PH0_MASK	0x000003ff
 #define  RCAR_PWMCNT_PH0_SHIFT	0
 
-#ifdef CONFIG_RCAR_DDR_BACKUP
-/* PWM0 */
-static struct hw_register pwm0_ip_regs[] = {
-	{"PWMCNT",   0x0004, 32, 0},
-	{"PWMCR",    0x0000, 32, 0},
-};
-
-static struct rcar_ip pwm0_ip = {
-	.ip_name   = "PWM0",
-	.reg_count = ARRAY_SIZE(pwm0_ip_regs),
-	.ip_reg    = pwm0_ip_regs,
-};
-
-/* PWM1 */
-static struct hw_register pwm1_ip_regs[] = {
-	{"PWMCNT",   0x0004, 32, 0},
-	{"PWMCR",    0x0000, 32, 0},
-};
-
-static struct rcar_ip pwm1_ip = {
-	.ip_name   = "PWM1",
-	.reg_count = ARRAY_SIZE(pwm1_ip_regs),
-	.ip_reg    = pwm1_ip_regs,
-};
-
-/* PWM2 */
-static struct hw_register pwm2_ip_regs[] = {
-	{"PWMCNT",   0x0004, 32, 0},
-	{"PWMCR",    0x0000, 32, 0},
-};
-
-static struct rcar_ip pwm2_ip = {
-	.ip_name   = "PWM2",
-	.reg_count = ARRAY_SIZE(pwm2_ip_regs),
-	.ip_reg    = pwm2_ip_regs,
-};
-
-/* PWM3 */
-static struct hw_register pwm3_ip_regs[] = {
-	{"PWMCNT",   0x0004, 32, 0},
-	{"PWMCR",    0x0000, 32, 0},
-};
-
-static struct rcar_ip pwm3_ip = {
-	.ip_name   = "PWM3",
-	.reg_count = ARRAY_SIZE(pwm3_ip_regs),
-	.ip_reg    = pwm3_ip_regs,
-};
-
-/* PWM4 */
-static struct hw_register pwm4_ip_regs[] = {
-	{"PWMCNT",   0x0004, 32, 0},
-	{"PWMCR",    0x0000, 32, 0},
-};
-
-static struct rcar_ip pwm4_ip = {
-	.ip_name   = "PWM4",
-	.reg_count = ARRAY_SIZE(pwm4_ip_regs),
-	.ip_reg    = pwm4_ip_regs,
-};
-
-/* PWM5 */
-static struct hw_register pwm5_ip_regs[] = {
-	{"PWMCNT",   0x0004, 32, 0},
-	{"PWMCR",    0x0000, 32, 0},
-};
-
-static struct rcar_ip pwm5_ip = {
-	.ip_name   = "PWM5",
-	.reg_count = ARRAY_SIZE(pwm5_ip_regs),
-	.ip_reg    = pwm5_ip_regs,
-};
-
-/* PWM6 */
-static struct hw_register pwm6_ip_regs[] = {
-	{"PWMCNT",   0x0004, 32, 0},
-	{"PWMCR",    0x0000, 32, 0},
-};
-
-static struct rcar_ip pwm6_ip = {
-	.ip_name   = "PWM6",
-	.reg_count = ARRAY_SIZE(pwm6_ip_regs),
-	.ip_reg    = pwm6_ip_regs,
-};
-
-struct pwm_ip_info {
-	const char *name;
-	struct rcar_ip *ip;
-};
-
-static struct pwm_ip_info ip_info_tbl[] = {
-	{"e6e30000.pwm", &pwm0_ip},
-	{"e6e31000.pwm", &pwm1_ip},
-	{"e6e32000.pwm", &pwm2_ip},
-	{"e6e33000.pwm", &pwm3_ip},
-	{"e6e34000.pwm", &pwm4_ip},
-	{"e6e35000.pwm", &pwm5_ip},
-	{"e6e36000.pwm", &pwm6_ip},
-	{NULL, NULL},
-};
-
-static struct rcar_ip *rcar_pwm_get_ip(const char *name)
-{
-	struct pwm_ip_info *ip_info = ip_info_tbl;
-	struct rcar_ip *ip = NULL;
-
-	while (ip_info->name) {
-		if (!strcmp(ip_info->name, name)) {
-			ip = ip_info->ip;
-			break;
-		}
-		ip_info++;
-	}
-
-	return ip;
-}
-#endif /* CONFIG_RCAR_DDR_BACKUP */
-
 struct rcar_pwm_chip {
 	struct pwm_chip chip;
 	void __iomem *base;
@@ -382,44 +263,29 @@
 #ifdef CONFIG_PM_SLEEP
 static int rcar_pwm_suspend(struct device *dev)
 {
-	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
-	struct platform_device *pdev = to_platform_device(dev);
-	struct rcar_ip *ip = rcar_pwm_get_ip(pdev->name);
-
-	if (ip) {
-		struct rcar_pwm_chip *pwm = platform_get_drvdata(pdev);
-
-		if (!ip->virt_addr)
-			ip->virt_addr = pwm->base;
-		pm_runtime_get_sync(dev);
-		ret = rcar_handle_registers(ip, DO_BACKUP);
-		pm_runtime_put(dev);
-	} else {
-		pr_err("%s: Failed to find PWM device\n", __func__);
-		ret = -ENODEV;
-	}
-#endif /* CONFIG_RCAR_DDR_BACKUP */
-	return ret;
+	return 0;
 }
 
 static int rcar_pwm_resume(struct device *dev)
 {
-	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
 	struct platform_device *pdev = to_platform_device(dev);
-	struct rcar_ip *ip = rcar_pwm_get_ip(pdev->name);
+	struct rcar_pwm_chip *rcar_pwm = platform_get_drvdata(pdev);
+	struct pwm_device *pwm_dev;
+	struct pwm_state state;
 
-	if (ip) {
-		pm_runtime_get_sync(dev);
-		ret = rcar_handle_registers(ip, DO_RESTORE);
-		pm_runtime_put(dev);
-	} else {
-		pr_err("%s: Failed to find PWM device\n", __func__);
-		ret = -ENODEV;
-	}
-#endif /* CONFIG_RCAR_DDR_BACKUP */
-	return ret;
+	pm_runtime_get_sync(dev);
+
+	pwm_dev = &rcar_pwm->chip.pwms[0];
+	pwm_get_state(pwm_dev, &state);
+	rcar_pwm_config(&rcar_pwm->chip, pwm_dev, state.duty_cycle,
+			state.period);
+
+	if (pwm_is_enabled(pwm_dev))
+		rcar_pwm_enable(&rcar_pwm->chip, pwm_dev);
+
+	pm_runtime_put(dev);
+
+	return 0;
 }
 
 static SIMPLE_DEV_PM_OPS(rcar_pwm_pm_ops,
diff --git a/drivers/soc/renesas/rcar-avs.c b/drivers/soc/renesas/rcar-avs.c
index 4b673c5..62adb0c 100644
--- a/drivers/soc/renesas/rcar-avs.c
+++ b/drivers/soc/renesas/rcar-avs.c
@@ -18,6 +18,7 @@
 #ifdef CONFIG_POWER_AVS
 #include <linux/io.h>
 #include <linux/of.h>
+#include <linux/of_address.h>
 #include <linux/slab.h>
 
 /* Change the default opp_table pattern in device tree.
@@ -61,37 +62,48 @@
 }
 
 /* Get AVS value */
-#define ADVFS_BASE		0xE60A0000
-#define KSEN_ADJCNTS		(ADVFS_BASE + 0x13C)
-#define VOLCOND_MASK_0_3	0x0f	/* VOLCOND[3:0] */
+#define VOLCOND_MASK_0_3  0x0f	/* VOLCOND[3:0] bits of KSEN_ADJCNTS register */
 
 #define AVS_TABLE_NUM	7
 
-unsigned int get_avs_value(void)
-{
-	unsigned int ret;
-	void __iomem *ksen_adjcnts = ioremap_nocache(KSEN_ADJCNTS, 4);
-	u32 ksen_adjcnts_value = ioread32(ksen_adjcnts);
-
-	ksen_adjcnts_value &= VOLCOND_MASK_0_3;
-	if (ksen_adjcnts_value >= 0 && ksen_adjcnts_value < AVS_TABLE_NUM) {
-		ret = ksen_adjcnts_value;
-	} else {
-		ret = 0;
-		pr_debug("rcar-cpufreq: hw get invalid avs value, use avs_tb0\n");
-	}
-	pr_info("rcar-cpufreq: use avs value: %d\n", ksen_adjcnts_value);
-	iounmap(ksen_adjcnts);
-
-	return ret;
-}
 #endif /* CONFIG_POWER_AVS */
 
+static const struct of_device_id rcar_avs_matches[] = {
+#if defined(CONFIG_ARCH_R8A7795) || defined(CONFIG_ARCH_R8A7796)
+	{ .compatible = "renesas,rcar-gen3-avs" },
+#endif
+	{ /* sentinel */ }
+};
+
 int __init rcar_avs_init(void)
 {
 #ifdef CONFIG_POWER_AVS
-	int avs_val = get_avs_value();
+	int avs_val;
+	struct device_node *np;
+	void __iomem *ksen_adjcnts;
 
+	/* Map and get KSEN_ADJCNTS register */
+	np = of_find_matching_node(NULL, rcar_avs_matches);
+	if (!np)
+		return -ENODEV;
+
+	ksen_adjcnts = of_iomap(np, 0); /* KSEN_ADJCNTS register from dts */
+	if (!ksen_adjcnts) {
+		pr_warn("%s: Cannot map regs\n", np->full_name);
+		return -ENOMEM;
+	}
+
+	/* Get and check avs value */
+	avs_val = ioread32(ksen_adjcnts);
+
+	avs_val &= VOLCOND_MASK_0_3;
+	if (!(avs_val >= 0 && avs_val < AVS_TABLE_NUM)) {
+		avs_val = 0;
+		pr_debug("rcar-cpufreq: hw get invalid avs value, use avs_tb0\n");
+	}
+	pr_info("rcar-cpufreq: use avs value: %d\n", avs_val);
+
+	/* Apply avs value */
 	change_default_opp_pattern(avs_val);
 #endif /* CONFIG_POWER_AVS */
 	return 0;
diff --git a/drivers/spi/spi-sh-msiof.c b/drivers/spi/spi-sh-msiof.c
index eaef234..7a327dc 100644
--- a/drivers/spi/spi-sh-msiof.c
+++ b/drivers/spi/spi-sh-msiof.c
@@ -1,7 +1,7 @@
 /*
  * SuperH MSIOF SPI Master Interface
  *
- * Copyright (C) 2016 Renesas Electronics Corporation
+ * Copyright (C) 2016-2017 Renesas Electronics Corporation
  * Copyright (c) 2009 Magnus Damm
  * Copyright (C) 2014 Glider bvba
  *
@@ -202,7 +202,6 @@
 	{ },
 };
 
-
 static int msiof_rcar_is_gen3(struct device *dev)
 {
 	struct device_node *node = dev->of_node;
@@ -549,7 +548,7 @@
 	sh_msiof_write(p, RMDR1, tmp);
 
 	tmp = 0;
-	if (soc_device_match(r8a7795es11)) {
+	if (soc_device_match(r8a7795es10)) {
 		if (p->mode == SPI_MSIOF_MASTER) {
 			tmp |= 0 << CTR_TSCKIZ_POL_SHIFT;
 			tmp |= 0 << CTR_RSCKIZ_POL_SHIFT;
@@ -1570,9 +1569,14 @@
 static int sh_msiof_spi_suspend(struct device *dev)
 {
 	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
 	struct platform_device *pdev = to_platform_device(dev);
+	struct sh_msiof_spi_priv *p = platform_get_drvdata(pdev);
 
+	ret = spi_master_suspend(p->master);
+	if (ret)
+		return ret;
+
+#ifdef CONFIG_RCAR_DDR_BACKUP
 	pm_runtime_get_sync(dev);
 	ret = msiof_save_regs(pdev);
 	pm_runtime_put(dev);
@@ -1583,13 +1587,19 @@
 static int sh_msiof_spi_resume(struct device *dev)
 {
 	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
 	struct platform_device *pdev = to_platform_device(dev);
+	struct sh_msiof_spi_priv *p = platform_get_drvdata(pdev);
 
+#ifdef CONFIG_RCAR_DDR_BACKUP
 	pm_runtime_get_sync(dev);
 	ret = msiof_restore_regs(pdev);
 	pm_runtime_put(dev);
 #endif /* CONFIG_RCAR_DDR_BACKUP */
+
+	ret = spi_master_resume(p->master);
+	if (ret)
+		return ret;
+
 	return ret;
 }
 
diff --git a/drivers/thermal/rcar_gen3_thermal.c b/drivers/thermal/rcar_gen3_thermal.c
index 2e5816b..95ea3a8 100644
--- a/drivers/thermal/rcar_gen3_thermal.c
+++ b/drivers/thermal/rcar_gen3_thermal.c
@@ -49,7 +49,7 @@
 #define PTAT_SIZE		REG_GEN3_PTAT3
 
 /* CTSR bit */
-#define PONM1            (0x1 << 8)	/* For H3 WS1.x */
+#define PONM1            (0x1 << 8)	/* For H3 ES1.x */
 #define AOUT            (0x1 << 7)
 #define THBGR           (0x1 << 5)
 #define VMEN            (0x1 << 4)
@@ -57,7 +57,7 @@
 #define THSST           (0x1 << 0)
 
 /* THCTR bit */
-#define PONM2            (0x1 << 6)	/* For H3 WS2.0 and M3 WS1.0 */
+#define PONM2            (0x1 << 6)	/* For H3 ES2.0 and M3 ES1.0 */
 
 #define CTEMP_MASK	0xFFF
 
@@ -74,13 +74,18 @@
 #define GEN3_FUSE_MASK	0xFFF
 
 /* Attribute structs describing Salvator-X revisions */
-/* H3 WS1.0 and WS1.1 */
+/* H3 ES1.0 and ES1.1 */
 static const struct soc_device_attribute r8a7795es1[]  = {
 	{ .soc_id = "r8a7795", .revision = "ES1.*" },
 	{}
 };
 
-/* M3 WS1.0 */
+static const struct soc_device_attribute r8a7795[]  = {
+	{ .soc_id = "r8a7795", .revision = "ES2.0" },
+	{}
+};
+
+/* M3 ES1.0 */
 static const struct soc_device_attribute r8a7796es10[]  = {
 	{ .soc_id = "r8a7796", .revision = "ES1.0" },
 	{}
@@ -170,11 +175,12 @@
 		return -ENOMEM;
 	}
 
-	/* For H3 WS1.0, H3 WS1.1 and M3 ES1.0
+	/* For H3 ES1.x, H3 ES2.0 and M3 ES1.0
 	 * these registers have not been programmed yet.
 	 * We will use fixed value as temporary solution.
 	 */
 	if (soc_device_match(r8a7795es1)
+		|| soc_device_match(r8a7795)
 		|| soc_device_match(r8a7796es10)) {
 		priv->factor.ptat_1 = 2351;
 		priv->factor.ptat_2 = 1509;
@@ -378,7 +384,7 @@
 
 		spin_unlock_irqrestore(&priv->lock, flags);
 	} else
-		/* H3 WS2.0 has the same init flow with M3 WS1.0 */
+		/* H3 ES2.0 has the same init flow with M3 ES1.0 */
 		rcar_gen3_r8a7796_thermal_init(priv);
 
 	return 0;
diff --git a/drivers/usb/renesas_usbhs/common.c b/drivers/usb/renesas_usbhs/common.c
index 4948740..8151197 100644
--- a/drivers/usb/renesas_usbhs/common.c
+++ b/drivers/usb/renesas_usbhs/common.c
@@ -443,6 +443,10 @@
 	struct usbhs_priv *priv = container_of(work,
 					       struct usbhs_priv,
 					       notify_hotplug_work.work);
+
+	if (priv->suspended)
+		return;
+
 	usbhsc_hotplug(priv);
 }
 
@@ -735,10 +739,9 @@
 {
 	struct usbhs_priv *priv = dev_get_drvdata(dev);
 	struct usbhs_mod *mod = usbhs_mod_get_current(priv);
-	struct renesas_usbhs_platform_info *info = dev_get_platdata(dev);
-	struct renesas_usbhs_driver_callback *dfunc = &info->driver_callback;
 
-	dfunc->notify_hotplug = NULL;
+	priv->suspended = 1;
+
 	if (mod) {
 		usbhs_mod_call(priv, stop, priv);
 		usbhs_mod_change(priv, -1);
@@ -754,14 +757,13 @@
 {
 	struct usbhs_priv *priv = dev_get_drvdata(dev);
 	struct platform_device *pdev = usbhs_priv_to_pdev(priv);
-	struct renesas_usbhs_platform_info *info = dev_get_platdata(dev);
-	struct renesas_usbhs_driver_callback *dfunc = &info->driver_callback;
 
 	if (!usbhsc_flags_has(priv, USBHSF_RUNTIME_PWCTRL))
 		usbhsc_power_ctrl(priv, 1);
 
 	usbhs_platform_call(priv, phy_reset, pdev);
-	dfunc->notify_hotplug = usbhsc_drvcllbck_notify_hotplug;
+
+	priv->suspended = 0;
 
 	usbhsc_drvcllbck_notify_hotplug(pdev);
 
diff --git a/drivers/usb/renesas_usbhs/common.h b/drivers/usb/renesas_usbhs/common.h
index 8c5fc12..6e02aa3 100644
--- a/drivers/usb/renesas_usbhs/common.h
+++ b/drivers/usb/renesas_usbhs/common.h
@@ -280,6 +280,8 @@
 
 	struct usb_phy *usb_phy;
 	struct phy *phy;
+
+	int suspended;
 };
 
 /*
diff --git a/drivers/watchdog/renesas_wdt.c b/drivers/watchdog/renesas_wdt.c
index 3c7708d..b2308a8 100644
--- a/drivers/watchdog/renesas_wdt.c
+++ b/drivers/watchdog/renesas_wdt.c
@@ -2,7 +2,7 @@
  * Watchdog driver for Renesas WDT watchdog
  *
  * Copyright (C) 2015-16 Wolfram Sang, Sang Engineering <wsa@sang-engineering.com>
- * Copyright (C) 2015-16 Renesas Electronics Corporation
+ * Copyright (C) 2015-17 Renesas Electronics Corporation
  *
  * 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
@@ -16,7 +16,6 @@
 #include <linux/of.h>
 #include <linux/platform_device.h>
 #include <linux/pm_runtime.h>
-#include <linux/soc/renesas/s2ram_ddr_backup.h>
 #include <linux/watchdog.h>
 
 #define RWTCNT		0
@@ -27,19 +26,6 @@
 
 #define RWDT_DEFAULT_TIMEOUT 60U
 
-#ifdef CONFIG_RCAR_DDR_BACKUP
-static struct hw_register rwdt_ip_regs[] = {
-	{"RWTCNT",   0x00, 16, 0},
-	{"RWTCSRA",  0x04, 8, 0},
-};
-
-static struct rcar_ip rwdt_ip = {
-	.ip_name = "RWDT",
-	.reg_count = ARRAY_SIZE(rwdt_ip_regs),
-	.ip_reg = rwdt_ip_regs,
-};
-#endif /* CONFIG_RCAR_DDR_BACKUP*/
-
 static const unsigned int clk_divs[] = { 1, 4, 16, 32, 64, 128, 1024 };
 
 static bool nowayout = WATCHDOG_NOWAYOUT;
@@ -226,23 +212,22 @@
 static int rwdt_suspend(struct device *dev)
 {
 	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
 	struct rwdt_priv *priv = dev_get_drvdata(dev);
 
-	if (!rwdt_ip.virt_addr)
-		rwdt_ip.virt_addr = priv->base;
+	if (watchdog_active(&priv->wdev))
+		ret = rwdt_stop(&priv->wdev);
 
-	ret = rcar_handle_registers(&rwdt_ip, DO_BACKUP);
-#endif /* CONFIG_RCAR_DDR_BACKUP */
 	return ret;
 }
 
 static int rwdt_resume(struct device *dev)
 {
 	int ret = 0;
-#ifdef CONFIG_RCAR_DDR_BACKUP
-	ret = rcar_handle_registers(&rwdt_ip, DO_RESTORE);
-#endif /* CONFIG_RCAR_DDR_BACKUP */
+	struct rwdt_priv *priv = dev_get_drvdata(dev);
+
+	if (watchdog_active(&priv->wdev))
+		ret = rwdt_start(&priv->wdev);
+
 	return ret;
 }
 
diff --git a/include/linux/mfd/tmio.h b/include/linux/mfd/tmio.h
index 2f2cc7b..3b95dc7 100644
--- a/include/linux/mfd/tmio.h
+++ b/include/linux/mfd/tmio.h
@@ -99,9 +99,6 @@
  */
 #define TMIO_MMC_SDIO_STATUS_QUIRK	(1 << 8)
 
-/* The start or stop of SD clock don't wait 10msec. */
-#define TMIO_MMC_CLK_NO_SLEEP		(1 << 9)
-
 /*
  * Some controllers allows to set SDx actual clock
  */
diff --git a/sound/soc/sh/rcar/adg.c b/sound/soc/sh/rcar/adg.c
index 2145957..85a33ac 100644
--- a/sound/soc/sh/rcar/adg.c
+++ b/sound/soc/sh/rcar/adg.c
@@ -34,6 +34,9 @@
 	struct clk_onecell_data onecell;
 	struct rsnd_mod mod;
 	u32 flags;
+	u32 ckr;
+	u32 rbga;
+	u32 rbgb;
 
 	int rbga_rate_for_441khz; /* RBGA */
 	int rbgb_rate_for_48khz;  /* RBGB */
@@ -316,9 +319,11 @@
 	struct rsnd_priv *priv = rsnd_mod_to_priv(ssi_mod);
 	struct rsnd_adg *adg = rsnd_priv_to_adg(priv);
 	struct device *dev = rsnd_priv_to_dev(priv);
+	struct rsnd_mod *adg_mod = rsnd_mod_get(adg);
 	struct clk *clk;
 	int i;
 	u32 data;
+	u32 ckr = 0;
 	int sel_table[] = {
 		[CLKA] = 0x1,
 		[CLKB] = 0x2,
@@ -360,15 +365,14 @@
 	rsnd_adg_set_ssi_clk(ssi_mod, data);
 
 	if (!(adg_mode_flags(adg) & LRCLK_ASYNC)) {
-		struct rsnd_mod *adg_mod = rsnd_mod_get(adg);
-		u32 ckr = 0;
-
 		if (0 == (rate % 8000))
 			ckr = 0x80000000;
-
-		rsnd_mod_bset(adg_mod, SSICKR, 0x80000000, ckr);
 	}
 
+	rsnd_mod_bset(adg_mod, BRGCKR, 0x80FF0000, adg->ckr | ckr);
+	rsnd_mod_write(adg_mod, BRRA,  adg->rbga);
+	rsnd_mod_write(adg_mod, BRRB,  adg->rbgb);
+
 	dev_dbg(dev, "ADG: %s[%d] selects 0x%x for %d\n",
 		rsnd_mod_name(ssi_mod), rsnd_mod_id(ssi_mod),
 		data, rate);
@@ -376,6 +380,25 @@
 	return 0;
 }
 
+void rsnd_adg_clk_control(struct rsnd_priv *priv, int enable)
+{
+	struct rsnd_adg *adg = rsnd_priv_to_adg(priv);
+	struct device *dev = rsnd_priv_to_dev(priv);
+	struct clk *clk;
+	int i, ret;
+
+	for_each_rsnd_clk(clk, adg, i) {
+		ret = 0;
+		if (enable)
+			ret = clk_prepare_enable(clk);
+		else
+			clk_disable_unprepare(clk);
+
+		if (ret < 0)
+			dev_warn(dev, "can't use clk %d\n", i);
+	}
+}
+
 static void rsnd_adg_get_clkin(struct rsnd_priv *priv,
 			       struct rsnd_adg *adg)
 {
@@ -387,27 +410,21 @@
 		[CLKC]	= "clk_c",
 		[CLKI]	= "clk_i",
 	};
-	int i, ret;
+	int i;
 
 	for (i = 0; i < CLKMAX; i++) {
 		clk = devm_clk_get(dev, clk_name[i]);
 		adg->clk[i] = IS_ERR(clk) ? NULL : clk;
 	}
 
-	for_each_rsnd_clk(clk, adg, i) {
-		ret = clk_prepare_enable(clk);
-		if (ret < 0)
-			dev_warn(dev, "can't use clk %d\n", i);
-
+	for_each_rsnd_clk(clk, adg, i)
 		dev_dbg(dev, "clk %d : %p : %ld\n", i, clk, clk_get_rate(clk));
-	}
 }
 
 static void rsnd_adg_get_clkout(struct rsnd_priv *priv,
 				struct rsnd_adg *adg)
 {
 	struct clk *clk;
-	struct rsnd_mod *adg_mod = rsnd_mod_get(adg);
 	struct device *dev = rsnd_priv_to_dev(priv);
 	struct device_node *np = dev->of_node;
 	u32 ckr, rbgx, rbga, rbgb;
@@ -532,13 +549,13 @@
 		}
 	}
 
-	rsnd_mod_bset(adg_mod, SSICKR, 0x80FF0000, ckr);
-	rsnd_mod_write(adg_mod, BRRA,  rbga);
-	rsnd_mod_write(adg_mod, BRRB,  rbgb);
+	adg->ckr = ckr;
+	adg->rbga = rbga;
+	adg->rbgb = rbgb;
 
 	for_each_rsnd_clkout(clk, adg, i)
 		dev_dbg(dev, "clkout %d : %p : %ld\n", i, clk, clk_get_rate(clk));
-	dev_dbg(dev, "SSICKR = 0x%08x, BRRA/BRRB = 0x%x/0x%x\n",
+	dev_dbg(dev, "BRGCKR = 0x%08x, BRRA/BRRB = 0x%x/0x%x\n",
 		ckr, rbga, rbgb);
 }
 
@@ -565,16 +582,12 @@
 
 	priv->adg = adg;
 
+	rsnd_adg_clk_enable(priv);
+
 	return 0;
 }
 
 void rsnd_adg_remove(struct rsnd_priv *priv)
 {
-	struct rsnd_adg *adg = rsnd_priv_to_adg(priv);
-	struct clk *clk;
-	int i;
-
-	for_each_rsnd_clk(clk, adg, i) {
-		clk_disable_unprepare(clk);
-	}
+	rsnd_adg_clk_disable(priv);
 }
diff --git a/sound/soc/sh/rcar/core.c b/sound/soc/sh/rcar/core.c
index 940012d..babbbbc 100644
--- a/sound/soc/sh/rcar/core.c
+++ b/sound/soc/sh/rcar/core.c
@@ -993,7 +993,11 @@
 
 void _rsnd_kctrl_remove(struct rsnd_kctrl_cfg *cfg)
 {
-	snd_ctl_remove(cfg->card, cfg->kctrl);
+	if (cfg->card && cfg->kctrl)
+		snd_ctl_remove(cfg->card, cfg->kctrl);
+
+	cfg->card = NULL;
+	cfg->kctrl = NULL;
 }
 
 int rsnd_kctrl_new_m(struct rsnd_mod *mod,
@@ -1251,12 +1255,11 @@
 	return ret;
 }
 
-#ifdef CONFIG_PM_SLEEP
 static int rsnd_suspend(struct device *dev)
 {
 	struct rsnd_priv *priv = dev_get_drvdata(dev);
 
-	rsnd_adg_remove(priv);
+	rsnd_adg_clk_disable(priv);
 
 	return 0;
 }
@@ -1264,24 +1267,21 @@
 static int rsnd_resume(struct device *dev)
 {
 	struct rsnd_priv *priv = dev_get_drvdata(dev);
-	int ret;
 
-	ret = rsnd_adg_probe(priv);
+	rsnd_adg_clk_enable(priv);
 
-	return ret;
+	return 0;
 }
 
-static SIMPLE_DEV_PM_OPS(rsnd_pm_ops,
-			rsnd_suspend, rsnd_resume);
-#define DEV_PM_OPS (&rsnd_pm_ops)
-#else
-#define DEV_PM_OPS NULL
-#endif  /* CONFIG_PM_SLEEP */
+static const struct dev_pm_ops rsnd_pm_ops = {
+	.suspend		= rsnd_suspend,
+	.resume			= rsnd_resume,
+};
 
 static struct platform_driver rsnd_driver = {
 	.driver	= {
 		.name	= "rcar_sound",
-		.pm	= DEV_PM_OPS,
+		.pm	= &rsnd_pm_ops,
 		.of_match_table = rsnd_of_match,
 	},
 	.probe		= rsnd_probe,
diff --git a/sound/soc/sh/rcar/dma.c b/sound/soc/sh/rcar/dma.c
index 6bc93cb..b3bdd36 100644
--- a/sound/soc/sh/rcar/dma.c
+++ b/sound/soc/sh/rcar/dma.c
@@ -707,6 +707,17 @@
 	return 0;
 }
 
+void rsnd_dma_detach(struct rsnd_mod *mod, struct rsnd_mod **dma_mod)
+{
+	if (*dma_mod) {
+		struct rsnd_priv *priv = rsnd_mod_to_priv(mod);
+		struct device *dev = rsnd_priv_to_dev(priv);
+
+		devm_kfree(dev, *dma_mod);
+		*dma_mod = NULL;
+	}
+}
+
 int rsnd_dma_probe(struct rsnd_priv *priv)
 {
 	struct platform_device *pdev = rsnd_priv_to_pdev(priv);
diff --git a/sound/soc/sh/rcar/gen.c b/sound/soc/sh/rcar/gen.c
index 7d2fdf8..e785fe94 100644
--- a/sound/soc/sh/rcar/gen.c
+++ b/sound/soc/sh/rcar/gen.c
@@ -311,7 +311,7 @@
 	static const struct rsnd_regmap_field_conf conf_adg[] = {
 		RSND_GEN_S_REG(BRRA,		0x00),
 		RSND_GEN_S_REG(BRRB,		0x04),
-		RSND_GEN_S_REG(SSICKR,		0x08),
+		RSND_GEN_S_REG(BRGCKR,		0x08),
 		RSND_GEN_S_REG(AUDIO_CLK_SEL0,	0x0c),
 		RSND_GEN_S_REG(AUDIO_CLK_SEL1,	0x10),
 		RSND_GEN_S_REG(AUDIO_CLK_SEL2,	0x14),
@@ -362,7 +362,7 @@
 	static const struct rsnd_regmap_field_conf conf_adg[] = {
 		RSND_GEN_S_REG(BRRA,		0x00),
 		RSND_GEN_S_REG(BRRB,		0x04),
-		RSND_GEN_S_REG(SSICKR,		0x08),
+		RSND_GEN_S_REG(BRGCKR,		0x08),
 		RSND_GEN_S_REG(AUDIO_CLK_SEL0,	0x0c),
 		RSND_GEN_S_REG(AUDIO_CLK_SEL1,	0x10),
 	};
diff --git a/sound/soc/sh/rcar/rsnd.h b/sound/soc/sh/rcar/rsnd.h
index 8ca1705..bf9596b 100644
--- a/sound/soc/sh/rcar/rsnd.h
+++ b/sound/soc/sh/rcar/rsnd.h
@@ -154,7 +154,7 @@
 	/* ADG */
 	RSND_REG_BRRA,
 	RSND_REG_BRRB,
-	RSND_REG_SSICKR,
+	RSND_REG_BRGCKR,
 	RSND_REG_DIV_EN,		/* Gen2 only */
 	RSND_REG_AUDIO_CLK_SEL0,
 	RSND_REG_AUDIO_CLK_SEL1,
@@ -200,6 +200,7 @@
  */
 int rsnd_dma_attach(struct rsnd_dai_stream *io,
 		    struct rsnd_mod *mod, struct rsnd_mod **dma_mod, int id);
+void rsnd_dma_detach(struct rsnd_mod *mod, struct rsnd_mod **dma_mod);
 int rsnd_dma_probe(struct rsnd_priv *priv);
 struct dma_chan *rsnd_dma_request_channel(struct device_node *of_node,
 					  struct rsnd_mod *mod, char *name);
@@ -276,9 +277,8 @@
 /*
  * status
  *
- * 0xH0000CBA
+ * 0xH0000CB0
  *
- * A	0: probe	1: remove
  * B	0: init		1: quit
  * C	0: start	1: stop
  *
@@ -288,19 +288,19 @@
  * H	0: fallback
  * H	0: hw_params
  */
-#define __rsnd_mod_shift_probe		0
-#define __rsnd_mod_shift_remove		0
 #define __rsnd_mod_shift_init		4
 #define __rsnd_mod_shift_quit		4
 #define __rsnd_mod_shift_start		8
 #define __rsnd_mod_shift_stop		8
+#define __rsnd_mod_shift_probe		28 /* always called */
+#define __rsnd_mod_shift_remove		28 /* always called */
 #define __rsnd_mod_shift_irq		28 /* always called */
 #define __rsnd_mod_shift_pcm_new	28 /* always called */
 #define __rsnd_mod_shift_fallback	28 /* always called */
 #define __rsnd_mod_shift_hw_params	28 /* always called */
 
-#define __rsnd_mod_add_probe		 1
-#define __rsnd_mod_add_remove		-1
+#define __rsnd_mod_add_probe		0
+#define __rsnd_mod_add_remove		0
 #define __rsnd_mod_add_init		 1
 #define __rsnd_mod_add_quit		-1
 #define __rsnd_mod_add_start		 1
@@ -311,7 +311,7 @@
 #define __rsnd_mod_add_hw_params	0
 
 #define __rsnd_mod_call_probe		0
-#define __rsnd_mod_call_remove		1
+#define __rsnd_mod_call_remove		0
 #define __rsnd_mod_call_init		0
 #define __rsnd_mod_call_quit		1
 #define __rsnd_mod_call_start		0
@@ -454,6 +454,9 @@
 				  unsigned int out_rate);
 int rsnd_adg_set_cmd_timsel_gen2(struct rsnd_mod *mod,
 				 struct rsnd_dai_stream *io);
+#define rsnd_adg_clk_enable(priv)	rsnd_adg_clk_control(priv, 1)
+#define rsnd_adg_clk_disable(priv)	rsnd_adg_clk_control(priv, 0)
+void rsnd_adg_clk_control(struct rsnd_priv *priv, int enable);
 
 /*
  *	R-Car sound priv
diff --git a/sound/soc/sh/rcar/src.c b/sound/soc/sh/rcar/src.c
index 1e9ca57..85f9879 100644
--- a/sound/soc/sh/rcar/src.c
+++ b/sound/soc/sh/rcar/src.c
@@ -390,6 +390,9 @@
 {
 	struct rsnd_src *src = rsnd_mod_to_src(mod);
 
+	/* reset sync convert_rate */
+	src->sync.val = 0;
+
 	rsnd_mod_power_on(mod);
 
 	rsnd_src_activation(mod);
@@ -398,9 +401,6 @@
 
 	rsnd_src_status_clear(mod);
 
-	/* reset sync convert_rate */
-	src->sync.val = 0;
-
 	return 0;
 }
 
diff --git a/sound/soc/sh/rcar/ssi.c b/sound/soc/sh/rcar/ssi.c
index 8f077cc..5616c94 100644
--- a/sound/soc/sh/rcar/ssi.c
+++ b/sound/soc/sh/rcar/ssi.c
@@ -701,7 +701,10 @@
 	int irq = ssi->irq;
 
 	/* PIO will request IRQ again */
-	devm_free_irq(dev, irq, mod);
+	if (ssi->dma)
+		devm_free_irq(dev, irq, mod);
+
+	rsnd_dma_detach(mod, &ssi->dma);
 
 	return 0;
 }