Merge "lib: heap: Fixed compilation warning related to unused variable."
diff --git a/app/aboot/aboot.c b/app/aboot/aboot.c
index 74e17e0..4407631 100644
--- a/app/aboot/aboot.c
+++ b/app/aboot/aboot.c
@@ -3166,6 +3166,7 @@
 	struct ptentry *ptn;
 	struct ptable *ptable;
 	unsigned extra = 0;
+	uint64_t partition_size = 0;
 
 	ptable = flash_get_ptable();
 	if (ptable == NULL) {
@@ -3197,6 +3198,17 @@
 	else
 		sz = ROUND_TO_PAGE(sz, page_mask);
 
+	partition_size = (uint64_t)ptn->length * (uint64_t)flash_num_pages_per_blk() *  (uint64_t)flash_page_size();
+	if (partition_size > UINT_MAX) {
+		fastboot_fail("Invalid partition size");
+		return;
+	}
+
+	if (sz > partition_size) {
+		fastboot_fail("Image size too large");
+		return;
+	}
+
 	dprintf(INFO, "writing %d bytes to '%s'\n", sz, ptn->name);
 	if (!memcmp((void *)data, UBI_MAGIC, UBI_MAGIC_SIZE)) {
 		if (flash_ubi_img(ptn, data, sz)) {
diff --git a/include/dev/flash.h b/include/dev/flash.h
index 9c41561..f908db8 100644
--- a/include/dev/flash.h
+++ b/include/dev/flash.h
@@ -77,6 +77,8 @@
 {
 	return flash_read_ext(ptn, 0, offset, data, bytes);
 }
+
+unsigned flash_num_pages_per_blk(void);
 unsigned flash_page_size(void);
 unsigned flash_block_size(void);
 unsigned flash_spare_size(void);
diff --git a/include/target.h b/include/target.h
index e0a0264..d0d830d 100644
--- a/include/target.h
+++ b/include/target.h
@@ -70,6 +70,7 @@
 
 const char * target_usb_controller();
 void target_usb_phy_reset(void);
+void target_usb_phy_sec_reset(void);
 void target_usb_phy_mux_configure(void);
 target_usb_iface_t * target_usb30_init();
 bool target_is_cdp_qvga();
diff --git a/platform/msm8996/acpuclock.c b/platform/msm8996/acpuclock.c
index 7ed7ff6..5d2e7eb 100644
--- a/platform/msm8996/acpuclock.c
+++ b/platform/msm8996/acpuclock.c
@@ -208,6 +208,40 @@
 	writel(reg, GCC_USB30_GDSCR);
 }
 
+/* enables usb20 clocks */
+void clock_usb20_init(void)
+{
+	int ret;
+
+	ret = clk_get_set_enable("usb20_noc_usb20_clk", 0, true);
+	if(ret)
+	{
+		dprintf(CRITICAL, "failed to set usb20_noc_clk. ret = %d\n", ret);
+		ASSERT(0);
+	}
+
+	ret = clk_get_set_enable("usb20_master_clk", 120000000, true);
+	if(ret)
+	{
+		dprintf(CRITICAL, "failed to set usb20_master_clk. ret = %d\n", ret);
+		ASSERT(0);
+	}
+
+	ret = clk_get_set_enable("usb20_mock_utmi_clk", 60000000, true);
+	if(ret)
+	{
+		dprintf(CRITICAL, "failed to set usb20_mock_utmi_clk ret = %d\n", ret);
+		ASSERT(0);
+	}
+
+	ret = clk_get_set_enable("usb20_sleep_clk", 0, true);
+	if(ret)
+	{
+		dprintf(CRITICAL, "failed to set usb2_sleep_clk ret = %d\n", ret);
+		ASSERT(0);
+	}
+}
+
 /* enables usb30 clocks */
 void clock_usb30_init(void)
 {
diff --git a/platform/msm8996/include/platform/clock.h b/platform/msm8996/include/platform/clock.h
index 01a551e..6ff55e2 100644
--- a/platform/msm8996/include/platform/clock.h
+++ b/platform/msm8996/include/platform/clock.h
@@ -111,6 +111,7 @@
 void clock_ce_enable(uint8_t instance);
 void clock_ce_disable(uint8_t instance);
 void clock_usb30_init(void);
+void clock_usb20_init(void);
 void clock_reset_usb_phy();
 
 void mmss_dsi_clock_enable(uint32_t cfg_rcgr, uint32_t dual_dsi);
diff --git a/platform/msm8996/include/platform/iomap.h b/platform/msm8996/include/platform/iomap.h
index 2fb9c8a..42ef8a7 100644
--- a/platform/msm8996/include/platform/iomap.h
+++ b/platform/msm8996/include/platform/iomap.h
@@ -75,15 +75,33 @@
 #define GCC_BLSP2_QUP2_CFG_RCGR     (CLK_CTL_BASE + 0x28010)
 #define GCC_BLSP2_QUP2_CMD_RCGR     (CLK_CTL_BASE + 0x2800C)
 
+/* USB platform specific bases*/
+unsigned int usb_ctrl_base();
+unsigned int usb_qscratch_base();
+unsigned int usb_phy_base();
+unsigned int usb_phy_bcr();
+
+#define MSM_USB30_BASE              (usb_ctrl_base())
+#define MSM_USB30_QSCRATCH_BASE     (usb_qscratch_base())
+#define QUSB2_PHY_BASE              (usb_phy_base())
+#define GCC_QUSB2_PHY_BCR           (usb_phy_bcr())
+
 /* USB3.0 */
-#define MSM_USB30_BASE              0x6A00000
-#define MSM_USB30_QSCRATCH_BASE     0x6AF8800
+#define MSM_USB30_PRIM_BASE              0x6A00000
+#define MSM_USB30_QSCRATCH_PRIM_BASE     0x6AF8800
+/* USB2.0 */
+#define MSM_USB20_SEC_BASE              0x7600000
+#define MSM_USB20_SEC_QSCRATCH_BASE     0x76F8800
 /* SS QMP (Qulacomm Multi Protocol) */
 #define QMP_PHY_BASE                0x7410000
 
-/* QUSB2 PHY */
-#define QUSB2_PHY_BASE              0x7411000
-#define GCC_QUSB2_PHY_BCR           (CLK_CTL_BASE + 0x00012038)
+/* QUSB2 PHY primary */
+#define QUSB2_PRIM_PHY_BASE              0x7411000
+#define GCC_QUSB2_PRIM_PHY_BCR           (CLK_CTL_BASE + 0x00012038)
+
+/* QUSB2 PHY secondary */
+#define QUSB2_SEC_PHY_BASE              0x7412000
+#define GCC_QUSB2_SEC_PHY_BCR           (CLK_CTL_BASE + 0x0001203C)
 
 #define AHB2_PHY_BASE               0x7416000
 #define PERIPH_SS_AHB2PHY_TOP_CFG   (AHB2_PHY_BASE + 0x10)
@@ -138,6 +156,20 @@
 #define USB_PHY_CFG_AHB2PHY_CBCR    (CLK_CTL_BASE + 0x6A004)
 #define GCC_AGGRE2_USB3_AXI_CBCR    (CLK_CTL_BASE + 0x83018)
 
+/* USB20 clocks */
+#define USB_20_BCR                  (CLK_CTL_BASE + 0x12000)
+#define USB20_MASTER_CBCR           (CLK_CTL_BASE + 0x12004)
+#define USB20_SLEEP_CBCR            (CLK_CTL_BASE + 0x12008)
+#define USB20_MOCK_UTMI_CBCR        (CLK_CTL_BASE + 0x1200C)
+#define USB20_MASTER_CMD_RCGR       (CLK_CTL_BASE + 0x12010)
+#define USB20_MASTER_CFG_RCGR       (CLK_CTL_BASE + 0x12014)
+#define USB20_MASTER_M              (CLK_CTL_BASE + 0x12018)
+#define USB20_MASTER_N              (CLK_CTL_BASE + 0x1201c)
+#define USB20_MASTER_D              (CLK_CTL_BASE + 0x12020)
+#define USB20_MOCK_UTMI_CMD_RCGR    (CLK_CTL_BASE + 0x12024)
+#define USB20_MOCK_UTMI_CFG_RCGR    (CLK_CTL_BASE + 0x12028)
+#define PERIPH_NOC_USB20_AHB_CBCR   (CLK_CTL_BASE + 0x06010)
+
 /* SDCC */
 #define SDCC1_BCR                   (CLK_CTL_BASE + 0x13000) /* block reset */
 #define SDCC1_APPS_CBCR             (CLK_CTL_BASE + 0x13004) /* branch control */
@@ -209,7 +241,7 @@
  * as device memory, define the start address
  * and size in MB
  */
-#define RPMB_SND_RCV_BUF            0x91A00000
+#define RPMB_SND_RCV_BUF            0x91C00000
 #define RPMB_SND_RCV_BUF_SZ         0x2
 
 #define TCSR_BOOT_MISC_DETECT       0x007B3000
diff --git a/platform/msm8996/include/platform/irqs.h b/platform/msm8996/include/platform/irqs.h
index 61d267b..e5cc23d 100644
--- a/platform/msm8996/include/platform/irqs.h
+++ b/platform/msm8996/include/platform/irqs.h
@@ -45,7 +45,13 @@
 
 #define INT_QTMR_FRM_0_PHYSICAL_TIMER_EXP      (GIC_SPI_START + 31)
 
-#define USB30_EE1_IRQ                          (GIC_SPI_START + 131)
+/* to support secondary port usage, secondary port Interrupt*/
+int usb_irq();
+
+#define USB30_EE1_IRQ  			   (usb_irq())
+
+#define USB30_IRQ                          (GIC_SPI_START + 131)
+#define USB20_IRQ                          (GIC_SPI_START + 138)
 
 #define GLINK_IPC_IRQ                          (GIC_SPI_START + 168)
 
diff --git a/platform/msm8996/msm8996-clock.c b/platform/msm8996/msm8996-clock.c
index 782a624..8a02900 100644
--- a/platform/msm8996/msm8996-clock.c
+++ b/platform/msm8996/msm8996-clock.c
@@ -335,6 +335,16 @@
 	},
 };
 
+static struct branch_clk gcc_periph_noc_usb20_ahb_clk = {
+	.cbcr_reg    = (uint32_t *) PERIPH_NOC_USB20_AHB_CBCR,
+	.has_sibling = 1,
+
+	.c = {
+		.dbg_name = "periph_noc_usb20_ahb_clk",
+		.ops      = &clk_ops_branch,
+	},
+};
+
 static struct clk_freq_tbl ftbl_gcc_usb30_master_clk[] = {
 	F(  19200000, cxo,    1,    0,    0),
 	F( 120000000, gpll0,    5,    0,    0),
@@ -342,6 +352,13 @@
 	F_END
 };
 
+static struct clk_freq_tbl ftbl_gcc_usb20_master_clk[] = {
+	F(  19200000, cxo,    1,    0,    0),
+	F( 120000000, gpll0,    5,    0,    0),
+	F( 150000000, gpll0,    4,    0,    0),
+	F_END
+};
+
 static struct rcg_clk usb30_master_clk_src = {
 	.cmd_reg      = (uint32_t *) USB30_MASTER_CMD_RCGR,
 	.cfg_reg      = (uint32_t *) USB30_MASTER_CFG_RCGR,
@@ -359,6 +376,23 @@
 	},
 };
 
