/* * Add HW recommended delays after toggling the software * reset bit off and back on.
*/
writel(DSI_28nm_PHY_PLL_TEST_CFG_PLL_SW_RESET, base + REG_DSI_28nm_PHY_PLL_TEST_CFG);
udelay(1);
writel(0, base + REG_DSI_28nm_PHY_PLL_TEST_CFG);
udelay(1);
}
/* Force postdiv2 to be div-4 */
writel(3, base + REG_DSI_28nm_PHY_PLL_POSTDIV2_CFG);
/* Configure the Loop filter resistance */ for (i = 0; i < LPFR_LUT_SIZE; i++) if (rate <= lpfr_lut[i].vco_rate) break; if (i == LPFR_LUT_SIZE) {
DRM_DEV_ERROR(dev, "unable to get loop filter resistance. vco=%lu\n",
rate); return -EINVAL;
}
writel(lpfr_lut[i].resistance, base + REG_DSI_28nm_PHY_PLL_LPFR_CFG);
/* Loop filter capacitance values : c1 and c2 */
writel(0x70, base + REG_DSI_28nm_PHY_PLL_LPFC1_CFG);
writel(0x15, base + REG_DSI_28nm_PHY_PLL_LPFC2_CFG);
writel(0x02, base + REG_DSI_28nm_PHY_PLL_CHGPUMP_CFG);
writel(0x2b, base + REG_DSI_28nm_PHY_PLL_CAL_CFG3);
writel(0x06, base + REG_DSI_28nm_PHY_PLL_CAL_CFG4);
writel(0x0d, base + REG_DSI_28nm_PHY_PLL_LKDET_CFG2);
writel(sdm_cfg1, base + REG_DSI_28nm_PHY_PLL_SDM_CFG1);
writel(DSI_28nm_PHY_PLL_SDM_CFG2_FREQ_SEED_7_0(sdm_cfg2),
base + REG_DSI_28nm_PHY_PLL_SDM_CFG2);
writel(DSI_28nm_PHY_PLL_SDM_CFG3_FREQ_SEED_15_8(sdm_cfg3),
base + REG_DSI_28nm_PHY_PLL_SDM_CFG3);
writel(0, base + REG_DSI_28nm_PHY_PLL_SDM_CFG4);
/* Add hardware recommended delay for correct PLL configuration */ if (pll_28nm->phy->cfg->quirks & DSI_PHY_28NM_QUIRK_PHY_LP)
udelay(1000); else
udelay(1);
writel(refclk_cfg, base + REG_DSI_28nm_PHY_PLL_REFCLK_CFG);
writel(0x00, base + REG_DSI_28nm_PHY_PLL_PWRGEN_CFG);
writel(0x31, base + REG_DSI_28nm_PHY_PLL_VCOLPF_CFG);
writel(sdm_cfg0, base + REG_DSI_28nm_PHY_PLL_SDM_CFG0);
writel(0x12, base + REG_DSI_28nm_PHY_PLL_CAL_CFG0);
writel(0x30, base + REG_DSI_28nm_PHY_PLL_CAL_CFG6);
writel(0x00, base + REG_DSI_28nm_PHY_PLL_CAL_CFG7);
writel(0x60, base + REG_DSI_28nm_PHY_PLL_CAL_CFG8);
writel(0x00, base + REG_DSI_28nm_PHY_PLL_CAL_CFG9);
writel(cal_cfg10 & 0xff, base + REG_DSI_28nm_PHY_PLL_CAL_CFG10);
writel(cal_cfg11 & 0xff, base + REG_DSI_28nm_PHY_PLL_CAL_CFG11);
writel(0x20, base + REG_DSI_28nm_PHY_PLL_EFUSE_CFG);
/* Check to see if the ref clk doubler is enabled */
doubler = readl(base + REG_DSI_28nm_PHY_PLL_REFCLK_CFG) &
DSI_28nm_PHY_PLL_REFCLK_CFG_DBLR;
ref_clk += (doubler * VCO_REF_CLK_RATE);
/* * PLL power up sequence. * Add necessary delays recommended by hardware.
*/
val = DSI_28nm_PHY_PLL_GLB_CFG_PLL_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(1);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_PWRGEN_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(200);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_LDO_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(500);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_ENABLE;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(600);
for (i = 0; i < 2; i++) { /* DSI Uniphy lock detect setting */
writel(0x0c, base + REG_DSI_28nm_PHY_PLL_LKDET_CFG2);
udelay(100);
writel(0x0d, base + REG_DSI_28nm_PHY_PLL_LKDET_CFG2);
/* poll for PLL ready status */
locked = pll_28nm_poll_for_ready(pll_28nm, max_reads,
timeout_us); if (locked) break;
pll_28nm_software_reset(pll_28nm);
/* * PLL power up sequence. * Add necessary delays recommended by hardware.
*/
val = DSI_28nm_PHY_PLL_GLB_CFG_PLL_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(1);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_PWRGEN_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(200);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_LDO_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(250);
val &= ~DSI_28nm_PHY_PLL_GLB_CFG_PLL_LDO_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(200);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_LDO_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(500);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_ENABLE;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(600);
}
/* * PLL power up sequence. * Add necessary delays recommended by hardware.
*/
writel(0x34, base + REG_DSI_28nm_PHY_PLL_CAL_CFG1);
val = DSI_28nm_PHY_PLL_GLB_CFG_PLL_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(200);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_PWRGEN_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(200);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_LDO_PWRDN_B;
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_ENABLE;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(600);
for (i = 0; i < 7; i++) { /* DSI Uniphy lock detect setting */
writel(0x0d, base + REG_DSI_28nm_PHY_PLL_LKDET_CFG2);
writel(0x0c, base + REG_DSI_28nm_PHY_PLL_LKDET_CFG2);
udelay(100);
writel(0x0d, base + REG_DSI_28nm_PHY_PLL_LKDET_CFG2);
/* poll for PLL ready status */
locked = pll_28nm_poll_for_ready(pll_28nm,
max_reads, timeout_us); if (locked) break;
pll_28nm_software_reset(pll_28nm);
/* * PLL power up sequence. * Add necessary delays recommended by hardware.
*/
writel(0x00, base + REG_DSI_28nm_PHY_PLL_PWRGEN_CFG);
udelay(50);
val = DSI_28nm_PHY_PLL_GLB_CFG_PLL_PWRDN_B;
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_PWRGEN_PWRDN_B;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(100);
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_LDO_PWRDN_B;
val |= DSI_28nm_PHY_PLL_GLB_CFG_PLL_ENABLE;
writel(val, base + REG_DSI_28nm_PHY_PLL_GLB_CFG);
udelay(600);
}
ret = dsi_pll_28nm_clk_set_rate(phy->vco_hw,
cached_state->vco_rate, 0); if (ret) {
DRM_DEV_ERROR(&pll_28nm->phy->pdev->dev, "restore vco rate failed. ret=%d\n", ret); return ret;
}
writel(cached_state->postdiv3, base + REG_DSI_28nm_PHY_PLL_POSTDIV3_CFG);
writel(cached_state->postdiv1, base + REG_DSI_28nm_PHY_PLL_POSTDIV1_CFG);
writel(cached_state->byte_mux, base + REG_DSI_28nm_PHY_PLL_VREG_CFG);
writel(DSI_28nm_PHY_TIMING_CTRL_0_CLK_ZERO(timing->clk_zero),
base + REG_DSI_28nm_PHY_TIMING_CTRL_0);
writel(DSI_28nm_PHY_TIMING_CTRL_1_CLK_TRAIL(timing->clk_trail),
base + REG_DSI_28nm_PHY_TIMING_CTRL_1);
writel(DSI_28nm_PHY_TIMING_CTRL_2_CLK_PREPARE(timing->clk_prepare),
base + REG_DSI_28nm_PHY_TIMING_CTRL_2); if (timing->clk_zero & BIT(8))
writel(DSI_28nm_PHY_TIMING_CTRL_3_CLK_ZERO_8,
base + REG_DSI_28nm_PHY_TIMING_CTRL_3);
writel(DSI_28nm_PHY_TIMING_CTRL_4_HS_EXIT(timing->hs_exit),
base + REG_DSI_28nm_PHY_TIMING_CTRL_4);
writel(DSI_28nm_PHY_TIMING_CTRL_5_HS_ZERO(timing->hs_zero),
base + REG_DSI_28nm_PHY_TIMING_CTRL_5);
writel(DSI_28nm_PHY_TIMING_CTRL_6_HS_PREPARE(timing->hs_prepare),
base + REG_DSI_28nm_PHY_TIMING_CTRL_6);
writel(DSI_28nm_PHY_TIMING_CTRL_7_HS_TRAIL(timing->hs_trail),
base + REG_DSI_28nm_PHY_TIMING_CTRL_7);
writel(DSI_28nm_PHY_TIMING_CTRL_8_HS_RQST(timing->hs_rqst),
base + REG_DSI_28nm_PHY_TIMING_CTRL_8);
writel(DSI_28nm_PHY_TIMING_CTRL_9_TA_GO(timing->ta_go) |
DSI_28nm_PHY_TIMING_CTRL_9_TA_SURE(timing->ta_sure),
base + REG_DSI_28nm_PHY_TIMING_CTRL_9);
writel(DSI_28nm_PHY_TIMING_CTRL_10_TA_GET(timing->ta_get),
base + REG_DSI_28nm_PHY_TIMING_CTRL_10);
writel(DSI_28nm_PHY_TIMING_CTRL_11_TRIG3_CMD(0),
base + REG_DSI_28nm_PHY_TIMING_CTRL_11);
}
writel(0x0, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_0);
writel(1, base + REG_DSI_28nm_PHY_REGULATOR_CAL_PWR_CFG);
writel(0, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_5);
writel(0, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_3);
writel(0x3, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_2);
writel(0x9, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_1);
writel(0x7, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_0);
writel(0x20, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_4);
writel(0x00, phy->base + REG_DSI_28nm_PHY_LDO_CNTRL);
}
writel(0x0, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_0);
writel(0, base + REG_DSI_28nm_PHY_REGULATOR_CAL_PWR_CFG);
writel(0x7, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_5);
writel(0, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_3);
writel(0x1, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_2);
writel(0x1, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_1);
writel(0x20, base + REG_DSI_28nm_PHY_REGULATOR_CTRL_4);
writel(0x00, base + REG_DSI_28nm_PHY_CTRL_1);
writel(0x5f, base + REG_DSI_28nm_PHY_CTRL_0);
writel(0x6, base + REG_DSI_28nm_PHY_STRENGTH_1);
for (i = 0; i < 4; i++) {
writel(0, base + REG_DSI_28nm_PHY_LN_CFG_0(i));
writel(0, base + REG_DSI_28nm_PHY_LN_CFG_1(i));
writel(0, base + REG_DSI_28nm_PHY_LN_CFG_2(i));
writel(0, base + REG_DSI_28nm_PHY_LN_CFG_3(i));
writel(0, base + REG_DSI_28nm_PHY_LN_CFG_4(i));
writel(0, base + REG_DSI_28nm_PHY_LN_TEST_DATAPATH(i));
writel(0, base + REG_DSI_28nm_PHY_LN_DEBUG_SEL(i));
writel(0x1, base + REG_DSI_28nm_PHY_LN_TEST_STR_0(i));
writel(0x97, base + REG_DSI_28nm_PHY_LN_TEST_STR_1(i));
}
writel(0, base + REG_DSI_28nm_PHY_LNCK_CFG_4);
writel(0xc0, base + REG_DSI_28nm_PHY_LNCK_CFG_1);
writel(0x1, base + REG_DSI_28nm_PHY_LNCK_TEST_STR0);
writel(0xbb, base + REG_DSI_28nm_PHY_LNCK_TEST_STR1);
writel(0x5f, base + REG_DSI_28nm_PHY_CTRL_0);
val = readl(base + REG_DSI_28nm_PHY_GLBL_TEST_CTRL); if (phy->id == DSI_1 && phy->usecase == MSM_DSI_PHY_SLAVE)
val &= ~DSI_28nm_PHY_GLBL_TEST_CTRL_BITCLK_HS_SEL; else
val |= DSI_28nm_PHY_GLBL_TEST_CTRL_BITCLK_HS_SEL;
writel(val, base + REG_DSI_28nm_PHY_GLBL_TEST_CTRL);
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.