static void rpm_clk_disable(unsigned id) { unsigned long flags; spin_lock_irqsave(&rpm_clock_lock, flags); if (rpm_clk[id].count > 0) rpm_clk[id].count--; else { pr_warning("%s: Reference counts are incorrect for clock %d!\n", __func__, id); goto out; } if (!rpm_clk[id].count) { unsigned peer_id = rpm_clk[id].peer_clk_id; if (rpm_clk[id].last_set_khz) { struct msm_rpm_iv_pair iv; unsigned peer_khz = 0, peer_sleep_khz = 0; int rc; iv.id = rpm_clk[id].rpm_clk_id; /* Take peer clock rate into account only if enabled. */ if (rpm_clk[peer_id].count) { peer_khz = rpm_clk[peer_id].last_set_khz; peer_sleep_khz = rpm_clk[peer_id].last_set_sleep_khz; } iv.value = peer_khz; rc = msm_rpmrs_set_noirq(MSM_RPM_CTX_SET_0, &iv, 1); if (rc) goto out; iv.value = peer_sleep_khz; rc = msm_rpmrs_set_noirq(MSM_RPM_CTX_SET_SLEEP, &iv, 1); } /* Turn off local smi_clk after disabling remote clock. */ if ((id == R_SMI_CLK || id == R_SMI_A_CLK) && !rpm_clk[peer_id].count) { uint32_t regval; spin_lock(&local_clock_reg_lock); regval = secure_readl(MMSS_MAXI_EN2); regval &= ~SMI_2X_AXI_CLK_EN; secure_writel(regval, MMSS_MAXI_EN2); spin_unlock(&local_clock_reg_lock); } } out: spin_unlock_irqrestore(&rpm_clock_lock, flags); return; }
static void hdmi_msm_reset_core() { uint32_t reg_val = 0; hdmi_msm_set_mode(0); // Disable clocks hdmi_app_clk_init(0); udelay(5); // Enable clocks hdmi_app_clk_init(1); reg_val = secure_readl(SW_RESET_CORE_REG); reg_val |= BIT(11); secure_writel(reg_val, SW_RESET_CORE_REG); udelay(5); reg_val = secure_readl(SW_RESET_AHB_REG); reg_val |= BIT(9); secure_writel(reg_val, SW_RESET_AHB_REG); udelay(5); reg_val = secure_readl(SW_RESET_AHB_REG); reg_val |= BIT(9); secure_writel(reg_val, SW_RESET_AHB_REG); udelay(20); reg_val = secure_readl(SW_RESET_CORE_REG); reg_val &= ~(BIT(11)); secure_writel(reg_val, SW_RESET_CORE_REG); udelay(5); reg_val = secure_readl(SW_RESET_AHB_REG); reg_val &= ~(BIT(9)); secure_writel(reg_val, SW_RESET_AHB_REG); udelay(5); reg_val = secure_readl(SW_RESET_AHB_REG); reg_val &= ~(BIT(9)); secure_writel(reg_val, SW_RESET_AHB_REG); udelay(5); }
void hdmi_app_clk_init(int on) { uint32_t val = 0; if (on) { // Enable clocks val = secure_readl(MISC_CC2_REG); val |= BIT(11); secure_writel(val, MISC_CC2_REG); udelay(10); val = secure_readl(MMSS_AHB_EN_REG); val |= BIT(14); secure_writel(val, MMSS_AHB_EN_REG); udelay(10); val = secure_readl(MMSS_AHB_EN_REG); val |= BIT(4); secure_writel(val, MMSS_AHB_EN_REG); udelay(10); } else { // Disable clocks val = secure_readl(MISC_CC2_REG); val &= ~(BIT(11)); secure_writel(val, MISC_CC2_REG); udelay(10); val = secure_readl(MMSS_AHB_EN_REG); val &= ~(BIT(14)); secure_writel(val, MMSS_AHB_EN_REG); udelay(10); val = secure_readl(MMSS_AHB_EN_REG); val &= ~(BIT(4)); secure_writel(val, MMSS_AHB_EN_REG); udelay(10); } }
static int rpm_clk_enable(unsigned id) { unsigned long flags; int rc = 0; spin_lock_irqsave(&rpm_clock_lock, flags); /* Don't send requests to the RPM if the rate has not been set. */ if (rpm_clk[id].last_set_khz == 0) goto out; if (!rpm_clk[id].count) { struct msm_rpm_iv_pair iv; unsigned this_khz = rpm_clk[id].last_set_khz; unsigned this_sleep_khz = rpm_clk[id].last_set_sleep_khz; unsigned peer_id = rpm_clk[id].peer_clk_id; unsigned peer_khz = 0, peer_sleep_khz = 0; /* Turn on local smi_clk before enabling remote clock. */ if (id == R_SMI_CLK || id == R_SMI_A_CLK) { uint32_t regval; spin_lock(&local_clock_reg_lock); regval = secure_readl(MMSS_MAXI_EN2); regval |= SMI_2X_AXI_CLK_EN; secure_writel(regval, MMSS_MAXI_EN2); spin_unlock(&local_clock_reg_lock); } iv.id = rpm_clk[id].rpm_clk_id; /* Take peer clock's rate into account only if it's enabled. */ if (rpm_clk[peer_id].count) { peer_khz = rpm_clk[peer_id].last_set_khz; peer_sleep_khz = rpm_clk[peer_id].last_set_sleep_khz; } iv.value = max(this_khz, peer_khz); rc = msm_rpmrs_set_noirq(MSM_RPM_CTX_SET_0, &iv, 1); if (rc) goto out; iv.value = max(this_sleep_khz, peer_sleep_khz); rc = msm_rpmrs_set_noirq(MSM_RPM_CTX_SET_SLEEP, &iv, 1); } out: if (!rc) rpm_clk[id].count++; spin_unlock_irqrestore(&rpm_clock_lock, flags); return rc; }
} /* Enable/disable for non-shared NT PLLs. */ int nt_pll_enable(uint8_t src, uint8_t enable) { static const struct { uint32_t const mode_reg; uint32_t const status_reg; } pll_reg[] = { [PLL_1] = { MM_PLL0_MODE_REG, MM_PLL0_STATUS_REG},[PLL_2] = { MM_PLL1_MODE_REG, MM_PLL1_STATUS_REG},[PLL_3] = { MM_PLL2_MODE_REG, MM_PLL2_STATUS_REG},}; uint32_t pll_mode; pll_mode = secure_readl(pll_reg[src].mode_reg); if (enable) { /* Disable PLL bypass mode. */ pll_mode |= (1 << 1); secure_writel(pll_mode, pll_reg[src].mode_reg); /* H/W requires a 5us delay between disabling the bypass and * de-asserting the reset. Delay 10us just to be safe. */ udelay(10); /* De-assert active-low PLL reset. */ pll_mode |= (1 << 2); secure_writel(pll_mode, pll_reg[src].mode_reg); /* Enable PLL output. */ pll_mode |= (1 << 0);