+static struct rcg_clk usb20_master_clk_src = {
+	.cmd_reg      = (uint32_t *) USB20_MASTER_CMD_RCGR,
+	.cfg_reg      = (uint32_t *) USB20_MASTER_CFG_RCGR,
+	.m_reg        = (uint32_t *) USB20_MASTER_M,
+	.n_reg        = (uint32_t *) USB20_MASTER_N,
+	.d_reg        = (uint32_t *) USB20_MASTER_D,
+
+	.set_rate     = clock_lib2_rcg_set_rate_mnd,
+	.freq_tbl     = ftbl_gcc_usb20_master_clk,
+	.current_freq = &rcg_dummy_freq,
+
+	.c = {
+		.dbg_name = "usb20_master_clk_src",
+		.ops      = &clk_ops_rcg,
+	},
+};
+
 static struct branch_clk gcc_usb30_master_clk = {
 	.cbcr_reg = (uint32_t *) USB30_MASTER_CBCR,
 	.bcr_reg  = (uint32_t *) USB_30_BCR,
@@ -370,6 +404,17 @@
 	},
 };
 
+static struct branch_clk gcc_usb20_master_clk = {
+	.cbcr_reg = (uint32_t *) USB20_MASTER_CBCR,
+	.bcr_reg  = (uint32_t *) USB_20_BCR,
+	.parent   = &usb20_master_clk_src.c,
+
+	.c = {
+		.dbg_name = "usb20_master_clk",
+		.ops      = &clk_ops_branch,
+	},
+};
+
 static struct branch_clk gcc_aggre2_usb3_axi_clk = {
 	.cbcr_reg     = (uint32_t *) GCC_AGGRE2_USB3_AXI_CBCR,
 	.parent       = &usb30_master_clk_src.c,
@@ -385,6 +430,11 @@
 	F_END
 };
 
