Merge "msm_serial_hs : Fix L2 port errors in HSUART driver"
diff --git a/Documentation/devicetree/bindings/arm/msm/msm_tspp.txt b/Documentation/devicetree/bindings/arm/msm/msm_tspp.txt
new file mode 100644
index 0000000..2b5e143
--- /dev/null
+++ b/Documentation/devicetree/bindings/arm/msm/msm_tspp.txt
@@ -0,0 +1,73 @@
+TSPP Driver
+
+For information on the TSPP driver, please refer to the TSPP driver
+documentation: Documentation/arm/msm/tspp.txt.
+
+The devicetree representation of the TSPP block should be:
+
+Required properties:
+
+- compatible: "qcom,msm_tspp"
+- cell-index: <0> - represents device ID.
+- reg: physical memory base addresses and sizes for the following:
+	TSIF0, TSIF1, TSPP and TSPP_BAM.
+- reg-names: names of the memory regions.
+- interrupts: represents IRQ numbers for the following:
+	TSIF_TSPP_IRQ, TSIF0_IRQ, TSIF1_IRQ, TSIF_BAM_IRQ.
+- interrupt-names: TSPP, TSIF and BAM interrupt names.
+- qcom,tsif-pclk: interface clock name.
+- qcom,tsif-ref-clk: reference clock name.
+	The driver uses clk_get to get the clocks by name. The clocks
+	should be defined in the relevant clock file (e.g. clock-8974.c).
+- gpios: GPIO numbers for TSIF0 (CLK, EN, DATA and SYNC) and TSIF1 (same).
+- qcom,gpio-names: GPIO names - strings describing the GPIO functionality.
+- qcom,gpios-func: GPIO functionality according to the GPIO functionality table.
+	GPIO pins can have more than a single functionality, and the TSPP driver
+	is responsible for configuring the GPIOs to work in TSIF functionality
+	based on this parameter.
+	Note: it is assumed that the functionality value (e.g. 1 in 8974 case)
+	is applicable to all TSIF GPIOs.
+
+Example (for 8974 platform, avaialble at msm8974.dtsi):
+
+	tspp: msm_tspp@f99d8000 {
+		compatible = "qcom,msm_tspp";
+		cell-index = <0>;
+		reg = <0xf99d8000 0x1000>, /* MSM_TSIF0_PHYS */
+		      <0xf99d9000 0x1000>, /* MSM_TSIF1_PHYS */
+		      <0xf99da000 0x1000>, /* MSM_TSPP_PHYS  */
+		      <0xf99c4000 0x14000>; /* MSM_TSPP_BAM_PHYS */
+		reg-names = "MSM_TSIF0_PHYS",
+			"MSM_TSIF1_PHYS",
+			"MSM_TSPP_PHYS",
+			"MSM_TSPP_BAM_PHYS";
+		interrupts = <0 153 0>, /* TSIF_TSPP_IRQ */
+			<0 151 0>, /* TSIF0_IRQ */
+			<0 152 0>, /* TSIF1_IRQ */
+			<0 154 0>; /* TSIF_BAM_IRQ */
+		interrupt-names = "TSIF_TSPP_IRQ",
+			"TSIF0_IRQ",
+			"TSIF1_IRQ",
+			"TSIF_BAM_IRQ";
+		qcom,tsif-pclk = "iface_clk";
+		qcom,tsif-ref-clk = "ref_clk";
+		gpios = <&msmgpio 89 0>, /* TSIF0 CLK  */
+			<&msmgpio 90 0>, /* TSIF0 EN   */
+			<&msmgpio 91 0>, /* TSIF0 DATA */
+			<&msmgpio 92 0>, /* TSIF0 SYNC */
+			<&msmgpio 93 0>, /* TSIF1 CLK  */
+			<&msmgpio 94 0>, /* TSIF1 EN   */
+			<&msmgpio 95 0>, /* TSIF1 DATA */
+			<&msmgpio 96 0>; /* TSIF1 SYNC */
+		qcom,gpio-names = "tsif_clk",
+				"tsif_en",
+				"tsif_data",
+				"tsif_sync",
+				"tsif_clk",
+				"tsif_en",
+				"tsif_data",
+				"tsif_sync";
+		qcom,gpios-func = <1>;
+	};
+
+
diff --git a/arch/arm/boot/dts/msm-iommu.dtsi b/arch/arm/boot/dts/msm-iommu.dtsi
index 024c11f..5a9e1ee 100755
--- a/arch/arm/boot/dts/msm-iommu.dtsi
+++ b/arch/arm/boot/dts/msm-iommu.dtsi
@@ -18,6 +18,7 @@
 		ranges;
 		reg = <0xfda64000 0x10000>;
 		reg-names = "iommu_base";
+		interrupts = <0 67 0>;
 		vdd-supply = <&gdsc_jpeg>;
 		qcom,needs-alt-core-clk;
 		label = "jpeg_iommu";
@@ -84,6 +85,7 @@
 		ranges;
 		reg = <0xfd928000 0x10000>;
 		reg-names = "iommu_base";
+		interrupts = <0 73 0>;
 		vdd-supply = <&gdsc_mdss>;
 		qcom,iommu-secure-id = <1>;
 		label = "mdp_iommu";
@@ -151,6 +153,7 @@
 		reg = <0xfdc84000 0x10000
 		       0xfdce0004 0x4>;
 		reg-names = "iommu_base", "clk_base";
+		interrupts = <0 45 0>;
 		vdd-supply = <&gdsc_venus>;
 		qcom,iommu-secure-id = <0>;
 		qcom,needs-alt-core-clk;
@@ -238,6 +241,7 @@
 		ranges;
 		reg = <0xfdb10000 0x10000>;
 		reg-names = "iommu_base";
+		interrupts = <0 38 0>;
 		vdd-supply = <&gdsc_oxili_cx>;
 		qcom,alt-vdd-supply = <&gdsc_oxili_gx>;
 		qcom,needs-alt-core-clk;
@@ -292,6 +296,7 @@
 		ranges;
 		reg = <0xfda44000 0x10000>;
 		reg-names = "iommu_base";
+		interrupts = <0 62 0>;
 		vdd-supply = <&gdsc_vfe>;
 		qcom,needs-alt-core-clk;
 		label = "vfe_iommu";
diff --git a/arch/arm/boot/dts/msm-pm8941.dtsi b/arch/arm/boot/dts/msm-pm8941.dtsi
index 098f543..74a95e6 100644
--- a/arch/arm/boot/dts/msm-pm8941.dtsi
+++ b/arch/arm/boot/dts/msm-pm8941.dtsi
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -77,7 +77,6 @@
 			qcom,bms-calculate-soc-ms = <20000>;
 			qcom,bms-chg-term-ua = <100000>;
 			qcom,bms-batt-type = <0>;