+static struct clk_freq_tbl ftbl_gcc_usb20_mock_utmi_clk_src[] = {
+	F(  60000000, gpll0,   10,    0,     0),
+	F_END
+};
+
 static struct rcg_clk usb30_mock_utmi_clk_src = {
 	.cmd_reg      = (uint32_t *) USB30_MOCK_UTMI_CMD_RCGR,
 	.cfg_reg      = (uint32_t *) USB30_MOCK_UTMI_CFG_RCGR,
@@ -398,6 +448,19 @@
 	},
 };
 
+static struct rcg_clk usb20_mock_utmi_clk_src = {
+	.cmd_reg      = (uint32_t *) USB20_MOCK_UTMI_CMD_RCGR,
+	.cfg_reg      = (uint32_t *) USB20_MOCK_UTMI_CFG_RCGR,
+	.set_rate     = clock_lib2_rcg_set_rate_hid,
+	.freq_tbl     = ftbl_gcc_usb20_mock_utmi_clk_src,
+	.current_freq = &rcg_dummy_freq,
+
+	.c = {
+		.dbg_name = "usb20_mock_utmi_clk_src",
+		.ops      = &clk_ops_rcg,
+	},
+};
+
 static struct branch_clk gcc_usb30_mock_utmi_clk = {
 	.cbcr_reg    = (uint32_t *) USB30_MOCK_UTMI_CBCR,
 	.has_sibling = 0,
@@ -409,6 +472,18 @@
 	},
 };
 
+static struct branch_clk gcc_usb20_mock_utmi_clk = {
+	.cbcr_reg    = (uint32_t *) USB20_MOCK_UTMI_CBCR,
+	.has_sibling = 0,
+	.parent      = &usb20_mock_utmi_clk_src.c,
+
+	.c = {
+		.dbg_name = "usb20_mock_utmi_clk",
+		.ops      = &clk_ops_branch,
+	},
+};
+
+
 static struct branch_clk gcc_usb30_sleep_clk = {
 	.cbcr_reg    = (uint32_t *) USB30_SLEEP_CBCR,
 	.has_sibling = 1,
@@ -419,6 +494,16 @@
 	},
 };
 
+static struct branch_clk gcc_usb20_sleep_clk = {
+	.cbcr_reg    = (uint32_t *) USB20_SLEEP_CBCR,
+	.has_sibling = 1,
+
+	.c = {
+		.dbg_name = "usb20_sleep_clk",
+		.ops      = &clk_ops_branch,
+	},
+};
+
 static struct clk_freq_tbl ftbl_gcc_usb30_phy_aux_clk_src[] = {
 	F(   1200000,         cxo,   16,    0,     0),
 	F_END
@@ -750,6 +835,12 @@
 
 	CLK_LOOKUP("usb_phy_cfg_ahb2phy_clk",     gcc_usb_phy_cfg_ahb2phy_clk.c),
 
+	/* USB20 clocks */
+	CLK_LOOKUP("usb20_noc_usb20_clk",     gcc_periph_noc_usb20_ahb_clk.c),
+	CLK_LOOKUP("usb20_master_clk",    gcc_usb20_master_clk.c),
+	CLK_LOOKUP("usb20_mock_utmi_clk", gcc_usb20_mock_utmi_clk.c),
+	CLK_LOOKUP("usb20_sleep_clk",     gcc_usb20_sleep_clk.c),
+
 	/* mdss clocks */
 	CLK_LOOKUP("mdss_mdp_clk",     mdss_mdp_clk.c),
 	CLK_LOOKUP("mdss_vsync_clk",       mdss_vsync_clk.c),
diff --git a/platform/msm8996/platform.c b/platform/msm8996/platform.c
index 79bf7c9..a3c2d3e 100644
--- a/platform/msm8996/platform.c
+++ b/platform/msm8996/platform.c
@@ -181,3 +181,46 @@
 
 	return false;
 }