-			qcom,bms-use-external-rsense;
 
 			qcom,bms-iadc@3800 {
 				reg = <0x3800 0x100>;
diff --git a/arch/arm/boot/dts/msm9625-cdp.dts b/arch/arm/boot/dts/msm9625-cdp.dts
index 232fba7..f2a798a 100644
--- a/arch/arm/boot/dts/msm9625-cdp.dts
+++ b/arch/arm/boot/dts/msm9625-cdp.dts
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -17,7 +17,7 @@
 / {
 	model = "Qualcomm MSM 9625 CDP";
 	compatible = "qcom,msm9625-cdp", "qcom,msm9625";
-	qcom,msm-id = <134 1 0>, <152 1 0>;
+	qcom,msm-id = <134 1 0>, <152 1 0>, <149 1 0>, <150 1 0>;
 
 	i2c@f9925000 {
 		charger@57 {
diff --git a/arch/arm/boot/dts/msm9625-mtp.dts b/arch/arm/boot/dts/msm9625-mtp.dts
index faf86d4..584fc7f 100644
--- a/arch/arm/boot/dts/msm9625-mtp.dts
+++ b/arch/arm/boot/dts/msm9625-mtp.dts
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -17,7 +17,7 @@
 / {
 	model = "Qualcomm MSM 9625 MTP";
 	compatible = "qcom,msm9625-mtp", "qcom,msm9625";
-	qcom,msm-id = <134 7 0>, <152 7 0>;
+	qcom,msm-id = <134 7 0>, <152 7 0>, <149 7 0>, <150 7 0>;
 
 	i2c@f9925000 {
 		charger@57 {
diff --git a/arch/arm/configs/msm8910_defconfig b/arch/arm/configs/msm8910_defconfig
index 4b1e3f2..dfd6b5e 100644
--- a/arch/arm/configs/msm8910_defconfig
+++ b/arch/arm/configs/msm8910_defconfig
@@ -43,6 +43,9 @@
 # CONFIG_MSM_PROC_COMM is not set
 CONFIG_MSM_SMD=y
 CONFIG_MSM_SMD_PKG4=y
+CONFIG_MSM_IPC_ROUTER=y
+CONFIG_MSM_IPC_ROUTER_SMD_XPRT=y
+CONFIG_MSM_QMI_INTERFACE=y
 # CONFIG_MSM_HW3D is not set
 CONFIG_MSM_DIRECT_SCLK_ACCESS=y
 CONFIG_MSM_WATCHDOG_V2=y
diff --git a/arch/arm/configs/msm8974-perf_defconfig b/arch/arm/configs/msm8974-perf_defconfig
index be2e483..a5a9620 100644
--- a/arch/arm/configs/msm8974-perf_defconfig
+++ b/arch/arm/configs/msm8974-perf_defconfig
@@ -430,3 +430,5 @@
 CONFIG_CRC_CCITT=y
 CONFIG_SYNC=y
 CONFIG_SW_SYNC=y
+CONFIG_MOBICORE_SUPPORT=m
+CONFIG_MOBICORE_API=m
diff --git a/arch/arm/configs/msm8974_defconfig b/arch/arm/configs/msm8974_defconfig
index c882db5..ef61e66 100644
--- a/arch/arm/configs/msm8974_defconfig
+++ b/arch/arm/configs/msm8974_defconfig
@@ -446,3 +446,5 @@
 CONFIG_CRC_CCITT=y
 CONFIG_SYNC=y
 CONFIG_SW_SYNC=y
+CONFIG_MOBICORE_SUPPORT=m
+CONFIG_MOBICORE_API=m
diff --git a/arch/arm/mach-msm/Kconfig b/arch/arm/mach-msm/Kconfig
index 3f22221..94210fd 100644
--- a/arch/arm/mach-msm/Kconfig
+++ b/arch/arm/mach-msm/Kconfig
@@ -392,6 +392,7 @@
 	select MSM_GPIOMUX
 	select MSM_NATIVE_RESTART
 	select MSM_RESTART_V2
+	select QMI_ENCDEC
 
 config ARCH_MSM8226
 	bool "MSM8226"
diff --git a/arch/arm/mach-msm/board-8960.c b/arch/arm/mach-msm/board-8960.c
index f4e7880..f6b62f9 100644
--- a/arch/arm/mach-msm/board-8960.c
+++ b/arch/arm/mach-msm/board-8960.c
@@ -1438,26 +1438,49 @@
 
 static struct resource tspp_resources[] = {
 	[0] = {
+		.name = "TSIF_TSPP_IRQ",
 		.flags = IORESOURCE_IRQ,
 		.start = TSIF_TSPP_IRQ,
-		.end   = TSIF1_IRQ,
+		.end   = TSIF_TSPP_IRQ,
 	},
 	[1] = {
+		.name = "TSIF0_IRQ",
+		.flags = IORESOURCE_IRQ,
+		.start = TSIF1_IRQ,
+		.end   = TSIF1_IRQ,
+	},
+	[2] = {
+		.name = "TSIF1_IRQ",
+		.flags = IORESOURCE_IRQ,
+		.start = TSIF2_IRQ,
+		.end   = TSIF2_IRQ,
+	},
+	[3] = {
+		.name = "TSIF_BAM_IRQ",
+		.flags = IORESOURCE_IRQ,
+		.start = TSIF_BAM_IRQ,
+		.end   = TSIF_BAM_IRQ,
+	},
+	[4] = {
+		.name = "MSM_TSIF0_PHYS",
 		.flags = IORESOURCE_MEM,
 		.start = MSM_TSIF0_PHYS,
 		.end   = MSM_TSIF0_PHYS + MSM_TSIF_SIZE - 1,
 	},
-	[2] = {
+	[5] = {
+		.name = "MSM_TSIF1_PHYS",
 		.flags = IORESOURCE_MEM,
 		.start = MSM_TSIF1_PHYS,
 		.end   = MSM_TSIF1_PHYS + MSM_TSIF_SIZE - 1,
 	},
-	[3] = {
+	[6] = {
+		.name = "MSM_TSPP_PHYS",
 		.flags = IORESOURCE_MEM,
 		.start = MSM_TSPP_PHYS,
 		.end   = MSM_TSPP_PHYS + MSM_TSPP_SIZE - 1,
 	},
-	[4] = {
+	[7] = {
+		.name = "MSM_TSPP_BAM_PHYS",
 		.flags = IORESOURCE_MEM,
 		.start = MSM_TSPP_BAM_PHYS,
 		.end   = MSM_TSPP_BAM_PHYS + MSM_TSPP_BAM_SIZE - 1,
diff --git a/arch/arm/mach-msm/clock-8974.c b/arch/arm/mach-msm/clock-8974.c
index 66c01d6..1ac40cb 100644
--- a/arch/arm/mach-msm/clock-8974.c
+++ b/arch/arm/mach-msm/clock-8974.c
@@ -770,6 +770,8 @@
 		.dbg_name = "mmpll1_clk_src",
 		.rate = 846000000,
 		.ops = &clk_ops_pll_vote,
+		/* May be reassigned at runtime; alloc memory at compile time */
+		VDD_DIG_FMAX_MAP1(LOW, 846000000),
 		CLK_INIT(mmpll1_clk_src.c),
 	},
 };
@@ -781,7 +783,7 @@
 	.c = {
 		.parent = &cxo_clk_src.c,
 		.dbg_name = "mmpll3_clk_src",
-		.rate = 1000000000,
+		.rate = 820000000,
 		.ops = &clk_ops_local_pll,
 		CLK_INIT(mmpll3_clk_src.c),
 	},
@@ -2393,6 +2395,19 @@
 	F_END
 };
 
+static struct clk_freq_tbl ftbl_mmss_axi_v2_clk[] = {
+	F_MM( 19200000,    cxo,     1,   0,   0),
+	F_MM( 37500000,  gpll0,    16,   0,   0),
+	F_MM( 50000000,  gpll0,    12,   0,   0),
+	F_MM( 75000000,  gpll0,     8,   0,   0),
+	F_MM(100000000,  gpll0,     6,   0,   0),
+	F_MM(150000000,  gpll0,     4,   0,   0),
+	F_MM(333430000, mmpll1,   3.5,   0,   0),
+	F_MM(400000000, mmpll0,     2,   0,   0),
+	F_MM(466800000, mmpll1,   2.5,   0,   0),
+	F_END
+};
+
 static struct rcg_clk axi_clk_src = {
 	.cmd_rcgr_reg = 0x5040,
 	.set_rate = set_rate_hid,
@@ -2420,6 +2435,18 @@
 	F_END
 };
 
+static struct clk_freq_tbl ftbl_ocmemnoc_v2_clk[] = {
+	F_MM( 19200000,    cxo,   1,   0,   0),
+	F_MM( 37500000,  gpll0,  16,   0,   0),
+	F_MM( 50000000,  gpll0,  12,   0,   0),
+	F_MM( 75000000,  gpll0,   8,   0,   0),
+	F_MM(100000000,  gpll0,   6,   0,   0),
+	F_MM(150000000,  gpll0,   4,   0,   0),
+	F_MM(333430000, mmpll1, 3.5,   0,   0),
+	F_MM(400000000, mmpll0,   2,   0,   0),
+	F_END
+};
+
 struct rcg_clk ocmemnoc_clk_src = {
 	.cmd_rcgr_reg = OCMEMNOC_CMD_RCGR,
 	.set_rate = set_rate_hid,
@@ -3183,6 +3210,16 @@
 	F_END
 };
 
+static struct clk_freq_tbl ftbl_venus0_vcodec0_v2_clk[] = {
+	F_MM( 50000000,  gpll0,  12,   0,   0),
+	F_MM(100000000,  gpll0,   6,   0,   0),
+	F_MM(133330000, mmpll0,   6,   0,   0),
+	F_MM(200000000, mmpll0,   4,   0,   0),
+	F_MM(266670000, mmpll0,   3,   0,   0),
+	F_MM(465000000, mmpll3,   2,   0,   0),
+	F_END
+};
+
 static struct rcg_clk vcodec0_clk_src = {
 	.cmd_rcgr_reg = VCODEC0_CMD_RCGR,
 	.set_rate = set_rate_mnd,
@@ -5116,8 +5153,8 @@
 	CLK_LOOKUP("iface_clk", gcc_sdcc4_ahb_clk.c, "msm_sdcc.4"),
 	CLK_LOOKUP("core_clk", gcc_sdcc4_apps_clk.c, "msm_sdcc.4"),
 
-	CLK_LOOKUP("iface_clk", gcc_tsif_ahb_clk.c, ""),
-	CLK_LOOKUP("ref_clk", gcc_tsif_ref_clk.c, ""),
+	CLK_LOOKUP("iface_clk", gcc_tsif_ahb_clk.c, "f99d8000.msm_tspp"),
+	CLK_LOOKUP("ref_clk", gcc_tsif_ref_clk.c, "f99d8000.msm_tspp"),
 
 	CLK_LOOKUP("mem_clk", gcc_usb30_master_clk.c,           "usb_bam"),
 	CLK_LOOKUP("mem_iface_clk", gcc_sys_noc_usb3_axi_clk.c, "usb_bam"),
@@ -5531,7 +5568,7 @@
 	.base = &virt_bases[MMSS_BASE],
 };
 
-/* MMPLL1 at 1000 MHz, main output enabled. */
+/* MMPLL1 at 846 MHz, main output enabled. */
 static struct pll_config mmpll1_config __initdata = {
 	.l = 0x2C,
 	.m = 0x1,
@@ -5548,6 +5585,23 @@
 	.main_output_mask = BIT(0),
 };
 
+/* MMPLL1 at 1167 MHz, main output enabled. */
+static struct pll_config mmpll1_v2_config __initdata = {
+	.l = 60,
+	.m = 25,
+	.n = 32,
+	.vco_val = 0x0,
+	.vco_mask = BM(21, 20),
+	.pre_div_val = 0x0,
+	.pre_div_mask = BM(14, 12),
+	.post_div_val = 0x0,
+	.post_div_mask = BM(9, 8),
+	.mn_ena_val = BIT(24),
+	.mn_ena_mask = BIT(24),
+	.main_output_val = BIT(0),
+	.main_output_mask = BIT(0),
+};
+
 static struct pll_config_regs mmpll3_regs __initdata = {
 	.l_reg = (void __iomem *)MMPLL3_L_REG,
 	.m_reg = (void __iomem *)MMPLL3_M_REG,
@@ -5574,6 +5628,23 @@
 	.main_output_mask = BIT(0),
 };
 
+/* MMPLL3 at 930 MHz, main output enabled. */
+static struct pll_config mmpll3_v2_config __initdata = {
+	.l = 48,
+	.m = 7,
+	.n = 16,
+	.vco_val = 0x0,
+	.vco_mask = BM(21, 20),
+	.pre_div_val = 0x0,
+	.pre_div_mask = BM(14, 12),
+	.post_div_val = 0x0,
+	.post_div_mask = BM(9, 8),
+	.mn_ena_val = BIT(24),
+	.mn_ena_mask = BIT(24),
+	.main_output_val = BIT(0),
+	.main_output_mask = BIT(0),
+};
+
 static struct pll_config_regs lpapll0_regs __initdata = {
 	.l_reg = (void __iomem *)LPAPLL_L_REG,
 	.m_reg = (void __iomem *)LPAPLL_M_REG,
@@ -5620,8 +5691,14 @@
 	int ret;
 
 	configure_sr_hpm_lp_pll(&mmpll0_config, &mmpll0_regs, 1);
-	configure_sr_hpm_lp_pll(&mmpll1_config, &mmpll1_regs, 1);
-	configure_sr_hpm_lp_pll(&mmpll3_config, &mmpll3_regs, 0);
+
+	if (SOCINFO_VERSION_MAJOR(socinfo_get_version()) == 2) {
+		configure_sr_hpm_lp_pll(&mmpll1_v2_config, &mmpll1_regs, 1);
+		configure_sr_hpm_lp_pll(&mmpll3_v2_config, &mmpll3_regs, 0);
+	} else {
+		configure_sr_hpm_lp_pll(&mmpll1_config, &mmpll1_regs, 1);
+		configure_sr_hpm_lp_pll(&mmpll3_config, &mmpll3_regs, 0);
+	}
 	configure_sr_hpm_lp_pll(&lpapll0_config, &lpapll0_regs, 1);
 
 	/* Vote for GPLL0 to turn on. Needed by acpuclock. */
@@ -5677,8 +5754,13 @@
 
 static void __init msm8974_clock_post_init(void)
 {
-	clk_set_rate(&axi_clk_src.c, 282000000);
-	clk_set_rate(&ocmemnoc_clk_src.c, 282000000);
+	if (SOCINFO_VERSION_MAJOR(socinfo_get_version()) == 2) {
+		clk_set_rate(&axi_clk_src.c, 333430000);
+		clk_set_rate(&ocmemnoc_clk_src.c, 333430000);
+	} else {
+		clk_set_rate(&axi_clk_src.c, 282000000);
+		clk_set_rate(&ocmemnoc_clk_src.c, 282000000);
+	}
 
 	/*
 	 * Hold an active set vote at a rate of 40MHz for the MMSS NOC AHB
@@ -5784,6 +5866,25 @@
 	enable_rpm_scaling();
 
 	reg_init();
+
+	/* v2 specific changes */
+	if (SOCINFO_VERSION_MAJOR(socinfo_get_version()) == 2) {
+		mmpll3_clk_src.c.rate =  930000000;
+		mmpll1_clk_src.c.rate = 1167000000;
+		mmpll1_clk_src.c.fmax[VDD_DIG_NOMINAL] = 1167000000;
+
+		ocmemnoc_clk_src.freq_tbl = ftbl_ocmemnoc_v2_clk;
+		ocmemnoc_clk_src.c.fmax[VDD_DIG_NOMINAL] = 333430000;
+
+		axi_clk_src.freq_tbl = ftbl_mmss_axi_v2_clk;
+		axi_clk_src.c.fmax[VDD_DIG_NOMINAL] = 333430000;
+		axi_clk_src.c.fmax[VDD_DIG_HIGH] = 466800000;
+
+		vcodec0_clk_src.freq_tbl = ftbl_venus0_vcodec0_v2_clk;
+		vcodec0_clk_src.c.fmax[VDD_DIG_HIGH] = 465000000;
+
+		mdp_clk_src.c.fmax[VDD_DIG_NOMINAL] = 240000000;
+	}
 }
 
 static int __init msm8974_clock_late_init(void)
diff --git a/arch/arm/mach-msm/devices-8064.c b/arch/arm/mach-msm/devices-8064.c
index 67485dc..c986064 100644
--- a/arch/arm/mach-msm/devices-8064.c
+++ b/arch/arm/mach-msm/devices-8064.c
@@ -754,26 +754,49 @@
 
 static struct resource tspp_resources[] = {
 	[0] = {
+		.name = "TSIF_TSPP_IRQ",
 		.flags = IORESOURCE_IRQ,
 		.start = TSIF_TSPP_IRQ,
-		.end   = TSIF1_IRQ,
+		.end   = TSIF_TSPP_IRQ,
 	},
 	[1] = {
+		.name = "TSIF0_IRQ",
+		.flags = IORESOURCE_IRQ,
+		.start = TSIF1_IRQ,
+		.end   = TSIF1_IRQ,
+	},
+	[2] = {
+		.name = "TSIF1_IRQ",
+		.flags = IORESOURCE_IRQ,
+		.start = TSIF2_IRQ,
+		.end   = TSIF2_IRQ,
+	},
+	[3] = {
+		.name = "TSIF_BAM_IRQ",
+		.flags = IORESOURCE_IRQ,
+		.start = TSIF_BAM_IRQ,
+		.end   = TSIF_BAM_IRQ,
+	},
+	[4] = {
+		.name = "MSM_TSIF0_PHYS",
 		.flags = IORESOURCE_MEM,
 		.start = MSM_TSIF0_PHYS,
 		.end   = MSM_TSIF0_PHYS + MSM_TSIF_SIZE - 1,
 	},
-	[2] = {
+	[5] = {
+		.name = "MSM_TSIF1_PHYS",
 		.flags = IORESOURCE_MEM,
 		.start = MSM_TSIF1_PHYS,
 		.end   = MSM_TSIF1_PHYS + MSM_TSIF_SIZE - 1,
 	},
-	[3] = {
+	[6] = {
+		.name = "MSM_TSPP_PHYS",
 		.flags = IORESOURCE_MEM,
 		.start = MSM_TSPP_PHYS,
 		.end   = MSM_TSPP_PHYS + MSM_TSPP_SIZE - 1,
 	},
-	[4] = {
+	[7] = {
+		.name = "MSM_TSPP_BAM_PHYS",
 		.flags = IORESOURCE_MEM,
 		.start = MSM_TSPP_BAM_PHYS,
 		.end   = MSM_TSPP_BAM_PHYS + MSM_TSPP_BAM_SIZE - 1,
diff --git a/arch/arm/mach-msm/include/mach/iommu.h b/arch/arm/mach-msm/include/mach/iommu.h
index 9e2c24e..bbf3153 100644
--- a/arch/arm/mach-msm/include/mach/iommu.h
+++ b/arch/arm/mach-msm/include/mach/iommu.h
@@ -119,6 +119,8 @@
 
 void msm_iommu_add_drv(struct msm_iommu_drvdata *drv);
 void msm_iommu_remove_drv(struct msm_iommu_drvdata *drv);
+void program_iommu_bfb_settings(void __iomem *base,
+			const struct msm_iommu_bfb_settings *bfb_settings);
 
 /**
  * struct msm_iommu_ctx_drvdata - an IOMMU context bank instance
diff --git a/arch/arm/mach-msm/include/mach/qdsp6v2/audio_acdb.h b/arch/arm/mach-msm/include/mach/qdsp6v2/audio_acdb.h
index b830134..31dd582 100644
--- a/arch/arm/mach-msm/include/mach/qdsp6v2/audio_acdb.h
+++ b/arch/arm/mach-msm/include/mach/qdsp6v2/audio_acdb.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -14,13 +14,8 @@
 #define _AUDIO_ACDB_H
 
 #include <linux/msm_audio_acdb.h>
-#if defined(CONFIG_ARCH_MSM8974) || defined(CONFIG_ARCH_MSM9625) \
-	|| defined(CONFIG_ARCH_MSM8226)
-
-#include <sound/q6adm-v2.h>
-#else
 #include <sound/q6adm.h>
-#endif
+
 enum {
 	RX_CAL,
 	TX_CAL,
@@ -62,14 +57,11 @@
 void get_all_vocproc_cal(struct acdb_cal_block *cal_block);
 void get_all_vocstrm_cal(struct acdb_cal_block *cal_block);
 void get_all_vocvol_cal(struct acdb_cal_block *cal_block);
-void get_voice_col_data(uint32_t vocproc_type,
-	struct acdb_cal_block *cal_block);
 void get_anc_cal(struct acdb_cal_block *cal_block);
 void get_afe_cal(int32_t path, struct acdb_cal_block *cal_block);
 void get_audproc_cal(int32_t path, struct acdb_cal_block *cal_block);
 void get_audstrm_cal(int32_t path, struct acdb_cal_block *cal_block);
 void get_audvol_cal(int32_t path, struct acdb_cal_block *cal_block);
-void get_vocproc_dev_cfg_cal(struct acdb_cal_block *cal_block);
 void get_vocproc_cal(struct acdb_cal_data *cal_data);
 void get_vocstrm_cal(struct acdb_cal_data *cal_data);
 void get_vocvol_cal(struct acdb_cal_data *cal_data);
diff --git a/arch/arm/mach-msm/krait-regulator.c b/arch/arm/mach-msm/krait-regulator.c
index f7b2b1e..dd61db3 100644
--- a/arch/arm/mach-msm/krait-regulator.c
+++ b/arch/arm/mach-msm/krait-regulator.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -10,7 +10,7 @@
  * GNU General Public License for more details.
  */
 
-#define pr_fmt(fmt) "%s: " fmt, __func__
+#define pr_fmt(fmt) "PDN %s: " fmt, __func__
 
 #include <linux/err.h>
 #include <linux/kernel.h>
@@ -247,6 +247,7 @@
 				LDO_PWR_DWN_MASK, LDO_PWR_DWN_MASK);
 
 	kvreg->mode = HS_MODE;
+	pr_debug("%s using BHS\n", kvreg->name);
 	return 0;
 }
 
@@ -282,6 +283,7 @@
 		BHS_EN_MASK | LDO_BYP_MASK, 0);
 
 	kvreg->mode = LDO_MODE;
+	pr_debug("%s using LDO\n", kvreg->name);
 	return 0;
 }
 
@@ -294,9 +296,15 @@
 	return 0;
 }
 
-static int set_pmic_gang_voltage(int uV)
+static int set_pmic_gang_voltage(struct pmic_gang_vreg *pvreg, int uV)
 {
 	int setpoint;
+	int rc;
+
+	if (pvreg->pmic_vmax_uV == uV)
+		return 0;
+
+	pr_debug("%d\n", uV);
 
 	if (uV < PMIC_VOLTAGE_MIN) {
 		pr_err("requested %d < %d, restricting it to %d\n",
@@ -311,10 +319,17 @@
 
 	setpoint = DIV_ROUND_UP(uV, LV_RANGE_STEP);
 
-	return msm_spm_apcs_set_vdd(setpoint);
+	rc = msm_spm_apcs_set_vdd(setpoint);
+	if (rc < 0)
+		pr_err("could not set %duV setpt = 0x%x rc = %d\n",
+				uV, setpoint, rc);
+	else
+		pvreg->pmic_vmax_uV = uV;
+
+	return rc;
 }
 
-static int configure_ldo_or_hs(struct krait_power_vreg *from, int vmax)
+static int configure_ldo_or_hs_all(struct krait_power_vreg *from, int vmax)
 {
 	struct pmic_gang_vreg *pvreg = from->pvreg;
 	struct krait_power_vreg *kvreg;
@@ -345,7 +360,7 @@
 }
 
 #define SLEW_RATE 2994
-static int pmic_gang_set_voltage_increase(struct krait_power_vreg *from,
+static int krait_voltage_increase(struct krait_power_vreg *from,
 							int vmax)
 {
 	struct pmic_gang_vreg *pvreg = from->pvreg;
@@ -353,20 +368,21 @@
 	int settling_us;
 
 	/*
-	 * since pmic gang voltage is increasing set the gang voltage
+	 * since krait voltage is increasing set the gang voltage
 	 * prior to changing ldo/hs states of the requesting krait
 	 */
-	rc = set_pmic_gang_voltage(vmax);
+	rc = set_pmic_gang_voltage(pvreg, vmax);
 	if (rc < 0) {
 		dev_err(&from->rdev->dev, "%s failed set voltage %d rc = %d\n",
 				pvreg->name, vmax, rc);
+		return rc;
 	}
 
 	/* delay until the voltage is settled when it is raised */
 	settling_us = DIV_ROUND_UP(vmax - pvreg->pmic_vmax_uV, SLEW_RATE);
 	udelay(settling_us);
 
-	rc = configure_ldo_or_hs(from, vmax);
+	rc = configure_ldo_or_hs_all(from, vmax);
 	if (rc < 0) {
 		dev_err(&from->rdev->dev, "%s failed ldo/hs conf %d rc = %d\n",
 				pvreg->name, vmax, rc);
@@ -375,25 +391,25 @@
 	return rc;
 }
 
-static int pmic_gang_set_voltage_decrease(struct krait_power_vreg *from,
+static int krait_voltage_decrease(struct krait_power_vreg *from,
 							int vmax)
 {
 	struct pmic_gang_vreg *pvreg = from->pvreg;
 	int rc = 0;
 
 	/*
-	 * since pmic gang voltage is decreasing ldos might get out of their
+	 * since krait voltage is decreasing ldos might get out of their
 	 * operating range. Hence configure such kraits to be in hs mode prior
 	 * to setting the pmic gang voltage
 	 */
-	rc = configure_ldo_or_hs(from, vmax);
+	rc = configure_ldo_or_hs_all(from, vmax);
 	if (rc < 0) {
 		dev_err(&from->rdev->dev, "%s failed ldo/hs conf %d rc = %d\n",
 				pvreg->name, vmax, rc);
 		return rc;
 	}
 
-	rc = set_pmic_gang_voltage(vmax);
+	rc = set_pmic_gang_voltage(pvreg, vmax);
 	if (rc < 0) {
 		dev_err(&from->rdev->dev, "%s failed set voltage %d rc = %d\n",
 				pvreg->name, vmax, rc);
@@ -402,19 +418,6 @@
 	return rc;
 }
 
-static int pmic_gang_set_voltage(struct krait_power_vreg *from,
-				 int vmax)
-{
-	struct pmic_gang_vreg *pvreg = from->pvreg;
-
-	if (pvreg->pmic_vmax_uV == vmax)
-		return 0;
-	else if (vmax < pvreg->pmic_vmax_uV)
-		return pmic_gang_set_voltage_decrease(from, vmax);
-
-	return pmic_gang_set_voltage_increase(from, vmax);
-}
-
 #define PHASE_SETTLING_TIME_US		10
 static unsigned int pmic_gang_set_phases(struct krait_power_vreg *from,
 				int load_uA)
@@ -478,12 +481,11 @@
 	return kvreg->uV;
 }
 
-static int get_vmax(struct krait_power_vreg *from, int min_uV)
+static int get_vmax(struct pmic_gang_vreg *pvreg)
 {
 	int vmax = 0;
 	int v;
 	struct krait_power_vreg *kvreg;
-	struct pmic_gang_vreg *pvreg = from->pvreg;
 
 	list_for_each_entry(kvreg, &pvreg->krait_power_vregs, link) {
 		if (!kvreg->online)
@@ -491,9 +493,6 @@
 
 		v = kvreg->uV;
 
-		if (kvreg == from)
-			v = min_uV;
-
 		if (vmax < v)
 			vmax = v;
 	}
@@ -518,28 +517,35 @@
 
 #define ROUND_UP_VOLTAGE(v, res) (DIV_ROUND_UP(v, res) * res)
 static int _set_voltage(struct regulator_dev *rdev,
-			int min_uV, int max_uV, unsigned *selector)
+			int orig_krait_uV, int requested_uV)
 {
 	struct krait_power_vreg *kvreg = rdev_get_drvdata(rdev);
 	struct pmic_gang_vreg *pvreg = kvreg->pvreg;
 	int rc;
 	int vmax;
 
-	vmax = get_vmax(kvreg, min_uV);
+	pr_debug("%s: %d to %d\n", kvreg->name, orig_krait_uV, requested_uV);
+	/*
+	 * Assign the voltage before updating the gang voltage as we iterate
+	 * over all the core voltages and choose HS or LDO for each of them
+	 */
+	kvreg->uV = requested_uV;
+
+	vmax = get_vmax(pvreg);
 
 	/* round up the pmic voltage as per its resolution */
 	vmax = ROUND_UP_VOLTAGE(vmax, LV_RANGE_STEP);
 
-	rc = pmic_gang_set_voltage(kvreg, vmax);
+	if (requested_uV > orig_krait_uV)
+		rc = krait_voltage_increase(kvreg, vmax);
+	else
+		rc = krait_voltage_decrease(kvreg, vmax);
+
 	if (rc < 0) {
-		dev_err(&rdev->dev, "%s failed set voltage (%d, %d) rc = %d\n",
-				kvreg->name, min_uV, max_uV, rc);
-		goto out;
+		dev_err(&rdev->dev, "%s failed to set %duV from %duV rc = %d\n",
+				kvreg->name, requested_uV, orig_krait_uV, rc);
 	}
 
-	pvreg->pmic_vmax_uV = vmax;
-
-out:
 	return rc;
 }
 
@@ -562,14 +568,13 @@
 	}
 
 	mutex_lock(&pvreg->krait_power_vregs_lock);
-	kvreg->uV = min_uV;
-
 	if (!kvreg->online) {
+		kvreg->uV = min_uV;
 		mutex_unlock(&pvreg->krait_power_vregs_lock);
 		return 0;
 	}
 
-	rc = _set_voltage(rdev, min_uV, max_uV, selector);
+	rc = _set_voltage(rdev, kvreg->uV, min_uV);
 	mutex_unlock(&pvreg->krait_power_vregs_lock);
 
 	return rc;
@@ -673,12 +678,14 @@
 
 	mutex_lock(&pvreg->krait_power_vregs_lock);
 	kvreg->online = true;
-	rc = _get_optimum_mode(rdev, kvreg->uV, kvreg->uV,
-							kvreg->load_uA);
+	rc = _get_optimum_mode(rdev, kvreg->uV, kvreg->uV, kvreg->load_uA);
 	if (rc < 0)
 		goto en_err;
-	rc = _set_voltage(rdev, kvreg->uV,
-					rdev->constraints->max_uV, NULL);
+	/*
+	 * since the core is being enabled, behave as if it is increasing
+	 * the core voltage
+	 */
+	rc = _set_voltage(rdev, 0, kvreg->uV);
 en_err:
 	mutex_unlock(&pvreg->krait_power_vregs_lock);
 	return rc;
@@ -698,8 +705,7 @@
 	if (rc < 0)
 		goto dis_err;
 
-	rc = _set_voltage(rdev, kvreg->uV,
-					rdev->constraints->max_uV, NULL);
+	rc = _set_voltage(rdev, kvreg->uV, kvreg->uV);
 dis_err:
 	mutex_unlock(&pvreg->krait_power_vregs_lock);
 	return rc;
diff --git a/arch/arm/mach-msm/qdsp6v2/Makefile b/arch/arm/mach-msm/qdsp6v2/Makefile
index 323532c..34d336e 100644
--- a/arch/arm/mach-msm/qdsp6v2/Makefile
+++ b/arch/arm/mach-msm/qdsp6v2/Makefile
@@ -13,17 +13,17 @@
 endif
 obj-$(CONFIG_MSM_QDSP6_APR) += apr.o apr_v1.o apr_tal.o q6core.o dsp_debug.o
 obj-$(CONFIG_MSM_QDSP6_APRV2) += apr.o apr_v2.o apr_tal.o q6core.o dsp_debug.o
-obj-y += audio_acdb.o
 ifdef CONFIG_ARCH_MSM9615
+obj-y += audio_acdb.o
 obj-y += rtac.o
 endif
 obj-$(CONFIG_MSM_QDSP6_CODECS) += aac_in.o qcelp_in.o evrc_in.o amrnb_in.o audio_utils.o
 obj-$(CONFIG_MSM_QDSP6_CODECS) += audio_wma.o audio_wmapro.o audio_aac.o audio_multi_aac.o audio_utils_aio.o
-obj-$(CONFIG_MSM_QDSP6_CODECS) += rtac.o q6audio_v1.o q6audio_v1_aio.o
+obj-$(CONFIG_MSM_QDSP6_CODECS) += audio_acdb.o rtac.o q6audio_v1.o q6audio_v1_aio.o
 obj-$(CONFIG_MSM_QDSP6_CODECS) += audio_mp3.o audio_amrnb.o audio_amrwb.o audio_amrwbplus.o audio_evrc.o audio_qcelp.o amrwb_in.o
 obj-$(CONFIG_MSM_QDSP6V2_CODECS) += aac_in.o qcelp_in.o evrc_in.o amrnb_in.o audio_utils.o
 obj-$(CONFIG_MSM_QDSP6V2_CODECS) += audio_wma.o audio_wmapro.o audio_aac.o audio_multi_aac.o audio_utils_aio.o
-obj-$(CONFIG_MSM_QDSP6V2_CODECS) += rtac_v2.o q6audio_v2.o q6audio_v2_aio.o
+obj-$(CONFIG_MSM_QDSP6V2_CODECS) += q6audio_v2.o q6audio_v2_aio.o
 obj-$(CONFIG_MSM_QDSP6V2_CODECS)  += audio_mp3.o audio_amrnb.o audio_amrwb.o audio_evrc.o audio_qcelp.o amrwb_in.o
 obj-$(CONFIG_MSM_ADSP_LOADER) += adsp-loader.o
 obj-$(CONFIG_MSM_ULTRASOUND_A) += ultrasound/version_a/
diff --git a/arch/arm/mach-msm/qdsp6v2/audio_aac.c b/arch/arm/mach-msm/qdsp6v2/audio_aac.c
index 44ab611..2a8d5c8 100644
--- a/arch/arm/mach-msm/qdsp6v2/audio_aac.c
+++ b/arch/arm/mach-msm/qdsp6v2/audio_aac.c
@@ -2,7 +2,7 @@
  *
  * Copyright (C) 2008 Google, Inc.
  * Copyright (C) 2008 HTC Corporation
- * Copyright (c) 2010-2012, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2010-2013, The Linux Foundation. All rights reserved.
  *
  * This software is licensed under the terms of the GNU General Public
  * License version 2, as published by the Free Software Foundation, and
@@ -135,10 +135,9 @@
 		} else {
 			uint16_t sce_left = 1, sce_right = 2;
 			aac_config = audio->codec_cfg;
-			if ((aac_config->dual_mono_mode <
-				AUDIO_AAC_DUAL_MONO_PL_PR) ||
-				(aac_config->dual_mono_mode >
-				AUDIO_AAC_DUAL_MONO_PL_SR)) {
+			/* PL_PR is 0 only need to check PL_SR */
+			if (aac_config->dual_mono_mode >
+			    AUDIO_AAC_DUAL_MONO_PL_SR) {
 				pr_err("%s:AUDIO_SET_AAC_CONFIG: Invalid"
 					"dual_mono mode =%d\n", __func__,
 					aac_config->dual_mono_mode);
diff --git a/arch/arm/mach-msm/qdsp6v2/audio_acdb.c b/arch/arm/mach-msm/qdsp6v2/audio_acdb.c
index cad845f..ea22c12 100644
--- a/arch/arm/mach-msm/qdsp6v2/audio_acdb.c
+++ b/arch/arm/mach-msm/qdsp6v2/audio_acdb.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -64,15 +64,6 @@
 	atomic_t			vocstrm_total_cal_size;
 	atomic_t			vocvol_total_cal_size;
 
-	/* Voice Column data */
-	struct acdb_atomic_cal_block	vocproc_col_cal[MAX_VOCPROC_TYPES];
-	uint32_t			*col_data[MAX_VOCPROC_TYPES];
-
-	/* VocProc dev cfg cal*/
-	struct acdb_atomic_cal_block	vocproc_dev_cal[MAX_NETWORKS];
-	atomic_t			vocproc_dev_cal_size;
-	atomic_t			vocproc_dev_total_cal_size;
-
 	/* AFE cal */
 	struct acdb_atomic_cal_block	afe_cal[MAX_AUDPROC_TYPES];
 
@@ -203,45 +194,6 @@
 		atomic_read(&acdb_data.vocvol_total_cal_size);
 }
 
-void get_voice_col_data(uint32_t vocproc_type,
-			struct acdb_cal_block *cal_block)
-{
-	if (cal_block == NULL) {
-		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
-		goto done;
-	}
-
-	cal_block->cal_kvaddr = atomic_read(&acdb_data.
-				vocproc_col_cal[vocproc_type].cal_kvaddr);
-	cal_block->cal_paddr = atomic_read(&acdb_data.
-				vocproc_col_cal[vocproc_type].cal_paddr);
-	cal_block->cal_size = atomic_read(&acdb_data.
-				vocproc_col_cal[vocproc_type].cal_size);
-done:
-	return;
-}
-
-void store_voice_col_data(uint32_t vocproc_type, uint32_t cal_size,
-			  uint32_t *cal_data)
-{
-	if (cal_size > MAX_COL_SIZE) {
-		pr_err("%s: col size is to big %d\n", __func__,
-				cal_size);
-		goto done;
-	}
-	if (copy_from_user(acdb_data.col_data[vocproc_type],
-			(void *)((uint8_t *)cal_data + sizeof(cal_size)),
-			cal_size)) {
-		pr_err("%s: fail to copy col size %d\n",
-			__func__, cal_size);
-		goto done;
-	}
-	atomic_set(&acdb_data.vocproc_col_cal[vocproc_type].cal_size,
-		cal_size);
-done:
-	return;
-}
-
 void get_anc_cal(struct acdb_cal_block *cal_block)
 {
 	pr_debug("%s\n", __func__);
@@ -482,7 +434,7 @@
 	return;
 }
 
-void store_vocproc_dev_cfg_cal(int32_t len, struct cal_block *cal_blocks)
+void store_vocproc_cal(int32_t len, struct cal_block *cal_blocks)
 {
 	int i;
 	pr_debug("%s\n", __func__);
@@ -493,57 +445,6 @@
 		goto done;
 	}
 
-	atomic_set(&acdb_data.vocproc_dev_total_cal_size, 0);
-	for (i = 0; i < len; i++) {
-		if (cal_blocks[i].cal_offset >
-					atomic64_read(&acdb_data.mem_len)) {
-			pr_err("%s: offset %d is > mem_len %ld\n",
-				__func__, cal_blocks[i].cal_offset,
-				(long)atomic64_read(&acdb_data.mem_len));
-			atomic_set(&acdb_data.vocproc_dev_cal[i].cal_size, 0);
-		} else {
-			atomic_add(cal_blocks[i].cal_size,
-				&acdb_data.vocproc_dev_total_cal_size);
-			atomic_set(&acdb_data.vocproc_dev_cal[i].cal_size,
-				cal_blocks[i].cal_size);
-			atomic_set(&acdb_data.vocproc_dev_cal[i].cal_paddr,
-				cal_blocks[i].cal_offset +
-				atomic64_read(&acdb_data.paddr));
-			atomic_set(&acdb_data.vocproc_dev_cal[i].cal_kvaddr,
-				cal_blocks[i].cal_offset +
-				atomic64_read(&acdb_data.kvaddr));
-		}
-	}
-	atomic_set(&acdb_data.vocproc_dev_cal_size, len);
-done:
-	return;
-}
-
-void get_vocproc_dev_cfg_cal(struct acdb_cal_block *cal_block)
-{
-	pr_debug("%s\n", __func__);
-
-	cal_block->cal_kvaddr =
-		atomic_read(&acdb_data.vocproc_dev_cal[0].cal_kvaddr);
-	cal_block->cal_paddr =
-		atomic_read(&acdb_data.vocproc_dev_cal[0].cal_paddr);
-	cal_block->cal_size =
-		atomic_read(&acdb_data.vocproc_dev_total_cal_size);
-}
-
-
-
-void store_vocproc_cal(int32_t len, struct cal_block *cal_blocks)
-{
-	int i;
-	pr_debug("%s\n", __func__);
-
-	if (len > MAX_NETWORKS) {
-		pr_err("%s: Calibration sent for %d networks, only %d are "
-			"supported!\n", __func__, len, MAX_NETWORKS);
-		goto done;
-	}
-
 	atomic_set(&acdb_data.vocproc_total_cal_size, 0);
 	for (i = 0; i < len; i++) {
 		if (cal_blocks[i].cal_offset >
@@ -591,8 +492,8 @@
 	pr_debug("%s\n", __func__);
 
 	if (len > MAX_NETWORKS) {
-		pr_err("%s: Calibration sent for %d networks, only %d are "
-			"supported!\n", __func__, len, MAX_NETWORKS);
+		pr_err("%s: Calibration sent for %d networks, only %d are supported!\n",
+			__func__, len, MAX_NETWORKS);
 		goto done;
 	}
 
@@ -643,8 +544,8 @@
 	pr_debug("%s\n", __func__);
 
 	if (len > MAX_NETWORKS) {
-		pr_err("%s: Calibration sent for %d networks, only %d are "
-			"supported!\n", __func__, len, MAX_NETWORKS);
+		pr_err("%s: Calibration sent for %d networks, only %d are supported!\n",
+			__func__, len, MAX_NETWORKS);
 		goto done;
 	}
 
@@ -719,8 +620,7 @@
 	pr_debug("%s\n", __func__);
 
 	if (atomic64_read(&acdb_data.mem_len)) {
-		pr_debug("%s: ACDB opened but memory allocated, "
-			"using existing allocation!\n",
+		pr_debug("%s: ACDB opened but memory allocated, using existing allocation!\n",
 			__func__);
 	}
 
@@ -730,19 +630,12 @@
 
 static int deregister_memory(void)
 {
-	int i;
-
 	if (atomic64_read(&acdb_data.mem_len)) {
 		mutex_lock(&acdb_data.acdb_mutex);
 		atomic64_set(&acdb_data.mem_len, 0);
 		atomic_set(&acdb_data.vocstrm_total_cal_size, 0);
 		atomic_set(&acdb_data.vocproc_total_cal_size, 0);
 		atomic_set(&acdb_data.vocvol_total_cal_size, 0);
-
-		for (i = 0; i < MAX_VOCPROC_TYPES; i++) {
-			kfree(acdb_data.col_data[i]);
-			acdb_data.col_data[i] = NULL;
-		}
 		ion_unmap_kernel(acdb_data.ion_client, acdb_data.ion_handle);
 		ion_free(acdb_data.ion_client, acdb_data.ion_handle);
 		ion_client_destroy(acdb_data.ion_client);
@@ -754,18 +647,12 @@
 static int register_memory(void)
 {
 	int			result;
-	int			i;
 	unsigned long		paddr;
 	void                    *kvptr;
 	unsigned long		kvaddr;
 	unsigned long		mem_len;
 
 	mutex_lock(&acdb_data.acdb_mutex);
-	for (i = 0; i < MAX_VOCPROC_TYPES; i++) {
-		acdb_data.col_data[i] = kmalloc(MAX_COL_SIZE, GFP_KERNEL);
-		atomic_set(&acdb_data.vocproc_col_cal[i].cal_kvaddr,
-			(uint32_t)acdb_data.col_data[i]);
-	}
 
 	acdb_data.ion_client =
 		msm_ion_client_create(UINT_MAX, "audio_acdb_client");
@@ -803,8 +690,7 @@
 	atomic64_set(&acdb_data.mem_len, mem_len);
 	mutex_unlock(&acdb_data.acdb_mutex);
 
-	pr_debug("%s done! paddr = 0x%lx, "
-		"kvaddr = 0x%lx, len = x%lx\n",
+	pr_debug("%s done! paddr = 0x%lx, kvaddr = 0x%lx, len = x%lx\n",
 		 __func__,
 		(long)atomic64_read(&acdb_data.paddr),
 		(long)atomic64_read(&acdb_data.kvaddr),
@@ -820,6 +706,7 @@
 	mutex_unlock(&acdb_data.acdb_mutex);
 	return result;
 }
+
 static long acdb_ioctl(struct file *f,
 		unsigned int cmd, unsigned long arg)
 {
@@ -906,18 +793,6 @@
 		goto done;
 	}
 
-	switch (cmd) {
-	case AUDIO_SET_VOCPROC_COL_CAL:
-		store_voice_col_data(VOCPROC_CAL, size, (uint32_t *)arg);
-		goto done;
-	case AUDIO_SET_VOCSTRM_COL_CAL:
-		store_voice_col_data(VOCSTRM_CAL, size, (uint32_t *)arg);
-		goto done;
-	case AUDIO_SET_VOCVOL_COL_CAL:
-		store_voice_col_data(VOCVOL_CAL, size, (uint32_t *)arg);
-		goto done;
-	}
-
 	if (copy_from_user(data, (void *)(arg + sizeof(size)), size)) {
 
 		pr_err("%s: fail to copy table size %d\n", __func__, size);
@@ -934,50 +809,50 @@
 	switch (cmd) {
 	case AUDIO_SET_AUDPROC_TX_CAL:
 		if (size > sizeof(struct cal_block))
-			pr_err("%s: More Audproc Cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More Audproc Cal then expected, size received: %d\n",
+				__func__, size);
 		store_audproc_cal(TX_CAL, (struct cal_block *)data);
 		break;
 	case AUDIO_SET_AUDPROC_RX_CAL:
 		if (size > sizeof(struct cal_block))
-			pr_err("%s: More Audproc Cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More Audproc Cal then expected, size received: %d\n",
+				__func__, size);
 		store_audproc_cal(RX_CAL, (struct cal_block *)data);
 		break;
 	case AUDIO_SET_AUDPROC_TX_STREAM_CAL:
 		if (size > sizeof(struct cal_block))
-			pr_err("%s: More Audproc Cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More Audproc Cal then expected, size received: %d\n",
+				__func__, size);
 		store_audstrm_cal(TX_CAL, (struct cal_block *)data);
 		break;
 	case AUDIO_SET_AUDPROC_RX_STREAM_CAL:
 		if (size > sizeof(struct cal_block))
-			pr_err("%s: More Audproc Cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More Audproc Cal then expected, size received: %d\n",
+				__func__, size);
 		store_audstrm_cal(RX_CAL, (struct cal_block *)data);
 		break;
 	case AUDIO_SET_AUDPROC_TX_VOL_CAL:
 		if (size > sizeof(struct cal_block))
-			pr_err("%s: More Audproc Cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More Audproc Cal then expected, size received: %d\n",
+				__func__, size);
 		store_audvol_cal(TX_CAL, (struct cal_block *)data);
 		break;
 	case AUDIO_SET_AUDPROC_RX_VOL_CAL:
 		if (size > sizeof(struct cal_block))
-			pr_err("%s: More Audproc Cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More Audproc Cal then expected, size received: %d\n",
+				__func__, size);
 		store_audvol_cal(RX_CAL, (struct cal_block *)data);
 		break;
 	case AUDIO_SET_AFE_TX_CAL:
 		if (size > sizeof(struct cal_block))
-			pr_err("%s: More AFE Cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More AFE Cal then expected, size received: %d\n",
+				__func__, size);
 		store_afe_cal(TX_CAL, (struct cal_block *)data);
 		break;
 	case AUDIO_SET_AFE_RX_CAL:
 		if (size > sizeof(struct cal_block))
-			pr_err("%s: More AFE Cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More AFE Cal then expected, size received: %d\n",
+				__func__, size);
 		store_afe_cal(RX_CAL, (struct cal_block *)data);
 		break;
 	case AUDIO_SET_VOCPROC_CAL:
@@ -992,14 +867,10 @@
 		store_vocvol_cal(size / sizeof(struct cal_block),
 						(struct cal_block *)data);
 		break;
-	case AUDIO_SET_VOCPROC_DEV_CFG_CAL:
-		store_vocproc_dev_cfg_cal(size / sizeof(struct cal_block),
-						(struct cal_block *)data);
-		break;
 	case AUDIO_SET_SIDETONE_CAL:
 		if (size > sizeof(struct sidetone_cal))
-			pr_err("%s: More sidetone cal then expected, "
-				"size received: %d\n", __func__, size);
+			pr_err("%s: More sidetone cal then expected, size received: %d\n",
+			       __func__, size);
 		store_sidetone_cal((struct sidetone_cal *)data);
 		break;
 	case AUDIO_SET_ANC_CAL:
diff --git a/arch/arm/mach-msm/qdsp6v2/audio_multi_aac.c b/arch/arm/mach-msm/qdsp6v2/audio_multi_aac.c
index b53edd9..658c07b 100644
--- a/arch/arm/mach-msm/qdsp6v2/audio_multi_aac.c
+++ b/arch/arm/mach-msm/qdsp6v2/audio_multi_aac.c
@@ -2,7 +2,7 @@
  *
  * Copyright (C) 2008 Google, Inc.
  * Copyright (C) 2008 HTC Corporation
- * Copyright (c) 2011-2012, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2011-2013, The Linux Foundation. All rights reserved.
  *
  * This software is licensed under the terms of the GNU General Public
  * License version 2, as published by the Free Software Foundation, and
@@ -147,10 +147,8 @@
 		} else {
 			uint16_t sce_left = 1, sce_right = 2;
 			aac_config = audio->codec_cfg;
-			if ((aac_config->dual_mono_mode <
-				AUDIO_AAC_DUAL_MONO_PL_PR) ||
-				(aac_config->dual_mono_mode >
-				AUDIO_AAC_DUAL_MONO_PL_SR)) {
+			if (aac_config->dual_mono_mode >
+			    AUDIO_AAC_DUAL_MONO_PL_SR) {
 				pr_err("%s:AUDIO_SET_AAC_CONFIG: Invalid dual_mono mode =%d\n",
 					 __func__, aac_config->dual_mono_mode);
 			} else {
diff --git a/arch/arm/mach-msm/qdsp6v2/dsp_debug.c b/arch/arm/mach-msm/qdsp6v2/dsp_debug.c
index 3635fbd..26c8f75 100644
--- a/arch/arm/mach-msm/qdsp6v2/dsp_debug.c
+++ b/arch/arm/mach-msm/qdsp6v2/dsp_debug.c
@@ -38,12 +38,14 @@
 
 void q6audio_dsp_not_responding(void)
 {
+	int i;
+
 	if (cb_ptr)
 		cb_ptr(DSP_STATE_CRASHED);
 	if (atomic_add_return(1, &dsp_crash_count) != 1) {
 		pr_err("q6audio_dsp_not_responding() \
 			- parking additional crasher...\n");
-		for (;;)
+		for (i = 0; i < 600; i++)
 			msleep(1000);
 	}
 	if (dsp_wait_count) {
diff --git a/arch/arm/mach-msm/qdsp6v2/q6core.c b/arch/arm/mach-msm/qdsp6v2/q6core.c
index 9dd66e1..f23ba67 100644
--- a/arch/arm/mach-msm/qdsp6v2/q6core.c
+++ b/arch/arm/mach-msm/qdsp6v2/q6core.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2011, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -253,8 +253,6 @@
 	int len;
 	static int t_len;
 
-	if (count < 0)
-		return 0;
 	len = count > 63 ? 63 : count;
 	if (copy_from_user(l_buf + 20 , buf, len)) {
 		pr_info("Unable to copy data from user space\n");
diff --git a/arch/arm/mach-msm/socinfo.c b/arch/arm/mach-msm/socinfo.c
index 1ab1f71..ef40743 100644
--- a/arch/arm/mach-msm/socinfo.c
+++ b/arch/arm/mach-msm/socinfo.c
@@ -282,6 +282,8 @@
 	/* 9625 IDs */
 	[134] = MSM_CPU_9625,
 	[152] = MSM_CPU_9625,
+	[149] = MSM_CPU_9625,
+	[150] = MSM_CPU_9625,
 
 	/* 8960AB IDs */
 	[138] = MSM_CPU_8960AB,
diff --git a/drivers/crypto/msm/qce50.c b/drivers/crypto/msm/qce50.c
index d605a61..4eac9cb 100644
--- a/drivers/crypto/msm/qce50.c
+++ b/drivers/crypto/msm/qce50.c
@@ -1,6 +1,6 @@
 /* Qualcomm Crypto Engine driver.
  *
- * Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+ * Copyright (c) 2012-2013, Code Aurora Forum. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -895,7 +895,10 @@
 			len = ALIGN(len, pce_dev->ce_sps.ce_burst_size);
 		while (len > 0) {
 			if (len > SPS_MAX_PKT_SIZE) {
-				data_cnt = SPS_MAX_PKT_SIZE;
+				if ((len % SPS_MAX_PKT_SIZE) > 0)
+					data_cnt = (len % SPS_MAX_PKT_SIZE);
+				else
+					data_cnt = SPS_MAX_PKT_SIZE;
 				iovec->size = data_cnt;
 				iovec->addr = addr;
 				iovec->flags = 0;
diff --git a/drivers/crypto/msm/qce50.h b/drivers/crypto/msm/qce50.h
index 8533636..7a7aacc 100644
--- a/drivers/crypto/msm/qce50.h
+++ b/drivers/crypto/msm/qce50.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, Code Aurora Forum. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -36,7 +36,7 @@
 
 /* QCE max number of descriptor in a descriptor list */
 #define QCE_MAX_NUM_DESC    128
-#define SPS_MAX_PKT_SIZE  (32 * 1024  - 64)
+#define SPS_MAX_PKT_SIZE  (16 * 1024)
 
 /* State of consumer/producer Pipe */
 enum qce_pipe_st_enum {
diff --git a/drivers/gpu/msm/kgsl_iommu.c b/drivers/gpu/msm/kgsl_iommu.c
index 818bd63..abf125f 100644
--- a/drivers/gpu/msm/kgsl_iommu.c
+++ b/drivers/gpu/msm/kgsl_iommu.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2011-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2011-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -11,6 +11,7 @@
  *
  */
 #include <linux/types.h>
+#include <linux/delay.h>
 #include <linux/device.h>
 #include <linux/spinlock.h>
 #include <linux/genalloc.h>
@@ -40,6 +41,8 @@
 	{ 0x20, 0, 0 },				/* FSR */
 	{ 0x800, 0, 0 },			/* TLBIALL */
 	{ 0x820, 0, 0 },			/* RESUME */
+	{ 0x03C, 0, 0 },			/* TLBLKCR */
+	{ 0x818, 0, 0 },			/* V2PUR */
 };
 
 static struct kgsl_iommu_register_list kgsl_iommuv2_reg[KGSL_IOMMU_REG_MAX] = {
@@ -782,16 +785,26 @@
  */
 static int kgsl_iommu_init_sync_lock(struct kgsl_mmu *mmu)
 {
-	struct kgsl_iommu *iommu = mmu->device->mmu.priv;
+	struct kgsl_iommu *iommu = mmu->priv;
 	int status = 0;
 	uint32_t lock_phy_addr = 0;
 	uint32_t page_offset = 0;
 
-	if (KGSL_DEVICE_3D0 != mmu->device->id ||
-		!msm_soc_version_supports_iommu_v1() ||
+	if (!msm_soc_version_supports_iommu_v1() ||
 		!kgsl_mmu_is_perprocess())
 		return status;
 
+	/*
+	 * For 2D devices cpu side sync lock is required. For 3D device,
+	 * since we only have a single 3D core and we always ensure that
+	 * 3D core is idle while writing to IOMMU register using CPU this
+	 * lock is not required
+	 */
+	if (KGSL_DEVICE_2D0 == mmu->device->id ||
+		KGSL_DEVICE_2D1 == mmu->device->id) {
+		return status;
+	}
+
 	/* Return if already initialized */
 	if (iommu->sync_lock_initialized)
 		return status;
@@ -1260,6 +1273,111 @@
 	return status;
 }
 
+/*
+ * kgsl_iommu_lock_rb_in_tlb - Allocates tlb entries and locks the
+ * virtual to physical address translation of ringbuffer for 3D
+ * device into tlb.
+ * @mmu - Pointer to mmu structure
+ *
+ * Return - void
+ */
+static void kgsl_iommu_lock_rb_in_tlb(struct kgsl_mmu *mmu)
+{
+	struct kgsl_device *device = mmu->device;
+	struct adreno_device *adreno_dev = ADRENO_DEVICE(device);
+	struct adreno_ringbuffer *rb;
+	struct kgsl_iommu *iommu = mmu->priv;
+	unsigned int num_tlb_entries;
+	unsigned int tlblkcr = 0;
+	unsigned int v2pxx = 0;
+	unsigned int vaddr = 0;
+	int i, j, k, l;
+
+	if (!iommu->sync_lock_initialized)
+		return;
+
+	rb = &adreno_dev->ringbuffer;
+	num_tlb_entries = rb->buffer_desc.size / PAGE_SIZE;
+
+	for (i = 0; i < iommu->unit_count; i++) {
+		struct kgsl_iommu_unit *iommu_unit = &iommu->iommu_units[i];
+		for (j = 0; j < iommu_unit->dev_count; j++) {
+			tlblkcr = 0;
+			if (cpu_is_msm8960())
+				tlblkcr |= ((num_tlb_entries &
+					KGSL_IOMMU_TLBLKCR_FLOOR_MASK) <<
+					KGSL_IOMMU_TLBLKCR_FLOOR_SHIFT);
+			else
+				tlblkcr |= (((num_tlb_entries *
+					iommu_unit->dev_count) &
+					KGSL_IOMMU_TLBLKCR_FLOOR_MASK) <<
+					KGSL_IOMMU_TLBLKCR_FLOOR_SHIFT);
+			/* Do not invalidate locked entries on tlbiall flush */
+			tlblkcr	|= ((1 & KGSL_IOMMU_TLBLKCR_TLBIALLCFG_MASK)
+				<< KGSL_IOMMU_TLBLKCR_TLBIALLCFG_SHIFT);
+			tlblkcr	|= ((1 & KGSL_IOMMU_TLBLKCR_TLBIASIDCFG_MASK)
+				<< KGSL_IOMMU_TLBLKCR_TLBIASIDCFG_SHIFT);
+			tlblkcr	|= ((1 & KGSL_IOMMU_TLBLKCR_TLBIVAACFG_MASK)
+				<< KGSL_IOMMU_TLBLKCR_TLBIVAACFG_SHIFT);
+			/* Enable tlb locking */
+			tlblkcr |= ((1 & KGSL_IOMMU_TLBLKCR_LKE_MASK)
+				<< KGSL_IOMMU_TLBLKCR_LKE_SHIFT);
+			KGSL_IOMMU_SET_CTX_REG(iommu, iommu_unit,
+					iommu_unit->dev[j].ctx_id,
+					TLBLKCR, tlblkcr);
+		}
+		for (j = 0; j < iommu_unit->dev_count; j++) {
+			/* skip locking entries for private bank on 8960 */
+			if (cpu_is_msm8960() &&  KGSL_IOMMU_CONTEXT_PRIV == j)
+				continue;
+			/* Lock the ringbuffer virtual address into tlb */
+			vaddr = rb->buffer_desc.gpuaddr;
+			for (k = 0; k < num_tlb_entries; k++) {
+				v2pxx = 0;
+				v2pxx |= (((k + j * num_tlb_entries) &
+					KGSL_IOMMU_V2PXX_INDEX_MASK)
+					<< KGSL_IOMMU_V2PXX_INDEX_SHIFT);
+				v2pxx |= vaddr & (KGSL_IOMMU_V2PXX_VA_MASK <<
+						KGSL_IOMMU_V2PXX_VA_SHIFT);
+
+				KGSL_IOMMU_SET_CTX_REG(iommu, iommu_unit,
+						iommu_unit->dev[j].ctx_id,
+						V2PUR, v2pxx);
+				vaddr += PAGE_SIZE;
+				for (l = 0; l < iommu_unit->dev_count; l++) {
+					tlblkcr = KGSL_IOMMU_GET_CTX_REG(iommu,
+						iommu_unit,
+						iommu_unit->dev[l].ctx_id,
+						TLBLKCR);
+					mb();
+					tlblkcr &=
+					~(KGSL_IOMMU_TLBLKCR_VICTIM_MASK
+					<< KGSL_IOMMU_TLBLKCR_VICTIM_SHIFT);
+					tlblkcr |= (((k + 1 +
+					(j * num_tlb_entries)) &
+					KGSL_IOMMU_TLBLKCR_VICTIM_MASK) <<
+					KGSL_IOMMU_TLBLKCR_VICTIM_SHIFT);
+					KGSL_IOMMU_SET_CTX_REG(iommu,
+						iommu_unit,
+						iommu_unit->dev[l].ctx_id,
+						TLBLKCR, tlblkcr);
+				}
+			}
+		}
+		for (j = 0; j < iommu_unit->dev_count; j++) {
+			tlblkcr = KGSL_IOMMU_GET_CTX_REG(iommu, iommu_unit,
+						iommu_unit->dev[j].ctx_id,
+						TLBLKCR);
+			mb();
+			/* Disable tlb locking */
+			tlblkcr &= ~(KGSL_IOMMU_TLBLKCR_LKE_MASK
+				<< KGSL_IOMMU_TLBLKCR_LKE_SHIFT);
+			KGSL_IOMMU_SET_CTX_REG(iommu, iommu_unit,
+				iommu_unit->dev[j].ctx_id, TLBLKCR, tlblkcr);
+		}
+	}
+}
+
 static int kgsl_iommu_start(struct kgsl_mmu *mmu)
 {
 	int status;
@@ -1280,7 +1398,7 @@
 
 	/* We use the GPU MMU to control access to IOMMU registers on 8960 with
 	 * a225, hence we still keep the MMU active on 8960 */
-	if (cpu_is_msm8960()) {
+	if (cpu_is_msm8960() && KGSL_DEVICE_3D0 == mmu->device->id) {
 		struct kgsl_mh *mh = &(mmu->device->mh);
 		BUG_ON(iommu->iommu_units[0].reg_map.gpuaddr != 0 &&
 			mh->mpu_base > iommu->iommu_units[0].reg_map.gpuaddr);
@@ -1312,6 +1430,7 @@
 	 * changing pagetables we can use this lsb value of the pagetable w/o
 	 * having to read it again
 	 */
+	msm_iommu_lock();
 	for (i = 0; i < iommu->unit_count; i++) {
 		struct kgsl_iommu_unit *iommu_unit = &iommu->iommu_units[i];
 		for (j = 0; j < iommu_unit->dev_count; j++) {
@@ -1322,6 +1441,9 @@
 						TTBR0));
 		}
 	}
+	kgsl_iommu_lock_rb_in_tlb(mmu);
+	msm_iommu_unlock();
+
 
 	kgsl_iommu_disable_clk_on_ts(mmu, 0, false);
 	mmu->flags |= KGSL_FLAGS_STARTED;
@@ -1408,7 +1530,6 @@
 	 *
 	 *  call this with the global lock held
 	 */
-
 	if (mmu->flags & KGSL_FLAGS_STARTED) {
 		/* detach iommu attachment */
 		kgsl_detach_pagetable_iommu_domain(mmu);
@@ -1423,10 +1544,12 @@
 				for (j = 0; j < iommu_unit->dev_count; j++) {
 					if (iommu_unit->dev[j].fault) {
 						kgsl_iommu_enable_clk(mmu, j);
+						msm_iommu_lock();
 						KGSL_IOMMU_SET_CTX_REG(iommu,
 						iommu_unit,
 						iommu_unit->dev[j].ctx_id,
 						RESUME, 1);
+						msm_iommu_unlock();
 						iommu_unit->dev[j].fault = 0;
 					}
 				}
diff --git a/drivers/gpu/msm/kgsl_iommu.h b/drivers/gpu/msm/kgsl_iommu.h
index f539b07..25f0d45 100644
--- a/drivers/gpu/msm/kgsl_iommu.h
+++ b/drivers/gpu/msm/kgsl_iommu.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -19,6 +19,26 @@
 #define KGSL_IOMMU_CTX_OFFSET_V2	0x8000
 #define KGSL_IOMMU_CTX_SHIFT		12
 
+/* TLBLKCR feilds */
+#define KGSL_IOMMU_TLBLKCR_LKE_MASK		0x00000001
+#define KGSL_IOMMU_TLBLKCR_LKE_SHIFT		0
+#define KGSL_IOMMU_TLBLKCR_TLBIALLCFG_MASK	0x00000001
+#define KGSL_IOMMU_TLBLKCR_TLBIALLCFG_SHIFT	1
+#define KGSL_IOMMU_TLBLKCR_TLBIASIDCFG_MASK	0x00000001
+#define KGSL_IOMMU_TLBLKCR_TLBIASIDCFG_SHIFT	2
+#define KGSL_IOMMU_TLBLKCR_TLBIVAACFG_MASK	0x00000001
+#define KGSL_IOMMU_TLBLKCR_TLBIVAACFG_SHIFT	3
+#define KGSL_IOMMU_TLBLKCR_FLOOR_MASK		0x000000FF
+#define KGSL_IOMMU_TLBLKCR_FLOOR_SHIFT		8
+#define KGSL_IOMMU_TLBLKCR_VICTIM_MASK		0x000000FF
+#define KGSL_IOMMU_TLBLKCR_VICTIM_SHIFT		16
+
+/* V2PXX feilds */
+#define KGSL_IOMMU_V2PXX_INDEX_MASK		0x000000FF
+#define KGSL_IOMMU_V2PXX_INDEX_SHIFT		0
+#define KGSL_IOMMU_V2PXX_VA_MASK		0x000FFFFF
+#define KGSL_IOMMU_V2PXX_VA_SHIFT		12
+
 enum kgsl_iommu_reg_map {
 	KGSL_IOMMU_GLOBAL_BASE = 0,
 	KGSL_IOMMU_CTX_TTBR0,
@@ -26,6 +46,8 @@
 	KGSL_IOMMU_CTX_FSR,
 	KGSL_IOMMU_CTX_TLBIALL,
 	KGSL_IOMMU_CTX_RESUME,
+	KGSL_IOMMU_CTX_TLBLKCR,
+	KGSL_IOMMU_CTX_V2PUR,
 	KGSL_IOMMU_REG_MAX
 };
 
diff --git a/drivers/hwmon/qpnp-adc-current.c b/drivers/hwmon/qpnp-adc-current.c
index c28c61d..11f351c 100644
--- a/drivers/hwmon/qpnp-adc-current.c
+++ b/drivers/hwmon/qpnp-adc-current.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -537,6 +537,7 @@
 
 	return rc;
 }
+EXPORT_SYMBOL(qpnp_iadc_get_rsense);
 
 int32_t qpnp_check_pmic_temp(void)
 {
diff --git a/drivers/iommu/msm_iommu-v2.c b/drivers/iommu/msm_iommu-v2.c
index 79bd15c..687269e 100644
--- a/drivers/iommu/msm_iommu-v2.c
+++ b/drivers/iommu/msm_iommu-v2.c
@@ -251,10 +251,8 @@
 /*
  * May only be called for non-secure iommus
  */
-static void __program_iommu(void __iomem *base,
-			    struct msm_iommu_bfb_settings *bfb_settings)
+static void __program_iommu(void __iomem *base)
 {
-	int i;
 	__reset_iommu(base);
 
 	SET_CR0_SMCFCFG(base, 1);
@@ -266,12 +264,19 @@
 	SET_CR0_GFRE(base, 1);
 	SET_CR0_CLIENTPD(base, 0);
 
+	mb(); /* Make sure writes complete before returning */
+}
+
+void program_iommu_bfb_settings(void __iomem *base,
+			const struct msm_iommu_bfb_settings *bfb_settings)
+{
+	unsigned int i;
 	if (bfb_settings)
 		for (i = 0; i < bfb_settings->length; i++)
 			SET_GLOBAL_REG(base, bfb_settings->regs[i],
 					     bfb_settings->data[i]);
 
-	mb();	/* Make sure writes complete before returning */
+	mb(); /* Make sure writes complete before returning */
 }
 
 static void __reset_context(void __iomem *base, int ctx)
@@ -567,8 +572,7 @@
 
 	if (!msm_iommu_ctx_attached(dev->parent)) {
 		if (!is_secure) {
-			__program_iommu(iommu_drvdata->base,
-				iommu_drvdata->bfb_settings);
+			__program_iommu(iommu_drvdata->base);
 		} else {
 			ret = msm_iommu_sec_program_iommu(
 				iommu_drvdata->sec_id);
@@ -578,6 +582,8 @@
 				goto fail;
 			}
 		}
+		program_iommu_bfb_settings(iommu_drvdata->base,
+					   iommu_drvdata->bfb_settings);
 	}
 
 	__program_context(iommu_drvdata, ctx_drvdata, __pa(priv->pt.fl_table),
diff --git a/drivers/iommu/msm_iommu_sec.c b/drivers/iommu/msm_iommu_sec.c
index a6483b9..490fac8 100644
--- a/drivers/iommu/msm_iommu_sec.c
+++ b/drivers/iommu/msm_iommu_sec.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012 Linux Foundation. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -362,6 +362,11 @@
 	}
 
 	ret = msm_iommu_sec_program_iommu(iommu_drvdata->sec_id);
+
+	/* bfb settings are always programmed by HLOS */
+	program_iommu_bfb_settings(iommu_drvdata->base,
+				   iommu_drvdata->bfb_settings);
+
 	__disable_clocks(iommu_drvdata);
 	if (ret) {
 		regulator_disable(iommu_drvdata->gdsc);
diff --git a/drivers/leds/leds-qpnp.c b/drivers/leds/leds-qpnp.c
index e7d514e..dc0f7a1 100644
--- a/drivers/leds/leds-qpnp.c
+++ b/drivers/leds/leds-qpnp.c
@@ -1,5 +1,5 @@
 
-/* Copyright (c) 2012, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -703,7 +703,8 @@
 	if (led->wled_cfg->cs_out_en) {
 		rc = qpnp_led_masked_write(led, WLED_CURR_SINK_REG(led->base),
 			WLED_CURR_SINK_MASK,
-			(led->wled_cfg->num_strings << WLED_CURR_SINK_SHFT));
+			(((1 << led->wled_cfg->num_strings) - 1)
+			<< WLED_CURR_SINK_SHFT));
 		if (rc) {
 			dev_err(&led->spmi_dev->dev,
 				"WLED curr sink reg write failed(%d)\n", rc);
diff --git a/drivers/media/video/msm_vidc/msm_vidc_common.c b/drivers/media/video/msm_vidc/msm_vidc_common.c
index 955f4ca..78015e4 100644
--- a/drivers/media/video/msm_vidc/msm_vidc_common.c
+++ b/drivers/media/video/msm_vidc/msm_vidc_common.c
@@ -717,7 +717,8 @@
 	if (vb) {
 		vb->v4l2_planes[0].bytesused = fill_buf_done->filled_len1;
 		if (!(fill_buf_done->flags1 &
-			HAL_BUFFERFLAG_TIMESTAMPINVALID)) {
+			HAL_BUFFERFLAG_TIMESTAMPINVALID) &&
+			fill_buf_done->filled_len1) {
 			int64_t time_usec = fill_buf_done->timestamp_hi;
 			time_usec = (time_usec << 32) |
 				fill_buf_done->timestamp_lo;
@@ -2100,7 +2101,7 @@
 	op_flush = flags & V4L2_QCOM_CMD_FLUSH_CAPTURE;
 
 	if (ip_flush && !op_flush) {
-		dprintk(VIDC_WARN, "Input only flush not supported\n");
+		dprintk(VIDC_INFO, "Input only flush not supported\n");
 		return 0;
 	}
 	if (inst->state == MSM_VIDC_CORE_INVALID ||
diff --git a/drivers/misc/qseecom.c b/drivers/misc/qseecom.c
index 3d3563a..057e4e1 100644
--- a/drivers/misc/qseecom.c
+++ b/drivers/misc/qseecom.c
@@ -1771,16 +1771,25 @@
 
 int qseecom_set_bandwidth(struct qseecom_handle *handle, bool high)
 {
+	int ret = 0;
 	if ((handle == NULL) || (handle->dev == NULL)) {
 		pr_err("No valid kernel client\n");
 		return -EINVAL;
 	}
-	if (high)
-		return qsee_vote_for_clock(handle->dev, CLK_DFAB);
-	else {
+	if (high) {
+		ret = qsee_vote_for_clock(handle->dev, CLK_DFAB);
+		if (ret)
+			pr_err("Failed to vote for DFAB clock%d\n", ret);
+		ret = qsee_vote_for_clock(handle->dev, CLK_SFPB);
+		if (ret) {
+			pr_err("Failed to vote for SFPB clock%d\n", ret);
+			qsee_disable_clock_vote(handle->dev, CLK_DFAB);
+		}
+	} else {
 		qsee_disable_clock_vote(handle->dev, CLK_DFAB);
-		return 0;
+		qsee_disable_clock_vote(handle->dev, CLK_SFPB);
 	}
+	return ret;
 }
 EXPORT_SYMBOL(qseecom_set_bandwidth);
 
diff --git a/drivers/misc/tspp.c b/drivers/misc/tspp.c
index 563a013..4e504da5 100644
--- a/drivers/misc/tspp.c
+++ b/drivers/misc/tspp.c
@@ -41,6 +41,8 @@
 #include <mach/dma.h>
 #include <mach/msm_tspp.h>
 #include <linux/debugfs.h>
+#include <linux/of.h>
+#include <linux/of_gpio.h>
 
 /*
  * General defines
@@ -647,45 +649,19 @@
 }
 
 /*** GPIO functions ***/
-static void tspp_gpios_free(const struct msm_gpio *table, int size)
-{
-	int i;
-	const struct msm_gpio *g;
-	for (i = size-1; i >= 0; i--) {
-		g = table + i;
-		gpio_free(GPIO_PIN(g->gpio_cfg));
-	}
-}
-
-static int tspp_gpios_request(const struct msm_gpio *table, int size)
-{
-	int rc;
-	int i;
-	const struct msm_gpio *g;
-	for (i = 0; i < size; i++) {
-		g = table + i;
-		rc = gpio_request(GPIO_PIN(g->gpio_cfg), g->label);
-		if (rc) {
-			pr_err("tspp: gpio_request(%d) <%s> failed: %d\n",
-			       GPIO_PIN(g->gpio_cfg), g->label ?: "?", rc);
-			goto err;
-		}
-	}
-	return 0;
-err:
-	tspp_gpios_free(table, i);
-	return rc;
-}
-
 static int tspp_gpios_disable(const struct msm_gpio *table, int size)
 {
 	int rc = 0;
 	int i;
 	const struct msm_gpio *g;
+
 	for (i = size-1; i >= 0; i--) {
 		int tmp;
 		g = table + i;
-		tmp = gpio_tlmm_config(g->gpio_cfg, GPIO_CFG_DISABLE);
+
+		tmp = gpio_tlmm_config(GPIO_CFG(GPIO_PIN(g->gpio_cfg),
+			0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
+			GPIO_CFG_DISABLE);
 		if (tmp) {
 			pr_err("tspp_gpios_disable(0x%08x, GPIO_CFG_DISABLE) <%s> failed: %d\n",
 			       g->gpio_cfg, g->label ?: "?", rc);
@@ -704,8 +680,9 @@
 static int tspp_gpios_enable(const struct msm_gpio *table, int size)
 {
 	int rc;
-	int i;
+	int i, j;
 	const struct msm_gpio *g;
+
 	for (i = 0; i < size; i++) {
 		g = table + i;
 		rc = gpio_tlmm_config(g->gpio_cfg, GPIO_CFG_ENABLE);
@@ -721,39 +698,26 @@
 	}
 	return 0;
 err:
-	tspp_gpios_disable(table, i);
-	return rc;
-}
+	for (j = 0; j < i; j++)
+		tspp_gpios_disable(table, j);
 
-static int tspp_gpios_request_enable(const struct msm_gpio *table, int size)
-{
-	int rc = tspp_gpios_request(table, size);
-	if (rc)
-		return rc;
-	rc = tspp_gpios_enable(table, size);
-	if (rc)
-		tspp_gpios_free(table, size);
 	return rc;
 }
 
-static void tspp_gpios_disable_free(const struct msm_gpio *table, int size)
-{
-	tspp_gpios_disable(table, size);
-	tspp_gpios_free(table, size);
-}
-
 static int tspp_start_gpios(struct tspp_device *device)
 {
 	struct msm_tspp_platform_data *pdata =
 		device->pdev->dev.platform_data;
-	return tspp_gpios_request_enable(pdata->gpios, pdata->num_gpios);
+
+	return tspp_gpios_enable(pdata->gpios, pdata->num_gpios);
 }
 
 static void tspp_stop_gpios(struct tspp_device *device)
 {
 	struct msm_tspp_platform_data *pdata =
 		device->pdev->dev.platform_data;
-	tspp_gpios_disable_free(pdata->gpios, pdata->num_gpios);
+
+	tspp_gpios_disable(pdata->gpios, pdata->num_gpios);
 }
 
 /*** Clock functions ***/
@@ -1427,9 +1391,10 @@
 	event = &channel->event;
 
 	/* start the clocks if needed */
-	tspp_clock_start(pdev);
-	if (tspp_channels_in_use(pdev) == 0)
+	if (tspp_channels_in_use(pdev) == 0) {
+		tspp_clock_start(pdev);
 		wake_lock(&pdev->wake_lock);
+	}
 
 	/* mark it as used */
 	channel->used = 1;
@@ -1604,9 +1569,10 @@
 	channel->locked = NULL;
 	channel->used = 0;
 
-	if (tspp_channels_in_use(pdev) == 0)
+	if (tspp_channels_in_use(pdev) == 0) {
 		wake_unlock(&pdev->wake_lock);
-	tspp_clock_stop(pdev);
+		tspp_clock_stop(pdev);
+	}
 
 	return 0;
 }
@@ -2554,6 +2520,137 @@
 	}
 }
 
+/* copy device-tree data to platfrom data struct */
+static __devinit struct msm_tspp_platform_data *
+msm_tspp_dt_to_pdata(struct platform_device *pdev)
+{
+	struct device_node *node = pdev->dev.of_node;
+	struct msm_tspp_platform_data *data;
+	struct msm_gpio *gpios;
+	int i, rc;
+	int gpio;
+	u32 gpio_func;
+
+	/* Note: memory allocated by devm_kzalloc is freed automatically */
+	data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
+	if (!data) {
+		pr_err("tspp: Unable to allocate platform data\n");
+		return NULL;
+	}
+	rc = of_property_read_string(node, "qcom,tsif-pclk", &data->tsif_pclk);
+	if (rc) {
+		pr_err("tspp: Could not find tsif-pclk property, err = %d\n",
+			rc);
+		return NULL;
+	}
+	rc = of_property_read_string(node, "qcom,tsif-ref-clk",
+			&data->tsif_ref_clk);
+	if (rc) {
+		pr_err("tspp: Could not find tsif-ref-clk property, err = %d\n",
+			rc);
+		return NULL;
+	}
+
+	data->num_gpios = of_gpio_count(node);
+	if (data->num_gpios == 0) {
+		pr_err("tspp: Could not find GPIO definitions\n");
+		return NULL;
+	}
+	gpios = devm_kzalloc(&pdev->dev,
+			(data->num_gpios * sizeof(struct msm_gpio)),
+			GFP_KERNEL);
+	if (!gpios) {
+		pr_err("tspp: Unable to allocate memory for GPIOs table\n");
+		return NULL;
+	}
+	/* Assuming GPIO FUNC property is the same for all GPIOs */
+	if (of_property_read_u32(node, "qcom,gpios-func", &gpio_func)) {
+		pr_err("tspp: Could not find gpios-func property\n");
+		return NULL;
+	}
+	for (i = 0; i < data->num_gpios; i++) {
+		gpio = of_get_gpio(node, i);
+		gpios[i].gpio_cfg = GPIO_CFG(gpio, gpio_func,
+						GPIO_CFG_INPUT,
+						GPIO_CFG_PULL_DOWN,
+						GPIO_CFG_2MA);
+		rc = of_property_read_string_index(node, "qcom,gpio-names",
+						i, &gpios[i].label);
+		if (rc)
+			pr_warn("tspp: Could not find gpio-names property\n");
+	}
+
+	data->gpios = gpios;
+
+	return data;
+}
+
+static int msm_tspp_map_irqs(struct platform_device *pdev,
+				struct tspp_device *device)
+{
+	int rc;
+	int i;
+
+	/* get IRQ numbers from platform information */
+
+	/* map TSPP IRQ */
+	rc = platform_get_irq_byname(pdev, "TSIF_TSPP_IRQ");
+	if (rc > 0) {
+		device->tspp_irq = rc;
+		rc = request_irq(device->tspp_irq, tspp_isr, IRQF_SHARED,
+				 dev_name(&pdev->dev), device);
+		if (rc) {
+			dev_err(&pdev->dev,
+				"failed to request TSPP IRQ %d : %d",
+				device->tspp_irq, rc);
+			device->tspp_irq = 0;
+			return -EINVAL;
+		}
+	} else {
+		dev_err(&pdev->dev, "failed to get TSPP IRQ");
+		return -EINVAL;
+	}
+
+	/* map TSIF IRQs */
+	rc = platform_get_irq_byname(pdev, "TSIF0_IRQ");
+	if (rc > 0) {
+		device->tsif[0].tsif_irq = rc;
+	} else {
+		dev_err(&pdev->dev, "failed to get TSIF0 IRQ");
+		return -EINVAL;
+	}
+
+	rc = platform_get_irq_byname(pdev, "TSIF1_IRQ");
+	if (rc > 0) {
+		device->tsif[1].tsif_irq = rc;
+	} else {
+		dev_err(&pdev->dev, "failed to get TSIF1 IRQ");
+		return -EINVAL;
+	}
+
+	for (i = 0; i < TSPP_TSIF_INSTANCES; i++) {
+		rc = request_irq(device->tsif[i].tsif_irq,
+				tsif_isr, IRQF_SHARED,
+				dev_name(&pdev->dev), &device->tsif[i]);
+		if (rc) {
+			dev_warn(&pdev->dev, "failed to request TSIF%d IRQ: %d",
+				i, rc);
+			device->tsif[i].tsif_irq = 0;
+		}
+	}
+
+	/* map BAM IRQ */
+	rc = platform_get_irq_byname(pdev, "TSIF_BAM_IRQ");
+	if (rc > 0) {
+		device->bam_irq = rc;
+	} else {
+		dev_err(&pdev->dev, "failed to get TSPP BAM IRQ");
+		return -EINVAL;
+	}
+
+	return 0;
+}
+
 static int __devinit msm_tspp_probe(struct platform_device *pdev)
 {
 	int rc = -ENODEV;
@@ -2567,8 +2664,20 @@
 	struct resource *mem_bam;
 	struct tspp_channel *channel;
 
-	/* must have platform data */
-	data = pdev->dev.platform_data;
+	if (pdev->dev.of_node) {
+		/* get information from device tree */
+		data = msm_tspp_dt_to_pdata(pdev);
+		/* get device ID */
+		rc = of_property_read_u32(pdev->dev.of_node,
+					"cell-index", &pdev->id);
+		if (rc)
+			pdev->id = -1;
+
+		pdev->dev.platform_data = data;
+	} else {
+		/* must have platform data */
+		data = pdev->dev.platform_data;
+	}
 	if (!data) {
 		pr_err("tspp: Platform data not available");
 		rc = -EINVAL;
@@ -2617,7 +2726,8 @@
 	}
 
 	/* map I/O memory */
-	mem_tsif0 = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	mem_tsif0 = platform_get_resource_byname(pdev,
+				IORESOURCE_MEM, "MSM_TSIF0_PHYS");
 	if (!mem_tsif0) {
 		pr_err("tspp: Missing tsif0 MEM resource");
 		rc = -ENXIO;
@@ -2630,7 +2740,8 @@
 		goto err_map_tsif0;
 	}
 
-	mem_tsif1 = platform_get_resource(pdev, IORESOURCE_MEM, 1);
+	mem_tsif1 = platform_get_resource_byname(pdev,
+				IORESOURCE_MEM, "MSM_TSIF1_PHYS");
 	if (!mem_tsif1) {
 		dev_err(&pdev->dev, "Missing tsif1 MEM resource");
 		rc = -ENXIO;
@@ -2643,7 +2754,8 @@
 		goto err_map_tsif1;
 	}
 
-	mem_tspp = platform_get_resource(pdev, IORESOURCE_MEM, 2);
+	mem_tspp = platform_get_resource_byname(pdev,
+				IORESOURCE_MEM, "MSM_TSPP_PHYS");
 	if (!mem_tspp) {
 		dev_err(&pdev->dev, "Missing MEM resource");
 		rc = -ENXIO;
@@ -2655,7 +2767,8 @@
 		goto err_map_dev;
 	}
 
-	mem_bam = platform_get_resource(pdev, IORESOURCE_MEM, 3);
+	mem_bam = platform_get_resource_byname(pdev,
+				IORESOURCE_MEM, "MSM_TSPP_BAM_PHYS");
 	if (!mem_bam) {
 		pr_err("tspp: Missing bam MEM resource");
 		rc = -ENXIO;
@@ -2670,39 +2783,8 @@
 		goto err_map_bam;
 	}
 
-	/* map TSPP IRQ */
-	rc = platform_get_irq(pdev, 0);
-	if (rc > 0) {
-		device->tspp_irq = rc;
-		rc = request_irq(device->tspp_irq, tspp_isr, IRQF_SHARED,
-				 dev_name(&pdev->dev), device);
-		if (rc) {
-			dev_err(&pdev->dev, "failed to request IRQ %d : %d",
-				device->tspp_irq, rc);
-			goto err_irq;
-		}
-	} else {
-		dev_err(&pdev->dev, "failed to get tspp IRQ");
+	if (msm_tspp_map_irqs(pdev, device))
 		goto err_irq;
-	}
-
-	/* map TSIF IRQs */
-	device->tsif[0].tsif_irq = TSIF1_IRQ;
-	device->tsif[1].tsif_irq = TSIF2_IRQ;
-
-	for (i = 0; i < TSPP_TSIF_INSTANCES; i++) {
-		rc = request_irq(device->tsif[i].tsif_irq,
-				tsif_isr, IRQF_SHARED,
-				dev_name(&pdev->dev), &device->tsif[i]);
-		if (rc) {
-			dev_warn(&pdev->dev, "failed to request TSIF%d IRQ: %d",
-				i, rc);
-			device->tsif[i].tsif_irq = 0;
-		}
-	}
-
-	/* BAM IRQ */
-	device->bam_irq = TSIF_BAM_IRQ;
 
 	/* GPIOs */
 	rc = tspp_start_gpios(device);
@@ -2737,17 +2819,17 @@
 	device->bam_props.irq = device->bam_irq;
 	device->bam_props.manage = SPS_BAM_MGR_LOCAL;
 
+	if (tspp_clock_start(device) != 0) {
+		dev_err(&pdev->dev, "Can't start clocks");
+		goto err_clock;
+	}
+
 	if (sps_register_bam_device(&device->bam_props,
 		&device->bam_handle) != 0) {
 		pr_err("tspp: failed to register bam");
 		goto err_bam;
 	}
 
-	if (tspp_clock_start(device) != 0) {
-		dev_err(&pdev->dev, "Can't start clocks");
-		goto err_clock;
-	}
-
 	spin_lock_init(&device->spinlock);
 	tasklet_init(&device->tlet, tspp_sps_complete_tlet,
 			(unsigned long)device);
@@ -2756,7 +2838,11 @@
 	tspp_global_reset(device);
 
 	version = readl_relaxed(device->base + TSPP_VERSION);
-	if (version != 1)
+	/*
+	 * TSPP version can be bits [7:0] or alternatively,
+	 * TSPP major version is bits [31:28].
+	 */
+	if ((version != 0x1) && (((version >> 28) & 0xF) != 0x1))
 		pr_warn("tspp: unrecognized hw version=%i", version);
 
 	/* initialize the channels */
@@ -2776,21 +2862,30 @@
 	return 0;
 
 err_channel:
-	/* uninitialize channels */
+	/* un-initialize channels */
 	for (j = 0; j < i; j++) {
 		channel = &(device->channels[i]);
 		device_destroy(tspp_class, channel->cdev.dev);
 		cdev_del(&channel->cdev);
 	}
-err_clock:
+
 	sps_deregister_bam_device(device->bam_handle);
+err_clock:
 err_bam:
 	tspp_debugfs_exit(device);
 	for (i = 0; i < TSPP_TSIF_INSTANCES; i++)
 		tsif_debugfs_exit(&device->tsif[i]);
+
+	tspp_stop_gpios(device);
 err_gpio:
 err_irq:
-	tspp_stop_gpios(device);
+	for (i = 0; i < TSPP_TSIF_INSTANCES; i++) {
+		if (device->tsif[i].tsif_irq)
+			free_irq(device->tsif[i].tsif_irq,  &device->tsif[i]);
+	}
+	if (device->tspp_irq)
+		free_irq(device->tspp_irq, device);
+
 	iounmap(device->bam_props.virt_addr);
 err_map_bam:
 err_res_bam:
@@ -2830,7 +2925,10 @@
 		cdev_del(&channel->cdev);
 	}
 
+	/* de-registering BAM device requires clocks */
+	tspp_clock_start(device);
 	sps_deregister_bam_device(device->bam_handle);
+	tspp_clock_stop(device);
 
 	for (i = 0; i < TSPP_TSIF_INSTANCES; i++) {
 		tsif_debugfs_exit(&device->tsif[i]);
@@ -2879,12 +2977,18 @@
 	.runtime_resume = tspp_runtime_resume,
 };
 
+static struct of_device_id msm_match_table[] = {
+	{.compatible = "qcom,msm_tspp"},
+	{}
+};
+
 static struct platform_driver msm_tspp_driver = {
 	.probe          = msm_tspp_probe,
 	.remove         = __exit_p(msm_tspp_remove),
 	.driver         = {
 		.name   = "msm_tspp",
 		.pm     = &tspp_dev_pm_ops,
+		.of_match_table = msm_match_table,
 	},
 };
 
diff --git a/drivers/mmc/host/msm_sdcc.c b/drivers/mmc/host/msm_sdcc.c
index 1b2b33a..2fedc97 100644
--- a/drivers/mmc/host/msm_sdcc.c
+++ b/drivers/mmc/host/msm_sdcc.c
@@ -1965,7 +1965,7 @@
 			msmsdcc_do_cmdirq(host, status);
 		}
 
-		if (host->curr.data) {
+		if (data) {
 			/* Check for data errors */
 			if (status & (MCI_DATACRCFAIL|MCI_DATATIMEOUT|
 				      MCI_TXUNDERRUN|MCI_RXOVERRUN)) {
diff --git a/drivers/power/pm8921-charger.c b/drivers/power/pm8921-charger.c
index 5485e27..f9aff40 100644
--- a/drivers/power/pm8921-charger.c
+++ b/drivers/power/pm8921-charger.c
@@ -1404,6 +1404,8 @@
 				  enum power_supply_property psp,
 				  union power_supply_propval *val)
 {
+	int type;
+
 	/* Check if called before init */
 	if (!the_chip)
 		return -EINVAL;
@@ -1423,10 +1425,11 @@
 			return 0;
 		}
 
-		/* USB with max current greater than 500 mA connected */
-		if (usb_target_ma > USB_WALL_THRESHOLD_MA)
+		type = the_chip->usb_psy.type;
+		if (type == POWER_SUPPLY_TYPE_USB_DCP ||
+			type == POWER_SUPPLY_TYPE_USB_ACA ||
+			type == POWER_SUPPLY_TYPE_USB_CDP)
 			val->intval = is_usb_chg_plugged_in(the_chip);
-			return 0;
 
 		break;
 	default:
@@ -1521,11 +1524,9 @@
 	case POWER_SUPPLY_PROP_ONLINE:
 		val->intval = 0;
 
-		/* USB charging */
-		if (usb_target_ma < USB_WALL_THRESHOLD_MA)
+		if (the_chip->usb_psy.type == POWER_SUPPLY_TYPE_USB)
 			val->intval = is_usb_chg_plugged_in(the_chip);
-		else
-		    return 0;
+
 		break;
 
 	case POWER_SUPPLY_PROP_SCOPE:
@@ -2186,7 +2187,7 @@
 		return -EINVAL;
 	}
 
-	if (type < POWER_SUPPLY_TYPE_USB)
+	if (type < POWER_SUPPLY_TYPE_USB && type > POWER_SUPPLY_TYPE_BATTERY)
 		return -EINVAL;
 
 	the_chip->usb_psy.type = type;
@@ -4757,6 +4758,9 @@
 	platform_set_drvdata(pdev, chip);
 	the_chip = chip;
 
+	/* set initial state of the USB charger type to UNKNOWN */
+	power_supply_set_supply_type(&chip->usb_psy, POWER_SUPPLY_TYPE_UNKNOWN);
+
 	wake_lock_init(&chip->eoc_wake_lock, WAKE_LOCK_SUSPEND, "pm8921_eoc");
 	INIT_DELAYED_WORK(&chip->eoc_work, eoc_worker);
 	INIT_DELAYED_WORK(&chip->vin_collapse_check_work,
diff --git a/drivers/power/qpnp-bms.c b/drivers/power/qpnp-bms.c
index 14afae9..8002e9e 100644
--- a/drivers/power/qpnp-bms.c
+++ b/drivers/power/qpnp-bms.c
@@ -93,6 +93,7 @@
 	int		iavg_ua;
 	int		uuc_uah;
 	int		ocv_charge_uah;
+	int		delta_time_s;
 };
 
 struct raw_soc_params {
@@ -567,7 +568,7 @@
 	} else if (chip->prev_last_good_ocv_raw != raw->last_good_ocv_raw) {
 		convert_and_store_ocv(chip, raw);
 		/* forget the old cc value upon ocv */
-		chip->last_cc_uah = 0;
+		chip->last_cc_uah = INT_MIN;
 	} else {
 		raw->last_good_ocv_uv = chip->last_ocv_uv;
 	}
@@ -711,46 +712,18 @@
 }
 
 static void calculate_iavg(struct qpnp_bms_chip *chip, int cc_uah,
-				int *iavg_ua)
+				int *iavg_ua, int delta_time_s)
 {
-	int delta_cc_uah, delta_time_s, rc;
-	struct rtc_time tm;
-	struct rtc_device *rtc;
-	unsigned long now_tm_sec = 0;
+	int delta_cc_uah = 0;
 
-	rc = 0;
 	/* if anything fails report the previous iavg_ua */
 	*iavg_ua = chip->prev_iavg_ua;
 
-	rtc = rtc_class_open(CONFIG_RTC_HCTOSYS_DEVICE);
-	if (rtc == NULL) {
-		pr_err("%s: unable to open rtc device (%s)\n",
-			__FILE__, CONFIG_RTC_HCTOSYS_DEVICE);
-		goto out;
-	}
-
-	rc = rtc_read_time(rtc, &tm);
-	if (rc) {
-		pr_err("Error reading rtc device (%s) : %d\n",
-			CONFIG_RTC_HCTOSYS_DEVICE, rc);
-		goto out;
-	}
-
-	rc = rtc_valid_tm(&tm);
-	if (rc) {
-		pr_err("Invalid RTC time (%s): %d\n",
-			CONFIG_RTC_HCTOSYS_DEVICE, rc);
-		goto out;
-	}
-	rtc_tm_to_time(&tm, &now_tm_sec);
-
-	if (chip->tm_sec == 0) {
+	if (chip->last_cc_uah == INT_MIN) {
 		get_battery_current(chip, iavg_ua);
 		goto out;
 	}
 
-	delta_time_s = (now_tm_sec - chip->tm_sec);
-
 	/* use the previous iavg if called within 15 seconds */
 	if (delta_time_s < 15) {
 		*iavg_ua = chip->prev_iavg_ua;
@@ -761,19 +734,13 @@
 
 	*iavg_ua = div_s64((s64)delta_cc_uah * 3600, delta_time_s);
 
-	pr_debug("tm_sec = %ld, now_tm_sec = %ld delta_s = %d delta_cc = %d iavg_ua = %d\n",
-				chip->tm_sec, now_tm_sec,
-				delta_time_s, delta_cc_uah, (int)*iavg_ua);
-
 out:
+	pr_debug("delta_cc = %d iavg_ua = %d\n", delta_cc_uah, (int)*iavg_ua);
 	/* remember the iavg */
 	chip->prev_iavg_ua = *iavg_ua;
 
 	/* remember cc_uah */
 	chip->last_cc_uah = cc_uah;
-
-	/* remember this time */
-	chip->tm_sec = now_tm_sec;
 }
 
 static int calculate_termination_uuc(struct qpnp_bms_chip *chip,
@@ -825,6 +792,7 @@
 	return uuc_uah;
 }
 
+#define TIME_PER_PERCENT_UUC			60
 static int adjust_uuc(struct qpnp_bms_chip *chip,
 			struct soc_params *params,
 			int new_pc_unusable,
@@ -833,18 +801,23 @@
 {
 	int new_unusable_mv, new_iavg_ma;
 	int batt_temp_degc = batt_temp / 10;
+	int max_percent_change;
+
+	max_percent_change = max(params->delta_time_s
+				/ TIME_PER_PERCENT_UUC, 1);
 
 	if (chip->prev_pc_unusable == -EINVAL
-		|| abs(chip->prev_pc_unusable - new_pc_unusable) <= 1) {
+		|| abs(chip->prev_pc_unusable - new_pc_unusable)
+			<= max_percent_change) {
 		chip->prev_pc_unusable = new_pc_unusable;
 		return new_uuc_uah;
 	}
 
 	/* the uuc is trying to change more than 1% restrict it */
 	if (new_pc_unusable > chip->prev_pc_unusable)
-		chip->prev_pc_unusable++;
+		chip->prev_pc_unusable += max_percent_change;
 	else
-		chip->prev_pc_unusable--;
+		chip->prev_pc_unusable -= max_percent_change;
 
 	new_uuc_uah = (params->fcc_uah * chip->prev_pc_unusable) / 100;
 
@@ -974,6 +947,58 @@
 	params->ocv_charge_uah = (int)ocv_charge_uah;
 }
 
+static int get_current_time(unsigned long *now_tm_sec)
+{
+	struct rtc_time tm;
+	struct rtc_device *rtc;
+	int rc;
+
+	rtc = rtc_class_open(CONFIG_RTC_HCTOSYS_DEVICE);
+	if (rtc == NULL) {
+		pr_err("%s: unable to open rtc device (%s)\n",
+			__FILE__, CONFIG_RTC_HCTOSYS_DEVICE);
+		rc = -EINVAL;
+		goto close_time;
+	}
+
+	rc = rtc_read_time(rtc, &tm);
+	if (rc) {
+		pr_err("Error reading rtc device (%s) : %d\n",
+			CONFIG_RTC_HCTOSYS_DEVICE, rc);
+		goto close_time;
+	}
+
+	rc = rtc_valid_tm(&tm);
+	if (rc) {
+		pr_err("Invalid RTC time (%s): %d\n",
+			CONFIG_RTC_HCTOSYS_DEVICE, rc);
+		goto close_time;
+	}
+	rtc_tm_to_time(&tm, now_tm_sec);
+
+close_time:
+	rtc_class_close(rtc);
+	return rc;
+}
+
+static int calculate_delta_time(struct qpnp_bms_chip *chip, int *delta_time_s)
+{
+	unsigned long now_tm_sec = 0;
+
+	/* default to delta time = 0 if anything fails */
+	*delta_time_s = 0;
+
+	get_current_time(&now_tm_sec);
+
+	*delta_time_s = (now_tm_sec - chip->tm_sec);
+	pr_debug("tm_sec = %ld, now_tm_sec = %ld delta_s = %d\n",
+		chip->tm_sec, now_tm_sec, *delta_time_s);
+
+	/* remember this time */
+	chip->tm_sec = now_tm_sec;
+	return 0;
+}
+
 static void calculate_soc_params(struct qpnp_bms_chip *chip,
 						struct raw_soc_params *raw,
 						struct soc_params *params,
@@ -981,6 +1006,7 @@
 {
 	int soc_rbatt;
 
+	calculate_delta_time(chip, &params->delta_time_s);
 	params->fcc_uah = calculate_fcc(chip, batt_temp);
 	pr_debug("FCC = %uuAh batt_temp = %d\n", params->fcc_uah, batt_temp);
 
@@ -1004,7 +1030,8 @@
 		soc_rbatt = 0;
 	params->rbatt_mohm = get_rbatt(chip, soc_rbatt, batt_temp);
 
-	calculate_iavg(chip, params->cc_uah, &params->iavg_ua);
+	calculate_iavg(chip, params->cc_uah, &params->iavg_ua,
+						params->delta_time_s);
 
 	params->uuc_uah = calculate_unusable_charge_uah(chip, params,
 							batt_temp);
@@ -2026,6 +2053,7 @@
 	chip->calculated_soc = -EINVAL;
 	chip->last_soc = -EINVAL;
 	chip->last_soc_est = -EINVAL;
+	chip->last_cc_uah = INT_MIN;
 	chip->first_time_calc_soc = 1;
 	chip->first_time_calc_uuc = 1;
 }
@@ -2101,6 +2129,7 @@
 static int read_iadc_channel_select(struct qpnp_bms_chip *chip)
 {
 	u8 iadc_channel_select;
+	int32_t rds_rsense_nohm;
 	int rc;
 
 	rc = qpnp_read_wrapper(chip, &iadc_channel_select,
@@ -2111,10 +2140,17 @@
 	}
 
 	iadc_channel_select &= ADC_CH_SEL_MASK;
-	if (iadc_channel_select == INTERNAL_RSENSE) {
-		pr_debug("Internal rsense used\n");
-		if (chip->use_external_rsense) {
-			pr_debug("Changing rsense to external\n");
+	if (iadc_channel_select != EXTERNAL_RSENSE
+			&& iadc_channel_select != INTERNAL_RSENSE) {
+		pr_err("IADC1_BMS_IADC configured incorrectly. Selected channel = %d\n",
+						iadc_channel_select);
+		return -EINVAL;
+	}
+
+	if (chip->use_external_rsense) {
+		pr_debug("External rsense selected\n");
+		if (iadc_channel_select == INTERNAL_RSENSE) {
+			pr_debug("Internal rsense detected; Changing rsense to external\n");
 			rc = qpnp_masked_write_iadc(chip,
 					IADC1_BMS_ADC_CH_SEL_CTL,
 					ADC_CH_SEL_MASK,
@@ -2127,10 +2163,10 @@
 			}
 			reset_cc(chip);
 		}
-	} else if (iadc_channel_select == EXTERNAL_RSENSE) {
-		pr_debug("External rsense used\n");
-		if (!chip->use_external_rsense) {
-			pr_debug("Changing rsense to internal\n");
+	} else {
+		pr_debug("Internal rsense selected\n");
+		if (iadc_channel_select == EXTERNAL_RSENSE) {
+			pr_debug("External rsense detected; Changing rsense to internal\n");
 			rc = qpnp_masked_write_iadc(chip,
 					IADC1_BMS_ADC_CH_SEL_CTL,
 					ADC_CH_SEL_MASK,
@@ -2143,10 +2179,16 @@
 			}
 			reset_cc(chip);
 		}
-	} else {
-		pr_err("IADC1_BMS_IADC configured incorrectly. Selected channel = %d\n",
-							iadc_channel_select);
-		return -EINVAL;
+
+		rc = qpnp_iadc_get_rsense(&rds_rsense_nohm);
+		if (rc) {
+			pr_err("Unable to read RDS resistance value from IADC; rc = %d\n",
+								rc);
+			return rc;
+		}
+		chip->r_sense_mohm = rds_rsense_nohm/1000000;
+		pr_debug("rds_rsense = %d nOhm, saved as %d mOhm\n",
+					rds_rsense_nohm, chip->r_sense_mohm);
 	}
 	return 0;
 }
@@ -2252,10 +2294,9 @@
 	vbatt = 0;
 	get_battery_voltage(&vbatt);
 
-	pr_debug("OK battery_capacity_at_boot=%d vbatt = %d\n",
+	pr_info("probe success: soc =%d vbatt = %d ocv = %d r_sense_mohm = %u\n",
 				get_prop_bms_capacity(chip),
-				vbatt);
-	pr_info("probe success\n");
+				vbatt, chip->last_ocv_uv, chip->r_sense_mohm);
 	return 0;
 
 unregister_dc:
diff --git a/drivers/usb/gadget/f_qdss.c b/drivers/usb/gadget/f_qdss.c
index 085d0bd..70192de 100644
--- a/drivers/usb/gadget/f_qdss.c
+++ b/drivers/usb/gadget/f_qdss.c
@@ -408,6 +408,7 @@
 {
 	pr_debug("qdss_unbind\n");
 
+	clear_eps(f);
 	clear_desc(c->cdev->gadget, f);
 }
 
diff --git a/drivers/usb/host/xhci.c b/drivers/usb/host/xhci.c
index 2c26998..df41b4f 100644
--- a/drivers/usb/host/xhci.c
+++ b/drivers/usb/host/xhci.c
@@ -2464,7 +2464,7 @@
 	/* Wait for the configure endpoint command to complete */
 	timeleft = wait_for_completion_interruptible_timeout(
 			cmd_completion,
-			USB_CTRL_SET_TIMEOUT);
+			XHCI_CMD_DEFAULT_TIMEOUT);
 	if (timeleft <= 0) {
 		xhci_warn(xhci, "%s while waiting for %s command\n",
 				timeleft == 0 ? "Timeout" : "Signal",
@@ -3433,7 +3433,7 @@
 
 	/* XXX: how much time for xHC slot assignment? */
 	timeleft = wait_for_completion_interruptible_timeout(&xhci->addr_dev,
-			USB_CTRL_SET_TIMEOUT);
+			XHCI_CMD_DEFAULT_TIMEOUT);
 	if (timeleft <= 0) {
 		xhci_warn(xhci, "%s while waiting for a slot\n",
 				timeleft == 0 ? "Timeout" : "Signal");
@@ -3549,7 +3549,7 @@
 
 	/* ctrl tx can take up to 5 sec; XXX: need more time for xHC? */
 	timeleft = wait_for_completion_interruptible_timeout(&xhci->addr_dev,
-			USB_CTRL_SET_TIMEOUT);
+			XHCI_CMD_DEFAULT_TIMEOUT);
 	/* FIXME: From section 4.3.4: "Software shall be responsible for timing
 	 * the SetAddress() "recovery interval" required by USB and aborting the
 	 * command on a timeout.
diff --git a/drivers/usb/host/xhci.h b/drivers/usb/host/xhci.h
index 127b0e9..8f3651b 100644
--- a/drivers/usb/host/xhci.h
+++ b/drivers/usb/host/xhci.h
@@ -1248,6 +1248,9 @@
 	union xhci_trb		*last_trb;
 };
 
+/* xHCI command default timeout value */
+#define XHCI_CMD_DEFAULT_TIMEOUT	(5 * HZ)
+
 struct xhci_dequeue_state {
 	struct xhci_segment *new_deq_seg;
 	union xhci_trb *new_deq_ptr;
diff --git a/drivers/usb/otg/msm_otg.c b/drivers/usb/otg/msm_otg.c
index a4bb7b2..2439af0 100644
--- a/drivers/usb/otg/msm_otg.c
+++ b/drivers/usb/otg/msm_otg.c
@@ -1197,7 +1197,7 @@
 		motg->chg_type == USB_ACA_C_CHARGER))
 		charger_type = POWER_SUPPLY_TYPE_USB_ACA;
 	else
-		charger_type = POWER_SUPPLY_TYPE_BATTERY;
+		charger_type = POWER_SUPPLY_TYPE_UNKNOWN;
 
 	if (!psy) {
 		pr_err("No USB power supply registered!\n");
@@ -2276,6 +2276,11 @@
 	case USB_CHG_STATE_SECONDARY_DONE:
 		motg->chg_state = USB_CHG_STATE_DETECTED;
 	case USB_CHG_STATE_DETECTED:
+		/*
+		 * Notify the charger type to power supply
+		 * owner as soon as we determine the charger.
+		 */
+		msm_otg_notify_chg_type(motg);
 		msm_chg_block_off(motg);
 		msm_chg_enable_aca_det(motg);
 		/*
diff --git a/drivers/video/msm/mdp4_util.c b/drivers/video/msm/mdp4_util.c
index 4858073..38fc969 100644
--- a/drivers/video/msm/mdp4_util.c
+++ b/drivers/video/msm/mdp4_util.c
@@ -634,6 +634,7 @@
 #if defined(CONFIG_FB_MSM_WRITEBACK_MSM_PANEL)
 	if (isr & INTR_OVERLAY2_DONE) {
 		mdp4_stat.intr_overlay2++;
+		mdp_pipe_ctrl(MDP_OVERLAY2_BLOCK, MDP_BLOCK_POWER_OFF, FALSE);
 		/* disable DTV interrupt */
 		if (panel & MDP4_PANEL_WRITEBACK)
 			mdp4_overlay2_done_wfd(&dma_wb_data);
diff --git a/drivers/video/msm/mdss/mdss_mdp_hwio.h b/drivers/video/msm/mdss/mdss_mdp_hwio.h
index b6ac126..a7f0148 100644
--- a/drivers/video/msm/mdss/mdss_mdp_hwio.h
+++ b/drivers/video/msm/mdss/mdss_mdp_hwio.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -340,6 +340,7 @@
 #define MDSS_MDP_REG_DSPP_HIST_LUT_BASE			0x230
 #define MDSS_MDP_REG_DSPP_PA_BASE			0x238
 #define MDSS_MDP_REG_DSPP_GAMUT_BASE			0x2DC
+#define MDSS_MDP_REG_DSPP_GC_BASE			0x2B0
 
 enum mdss_mpd_intf_index {
 	MDSS_MDP_NO_INTF,
diff --git a/drivers/video/msm/mdss/mdss_mdp_pp.c b/drivers/video/msm/mdss/mdss_mdp_pp.c
index 1482935..7fd6a58 100644
--- a/drivers/video/msm/mdss/mdss_mdp_pp.c
+++ b/drivers/video/msm/mdss/mdss_mdp_pp.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -131,6 +131,7 @@
 	u32 enhist_sts;
 	u32 dither_sts;
 	u32 gamut_sts;
+	u32 pgc_sts;
 };
 
 #define PP_FLAGS_DIRTY_PA	0x1
@@ -141,6 +142,7 @@
 #define PP_FLAGS_DIRTY_DITHER	0x20
 #define PP_FLAGS_DIRTY_GAMUT	0x40
 #define PP_FLAGS_DIRTY_HIST_COL	0x80
+#define PP_FLAGS_DIRTY_PGC	0x100
 
 #define PP_STS_ENABLE	0x1
 #define PP_STS_GAMUT_FIRST	0x2
@@ -160,6 +162,7 @@
 	struct mdp_pa_cfg_data pa_disp_cfg[MDSS_BLOCK_DISP_NUM];
 	struct mdp_pcc_cfg_data pcc_disp_cfg[MDSS_BLOCK_DISP_NUM];
 	struct mdp_igc_lut_data igc_disp_cfg[MDSS_BLOCK_DISP_NUM];
+	struct mdp_pgc_lut_data argc_disp_cfg[MDSS_BLOCK_DISP_NUM];
 	struct mdp_pgc_lut_data pgc_disp_cfg[MDSS_BLOCK_DISP_NUM];
 	struct mdp_hist_lut_data enhist_disp_cfg[MDSS_BLOCK_DISP_NUM];
 	struct mdp_dither_cfg_data dither_disp_cfg[MDSS_BLOCK_DISP_NUM];
@@ -287,6 +290,7 @@
 	struct mdp_pgc_lut_data *pgc_config;
 	struct pp_sts_type *pp_sts;
 	dspp_num = mixer->num;
+
 	/* no corresponding dspp */
 	if ((mixer->type != MDSS_MDP_MIXER_TYPE_INTF) ||
 		(dspp_num >= MDSS_MDP_MAX_DSPP))
@@ -299,7 +303,7 @@
 	pp_sts = &mdss_pp_res->pp_dspp_sts[dspp_num];
 	/* GC_LUT is in layer mixer */
 	if (flags & PP_FLAGS_DIRTY_ARGC) {
-		pgc_config = &mdss_pp_res->pgc_disp_cfg[disp_num];
+		pgc_config = &mdss_pp_res->argc_disp_cfg[disp_num];
 		if (pgc_config->flags & MDP_PP_OPS_WRITE) {
 			offset = MDSS_MDP_REG_LM_OFFSET(disp_num) +
 				MDSS_MDP_REG_LM_GC_LUT_BASE;
@@ -378,10 +382,12 @@
 	struct mdp_hist_lut_data *enhist_cfg;
 	struct mdp_dither_cfg_data *dither_cfg;
 	struct pp_hist_col_info *hist_info;
+	struct mdp_pgc_lut_data *pgc_config;
 	struct pp_sts_type *pp_sts;
 	u32 data, tbl_idx, col_state;
 	unsigned long flag;
 	int i;
+
 	dspp_num = mixer->num;
 	/* no corresponding dspp */
 	if ((mixer->type != MDSS_MDP_MIXER_TYPE_INTF) ||
@@ -533,6 +539,20 @@
 			opmode |= (1 << 24); /* GAMUT_ORDER */
 	}
 
+	if (flags & PP_FLAGS_DIRTY_PGC) {
+		pgc_config = &mdss_pp_res->pgc_disp_cfg[disp_num];
+		if (pgc_config->flags & MDP_PP_OPS_WRITE) {
+			offset = base + MDSS_MDP_REG_DSPP_GC_BASE;
+			pp_update_argc_lut(offset, pgc_config);
+		}
+		if (pgc_config->flags & MDP_PP_OPS_DISABLE)
+			pp_sts->pgc_sts &= ~PP_STS_ENABLE;
+		else if (pgc_config->flags & MDP_PP_OPS_ENABLE)
+			pp_sts->pgc_sts |= PP_STS_ENABLE;
+	}
+	if (pp_sts->pgc_sts & PP_STS_ENABLE)
+		opmode |= (1 << 22);
+
 	MDSS_MDP_REG_WRITE(base + MDSS_MDP_REG_DSPP_OP_MODE, opmode);
 	ctl->flush_bits |= BIT(13 + dspp_num); /* DSPP */
 	return 0;
@@ -1039,18 +1059,40 @@
 int mdss_mdp_argc_config(struct mdp_pgc_lut_data *config, u32 *copyback)
 {
 	int ret = 0;
-	u32 argc_offset, disp_num, dspp_num = 0;
+	u32 argc_offset = 0, disp_num, dspp_num = 0;
 	struct mdp_pgc_lut_data local_cfg;
+	struct mdp_pgc_lut_data *pgc_ptr;
 	u32 tbl_size;
 
-	if ((config->block < MDP_LOGICAL_BLOCK_DISP_0) ||
-		(config->block >= MDP_BLOCK_MAX))
+	if ((PP_BLOCK(config->block) < MDP_LOGICAL_BLOCK_DISP_0) ||
+		(PP_BLOCK(config->block) >= MDP_BLOCK_MAX))
 		return -EINVAL;
 
 	mutex_lock(&mdss_pp_mutex);
-	disp_num = config->block - MDP_LOGICAL_BLOCK_DISP_0;
+
+	disp_num = PP_BLOCK(config->block) - MDP_LOGICAL_BLOCK_DISP_0;
+	switch (config->block & MDSS_PP_LOCATION_MASK) {
+	case MDSS_PP_LM_CFG:
+		argc_offset = MDSS_MDP_REG_LM_OFFSET(dspp_num) +
+			MDSS_MDP_REG_LM_GC_LUT_BASE;
+		pgc_ptr = &mdss_pp_res->argc_disp_cfg[disp_num];
+		mdss_pp_res->pp_disp_flags[disp_num] |=
+			PP_FLAGS_DIRTY_ARGC;
+		break;
+	case MDSS_PP_DSPP_CFG:
+		argc_offset = MDSS_MDP_REG_DSPP_OFFSET(dspp_num) +
+					MDSS_MDP_REG_DSPP_GC_BASE;
+		pgc_ptr = &mdss_pp_res->pgc_disp_cfg[disp_num];
+		mdss_pp_res->pp_disp_flags[disp_num] |=
+			PP_FLAGS_DIRTY_PGC;
+		break;
+	default:
+		goto argc_config_exit;
+		break;
+	}
 
 	tbl_size = GC_LUT_SEGMENTS * sizeof(struct mdp_ar_gc_lut_data);
+
 	if (config->flags & MDP_PP_OPS_READ) {
 		ret = pp_get_dspp_num(disp_num, &dspp_num);
 		if (ret) {
@@ -1059,10 +1101,6 @@
 			goto argc_config_exit;
 		}
 		mdss_mdp_clk_ctrl(MDP_BLOCK_POWER_ON, false);
-
-		argc_offset = MDSS_MDP_REG_LM_OFFSET(dspp_num) +
-				MDSS_MDP_REG_LM_GC_LUT_BASE;
-		mdss_mdp_clk_ctrl(MDP_BLOCK_POWER_ON, false);
 		local_cfg = *config;
 		local_cfg.r_data =
 			&mdss_pp_res->gc_lut_r[disp_num][0];
@@ -1104,14 +1142,14 @@
 			ret = -EFAULT;
 			goto argc_config_exit;
 		}
-		mdss_pp_res->pgc_disp_cfg[disp_num] = *config;
-		mdss_pp_res->pgc_disp_cfg[disp_num].r_data =
+
+		*pgc_ptr = *config;
+		pgc_ptr->r_data =
 			&mdss_pp_res->gc_lut_r[disp_num][0];
-		mdss_pp_res->pgc_disp_cfg[disp_num].g_data =
+		pgc_ptr->g_data =
 			&mdss_pp_res->gc_lut_g[disp_num][0];
-		mdss_pp_res->pgc_disp_cfg[disp_num].b_data =
+		pgc_ptr->b_data =
 			&mdss_pp_res->gc_lut_b[disp_num][0];
-		mdss_pp_res->pp_disp_flags[disp_num] |= PP_FLAGS_DIRTY_ARGC;
 	}
 argc_config_exit:
 	mutex_unlock(&mdss_pp_mutex);
diff --git a/drivers/video/msm/vidc/1080p/ddl/vcd_ddl.c b/drivers/video/msm/vidc/1080p/ddl/vcd_ddl.c
index 1b7bed6..582744c 100644
--- a/drivers/video/msm/vidc/1080p/ddl/vcd_ddl.c
+++ b/drivers/video/msm/vidc/1080p/ddl/vcd_ddl.c
@@ -491,9 +491,6 @@
 	struct ddl_encoder_data *encoder =
 		&ddl->codec_data.encoder;
 	u32 vcd_status = VCD_S_SUCCESS;
-	struct vcd_transc *transc;
-	transc = (struct vcd_transc *)(ddl->client_data);
-	DDL_MSG_LOW("%s: transc = 0x%x", __func__, (u32)ddl->client_data);
 	if (encoder->slice_delivery_info.enable) {
 		return ddl_encode_frame_batch(ddl_handle,
 					input_frame,
diff --git a/drivers/video/msm/vidc/1080p/ddl/vcd_ddl_helper.c b/drivers/video/msm/vidc/1080p/ddl/vcd_ddl_helper.c
index 729fb2e..77faee3 100644
--- a/drivers/video/msm/vidc/1080p/ddl/vcd_ddl_helper.c
+++ b/drivers/video/msm/vidc/1080p/ddl/vcd_ddl_helper.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -506,6 +506,8 @@
 
 	width_round_up  = width;
 	height_round_up = height;
+	align = SZ_4K;
+
 	if (format == DDL_YUV_BUF_TYPE_TILE) {
 		width_round_up  = DDL_ALIGN(width, DDL_TILE_ALIGN_WIDTH);
 		height_round_up = DDL_ALIGN(height, DDL_TILE_ALIGN_HEIGHT);
diff --git a/drivers/video/msm/vidc/1080p/ddl/vcd_ddl_interrupt_handler.c b/drivers/video/msm/vidc/1080p/ddl/vcd_ddl_interrupt_handler.c
index 163af21..64cc570 100644
--- a/drivers/video/msm/vidc/1080p/ddl/vcd_ddl_interrupt_handler.c
+++ b/drivers/video/msm/vidc/1080p/ddl/vcd_ddl_interrupt_handler.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -1811,8 +1811,10 @@
 	slice_output = (struct vidc_1080p_enc_slice_batch_out_param *)
 		(encoder->batch_frame.slice_batch_out.align_virtual_addr);
 	DDL_MSG_LOW(" after get no of slices = %d\n", num_slices_comp);
-	if (slice_output == NULL)
+	if (slice_output == NULL) {
 		DDL_MSG_ERROR(" slice_output is NULL\n");
+		return; /* Bail out */
+	}
 	encoder->slice_delivery_info.num_slices_enc += num_slices_comp;
 	if (vidc_msg_timing) {
 		ddl_calc_core_proc_time_cnt(__func__, ENC_SLICE_OP_TIME,
diff --git a/drivers/video/msm/vidc/1080p/resource_tracker/vcd_res_tracker.c b/drivers/video/msm/vidc/1080p/resource_tracker/vcd_res_tracker.c
index d9cadef..c15218d 100644
--- a/drivers/video/msm/vidc/1080p/resource_tracker/vcd_res_tracker.c
+++ b/drivers/video/msm/vidc/1080p/resource_tracker/vcd_res_tracker.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -160,9 +160,13 @@
 static void res_trk_pmem_free(struct ddl_buf_addr *addr)
 {
 	struct ddl_context *ddl_context;
+
+	if (!addr)
+		return;
+
 	ddl_context = ddl_get_context();
 	if (ddl_context->video_ion_client) {
-		if (addr && addr->alloc_handle) {
+		if (addr->alloc_handle) {
 			ion_free(ddl_context->video_ion_client,
 			 addr->alloc_handle);
 			addr->alloc_handle = NULL;
diff --git a/drivers/video/msm/vidc/common/dec/vdec.c b/drivers/video/msm/vidc/common/dec/vdec.c
index 48f127a..afc5130 100644
--- a/drivers/video/msm/vidc/common/dec/vdec.c
+++ b/drivers/video/msm/vidc/common/dec/vdec.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -2485,7 +2485,7 @@
 	}
 
 	client_index = vid_dec_get_empty_client_index();
-	if (client_index == -1) {
+	if (client_index < 0) {
 		ERR("%s() : No free clients client_index == -1\n", __func__);
 		rc = -ENOMEM;
 		goto client_failure;
diff --git a/drivers/video/msm/vidc/common/enc/venc.c b/drivers/video/msm/vidc/common/enc/venc.c
index c18bb92..0648257 100644
--- a/drivers/video/msm/vidc/common/enc/venc.c
+++ b/drivers/video/msm/vidc/common/enc/venc.c
@@ -557,7 +557,7 @@
 
 	client_index = vid_enc_get_empty_client_index();
 
-	if (client_index == -1) {
+	if (client_index < 0) {
 		ERR("%s() : No free clients client_index == -1\n",
 			__func__);
 		rc = -ENODEV;
diff --git a/drivers/video/msm/vidc/common/vcd/vcd_client_sm.c b/drivers/video/msm/vidc/common/vcd/vcd_client_sm.c
index 884050b..14c8030 100644
--- a/drivers/video/msm/vidc/common/vcd/vcd_client_sm.c
+++ b/drivers/video/msm/vidc/common/vcd/vcd_client_sm.c
@@ -1628,6 +1628,7 @@
 	if (!cctxt || to_state >= VCD_CLIENT_STATE_MAX) {
 		VCD_MSG_ERROR("Bad parameters. cctxt=%p, to_state=%d",
 			      cctxt, to_state);
+		return;
 	}
 
 	state_ctxt = &cctxt->clnt_state;
diff --git a/drivers/video/msm/vidc/common/vcd/vcd_device_sm.c b/drivers/video/msm/vidc/common/vcd/vcd_device_sm.c
index f670a4a..9074358 100644
--- a/drivers/video/msm/vidc/common/vcd/vcd_device_sm.c
+++ b/drivers/video/msm/vidc/common/vcd/vcd_device_sm.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -36,6 +36,7 @@
 	if (!drv_ctxt || to_state >= VCD_DEVICE_STATE_MAX) {
 		VCD_MSG_ERROR("Bad parameters. drv_ctxt=%p, to_state=%d",
 				  drv_ctxt, to_state);
+		return;
 	}
 
 	state_ctxt = &drv_ctxt->dev_state;
diff --git a/drivers/video/msm/vidc/common/vcd/vcd_scheduler.c b/drivers/video/msm/vidc/common/vcd/vcd_scheduler.c
index ab21bac..fe0e131 100644
--- a/drivers/video/msm/vidc/common/vcd/vcd_scheduler.c
+++ b/drivers/video/msm/vidc/common/vcd/vcd_scheduler.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -88,8 +88,13 @@
 			prop_hdr.sz = sizeof(cctxt->frm_p_units);
 			rc = ddl_get_property(cctxt->ddl_handle, &prop_hdr,
 						  &cctxt->frm_p_units);
-			VCD_FAILED_RETURN(rc,
-				"Failed: Get DDL_I_FRAME_PROC_UNITS");
+			if (VCD_FAILED(rc)) {
+				kfree(sched_cctxt);
+				VCD_MSG_ERROR(
+					"Failed: Get DDL_I_FRAME_PROC_UNITS");
+				return rc;
+			}
+
 			if (cctxt->decoding) {
 				cctxt->frm_rate.fps_numerator =
 					VCD_DEC_INITIAL_FRAME_RATE;
@@ -99,8 +104,12 @@
 				prop_hdr.sz = sizeof(cctxt->frm_rate);
 				rc = ddl_get_property(cctxt->ddl_handle,
 						&prop_hdr, &cctxt->frm_rate);
-				VCD_FAILED_RETURN(rc,
-					"Failed: Get VCD_I_FRAME_RATE");
+				if (VCD_FAILED(rc)) {
+					kfree(sched_cctxt);
+					VCD_MSG_ERROR(
+						"Failed: Get VCD_I_FRAME_RATE");
+					return rc;
+				}
 			}
 			if (!cctxt->perf_set_by_client)
 				cctxt->reqd_perf_lvl = cctxt->frm_p_units *
diff --git a/drivers/video/msm/vidc/common/vcd/vcd_sub.c b/drivers/video/msm/vidc/common/vcd/vcd_sub.c
index 78d77d1..09cd91d 100644
--- a/drivers/video/msm/vidc/common/vcd/vcd_sub.c
+++ b/drivers/video/msm/vidc/common/vcd/vcd_sub.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -2022,6 +2022,11 @@
 	orig_frame = vcd_find_buffer_pool_entry(&cctxt->in_buf_pool,
 					 transc->ip_buf_entry->virtual);
 
+	if (!orig_frame) {
+		rc = VCD_ERR_ILLEGAL_PARM;
+		VCD_FAILED_RETURN(rc, "Couldn't find buffer");
+	}
+
 	if ((transc->ip_buf_entry->frame.virtual !=
 		 frame->vcd_frm.virtual)
 		|| !transc->ip_buf_entry->in_use) {
diff --git a/include/linux/msm_mdp.h b/include/linux/msm_mdp.h
index fdb8fb6..56eda83 100644
--- a/include/linux/msm_mdp.h
+++ b/include/linux/msm_mdp.h
@@ -286,6 +286,18 @@
 #define MDP_PP_IGC_FLAG_ROM0	0x10
 #define MDP_PP_IGC_FLAG_ROM1	0x20
 
+#define MDSS_PP_DSPP_CFG	0x0000
+#define MDSS_PP_SSPP_CFG	0x4000
+#define MDSS_PP_LM_CFG	0x8000
+#define MDSS_PP_WB_CFG	0xC000
+
+#define MDSS_PP_LOCATION_MASK	0xC000
+#define MDSS_PP_LOGICAL_MASK	0x3FFF
+
+#define PP_LOCAT(var) ((var) & MDSS_PP_LOCATION_MASK)
+#define PP_BLOCK(var) ((var) & MDSS_PP_LOGICAL_MASK)
+
+
 struct mdp_qseed_cfg {
 	uint32_t table_num;
 	uint32_t ops;
diff --git a/include/linux/qpnp/qpnp-adc.h b/include/linux/qpnp/qpnp-adc.h
index 3ab7b9d..903cc3f 100644
--- a/include/linux/qpnp/qpnp-adc.h
+++ b/include/linux/qpnp/qpnp-adc.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -1228,6 +1228,12 @@
 int32_t qpnp_iadc_read(enum qpnp_iadc_channels channel,
 				struct qpnp_iadc_result *result);
 /**
+ * qpnp_iadc_get_rsense() - Reads the RDS resistance value from the
+			trim registers.
+ * @rsense:	RDS resistance in nOhms.
+ */
+int32_t qpnp_iadc_get_rsense(int32_t *rsense);
+/**
  * qpnp_iadc_get_gain_and_offset() - Performs gain calibration
  *				over 17.8571mV and offset over selected
  *				channel. Channel can be internal rsense,
@@ -1314,6 +1320,8 @@
 { return -ENXIO; }
 static inline int32_t qpnp_adc_tm_is_ready(void)
 { return -ENXIO; }
+static inline int32_t qpnp_iadc_get_rsense(int32_t *rsense)
+{ return -ENXIO; }
 #endif
 
 #endif
diff --git a/include/sound/apr_audio-v2.h b/include/sound/apr_audio-v2.h
index 88acdfc..3571fad 100644
--- a/include/sound/apr_audio-v2.h
+++ b/include/sound/apr_audio-v2.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
@@ -6369,4 +6369,135 @@
 
 /*bharath, adsp_error_codes.h */
 
+/* LPASS clock for I2S Interface */
+
+/* Supported OSR clock values */
+#define Q6AFE_LPASS_OSR_CLK_12_P288_MHZ		0xBB8000
+#define Q6AFE_LPASS_OSR_CLK_8_P192_MHZ		0x7D0000
+#define Q6AFE_LPASS_OSR_CLK_6_P144_MHZ		0x5DC000
+#define Q6AFE_LPASS_OSR_CLK_4_P096_MHZ		0x3E8000
+#define Q6AFE_LPASS_OSR_CLK_3_P072_MHZ		0x2EE000
+#define Q6AFE_LPASS_OSR_CLK_2_P048_MHZ		0x1F4000
+#define Q6AFE_LPASS_OSR_CLK_1_P536_MHZ		0x177000
+#define Q6AFE_LPASS_OSR_CLK_1_P024_MHZ		 0xFA000
+#define Q6AFE_LPASS_OSR_CLK_768_kHZ		 0xBB800
+#define Q6AFE_LPASS_OSR_CLK_512_kHZ		 0x7D000
+#define Q6AFE_LPASS_OSR_CLK_DISABLE		     0x0
+
+/* Supported Bit clock values */
+#define Q6AFE_LPASS_IBIT_CLK_8_P192_MHZ		0x7D0000
+#define Q6AFE_LPASS_IBIT_CLK_6_P144_MHZ		0x5DC000
+#define Q6AFE_LPASS_IBIT_CLK_4_P096_MHZ		0x3E8000
+#define Q6AFE_LPASS_IBIT_CLK_3_P072_MHZ		0x2EE000
+#define Q6AFE_LPASS_IBIT_CLK_2_P048_MHZ		0x1F4000
+#define Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ		0x177000
+#define Q6AFE_LPASS_IBIT_CLK_1_P024_MHZ		 0xFA000
+#define Q6AFE_LPASS_IBIT_CLK_768_KHZ		 0xBB800
+#define Q6AFE_LPASS_IBIT_CLK_512_KHZ		 0x7D000
+#define Q6AFE_LPASS_IBIT_CLK_DISABLE		     0x0
+
+/* Supported LPASS CLK sources */
+#define Q6AFE_LPASS_CLK_SRC_EXTERNAL 0
+#define Q6AFE_LPASS_CLK_SRC_INTERNAL 1
+
+/* Supported LPASS CLK root*/
+#define Q6AFE_LPASS_CLK_ROOT_DEFAULT 0
+
+enum afe_lpass_clk_mode {
+	Q6AFE_LPASS_MODE_BOTH_INVALID,
+	Q6AFE_LPASS_MODE_CLK1_VALID,
+	Q6AFE_LPASS_MODE_CLK2_VALID,
+	Q6AFE_LPASS_MODE_BOTH_VALID,
+} __packed;
+
+struct afe_clk_cfg {
+/* Minor version used for tracking the version of the I2S
+ * configuration interface.
+ * Supported values: #AFE_API_VERSION_I2S_CONFIG
+ */
+	u32                  i2s_cfg_minor_version;
+
+/* clk value 1 in MHz. */
+	u32                  clk_val1;
+
+/* clk value 2 in MHz. */
+	u32                  clk_val2;
+
+/* clk_src
+ * #Q6AFE_LPASS_CLK_SRC_EXTERNAL
+ * #Q6AFE_LPASS_CLK_SRC_INTERNAL
+ */
+
+	u16                  clk_src;
+
+/* clk_root -0 for default */
+	u16                  clk_root;
+
+/* clk_set_mode
+ * #Q6AFE_LPASS_MODE_BOTH_INVALID
+ * #Q6AFE_LPASS_MODE_CLK1_VALID
+ * #Q6AFE_LPASS_MODE_CLK2_VALID
+ * #Q6AFE_LPASS_MODE_BOTH_VALID
+ */
+	u16                  clk_set_mode;
+
+/* This param id is used to configure I2S clk */
+	u16                  reserved;
+} __packed;
+
+/* This param id is used to configure I2S clk */
+#define AFE_PARAM_ID_LPAIF_CLK_CONFIG	0x00010238
+
+
+struct afe_lpass_clk_config_command {
+	struct apr_hdr			 hdr;
+	struct afe_port_cmd_set_param_v2 param;
+	struct afe_port_param_data_v2    pdata;
+	struct afe_clk_cfg clk_cfg;
+} __packed;
+
+enum afe_lpass_digital_clk_src {
+	Q6AFE_LPASS_DIGITAL_ROOT_INVALID,
+	Q6AFE_LPASS_DIGITAL_ROOT_PRI_MI2S_OSR,
+	Q6AFE_LPASS_DIGITAL_ROOT_SEC_MI2S_OSR,
+	Q6AFE_LPASS_DIGITAL_ROOT_TER_MI2S_OSR,
+	Q6AFE_LPASS_DIGITAL_ROOT_QUAD_MI2S_OSR,
+	Q6AFE_LPASS_DIGITAL_ROOT_CDC_ROOT_CLK,
+} __packed;
+
+/* This param id is used to configure internal clk */
+#define AFE_PARAM_ID_INTERNAL_DIGIATL_CDC_CLK_CONFIG	0x00010239
+
+struct afe_digital_clk_cfg {
+/* Minor version used for tracking the version of the I2S
+ * configuration interface.
+ * Supported values: #AFE_API_VERSION_I2S_CONFIG
+ */
+	u32                  i2s_cfg_minor_version;
+
+/* clk value in MHz. */
+	u32                  clk_val;
+
+/*	INVALID
+ *	PRI_MI2S_OSR
+ *	SEC_MI2S_OSR
+ *	TER_MI2S_OSR
+ *	QUAD_MI2S_OSR
+ *	DIGT_CDC_ROOT
+ */
+	u16                  clk_root;
+
+/* This field must be set to zero. */
+	u16                  reserved;
+} __packed;
+
+
+struct afe_lpass_digital_clk_config_command {
+	struct apr_hdr			 hdr;
+	struct afe_port_cmd_set_param_v2 param;
+	struct afe_port_param_data_v2    pdata;
+	struct afe_digital_clk_cfg clk_cfg;
+} __packed;
+
+
 #endif /*_APR_AUDIO_V2_H_ */
diff --git a/include/sound/q6afe-v2.h b/include/sound/q6afe-v2.h
index 3da152c..e39d45c 100644
--- a/include/sound/q6afe-v2.h
+++ b/include/sound/q6afe-v2.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -155,4 +155,9 @@
 
 int afe_pseudo_port_start_nowait(u16 port_id);
 int afe_pseudo_port_stop_nowait(u16 port_id);
+int afe_set_lpass_clock(u16 port_id, struct afe_clk_cfg *cfg);
+int afe_set_lpass_internal_digital_codec_clock(u16 port_id,
+				struct afe_digital_clk_cfg *cfg);
+int q6afe_check_osr_clk_freq(u32 freq);
+
 #endif /* __Q6AFE_V2_H__ */
diff --git a/include/sound/q6audio-v2.h b/include/sound/q6audio-v2.h
index 1a5dce1..fd6a490 100644
--- a/include/sound/q6audio-v2.h
+++ b/include/sound/q6audio-v2.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -21,6 +21,8 @@
 
 int q6audio_validate_port(u16 port_id);
 
+int q6audio_is_digital_pcm_interface(u16 port_id);
+
 int q6audio_get_port_id(u16 port_id);
 
 #endif
diff --git a/kernel/panic.c b/kernel/panic.c
index 8c6babc..4716d16 100644
--- a/kernel/panic.c
+++ b/kernel/panic.c
@@ -23,6 +23,7 @@
 #include <linux/init.h>
 #include <linux/nmi.h>
 #include <linux/dmi.h>
+#include <linux/coresight.h>
 
 #define PANIC_TIMER_STEP 100
 #define PANIC_BLINK_SPD 18
@@ -80,6 +81,7 @@
 	long i, i_next = 0;
 	int state = 0;
 
+	coresight_abort();
 	/*
 	 * Disable local interrupts. This will prevent panic_smp_self_stop
 	 * from deadlocking the first cpu that invokes the panic, since
diff --git a/sound/soc/msm/qdsp6/q6adm.c b/sound/soc/msm/qdsp6/q6adm.c
index 2d8d9ca..58a07d6 100644
--- a/sound/soc/msm/qdsp6/q6adm.c
+++ b/sound/soc/msm/qdsp6/q6adm.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -16,6 +16,7 @@
 #include <linux/jiffies.h>
 #include <linux/uaccess.h>
 #include <linux/atomic.h>
+#include <linux/err.h>
 
 #include <mach/qdsp6v2/audio_dev_ctl.h>
 #include <mach/qdsp6v2/audio_acdb.h>
@@ -54,6 +55,14 @@
 	int index;
 
 	pr_debug("SRS - %s", __func__);
+
+	index = afe_get_port_index(port_id);
+
+	if (IS_ERR_VALUE(index)) {
+		pr_err("%s: invald port id\n", __func__);
+		return index;
+	}
+
 	switch (srs_tech_id) {
 	case SRS_ID_GLOBAL: {
 		struct srs_trumedia_params_GLOBAL *glb_params = NULL;
@@ -199,7 +208,6 @@
 	open->hdr.src_port = port_id;
 	open->hdr.dest_svc = APR_SVC_ADM;
 	open->hdr.dest_domain = APR_DOMAIN_ADSP;
-	index = afe_get_port_index(port_id);
 	open->hdr.dest_port = atomic_read(&this_adm.copp_id[index]);
 	open->hdr.token = port_id;
 	open->hdr.opcode = ADM_CMD_SET_PARAMS;
diff --git a/sound/soc/msm/qdsp6/q6afe.c b/sound/soc/msm/qdsp6/q6afe.c
index 2d44a41..f29f02e 100644
--- a/sound/soc/msm/qdsp6/q6afe.c
+++ b/sound/soc/msm/qdsp6/q6afe.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2010-2013, .qualcomm.com. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -1587,7 +1587,7 @@
 				goto afe_error;
 			}
 
-			if (param[1] < 0 || param[1] > 100) {
+			if (param[1] > 100) {
 				pr_err("%s: Error, volume shoud be 0 to 100"
 					" percentage param = %lu\n",
 					__func__, param[1]);
diff --git a/sound/soc/msm/qdsp6v2/Makefile b/sound/soc/msm/qdsp6v2/Makefile
index 1d11907..58eec3c 100644
--- a/sound/soc/msm/qdsp6v2/Makefile
+++ b/sound/soc/msm/qdsp6v2/Makefile
@@ -1,6 +1,6 @@
 snd-soc-qdsp6v2-objs += msm-dai-q6-v2.o msm-pcm-q6-v2.o msm-pcm-routing-v2.o msm-compr-q6-v2.o  msm-multi-ch-pcm-q6-v2.o
 snd-soc-qdsp6v2-objs += msm-pcm-lpa-v2.o msm-pcm-afe-v2.o msm-pcm-voip-v2.o msm-pcm-voice-v2.o msm-dai-q6-hdmi-v2.o
 obj-$(CONFIG_SND_SOC_QDSP6V2) += snd-soc-qdsp6v2.o
-obj-y += q6adm.o q6afe.o q6asm.o q6audio-v2.o q6voice.o q6core.o
+obj-y += q6adm.o q6afe.o q6asm.o q6audio-v2.o q6voice.o q6core.o audio_acdb.o rtac.o
 ocmem-audio-objs += audio_ocmem.o
 obj-$(CONFIG_AUDIO_OCMEM) += ocmem-audio.o
diff --git a/sound/soc/msm/qdsp6v2/audio_acdb.c b/sound/soc/msm/qdsp6v2/audio_acdb.c
new file mode 100644
index 0000000..7061efa
--- /dev/null
+++ b/sound/soc/msm/qdsp6v2/audio_acdb.c
@@ -0,0 +1,967 @@
+/* Copyright (c) 2010-2013, The Linux Foundation. All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 and
+ * only version 2 as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ */
+#include <linux/slab.h>
+#include <linux/fs.h>
+#include <linux/module.h>
+#include <linux/miscdevice.h>
+#include <linux/mutex.h>
+#include <linux/uaccess.h>
+#include <linux/msm_ion.h>
+#include <linux/mm.h>
+#include "audio_acdb.h"
+
+
+#define MAX_NETWORKS			15
+#define MAX_IOCTL_DATA			(MAX_NETWORKS * 2)
+#define MAX_COL_SIZE			324
+
+#define ACDB_BLOCK_SIZE			4096
+#define NUM_VOCPROC_BLOCKS		(6 * MAX_NETWORKS)
+#define ACDB_TOTAL_VOICE_ALLOCATION	(ACDB_BLOCK_SIZE * NUM_VOCPROC_BLOCKS)
+
+
+struct sidetone_atomic_cal {
+	atomic_t	enable;
+	atomic_t	gain;
+};
+
+
+struct acdb_data {
+	struct mutex		acdb_mutex;
+
+	/* ANC Cal */
+	struct acdb_atomic_cal_block	anc_cal;
+
+	/* AudProc Cal */
+	atomic_t			asm_topology;
+	atomic_t			adm_topology[MAX_AUDPROC_TYPES];
+	struct acdb_atomic_cal_block	audproc_cal[MAX_AUDPROC_TYPES];
+	struct acdb_atomic_cal_block	audstrm_cal[MAX_AUDPROC_TYPES];
+	struct acdb_atomic_cal_block	audvol_cal[MAX_AUDPROC_TYPES];
+
+	/* VocProc Cal */
+	atomic_t			voice_rx_topology;
+	atomic_t			voice_tx_topology;
+	struct acdb_atomic_cal_block	vocproc_cal;
+	struct acdb_atomic_cal_block	vocstrm_cal;
+	struct acdb_atomic_cal_block	vocvol_cal;
+
+	/* Voice Column data */
+	struct acdb_atomic_cal_block	vocproc_col_cal[MAX_VOCPROC_TYPES];
+	uint32_t			*col_data[MAX_VOCPROC_TYPES];
+
+	/* VocProc dev cfg cal*/
+	struct acdb_atomic_cal_block	vocproc_dev_cal;
+
+	/* AFE cal */
+	struct acdb_atomic_cal_block	afe_cal[MAX_AUDPROC_TYPES];
+
+	/* Sidetone Cal */
+	struct sidetone_atomic_cal	sidetone_cal;
+
+	/* Allocation information */
+	struct ion_client		*ion_client;
+	struct ion_handle		*ion_handle;
+	atomic_t			map_handle;
+	atomic64_t			paddr;
+	atomic64_t			kvaddr;
+	atomic64_t			mem_len;
+};
+
+static struct acdb_data		acdb_data;
+static atomic_t usage_count;
+
+uint32_t get_voice_rx_topology(void)
+{
+	return atomic_read(&acdb_data.voice_rx_topology);
+}
+
+void store_voice_rx_topology(uint32_t topology)
+{
+	atomic_set(&acdb_data.voice_rx_topology, topology);
+}
+
+uint32_t get_voice_tx_topology(void)
+{
+	return atomic_read(&acdb_data.voice_tx_topology);
+}
+
+void store_voice_tx_topology(uint32_t topology)
+{
+	atomic_set(&acdb_data.voice_tx_topology, topology);
+}
+
+uint32_t get_adm_rx_topology(void)
+{
+	return atomic_read(&acdb_data.adm_topology[RX_CAL]);
+}
+
+void store_adm_rx_topology(uint32_t topology)
+{
+	atomic_set(&acdb_data.adm_topology[RX_CAL], topology);
+}
+
+uint32_t get_adm_tx_topology(void)
+{
+	return atomic_read(&acdb_data.adm_topology[TX_CAL]);
+}
+
+void store_adm_tx_topology(uint32_t topology)
+{
+	atomic_set(&acdb_data.adm_topology[TX_CAL], topology);
+}
+
+uint32_t get_asm_topology(void)
+{
+	return atomic_read(&acdb_data.asm_topology);
+}
+
+void store_asm_topology(uint32_t topology)
+{
+	atomic_set(&acdb_data.asm_topology, topology);
+}
+
+void get_voice_cal_allocation(struct acdb_cal_block *cal_block)
+{
+	cal_block->cal_size = ACDB_TOTAL_VOICE_ALLOCATION;
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.vocproc_cal.cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.vocproc_cal.cal_kvaddr);
+}
+
+void get_anc_cal(struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.anc_cal.cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.anc_cal.cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.anc_cal.cal_kvaddr);
+done:
+	return;
+}
+
+void store_anc_cal(struct cal_block *cal_block)
+{
+	pr_debug("%s,\n", __func__);
+
+	if (cal_block->cal_offset > atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		goto done;
+	}
+
+	atomic_set(&acdb_data.anc_cal.cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.anc_cal.cal_paddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+	atomic_set(&acdb_data.anc_cal.cal_kvaddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+done:
+	return;
+}
+
+void store_afe_cal(int32_t path, struct cal_block *cal_block)
+{
+	pr_debug("%s, path = %d\n", __func__, path);
+
+	if (cal_block->cal_offset > atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		goto done;
+	}
+	if ((path >= MAX_AUDPROC_TYPES) || (path < 0)) {
+		pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+			__func__, path);
+		goto done;
+	}
+
+	atomic_set(&acdb_data.afe_cal[path].cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.afe_cal[path].cal_paddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+	atomic_set(&acdb_data.afe_cal[path].cal_kvaddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+done:
+	return;
+}
+
+void get_afe_cal(int32_t path, struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s, path = %d\n", __func__, path);
+
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+	if ((path >= MAX_AUDPROC_TYPES) || (path < 0)) {
+		pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+			__func__, path);
+		goto done;
+	}
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.afe_cal[path].cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.afe_cal[path].cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.afe_cal[path].cal_kvaddr);
+done:
+	return;
+}
+
+void store_audproc_cal(int32_t path, struct cal_block *cal_block)
+{
+	pr_debug("%s, path = %d\n", __func__, path);
+
+	if (cal_block->cal_offset > atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		goto done;
+	}
+	if (path >= MAX_AUDPROC_TYPES) {
+		pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+			__func__, path);
+		goto done;
+	}
+
+	atomic_set(&acdb_data.audproc_cal[path].cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.audproc_cal[path].cal_paddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+	atomic_set(&acdb_data.audproc_cal[path].cal_kvaddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+done:
+	return;
+}
+
+void get_audproc_cal(int32_t path, struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s, path = %d\n", __func__, path);
+
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+	if (path >= MAX_AUDPROC_TYPES) {
+		pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+			__func__, path);
+		goto done;
+	}
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.audproc_cal[path].cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.audproc_cal[path].cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.audproc_cal[path].cal_kvaddr);
+done:
+	return;
+}
+
+void store_audstrm_cal(int32_t path, struct cal_block *cal_block)
+{
+	pr_debug("%s, path = %d\n", __func__, path);
+
+	if (cal_block->cal_offset > atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		goto done;
+	}
+	if (path >= MAX_AUDPROC_TYPES) {
+		pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+			__func__, path);
+		goto done;
+	}
+
+	atomic_set(&acdb_data.audstrm_cal[path].cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.audstrm_cal[path].cal_paddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+	atomic_set(&acdb_data.audstrm_cal[path].cal_kvaddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+done:
+	return;
+}
+
+void get_audstrm_cal(int32_t path, struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s, path = %d\n", __func__, path);
+
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+	if (path >= MAX_AUDPROC_TYPES) {
+		pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+			__func__, path);
+		goto done;
+	}
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.audstrm_cal[path].cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.audstrm_cal[path].cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.audstrm_cal[path].cal_kvaddr);
+done:
+	return;
+}
+
+void store_audvol_cal(int32_t path, struct cal_block *cal_block)
+{
+	pr_debug("%s, path = %d\n", __func__, path);
+
+	if (cal_block->cal_offset > atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		goto done;
+	}
+	if (path >= MAX_AUDPROC_TYPES) {
+		pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+			__func__, path);
+		goto done;
+	}
+
+	atomic_set(&acdb_data.audvol_cal[path].cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.audvol_cal[path].cal_paddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.paddr));
+	atomic_set(&acdb_data.audvol_cal[path].cal_kvaddr,
+		cal_block->cal_offset + atomic64_read(&acdb_data.kvaddr));
+done:
+	return;
+}
+
+void get_audvol_cal(int32_t path, struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s, path = %d\n", __func__, path);
+
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+	if (path >= MAX_AUDPROC_TYPES || path < 0) {
+		pr_err("ACDB=> Bad path sent to %s, path: %d\n",
+			__func__, path);
+		goto done;
+	}
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.audvol_cal[path].cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.audvol_cal[path].cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.audvol_cal[path].cal_kvaddr);
+done:
+	return;
+}
+
+void store_voice_col_data(uint32_t vocproc_type, uint32_t cal_size,
+			  uint32_t *cal_block)
+{
+	if (cal_size > MAX_COL_SIZE) {
+		pr_err("%s: col size is to big %d\n", __func__,
+				cal_size);
+		goto done;
+	}
+	if (copy_from_user(acdb_data.col_data[vocproc_type],
+			(void *)((uint8_t *)cal_block + sizeof(cal_size)),
+			cal_size)) {
+		pr_err("%s: fail to copy col size %d\n",
+			__func__, cal_size);
+		goto done;
+	}
+	atomic_set(&acdb_data.vocproc_col_cal[vocproc_type].cal_size,
+		cal_size);
+done:
+	return;
+}
+
+void get_voice_col_data(uint32_t vocproc_type,
+			struct acdb_cal_block *cal_block)
+{
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+
+	cal_block->cal_size = atomic_read(&acdb_data.
+				vocproc_col_cal[vocproc_type].cal_size);
+	cal_block->cal_paddr = atomic_read(&acdb_data.
+				vocproc_col_cal[vocproc_type].cal_paddr);
+	cal_block->cal_kvaddr = atomic_read(&acdb_data.
+				vocproc_col_cal[vocproc_type].cal_kvaddr);
+done:
+	return;
+}
+
+void store_vocproc_dev_cfg_cal(struct cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+
+	if (cal_block->cal_offset >
+				atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		atomic_set(&acdb_data.vocproc_dev_cal.cal_size, 0);
+		goto done;
+	}
+
+	atomic_set(&acdb_data.vocproc_dev_cal.cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.vocproc_dev_cal.cal_paddr,
+		cal_block->cal_offset +
+	atomic64_read(&acdb_data.paddr));
+			atomic_set(&acdb_data.vocproc_dev_cal.cal_kvaddr,
+			cal_block->cal_offset +
+			atomic64_read(&acdb_data.kvaddr));
+
+done:
+	return;
+}
+
+void get_vocproc_dev_cfg_cal(struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.vocproc_dev_cal.cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.vocproc_dev_cal.cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.vocproc_dev_cal.cal_kvaddr);
+}
+
+
+
+void store_vocproc_cal(struct cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+	if (cal_block->cal_offset >
+				atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		atomic_set(&acdb_data.vocproc_cal.cal_size, 0);
+		goto done;
+	}
+
+	atomic_set(&acdb_data.vocproc_cal.cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.vocproc_cal.cal_paddr,
+		cal_block->cal_offset +
+		atomic64_read(&acdb_data.paddr));
+	atomic_set(&acdb_data.vocproc_cal.cal_kvaddr,
+		cal_block->cal_offset +
+		atomic64_read(&acdb_data.kvaddr));
+
+done:
+	return;
+}
+
+void get_vocproc_cal(struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.vocproc_cal.cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.vocproc_cal.cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.vocproc_cal.cal_kvaddr);
+done:
+	return;
+}
+
+void store_vocstrm_cal(struct cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+	if (cal_block->cal_offset >
+			atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		atomic_set(&acdb_data.vocstrm_cal.cal_size, 0);
+		goto done;
+	}
+
+	atomic_set(&acdb_data.vocstrm_cal.cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.vocstrm_cal.cal_paddr,
+		cal_block->cal_offset +
+		atomic64_read(&acdb_data.paddr));
+	atomic_set(&acdb_data.vocstrm_cal.cal_kvaddr,
+		cal_block->cal_offset +
+		atomic64_read(&acdb_data.kvaddr));
+
+done:
+	return;
+}
+
+void get_vocstrm_cal(struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.vocstrm_cal.cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.vocstrm_cal.cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.vocstrm_cal.cal_kvaddr);
+done:
+	return;
+}
+
+void store_vocvol_cal(struct cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+	if (cal_block->cal_offset >
+			atomic64_read(&acdb_data.mem_len)) {
+		pr_err("%s: offset %d is > mem_len %ld\n",
+			__func__, cal_block->cal_offset,
+			(long)atomic64_read(&acdb_data.mem_len));
+		atomic_set(&acdb_data.vocvol_cal.cal_size, 0);
+		goto done;
+	}
+
+	atomic_set(&acdb_data.vocvol_cal.cal_size,
+		cal_block->cal_size);
+	atomic_set(&acdb_data.vocvol_cal.cal_paddr,
+		cal_block->cal_offset +
+		atomic64_read(&acdb_data.paddr));
+	atomic_set(&acdb_data.vocvol_cal.cal_kvaddr,
+		cal_block->cal_offset +
+		atomic64_read(&acdb_data.kvaddr));
+
+done:
+	return;
+}
+
+void get_vocvol_cal(struct acdb_cal_block *cal_block)
+{
+	pr_debug("%s\n", __func__);
+
+	if (cal_block == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+
+	cal_block->cal_size =
+		atomic_read(&acdb_data.vocvol_cal.cal_size);
+	cal_block->cal_paddr =
+		atomic_read(&acdb_data.vocvol_cal.cal_paddr);
+	cal_block->cal_kvaddr =
+		atomic_read(&acdb_data.vocvol_cal.cal_kvaddr);
+done:
+	return;
+}
+
+void store_sidetone_cal(struct sidetone_cal *cal_data)
+{
+	pr_debug("%s\n", __func__);
+
+	atomic_set(&acdb_data.sidetone_cal.enable, cal_data->enable);
+	atomic_set(&acdb_data.sidetone_cal.gain, cal_data->gain);
+}
+
+
+void get_sidetone_cal(struct sidetone_cal *cal_data)
+{
+	pr_debug("%s\n", __func__);
+
+	if (cal_data == NULL) {
+		pr_err("ACDB=> NULL pointer sent to %s\n", __func__);
+		goto done;
+	}
+
+	cal_data->enable = atomic_read(&acdb_data.sidetone_cal.enable);
+	cal_data->gain = atomic_read(&acdb_data.sidetone_cal.gain);
+done:
+	return;
+}
+
+static int acdb_open(struct inode *inode, struct file *f)
+{
+	s32 result = 0;
+	pr_debug("%s\n", __func__);
+
+	if (atomic64_read(&acdb_data.mem_len)) {
+		pr_debug("%s: ACDB opened but memory allocated, using existing allocation!\n",
+			__func__);
+	}
+
+	atomic_inc(&usage_count);
+	return result;
+}
+
+static int deregister_memory(void)
+{
+	int i;
+
+	if (atomic64_read(&acdb_data.mem_len)) {
+		mutex_lock(&acdb_data.acdb_mutex);
+		atomic64_set(&acdb_data.mem_len, 0);
+
+		for (i = 0; i < MAX_VOCPROC_TYPES; i++) {
+			kfree(acdb_data.col_data[i]);
+			acdb_data.col_data[i] = NULL;
+		}
+		ion_unmap_kernel(acdb_data.ion_client, acdb_data.ion_handle);
+		ion_free(acdb_data.ion_client, acdb_data.ion_handle);
+		ion_client_destroy(acdb_data.ion_client);
+		mutex_unlock(&acdb_data.acdb_mutex);
+	}
+	return 0;
+}
+
+static int register_memory(void)
+{
+	int			result;
+	int			i;
+	unsigned long		paddr;
+	void                    *kvptr;
+	unsigned long		kvaddr;
+	unsigned long		mem_len;
+
+	mutex_lock(&acdb_data.acdb_mutex);
+	for (i = 0; i < MAX_VOCPROC_TYPES; i++) {
+		acdb_data.col_data[i] = kmalloc(MAX_COL_SIZE, GFP_KERNEL);
+		atomic_set(&acdb_data.vocproc_col_cal[i].cal_kvaddr,
+			(uint32_t)acdb_data.col_data[i]);
+	}
+
+	acdb_data.ion_client =
+		msm_ion_client_create(UINT_MAX, "audio_acdb_client");
+	if (IS_ERR_OR_NULL(acdb_data.ion_client)) {
+		pr_err("%s: Could not register ION client!!!\n", __func__);
+		result = PTR_ERR(acdb_data.ion_client);
+		goto err;
+	}
+
+	acdb_data.ion_handle = ion_import_dma_buf(acdb_data.ion_client,
+		atomic_read(&acdb_data.map_handle));
+	if (IS_ERR_OR_NULL(acdb_data.ion_handle)) {
+		pr_err("%s: Could not import map handle!!!\n", __func__);
+		result = PTR_ERR(acdb_data.ion_handle);
+		goto err_ion_client;
+	}
+
+	result = ion_phys(acdb_data.ion_client, acdb_data.ion_handle,
+				&paddr, (size_t *)&mem_len);
+	if (result != 0) {
+		pr_err("%s: Could not get phys addr!!!\n", __func__);
+		goto err_ion_handle;
+	}
+
+	kvptr = ion_map_kernel(acdb_data.ion_client,
+		acdb_data.ion_handle);
+	if (IS_ERR_OR_NULL(kvptr)) {
+		pr_err("%s: Could not get kernel virt addr!!!\n", __func__);
+		result = PTR_ERR(kvptr);
+		goto err_ion_handle;
+	}
+	kvaddr = (unsigned long)kvptr;
+	atomic64_set(&acdb_data.paddr, paddr);
+	atomic64_set(&acdb_data.kvaddr, kvaddr);
+	atomic64_set(&acdb_data.mem_len, mem_len);
+	mutex_unlock(&acdb_data.acdb_mutex);
+
+	pr_debug("%s done! paddr = 0x%lx, kvaddr = 0x%lx, len = x%lx\n",
+		 __func__,
+		(long)atomic64_read(&acdb_data.paddr),
+		(long)atomic64_read(&acdb_data.kvaddr),
+		(long)atomic64_read(&acdb_data.mem_len));
+
+	return result;
+err_ion_handle:
+	ion_free(acdb_data.ion_client, acdb_data.ion_handle);
+err_ion_client:
+	ion_client_destroy(acdb_data.ion_client);
+err:
+	atomic64_set(&acdb_data.mem_len, 0);
+	mutex_unlock(&acdb_data.acdb_mutex);
+	return result;
+}
+static long acdb_ioctl(struct file *f,
+		unsigned int cmd, unsigned long arg)
+{
+	int32_t			result = 0;
+	int32_t			size;
+	int32_t			map_fd;
+	uint32_t		topology;
+	uint32_t		data[MAX_IOCTL_DATA];
+	pr_debug("%s\n", __func__);
+
+	switch (cmd) {
+	case AUDIO_REGISTER_PMEM:
+		pr_debug("AUDIO_REGISTER_PMEM\n");
+		if (atomic_read(&acdb_data.mem_len)) {
+			deregister_memory();
+			pr_debug("Remove the existing memory\n");
+		}
+
+		if (copy_from_user(&map_fd, (void *)arg, sizeof(map_fd))) {
+			pr_err("%s: fail to copy memory handle!\n", __func__);
+			result = -EFAULT;
+		} else {
+			atomic_set(&acdb_data.map_handle, map_fd);
+			result = register_memory();
+		}
+		goto done;
+
+	case AUDIO_DEREGISTER_PMEM:
+		pr_debug("AUDIO_DEREGISTER_PMEM\n");
+		deregister_memory();
+		goto done;
+	case AUDIO_SET_VOICE_RX_TOPOLOGY:
+		if (copy_from_user(&topology, (void *)arg,
+				sizeof(topology))) {
+			pr_err("%s: fail to copy topology!\n", __func__);
+			result = -EFAULT;
+		}
+		store_voice_rx_topology(topology);
+		goto done;
+	case AUDIO_SET_VOICE_TX_TOPOLOGY:
+		if (copy_from_user(&topology, (void *)arg,
+				sizeof(topology))) {
+			pr_err("%s: fail to copy topology!\n", __func__);
+			result = -EFAULT;
+		}
+		store_voice_tx_topology(topology);
+		goto done;
+	case AUDIO_SET_ADM_RX_TOPOLOGY:
+		if (copy_from_user(&topology, (void *)arg,
+				sizeof(topology))) {
+			pr_err("%s: fail to copy topology!\n", __func__);
+			result = -EFAULT;
+		}
+		store_adm_rx_topology(topology);
+		goto done;
+	case AUDIO_SET_ADM_TX_TOPOLOGY:
+		if (copy_from_user(&topology, (void *)arg,
+				sizeof(topology))) {
+			pr_err("%s: fail to copy topology!\n", __func__);
+			result = -EFAULT;
+		}
+		store_adm_tx_topology(topology);
+		goto done;
+	case AUDIO_SET_ASM_TOPOLOGY:
+		if (copy_from_user(&topology, (void *)arg,
+				sizeof(topology))) {
+			pr_err("%s: fail to copy topology!\n", __func__);
+			result = -EFAULT;
+		}
+		store_asm_topology(topology);
+		goto done;
+	}
+
+	if (copy_from_user(&size, (void *) arg, sizeof(size))) {
+
+		result = -EFAULT;
+		goto done;
+	}
+
+	if (size <= 0) {
+		pr_err("%s: Invalid size sent to driver: %d\n",
+			__func__, size);
+		result = -EFAULT;
+		goto done;
+	}
+
+	switch (cmd) {
+	case AUDIO_SET_VOCPROC_COL_CAL:
+		store_voice_col_data(VOCPROC_CAL, size, (uint32_t *)arg);
+		goto done;
+	case AUDIO_SET_VOCSTRM_COL_CAL:
+		store_voice_col_data(VOCSTRM_CAL, size, (uint32_t *)arg);
+		goto done;
+	case AUDIO_SET_VOCVOL_COL_CAL:
+		store_voice_col_data(VOCVOL_CAL, size, (uint32_t *)arg);
+		goto done;
+	}
+
+	if (copy_from_user(data, (void *)(arg + sizeof(size)), size)) {
+
+		pr_err("%s: fail to copy table size %d\n", __func__, size);
+		result = -EFAULT;
+		goto done;
+	}
+
+	if (data == NULL) {
+		pr_err("%s: NULL pointer sent to driver!\n", __func__);
+		result = -EFAULT;
+		goto done;
+	}
+
+	if (size > sizeof(struct cal_block))
+		pr_err("%s: More cal data for ioctl 0x%x then expected, size received: %d\n",
+			__func__, cmd, size);
+
+	switch (cmd) {
+	case AUDIO_SET_AUDPROC_TX_CAL:
+		store_audproc_cal(TX_CAL, (struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_AUDPROC_RX_CAL:
+		store_audproc_cal(RX_CAL, (struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_AUDPROC_TX_STREAM_CAL:
+		store_audstrm_cal(TX_CAL, (struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_AUDPROC_RX_STREAM_CAL:
+		store_audstrm_cal(RX_CAL, (struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_AUDPROC_TX_VOL_CAL:
+		store_audvol_cal(TX_CAL, (struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_AUDPROC_RX_VOL_CAL:
+		store_audvol_cal(RX_CAL, (struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_AFE_TX_CAL:
+		store_afe_cal(TX_CAL, (struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_AFE_RX_CAL:
+		store_afe_cal(RX_CAL, (struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_VOCPROC_CAL:
+		store_vocproc_cal((struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_VOCPROC_STREAM_CAL:
+		store_vocstrm_cal((struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_VOCPROC_VOL_CAL:
+		store_vocvol_cal((struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_VOCPROC_DEV_CFG_CAL:
+		store_vocproc_dev_cfg_cal((struct cal_block *)data);
+		goto done;
+	case AUDIO_SET_SIDETONE_CAL:
+		store_sidetone_cal((struct sidetone_cal *)data);
+		goto done;
+	case AUDIO_SET_ANC_CAL:
+		store_anc_cal((struct cal_block *)data);
+		goto done;
+	default:
+		pr_err("ACDB=> ACDB ioctl not found!\n");
+	}
+
+done:
+	return result;
+}
+
+static int acdb_mmap(struct file *file, struct vm_area_struct *vma)
+{
+	int result = 0;
+	int size = vma->vm_end - vma->vm_start;
+
+	pr_debug("%s\n", __func__);
+
+	if (atomic64_read(&acdb_data.mem_len)) {
+		if (size <= atomic64_read(&acdb_data.mem_len)) {
+			vma->vm_page_prot = pgprot_noncached(
+						vma->vm_page_prot);
+			result = remap_pfn_range(vma,
+				vma->vm_start,
+				atomic64_read(&acdb_data.paddr) >> PAGE_SHIFT,
+				size,
+				vma->vm_page_prot);
+		} else {
+			pr_err("%s: Not enough memory!\n", __func__);
+			result = -ENOMEM;
+		}
+	} else {
+		pr_err("%s: memory is not allocated, yet!\n", __func__);
+		result = -ENODEV;
+	}
+
+	return result;
+}
+
+static int acdb_release(struct inode *inode, struct file *f)
+{
+	s32 result = 0;
+
+	atomic_dec(&usage_count);
+	atomic_read(&usage_count);
+
+	pr_debug("%s: ref count %d!\n", __func__,
+		atomic_read(&usage_count));
+
+	if (atomic_read(&usage_count) >= 1)
+		result = -EBUSY;
+	else
+		result = deregister_memory();
+
+	return result;
+}
+
+static const struct file_operations acdb_fops = {
+	.owner = THIS_MODULE,
+	.open = acdb_open,
+	.release = acdb_release,
+	.unlocked_ioctl = acdb_ioctl,
+	.mmap = acdb_mmap,
+};
+
+struct miscdevice acdb_misc = {
+	.minor	= MISC_DYNAMIC_MINOR,
+	.name	= "msm_acdb",
+	.fops	= &acdb_fops,
+};
+
+static int __init acdb_init(void)
+{
+	memset(&acdb_data, 0, sizeof(acdb_data));
+	mutex_init(&acdb_data.acdb_mutex);
+	atomic_set(&usage_count, 0);
+
+	return misc_register(&acdb_misc);
+}
+
+static void __exit acdb_exit(void)
+{
+}
+
+module_init(acdb_init);
+module_exit(acdb_exit);
+
+MODULE_DESCRIPTION("SoC QDSP6v2 Audio ACDB driver");
+MODULE_LICENSE("GPL v2");
diff --git a/sound/soc/msm/qdsp6v2/audio_acdb.h b/sound/soc/msm/qdsp6v2/audio_acdb.h
new file mode 100644
index 0000000..c31823b
--- /dev/null
+++ b/sound/soc/msm/qdsp6v2/audio_acdb.h
@@ -0,0 +1,63 @@
+/* Copyright (c) 2010-2013, The Linux Foundation. All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 and
+ * only version 2 as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ */
+#ifndef _AUDIO_ACDB_H
+#define _AUDIO_ACDB_H
+
+#include <linux/msm_audio_acdb.h>
+#include <sound/q6adm-v2.h>
+
+enum {
+	RX_CAL,
+	TX_CAL,
+	MAX_AUDPROC_TYPES
+};
+
+enum {
+	VOCPROC_CAL,
+	VOCSTRM_CAL,
+	VOCVOL_CAL,
+	MAX_VOCPROC_TYPES
+};
+
+struct acdb_cal_block {
+	uint32_t		cal_size;
+	uint32_t		cal_kvaddr;
+	uint32_t		cal_paddr;
+};
+
+struct acdb_atomic_cal_block {
+	atomic_t		cal_size;
+	atomic_t		cal_kvaddr;
+	atomic_t		cal_paddr;
+};
+
+uint32_t get_voice_rx_topology(void);
+uint32_t get_voice_tx_topology(void);
+uint32_t get_adm_rx_topology(void);
+uint32_t get_adm_tx_topology(void);
+uint32_t get_asm_topology(void);
+void get_voice_cal_allocation(struct acdb_cal_block *cal_block);
+void get_anc_cal(struct acdb_cal_block *cal_block);
+void get_afe_cal(int32_t path, struct acdb_cal_block *cal_block);
+void get_audproc_cal(int32_t path, struct acdb_cal_block *cal_block);
+void get_audstrm_cal(int32_t path, struct acdb_cal_block *cal_block);
+void get_audvol_cal(int32_t path, struct acdb_cal_block *cal_block);
+void get_voice_col_data(uint32_t vocproc_type,
+	struct acdb_cal_block *cal_block);
+void get_vocproc_dev_cfg_cal(struct acdb_cal_block *cal_block);
+void get_vocproc_cal(struct acdb_cal_block *cal_block);
+void get_vocstrm_cal(struct acdb_cal_block *cal_block);
+void get_vocvol_cal(struct acdb_cal_block *cal_block);
+void get_sidetone_cal(struct sidetone_cal *cal_data);
+
+#endif
diff --git a/sound/soc/msm/qdsp6v2/q6adm.c b/sound/soc/msm/qdsp6v2/q6adm.c
index 1e0ad9e..660e6a8 100644
--- a/sound/soc/msm/qdsp6v2/q6adm.c
+++ b/sound/soc/msm/qdsp6v2/q6adm.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -18,7 +18,6 @@
 #include <linux/atomic.h>
 #include <linux/wait.h>
 
-#include <mach/qdsp6v2/audio_acdb.h>
 #include <mach/qdsp6v2/rtac.h>
 
 #include <sound/apr_audio-v2.h>
@@ -27,6 +26,9 @@
 #include <sound/q6audio-v2.h>
 #include <sound/q6afe-v2.h>
 
+#include "audio_acdb.h"
+
+
 #define TIMEOUT_MS 1000
 
 #define RESET_COPP_ID 99
diff --git a/sound/soc/msm/qdsp6v2/q6afe.c b/sound/soc/msm/qdsp6v2/q6afe.c
index d836610..846c80e 100644
--- a/sound/soc/msm/qdsp6v2/q6afe.c
+++ b/sound/soc/msm/qdsp6v2/q6afe.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -19,12 +19,12 @@
 #include <linux/jiffies.h>
 #include <linux/sched.h>
 #include <linux/msm_ion.h>
-#include <mach/qdsp6v2/audio_acdb.h>
 #include <sound/apr_audio-v2.h>
 #include <sound/q6afe-v2.h>
-
 #include <sound/q6audio-v2.h>
 
+#include "audio_acdb.h"
+
 
 struct afe_ctl {
 	void *apr;
@@ -2019,6 +2019,175 @@
 	return ret;
 }
 
+int afe_set_lpass_clock(u16 port_id, struct afe_clk_cfg *cfg)
+{
+	struct afe_lpass_clk_config_command clk_cfg;
+	int index = 0;
+	int ret = 0;
+
+	if (!cfg) {
+		pr_err("%s: clock cfg is NULL\n", __func__);
+		ret = -EINVAL;
+		return ret;
+	}
+	index = q6audio_get_port_index(port_id);
+	if (q6audio_is_digital_pcm_interface(port_id) < 0)
+		return -EINVAL;
+
+	ret = afe_q6_interface_prepare();
+	if (ret != 0)
+		return ret;
+
+	clk_cfg.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
+				APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
+	clk_cfg.hdr.pkt_size = sizeof(clk_cfg);
+	clk_cfg.hdr.src_port = 0;
+	clk_cfg.hdr.dest_port = 0;
+	clk_cfg.hdr.token = index;
+
+	clk_cfg.hdr.opcode = AFE_PORT_CMD_SET_PARAM_V2;
+	clk_cfg.param.port_id = q6audio_get_port_id(port_id);
+	clk_cfg.param.payload_size = sizeof(clk_cfg) - sizeof(struct apr_hdr)
+						- sizeof(clk_cfg.param);
+	clk_cfg.param.payload_address_lsw = 0x00;
+	clk_cfg.param.payload_address_msw = 0x00;
+	clk_cfg.param.mem_map_handle = 0x00;
+	clk_cfg.pdata.module_id = AFE_MODULE_AUDIO_DEV_INTERFACE;
+	clk_cfg.pdata.param_id = AFE_PARAM_ID_LPAIF_CLK_CONFIG;
+	clk_cfg.pdata.param_size =  sizeof(clk_cfg.clk_cfg);
+	clk_cfg.clk_cfg = *cfg;
+
+	pr_debug("%s: Minor version =%x clk val1 = %d\n"
+		 "clk val2 = %d, clk src = %x\n"
+		 "clk root = %x clk mode = %x resrv = %x\n"
+		 "port id = %x\n",
+		 __func__, cfg->i2s_cfg_minor_version,
+		 cfg->clk_val1, cfg->clk_val2, cfg->clk_src,
+		 cfg->clk_root, cfg->clk_set_mode,
+		 cfg->reserved, q6audio_get_port_id(port_id));
+
+	atomic_set(&this_afe.state, 1);
+	atomic_set(&this_afe.status, 0);
+	ret = apr_send_pkt(this_afe.apr, (uint32_t *) &clk_cfg);
+	if (ret < 0) {
+		pr_err("%s: AFE enable for port %d\n",
+		       __func__, port_id);
+		ret = -EINVAL;
+		goto fail_cmd;
+	}
+
+	ret = wait_event_timeout(this_afe.wait[index],
+			(atomic_read(&this_afe.state) == 0),
+			msecs_to_jiffies(TIMEOUT_MS));
+	if (!ret) {
+		pr_err("%s: wait_event timeout\n", __func__);
+		ret = -EINVAL;
+		goto fail_cmd;
+	}
+	if (atomic_read(&this_afe.status) != 0) {
+		pr_err("%s: config cmd failed\n", __func__);
+		ret = -EINVAL;
+		goto fail_cmd;
+	}
+
+fail_cmd:
+	return ret;
+}
+
+int afe_set_lpass_internal_digital_codec_clock(u16 port_id,
+			struct afe_digital_clk_cfg *cfg)
+{
+	struct afe_lpass_digital_clk_config_command clk_cfg;
+	int index = 0;
+	int ret = 0;
+
+	if (!cfg) {
+		pr_err("%s: clock cfg is NULL\n", __func__);
+		ret = -EINVAL;
+		return ret;
+	}
+	index = q6audio_get_port_index(port_id);
+	if (q6audio_is_digital_pcm_interface(port_id) < 0)
+		return -EINVAL;
+
+	ret = afe_q6_interface_prepare();
+	if (ret != 0)
+		return ret;
+
+	clk_cfg.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
+				APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
+	clk_cfg.hdr.pkt_size = sizeof(clk_cfg);
+	clk_cfg.hdr.src_port = 0;
+	clk_cfg.hdr.dest_port = 0;
+	clk_cfg.hdr.token = index;
+
+	clk_cfg.hdr.opcode = AFE_PORT_CMD_SET_PARAM_V2;
+	clk_cfg.param.port_id = q6audio_get_port_id(port_id);
+	clk_cfg.param.payload_size = sizeof(clk_cfg) - sizeof(struct apr_hdr)
+						- sizeof(clk_cfg.param);
+	clk_cfg.param.payload_address_lsw = 0x00;
+	clk_cfg.param.payload_address_msw = 0x00;
+	clk_cfg.param.mem_map_handle = 0x00;
+	clk_cfg.pdata.module_id = AFE_MODULE_AUDIO_DEV_INTERFACE;
+	clk_cfg.pdata.param_id = AFE_PARAM_ID_INTERNAL_DIGIATL_CDC_CLK_CONFIG;
+	clk_cfg.pdata.param_size =  sizeof(clk_cfg.clk_cfg);
+	clk_cfg.clk_cfg = *cfg;
+
+	pr_debug("%s: Minor version =%x clk val = %d\n"
+		 "clk root = %x resrv = %x port id = %x\n",
+		 __func__, cfg->i2s_cfg_minor_version,
+		 cfg->clk_val, cfg->clk_root, cfg->reserved,
+		 q6audio_get_port_id(port_id));
+
+	atomic_set(&this_afe.state, 1);
+	atomic_set(&this_afe.status, 0);
+	ret = apr_send_pkt(this_afe.apr, (uint32_t *) &clk_cfg);
+	if (ret < 0) {
+		pr_err("%s: AFE enable for port %d\n",
+		       __func__, port_id);
+		ret = -EINVAL;
+		goto fail_cmd;
+	}
+
+	ret = wait_event_timeout(this_afe.wait[index],
+			(atomic_read(&this_afe.state) == 0),
+			msecs_to_jiffies(TIMEOUT_MS));
+	if (!ret) {
+		pr_err("%s: wait_event timeout\n", __func__);
+		ret = -EINVAL;
+		goto fail_cmd;
+	}
+	if (atomic_read(&this_afe.status) != 0) {
+		pr_err("%s: config cmd failed\n", __func__);
+		ret = -EINVAL;
+		goto fail_cmd;
+	}
+
+fail_cmd:
+	return ret;
+}
+
+int q6afe_check_osr_clk_freq(u32 freq)
+{
+	int ret = 0;
+	switch (freq) {
+	case Q6AFE_LPASS_OSR_CLK_12_P288_MHZ:
+	case Q6AFE_LPASS_OSR_CLK_8_P192_MHZ:
+	case Q6AFE_LPASS_OSR_CLK_6_P144_MHZ:
+	case Q6AFE_LPASS_OSR_CLK_4_P096_MHZ:
+	case Q6AFE_LPASS_OSR_CLK_3_P072_MHZ:
+	case Q6AFE_LPASS_OSR_CLK_2_P048_MHZ:
+	case Q6AFE_LPASS_OSR_CLK_1_P536_MHZ:
+	case Q6AFE_LPASS_OSR_CLK_1_P024_MHZ:
+	case Q6AFE_LPASS_OSR_CLK_768_kHZ:
+	case Q6AFE_LPASS_OSR_CLK_512_kHZ:
+		break;
+	default:
+		ret = -EINVAL;
+	}
+	return ret;
+}
+
 static int __init afe_init(void)
 {
 	int i = 0;
diff --git a/sound/soc/msm/qdsp6v2/q6asm.c b/sound/soc/msm/qdsp6v2/q6asm.c
index 0cbd136..8d579c6 100644
--- a/sound/soc/msm/qdsp6v2/q6asm.c
+++ b/sound/soc/msm/qdsp6v2/q6asm.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+ * Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  * Author: Brian Swetland <swetland@google.com>
  *
  * This software is licensed under the terms of the GNU General Public
@@ -34,13 +34,15 @@
 
 #include <mach/memory.h>
 #include <mach/debug_mm.h>
-#include <mach/qdsp6v2/audio_acdb.h>
 #include <mach/qdsp6v2/rtac.h>
 #include <mach/msm_subsystem_map.h>
 
 #include <sound/apr_audio-v2.h>
 #include <sound/q6asm-v2.h>
 
+#include "audio_acdb.h"
+
+
 #define TRUE        0x01
 #define FALSE       0x00
 #define READDONE_IDX_STATUS 0
diff --git a/sound/soc/msm/qdsp6v2/q6audio-v2.c b/sound/soc/msm/qdsp6v2/q6audio-v2.c
index 5e2e618..985a33d 100644
--- a/sound/soc/msm/qdsp6v2/q6audio-v2.c
+++ b/sound/soc/msm/qdsp6v2/q6audio-v2.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -123,6 +123,31 @@
 	return ret;
 }
 
+int q6audio_is_digital_pcm_interface(u16 port_id)
+{
+	int ret = 0;
+
+	switch (port_id) {
+	case PRIMARY_I2S_RX:
+	case PRIMARY_I2S_TX:
+	case PCM_RX:
+	case PCM_TX:
+	case SECONDARY_I2S_RX:
+	case SECONDARY_I2S_TX:
+	case MI2S_RX:
+	case MI2S_TX:
+	case AFE_PORT_ID_TERTIARY_MI2S_TX:
+	case AFE_PORT_ID_TERTIARY_MI2S_RX:
+	case AFE_PORT_ID_QUATERNARY_MI2S_RX:
+	case AFE_PORT_ID_QUATERNARY_MI2S_TX:
+		break;
+	default:
+		ret = -EINVAL;
+	}
+
+	return ret;
+}
+
 int q6audio_validate_port(u16 port_id)
 {
 	int ret;
diff --git a/sound/soc/msm/qdsp6v2/q6voice.c b/sound/soc/msm/qdsp6v2/q6voice.c
index 349fcf2..63741ec 100644
--- a/sound/soc/msm/qdsp6v2/q6voice.c
+++ b/sound/soc/msm/qdsp6v2/q6voice.c
@@ -1,4 +1,4 @@
-/*  Copyright (c) 2012, The Linux Foundation. All rights reserved.
+/*  Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -18,7 +18,6 @@
 #include <linux/mutex.h>
 
 #include <asm/mach-types.h>
-#include <mach/qdsp6v2/audio_acdb.h>
 #include <mach/qdsp6v2/rtac.h>
 #include <mach/socinfo.h>
 #include <mach/qdsp6v2/apr_tal.h>
@@ -26,8 +25,10 @@
 #include "sound/apr_audio-v2.h"
 #include "sound/q6afe-v2.h"
 
+#include "audio_acdb.h"
 #include "q6voice.h"
 
+
 #define TIMEOUT_MS 200
 
 
@@ -1456,7 +1457,7 @@
 		goto fail;
 	}
 
-	get_all_vocstrm_cal(&cal_block);
+	get_vocstrm_cal(&cal_block);
 	if (cal_block.cal_size == 0) {
 		pr_err("%s: CVS cal size is 0\n", __func__);
 
@@ -1524,7 +1525,7 @@
 		goto fail;
 	}
 
-	get_all_vocstrm_cal(&cal_block);
+	get_vocstrm_cal(&cal_block);
 	if (cal_block.cal_size == 0)
 		return 0;
 
@@ -1714,7 +1715,7 @@
 		goto fail;
 	}
 
-	get_all_vocproc_cal(&cal_block);
+	get_vocproc_cal(&cal_block);
 	if (cal_block.cal_size == 0) {
 		pr_err("%s: CVP cal size is 0\n", __func__);
 
@@ -1782,7 +1783,7 @@
 		goto fail;
 	}
 
-	get_all_vocproc_cal(&cal_block);
+	get_vocproc_cal(&cal_block);
 	if (cal_block.cal_size == 0)
 		return 0;
 
@@ -1843,7 +1844,7 @@
 		goto fail;
 	}
 
-	get_all_vocvol_cal(&cal_block);
+	get_vocvol_cal(&cal_block);
 	if (cal_block.cal_size == 0) {
 		pr_err("%s: CVP vol cal size is 0\n", __func__);
 
@@ -1914,7 +1915,7 @@
 		goto fail;
 	}
 
-	get_all_vocvol_cal(&cal_block);
+	get_vocvol_cal(&cal_block);
 	if (cal_block.cal_size == 0)
 		return 0;
 
diff --git a/arch/arm/mach-msm/qdsp6v2/rtac_v2.c b/sound/soc/msm/qdsp6v2/rtac.c
similarity index 98%
rename from arch/arm/mach-msm/qdsp6v2/rtac_v2.c
rename to sound/soc/msm/qdsp6v2/rtac.c
index 409d796..1f2a487 100644
--- a/arch/arm/mach-msm/qdsp6v2/rtac_v2.c
+++ b/sound/soc/msm/qdsp6v2/rtac.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012, Code Aurora Forum. All rights reserved.
+/* Copyright (c) 2012-2013, The Linux Foundation. All rights reserved.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 and
@@ -19,13 +19,15 @@
 #include <linux/mutex.h>
 #include <linux/sched.h>
 #include <linux/msm_audio_acdb.h>
-#include <asm/atomic.h>
-#include <mach/qdsp6v2/audio_acdb.h>
+#include <linux/atomic.h>
 #include <mach/qdsp6v2/rtac.h>
-#include "q6audio_common.h"
+#include <sound/q6asm-v2.h>
 #include <sound/q6afe-v2.h>
 #include <sound/apr_audio-v2.h>
 
+#include "audio_acdb.h"
+
+
 #ifndef CONFIG_RTAC
 
 void rtac_add_adm_device(u32 port_id, u32 copp_id, u32 path_id, u32 popp_id) {}
@@ -1041,7 +1043,7 @@
 
 module_init(rtac_init);
 
-MODULE_DESCRIPTION("MSM 8x60 Real-Time Audio Calibration driver");
+MODULE_DESCRIPTION("SoC QDSP6v2 Real-Time Audio Calibration driver");
 MODULE_LICENSE("GPL v2");
 
 #endif