+
+
+/* USB platform specific bases*/
+uint32_t usb_ctrl_base()
+{
+	if (board_hardware_id() == HW_PLATFORM_SBC)
+		return	MSM_USB20_SEC_BASE;
+	else
+		return	MSM_USB30_PRIM_BASE;
+
+}
+
+uint32_t usb_qscratch_base()
+{
+	if (board_hardware_id() == HW_PLATFORM_SBC)
+		return	MSM_USB20_SEC_QSCRATCH_BASE;
+	else
+		return	MSM_USB30_QSCRATCH_PRIM_BASE;
+}
+
+uint32_t usb_phy_base()
+{
+	if (board_hardware_id() == HW_PLATFORM_SBC)
+		return	QUSB2_SEC_PHY_BASE;
+	else
+		return	QUSB2_PRIM_PHY_BASE;
+}
+
+uint32_t usb_phy_bcr()
+{
+	if (board_hardware_id() == HW_PLATFORM_SBC)
+		return	GCC_QUSB2_SEC_PHY_BCR;
+	else
+		return	GCC_QUSB2_PRIM_PHY_BCR;
+}
+
+int usb_irq()
+{
+	if (board_hardware_id() == HW_PLATFORM_SBC)
+		return	USB20_IRQ;
+	else
+		return	USB30_IRQ;
+}
diff --git a/platform/msm_shared/qpic_nand.c b/platform/msm_shared/qpic_nand.c
index baba30d..3fec647 100644
--- a/platform/msm_shared/qpic_nand.c
+++ b/platform/msm_shared/qpic_nand.c
@@ -1378,6 +1378,12 @@
 }
 
 unsigned
+flash_num_pages_per_blk(void)
+{
+	return flash.num_pages_per_blk;
+}
+
+unsigned
 flash_spare_size(void)
 {
     return flash.spare_size;
diff --git a/target/msm8996/init.c b/target/msm8996/init.c
index 25c1b14..51051c9 100644
--- a/target/msm8996/init.c
+++ b/target/msm8996/init.c
@@ -500,6 +500,11 @@
 	qusb2_phy_reset();
 }
 
+void target_usb_phy_sec_reset()
+{
+	qusb2_phy_reset();
+}
+
 target_usb_iface_t* target_usb30_init()
 {
 	target_usb_iface_t *t_usb_iface;
@@ -507,9 +512,20 @@
 	t_usb_iface = calloc(1, sizeof(target_usb_iface_t));
 	ASSERT(t_usb_iface);
 
-	t_usb_iface->phy_init   = usb30_qmp_phy_init;
-	t_usb_iface->phy_reset  = target_usb_phy_reset;
-	t_usb_iface->clock_init = clock_usb30_init;
+
+	/* for SBC we use secondary port */
+	if (board_hardware_id() == HW_PLATFORM_SBC)
+	{
+		/* secondary port have no QMP phy,use only QUSB2 phy that have only reset */
+		t_usb_iface->phy_init   = NULL;
+		t_usb_iface->phy_reset  = target_usb_phy_sec_reset;
+		t_usb_iface->clock_init = clock_usb20_init;
+	} else {
+		t_usb_iface->phy_init   = usb30_qmp_phy_init;
+		t_usb_iface->phy_reset  = target_usb_phy_reset;
+		t_usb_iface->clock_init = clock_usb30_init;
+	}
+
 	t_usb_iface->vbus_override = 1;
 
 	return t_usb_iface;
diff --git a/target/msm8996/rules.mk b/target/msm8996/rules.mk
index e59bfc2..c6918f7 100644
--- a/target/msm8996/rules.mk
+++ b/target/msm8996/rules.mk
@@ -8,13 +8,13 @@
 
 PLATFORM := msm8996
 
-MEMBASE := 0x91600000 # SDRAM
+MEMBASE := 0x91800000 # SDRAM
 MEMSIZE := 0x00400000 # 4MB
 
 BASE_ADDR    := 0x0000000
 
-SCRATCH_ADDR := 0x91C00000
-SCRATCH_SIZE := 740
+SCRATCH_ADDR := 0x91E00000
+SCRATCH_SIZE := 738
 KERNEL_ADDR  := 0x80000000
 KERNEL_SIZE  := 88