From: Tien Fong Chee <tien.fong.c...@intel.com>

The drivers is restructured such common functions, gen5 functions, and
arria10 functions are moved to clock_manager.c, clock_manager_gen5 and
clock_manager_arria10 respectively.

Signed-off-by: Tien Fong Chee <tien.fong.c...@intel.com>
Cc: Marek Vasut <ma...@denx.de>
Cc: Dinh Nguyen <dingnu...@kernel.org>
Cc: Ching Liang See <chin.liang....@intel.com>
Cc: Tien Fong <skywind...@gmail.com>
---
Changes for V2
- Reverted license changes, removing extern and volatile declaration.
---
 arch/arm/mach-socfpga/clock_manager.c              | 752 +++++++---------
 arch/arm/mach-socfpga/clock_manager_arria10.c      | 954 +++++++++++++++++++++
 .../{clock_manager.c => clock_manager_gen5.c}      | 240 +-----
 arch/arm/mach-socfpga/include/mach/clock_manager.h | 356 ++++++--
 4 files changed, 1573 insertions(+), 729 deletions(-)
 create mode 100644 arch/arm/mach-socfpga/clock_manager_arria10.c
 copy arch/arm/mach-socfpga/{clock_manager.c => clock_manager_gen5.c} (62%)

diff --git a/arch/arm/mach-socfpga/clock_manager.c 
b/arch/arm/mach-socfpga/clock_manager.c
index aa71636..d209f7d 100644
--- a/arch/arm/mach-socfpga/clock_manager.c
+++ b/arch/arm/mach-socfpga/clock_manager.c
@@ -1,5 +1,5 @@
 /*
- *  Copyright (C) 2013 Altera Corporation <www.altera.com>
+ *  Copyright (C) 2013-2016 Altera Corporation <www.altera.com>
  *
  * SPDX-License-Identifier:    GPL-2.0+
  */
@@ -7,416 +7,287 @@
 #include <common.h>
 #include <asm/io.h>
 #include <asm/arch/clock_manager.h>
+#include <fdtdec.h>
 
 DECLARE_GLOBAL_DATA_PTR;
 
+/* Function prototypes */
+/* Common prototypes */
+unsigned int cm_get_l4_sp_clk_hz(void);
+unsigned int cm_get_qspi_controller_clk_hz(void);
+unsigned int cm_get_mmc_controller_clk_hz(void);
+unsigned int cm_get_spi_controller_clk_hz(void);
+static void cm_print_clock_quick_summary(void);
+int do_showclocks(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]);
+void cm_wait_for_lock(uint32_t mask);
+void cm_wait_for_fsm(void);
+unsigned int cm_get_main_vco_clk_hz(void);
+unsigned int cm_get_per_vco_clk_hz(void);
+unsigned long cm_get_mpu_clk_hz(void);
+
 static const struct socfpga_clock_manager *clock_manager_base =
        (struct socfpga_clock_manager *)SOCFPGA_CLKMGR_ADDRESS;
 
-static void cm_wait_for_lock(uint32_t mask)
+/* Common functions */
+int set_cpu_clk_info(void)
 {
-       register uint32_t inter_val;
-       uint32_t retry = 0;
-       do {
-               inter_val = readl(&clock_manager_base->inter) & mask;
-               if (inter_val == mask)
-                       retry++;
-               else
-                       retry = 0;
-               if (retry >= 10)
-                       break;
-       } while (1);
-}
+       /* Calculate the clock frequencies required for drivers */
+       cm_get_l4_sp_clk_hz();
+       cm_get_mmc_controller_clk_hz();
 
-/* function to poll in the fsm busy bit */
-static void cm_wait_for_fsm(void)
-{
-       while (readl(&clock_manager_base->stat) & CLKMGR_STAT_BUSY)
-               ;
-}
+       gd->bd->bi_arm_freq = cm_get_mpu_clk_hz() / 1000000;
+       gd->bd->bi_dsp_freq = 0;
 
-/*
- * function to write the bypass register which requires a poll of the
- * busy bit
- */
-static void cm_write_bypass(uint32_t val)
-{
-       writel(val, &clock_manager_base->bypass);
-       cm_wait_for_fsm();
-}
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       gd->bd->bi_ddr_freq = cm_get_sdram_clk_hz() / 1000000;
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       gd->bd->bi_ddr_freq = 0;
+#endif
 
-/* function to write the ctrl register which requires a poll of the busy bit */
-static void cm_write_ctrl(uint32_t val)
-{
-       writel(val, &clock_manager_base->ctrl);
-       cm_wait_for_fsm();
+       return 0;
 }
 
-/* function to write a clock register that has phase information */
-static void cm_write_with_phase(uint32_t value,
-                               uint32_t reg_address, uint32_t mask)
+unsigned int cm_get_spi_controller_clk_hz(void)
 {
-       /* poll until phase is zero */
-       while (readl(reg_address) & mask)
-               ;
+       uint32_t clock = 0;
 
-       writel(value, reg_address);
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       uint32_t reg;
+       clock = cm_get_per_vco_clk_hz();
 
-       while (readl(reg_address) & mask)
-               ;
-}
+       /* get the clock prior L4 SP divider (periph_base_clk) */
+       reg = readl(&clock_manager_base->per_pll.perbaseclk);
+       clock /= (reg + 1);
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       clock = cm_get_l4_noc_hz(CLKMGR_MAINPLL_NOCDIV_L4MPCLK_LSB);
+#endif
 
-/*
- * Setup clocks while making no assumptions about previous state of the clocks.
- *
- * Start by being paranoid and gate all sw managed clocks
- * Put all plls in bypass
- * Put all plls VCO registers back to reset value (bandgap power down).
- * Put peripheral and main pll src to reset value to avoid glitch.
- * Delay 5 us.
- * Deassert bandgap power down and set numerator and denominator
- * Start 7 us timer.
- * set internal dividers
- * Wait for 7 us timer.
- * Enable plls
- * Set external dividers while plls are locking
- * Wait for pll lock
- * Assert/deassert outreset all.
- * Take all pll's out of bypass
- * Clear safe mode
- * set source main and peripheral clocks
- * Ungate clocks
- */
+       return clock;
+}
 
-void cm_basic_init(const struct cm_config * const cfg)
+unsigned int cm_get_qspi_controller_clk_hz(void)
 {
-       unsigned long end;
-
-       /* Start by being paranoid and gate all sw managed clocks */
-
-       /*
-        * We need to disable nandclk
-        * and then do another apb access before disabling
-        * gatting off the rest of the periperal clocks.
-        */
-       writel(~CLKMGR_PERPLLGRP_EN_NANDCLK_MASK &
-               readl(&clock_manager_base->per_pll.en),
-               &clock_manager_base->per_pll.en);
-
-       /* DO NOT GATE OFF DEBUG CLOCKS & BRIDGE CLOCKS */
-       writel(CLKMGR_MAINPLLGRP_EN_DBGTIMERCLK_MASK |
-               CLKMGR_MAINPLLGRP_EN_DBGTRACECLK_MASK |
-               CLKMGR_MAINPLLGRP_EN_DBGCLK_MASK |
-               CLKMGR_MAINPLLGRP_EN_DBGATCLK_MASK |
-               CLKMGR_MAINPLLGRP_EN_S2FUSER0CLK_MASK |
-               CLKMGR_MAINPLLGRP_EN_L4MPCLK_MASK,
-               &clock_manager_base->main_pll.en);
-
-       writel(0, &clock_manager_base->sdr_pll.en);
-
-       /* now we can gate off the rest of the peripheral clocks */
-       writel(0, &clock_manager_base->per_pll.en);
-
-       /* Put all plls in bypass */
-       cm_write_bypass(CLKMGR_BYPASS_PERPLL | CLKMGR_BYPASS_SDRPLL |
-                       CLKMGR_BYPASS_MAINPLL);
-
-       /* Put all plls VCO registers back to reset value. */
-       writel(CLKMGR_MAINPLLGRP_VCO_RESET_VALUE &
-              ~CLKMGR_MAINPLLGRP_VCO_REGEXTSEL_MASK,
-              &clock_manager_base->main_pll.vco);
-       writel(CLKMGR_PERPLLGRP_VCO_RESET_VALUE &
-              ~CLKMGR_PERPLLGRP_VCO_REGEXTSEL_MASK,
-              &clock_manager_base->per_pll.vco);
-       writel(CLKMGR_SDRPLLGRP_VCO_RESET_VALUE &
-              ~CLKMGR_SDRPLLGRP_VCO_REGEXTSEL_MASK,
-              &clock_manager_base->sdr_pll.vco);
-
-       /*
-        * The clocks to the flash devices and the L4_MAIN clocks can
-        * glitch when coming out of safe mode if their source values
-        * are different from their reset value.  So the trick it to
-        * put them back to their reset state, and change input
-        * after exiting safe mode but before ungating the clocks.
-        */
-       writel(CLKMGR_PERPLLGRP_SRC_RESET_VALUE,
-              &clock_manager_base->per_pll.src);
-       writel(CLKMGR_MAINPLLGRP_L4SRC_RESET_VALUE,
-              &clock_manager_base->main_pll.l4src);
-
-       /* read back for the required 5 us delay. */
-       readl(&clock_manager_base->main_pll.vco);
-       readl(&clock_manager_base->per_pll.vco);
-       readl(&clock_manager_base->sdr_pll.vco);
-
-
-       /*
-        * We made sure bgpwr down was assert for 5 us. Now deassert BG PWR DN
-        * with numerator and denominator.
-        */
-       writel(cfg->main_vco_base, &clock_manager_base->main_pll.vco);
-       writel(cfg->peri_vco_base, &clock_manager_base->per_pll.vco);
-       writel(cfg->sdram_vco_base, &clock_manager_base->sdr_pll.vco);
-
-       /*
-        * Time starts here. Must wait 7 us from
-        * BGPWRDN_SET(0) to VCO_ENABLE_SET(1).
-        */
-       end = timer_get_us() + 7;
-
-       /* main mpu */
-       writel(cfg->mpuclk, &clock_manager_base->main_pll.mpuclk);
-
-       /* main main clock */
-       writel(cfg->mainclk, &clock_manager_base->main_pll.mainclk);
-
-       /* main for dbg */
-       writel(cfg->dbgatclk, &clock_manager_base->main_pll.dbgatclk);
-
-       /* main for cfgs2fuser0clk */
-       writel(cfg->cfg2fuser0clk,
-              &clock_manager_base->main_pll.cfgs2fuser0clk);
-
-       /* Peri emac0 50 MHz default to RMII */
-       writel(cfg->emac0clk, &clock_manager_base->per_pll.emac0clk);
-
-       /* Peri emac1 50 MHz default to RMII */
-       writel(cfg->emac1clk, &clock_manager_base->per_pll.emac1clk);
-
-       /* Peri QSPI */
-       writel(cfg->mainqspiclk, &clock_manager_base->main_pll.mainqspiclk);
-
-       writel(cfg->perqspiclk, &clock_manager_base->per_pll.perqspiclk);
-
-       /* Peri pernandsdmmcclk */
-       writel(cfg->mainnandsdmmcclk,
-              &clock_manager_base->main_pll.mainnandsdmmcclk);
-
-       writel(cfg->pernandsdmmcclk,
-              &clock_manager_base->per_pll.pernandsdmmcclk);
-
-       /* Peri perbaseclk */
-       writel(cfg->perbaseclk, &clock_manager_base->per_pll.perbaseclk);
-
-       /* Peri s2fuser1clk */
-       writel(cfg->s2fuser1clk, &clock_manager_base->per_pll.s2fuser1clk);
-
-       /* 7 us must have elapsed before we can enable the VCO */
-       while (timer_get_us() < end)
-               ;
-
-       /* Enable vco */
-       /* main pll vco */
-       writel(cfg->main_vco_base | CLKMGR_MAINPLLGRP_VCO_EN,
-              &clock_manager_base->main_pll.vco);
+       uint32_t clock = 0;
 
-       /* periferal pll */
-       writel(cfg->peri_vco_base | CLKMGR_MAINPLLGRP_VCO_EN,
-              &clock_manager_base->per_pll.vco);
-
-       /* sdram pll vco */
-       writel(cfg->sdram_vco_base | CLKMGR_MAINPLLGRP_VCO_EN,
-              &clock_manager_base->sdr_pll.vco);
-
-       /* L3 MP and L3 SP */
-       writel(cfg->maindiv, &clock_manager_base->main_pll.maindiv);
-
-       writel(cfg->dbgdiv, &clock_manager_base->main_pll.dbgdiv);
-
-       writel(cfg->tracediv, &clock_manager_base->main_pll.tracediv);
-
-       /* L4 MP, L4 SP, can0, and can1 */
-       writel(cfg->perdiv, &clock_manager_base->per_pll.div);
-
-       writel(cfg->gpiodiv, &clock_manager_base->per_pll.gpiodiv);
-
-#define LOCKED_MASK \
-       (CLKMGR_INTER_SDRPLLLOCKED_MASK  | \
-       CLKMGR_INTER_PERPLLLOCKED_MASK  | \
-       CLKMGR_INTER_MAINPLLLOCKED_MASK)
-
-       cm_wait_for_lock(LOCKED_MASK);
-
-       /* write the sdram clock counters before toggling outreset all */
-       writel(cfg->ddrdqsclk & CLKMGR_SDRPLLGRP_DDRDQSCLK_CNT_MASK,
-              &clock_manager_base->sdr_pll.ddrdqsclk);
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       uint32_t reg;
+       /* identify the source of QSPI clock */
+       reg = readl(&clock_manager_base->per_pll.src);
+       reg = (reg & CLKMGR_PERPLLGRP_SRC_QSPI_MASK) >>
+             CLKMGR_PERPLLGRP_SRC_QSPI_OFFSET;
 
-       writel(cfg->ddr2xdqsclk & CLKMGR_SDRPLLGRP_DDR2XDQSCLK_CNT_MASK,
-              &clock_manager_base->sdr_pll.ddr2xdqsclk);
+       if (reg == CLKMGR_QSPI_CLK_SRC_F2S) {
+               clock = cm_get_f2s_per_ref_clk_hz();
+       } else if (reg == CLKMGR_QSPI_CLK_SRC_MAIN) {
+               clock = cm_get_main_vco_clk_hz();
 
-       writel(cfg->ddrdqclk & CLKMGR_SDRPLLGRP_DDRDQCLK_CNT_MASK,
-              &clock_manager_base->sdr_pll.ddrdqclk);
+               /* get the qspi clock */
+               reg = readl(&clock_manager_base->main_pll.mainqspiclk);
+               clock /= (reg + 1);
+       } else if (reg == CLKMGR_QSPI_CLK_SRC_PER) {
+               clock = cm_get_per_vco_clk_hz();
 
-       writel(cfg->s2fuser2clk & CLKMGR_SDRPLLGRP_S2FUSER2CLK_CNT_MASK,
-              &clock_manager_base->sdr_pll.s2fuser2clk);
+               /* get the qspi clock */
+               reg = readl(&clock_manager_base->per_pll.perqspiclk);
+               clock /= (reg + 1);
+       }
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       clock = cm_get_l4_noc_hz(CLKMGR_MAINPLL_NOCDIV_L4MAINCLK_LSB);
+#endif
 
-       /*
-        * after locking, but before taking out of bypass
-        * assert/deassert outresetall
-        */
-       uint32_t mainvco = readl(&clock_manager_base->main_pll.vco);
+       return clock;
+}
 
-       /* assert main outresetall */
-       writel(mainvco | CLKMGR_MAINPLLGRP_VCO_OUTRESETALL_MASK,
-              &clock_manager_base->main_pll.vco);
+void cm_wait_for_lock(uint32_t mask)
+{
+       register uint32_t inter_val;
+       uint32_t retry = 0;
+       do {
+#if defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+               inter_val = readl(&clock_manager_base->stat) & mask;
+#elif defined(CONFIG_TARGET_SOCFPGA_GEN5)
+               inter_val = readl(&clock_manager_base->inter) & mask;
+#endif
+               /* Wait for stable lock */
+               if (inter_val == mask)
+                       retry++;
+               else
+                       retry = 0;
+               if (retry >= 10)
+                       break;
+       } while (1);
+}
 
-       uint32_t periphvco = readl(&clock_manager_base->per_pll.vco);
+unsigned long cm_get_mpu_clk_hz(void)
+{
+       uint32_t reg, clk_hz;
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       clk_hz = cm_get_main_vco_clk_hz();
 
-       /* assert pheriph outresetall */
-       writel(periphvco | CLKMGR_PERPLLGRP_VCO_OUTRESETALL_MASK,
-              &clock_manager_base->per_pll.vco);
+       /* get the MPU clock */
+       reg = readl(&clock_manager_base->altera.mpuclk);
+       clk_hz /= (reg + 1);
+       reg = readl(&clock_manager_base->main_pll.mpuclk);
+       clk_hz /= (reg + 1);
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       uint32_t clk_src, mainmpuclk_reg;
 
-       /* assert sdram outresetall */
-       writel(cfg->sdram_vco_base | CLKMGR_MAINPLLGRP_VCO_EN|
-               CLKMGR_SDRPLLGRP_VCO_OUTRESETALL,
-               &clock_manager_base->sdr_pll.vco);
+       mainmpuclk_reg = readl(&clock_manager_base->main_pll.mpuclk);
 
-       /* deassert main outresetall */
-       writel(mainvco & ~CLKMGR_MAINPLLGRP_VCO_OUTRESETALL_MASK,
-              &clock_manager_base->main_pll.vco);
+       clk_src = (mainmpuclk_reg >> CLKMGR_MAINPLL_MPUCLK_SRC_LSB) &
+               CLKMGR_MAINPLL_MPUCLK_SRC_MSK;
 
-       /* deassert pheriph outresetall */
-       writel(periphvco & ~CLKMGR_PERPLLGRP_VCO_OUTRESETALL_MASK,
-              &clock_manager_base->per_pll.vco);
+       reg = readl(&clock_manager_base->altera.mpuclk);
+       /* Check MPU clock source: main, periph, osc1, intosc or f2s? */
+       switch (clk_src) {
+       case CLKMGR_MAINPLL_MPUCLK_SRC_MAIN:
+               clk_hz = cm_get_main_vco_clk_hz();
+               clk_hz /= ((reg & CLKMGR_MAINPLL_MPUCLK_CNT_MSK)
+                          + 1);
+               break;
+       case CLKMGR_MAINPLL_MPUCLK_SRC_PERI:
+               clk_hz = cm_get_per_vco_clk_hz();
+               clk_hz /= (((reg >> CLKMGR_MAINPLL_MPUCLK_PERICNT_LSB) &
+                          CLKMGR_MAINPLL_MPUCLK_CNT_MSK) + 1);
+               break;
+       case CLKMGR_MAINPLL_MPUCLK_SRC_OSC1:
+               clk_hz = eosc1_hz;
+               break;
+       case CLKMGR_MAINPLL_MPUCLK_SRC_INTOSC:
+               clk_hz = cb_intosc_hz;
+               break;
+       case CLKMGR_MAINPLL_MPUCLK_SRC_FPGA:
+               clk_hz = f2s_free_hz;
+               break;
+       default:
+               printf("cm_get_mpu_clk_hz invalid clk_src %d\n", clk_src);
+               return 0;
+       }
 
-       /* deassert sdram outresetall */
-       writel(cfg->sdram_vco_base | CLKMGR_MAINPLLGRP_VCO_EN,
-              &clock_manager_base->sdr_pll.vco);
+       clk_hz /= ((mainmpuclk_reg & CLKMGR_MAINPLL_MPUCLK_CNT_MSK) + 1);
+#endif
 
-       /*
-        * now that we've toggled outreset all, all the clocks
-        * are aligned nicely; so we can change any phase.
-        */
-       cm_write_with_phase(cfg->ddrdqsclk,
-                           (uint32_t)&clock_manager_base->sdr_pll.ddrdqsclk,
-                           CLKMGR_SDRPLLGRP_DDRDQSCLK_PHASE_MASK);
+       return clk_hz;
+}
 
-       /* SDRAM DDR2XDQSCLK */
-       cm_write_with_phase(cfg->ddr2xdqsclk,
-                           (uint32_t)&clock_manager_base->sdr_pll.ddr2xdqsclk,
-                           CLKMGR_SDRPLLGRP_DDR2XDQSCLK_PHASE_MASK);
+unsigned int cm_get_per_vco_clk_hz(void)
+{
+       uint32_t src_hz = 0;
+       uint32_t clk_src = 0;
+       uint32_t numer = 0;
+       uint32_t denom = 0;
+       uint32_t vco = 0;
 
-       cm_write_with_phase(cfg->ddrdqclk,
-                           (uint32_t)&clock_manager_base->sdr_pll.ddrdqclk,
-                           CLKMGR_SDRPLLGRP_DDRDQCLK_PHASE_MASK);
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       /* identify PER PLL clock source */
+       clk_src = readl(&clock_manager_base->per_pll.vco);
+       clk_src = (clk_src & CLKMGR_PERPLLGRP_VCO_SSRC_MASK) >>
+             CLKMGR_PERPLLGRP_VCO_SSRC_OFFSET;
+       if (clk_src == CLKMGR_VCO_SSRC_EOSC1)
+               src_hz = cm_get_osc_clk_hz(1);
+       else if (clk_src == CLKMGR_VCO_SSRC_EOSC2)
+               src_hz = cm_get_osc_clk_hz(2);
+       else if (clk_src == CLKMGR_VCO_SSRC_F2S)
+               src_hz = cm_get_f2s_per_ref_clk_hz();
 
-       cm_write_with_phase(cfg->s2fuser2clk,
-                           (uint32_t)&clock_manager_base->sdr_pll.s2fuser2clk,
-                           CLKMGR_SDRPLLGRP_S2FUSER2CLK_PHASE_MASK);
+       /* get the PER VCO clock */
+       vco = readl(&clock_manager_base->per_pll.vco);
+
+       numer = (vco & CLKMGR_PERPLLGRP_VCO_NUMER_MASK) >>
+               CLKMGR_PERPLLGRP_VCO_NUMER_OFFSET;
+
+       denom = (vco & CLKMGR_PERPLLGRP_VCO_DENOM_MASK) >>
+               CLKMGR_PERPLLGRP_VCO_DENOM_OFFSET;
+
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       clk_src = readl(&clock_manager_base->per_pll.vco0);
+
+       clk_src = (clk_src >> CLKMGR_PERPLL_VCO0_PSRC_LSB) &
+               CLKMGR_PERPLL_VCO0_PSRC_MSK;
+
+       if (clk_src == CLKMGR_PERPLL_VCO0_PSRC_EOSC) {
+               src_hz = eosc1_hz;
+       } else if (clk_src == CLKMGR_PERPLL_VCO0_PSRC_E_INTOSC) {
+               src_hz = cb_intosc_hz;
+       } else if (clk_src == CLKMGR_PERPLL_VCO0_PSRC_F2S) {
+               src_hz = f2s_free_hz;
+       } else if (clk_src == CLKMGR_PERPLL_VCO0_PSRC_MAIN) {
+               src_hz = cm_get_main_vco_clk_hz();
+               src_hz /= (readl
+                       (&clock_manager_base->main_pll.cntr15clk) &
+                       CLKMGR_MAINPLL_CNTRCLK_MSK) + 1;
+       } else {
+               printf("cm_get_per_vco_clk_hz invalid clk_src %d\n", clk_src);
+               return 0;
+       }
 
-       /* Take all three PLLs out of bypass when safe mode is cleared. */
-       cm_write_bypass(0);
+       vco = readl(&clock_manager_base->per_pll.vco1);
 
-       /* clear safe mode */
-       cm_write_ctrl(readl(&clock_manager_base->ctrl) | CLKMGR_CTRL_SAFEMODE);
+       numer = vco & CLKMGR_PERPLL_VCO1_NUMER_MSK;
 
-       /*
-        * now that safe mode is clear with clocks gated
-        * it safe to change the source mux for the flashes the the L4_MAIN
-        */
-       writel(cfg->persrc, &clock_manager_base->per_pll.src);
-       writel(cfg->l4src, &clock_manager_base->main_pll.l4src);
+       denom = (vco >> CLKMGR_PERPLL_VCO1_DENOM_LSB) &
+                       CLKMGR_PERPLL_VCO1_DENOM_MSK;
+#endif
 
-       /* Now ungate non-hw-managed clocks */
-       writel(~0, &clock_manager_base->main_pll.en);
-       writel(~0, &clock_manager_base->per_pll.en);
-       writel(~0, &clock_manager_base->sdr_pll.en);
+       vco = src_hz;
+       vco /= (1 + denom);
+       vco *= (1 + numer);
 
-       /* Clear the loss of lock bits (write 1 to clear) */
-       writel(CLKMGR_INTER_SDRPLLLOST_MASK | CLKMGR_INTER_PERPLLLOST_MASK |
-              CLKMGR_INTER_MAINPLLLOST_MASK,
-              &clock_manager_base->inter);
+       return vco;
 }
 
-static unsigned int cm_get_main_vco_clk_hz(void)
+unsigned int cm_get_main_vco_clk_hz(void)
 {
-       uint32_t reg, clock;
+       uint32_t src_hz, numer, denom, vco;
 
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
        /* get the main VCO clock */
-       reg = readl(&clock_manager_base->main_pll.vco);
-       clock = cm_get_osc_clk_hz(1);
-       clock /= ((reg & CLKMGR_MAINPLLGRP_VCO_DENOM_MASK) >>
-                 CLKMGR_MAINPLLGRP_VCO_DENOM_OFFSET) + 1;
-       clock *= ((reg & CLKMGR_MAINPLLGRP_VCO_NUMER_MASK) >>
-                 CLKMGR_MAINPLLGRP_VCO_NUMER_OFFSET) + 1;
-
-       return clock;
-}
-
-static unsigned int cm_get_per_vco_clk_hz(void)
-{
-       uint32_t reg, clock = 0;
-
-       /* identify PER PLL clock source */
-       reg = readl(&clock_manager_base->per_pll.vco);
-       reg = (reg & CLKMGR_PERPLLGRP_VCO_SSRC_MASK) >>
-             CLKMGR_PERPLLGRP_VCO_SSRC_OFFSET;
-       if (reg == CLKMGR_VCO_SSRC_EOSC1)
-               clock = cm_get_osc_clk_hz(1);
-       else if (reg == CLKMGR_VCO_SSRC_EOSC2)
-               clock = cm_get_osc_clk_hz(2);
-       else if (reg == CLKMGR_VCO_SSRC_F2S)
-               clock = cm_get_f2s_per_ref_clk_hz();
-
-       /* get the PER VCO clock */
-       reg = readl(&clock_manager_base->per_pll.vco);
-       clock /= ((reg & CLKMGR_PERPLLGRP_VCO_DENOM_MASK) >>
-                 CLKMGR_PERPLLGRP_VCO_DENOM_OFFSET) + 1;
-       clock *= ((reg & CLKMGR_PERPLLGRP_VCO_NUMER_MASK) >>
-                 CLKMGR_PERPLLGRP_VCO_NUMER_OFFSET) + 1;
-
-       return clock;
-}
+       vco = readl(&clock_manager_base->main_pll.vco);
+
+       numer = ((vco & CLKMGR_MAINPLLGRP_VCO_NUMER_MASK) >>
+               CLKMGR_MAINPLLGRP_VCO_NUMER_OFFSET);
+       denom = ((vco & CLKMGR_MAINPLLGRP_VCO_DENOM_MASK) >>
+                CLKMGR_MAINPLLGRP_VCO_DENOM_OFFSET);
+
+       src_hz = cm_get_osc_clk_hz(1);
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       uint32_t clk_src = readl(&clock_manager_base->main_pll.vco0);
+
+       clk_src = (clk_src >> CLKMGR_MAINPLL_VCO0_PSRC_LSB) &
+               CLKMGR_MAINPLL_VCO0_PSRC_MSK;
+
+       if (clk_src == CLKMGR_MAINPLL_VCO0_PSRC_EOSC) {
+               src_hz = eosc1_hz;
+       } else if (clk_src == CLKMGR_MAINPLL_VCO0_PSRC_E_INTOSC) {
+               src_hz = cb_intosc_hz;
+       } else if (clk_src == CLKMGR_MAINPLL_VCO0_PSRC_F2S) {
+               src_hz = f2s_free_hz;
+       } else {
+               printf("cm_get_main_vco_clk_hz invalid clk_src %d\n", clk_src);
+               return 0;
+       }
 
-unsigned long cm_get_mpu_clk_hz(void)
-{
-       uint32_t reg, clock;
+       vco = readl(&clock_manager_base->main_pll.vco1);
 
-       clock = cm_get_main_vco_clk_hz();
+       numer = vco & CLKMGR_MAINPLL_VCO1_NUMER_MSK;
 
-       /* get the MPU clock */
-       reg = readl(&clock_manager_base->altera.mpuclk);
-       clock /= (reg + 1);
-       reg = readl(&clock_manager_base->main_pll.mpuclk);
-       clock /= (reg + 1);
-       return clock;
-}
+       denom = (vco >> CLKMGR_MAINPLL_VCO1_DENOM_LSB) &
+                       CLKMGR_MAINPLL_VCO1_DENOM_MSK;
+#endif
 
-unsigned long cm_get_sdram_clk_hz(void)
-{
-       uint32_t reg, clock = 0;
-
-       /* identify SDRAM PLL clock source */
-       reg = readl(&clock_manager_base->sdr_pll.vco);
-       reg = (reg & CLKMGR_SDRPLLGRP_VCO_SSRC_MASK) >>
-             CLKMGR_SDRPLLGRP_VCO_SSRC_OFFSET;
-       if (reg == CLKMGR_VCO_SSRC_EOSC1)
-               clock = cm_get_osc_clk_hz(1);
-       else if (reg == CLKMGR_VCO_SSRC_EOSC2)
-               clock = cm_get_osc_clk_hz(2);
-       else if (reg == CLKMGR_VCO_SSRC_F2S)
-               clock = cm_get_f2s_sdr_ref_clk_hz();
-
-       /* get the SDRAM VCO clock */
-       reg = readl(&clock_manager_base->sdr_pll.vco);
-       clock /= ((reg & CLKMGR_SDRPLLGRP_VCO_DENOM_MASK) >>
-                 CLKMGR_SDRPLLGRP_VCO_DENOM_OFFSET) + 1;
-       clock *= ((reg & CLKMGR_SDRPLLGRP_VCO_NUMER_MASK) >>
-                 CLKMGR_SDRPLLGRP_VCO_NUMER_OFFSET) + 1;
-
-       /* get the SDRAM (DDR_DQS) clock */
-       reg = readl(&clock_manager_base->sdr_pll.ddrdqsclk);
-       reg = (reg & CLKMGR_SDRPLLGRP_DDRDQSCLK_CNT_MASK) >>
-             CLKMGR_SDRPLLGRP_DDRDQSCLK_CNT_OFFSET;
-       clock /= (reg + 1);
+       vco = src_hz;
+       vco /= (1 + denom);
+       vco *= (1 + numer);
 
-       return clock;
+       return vco;
 }
 
 unsigned int cm_get_l4_sp_clk_hz(void)
 {
-       uint32_t reg, clock = 0;
+       uint32_t clock = 0;
 
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       uint32_t reg;
        /* identify the source of L4 SP clock */
        reg = readl(&clock_manager_base->main_pll.l4src);
        reg = (reg & CLKMGR_MAINPLLGRP_L4SRC_L4SP) >>
@@ -443,106 +314,117 @@ unsigned int cm_get_l4_sp_clk_hz(void)
        reg = (reg & CLKMGR_MAINPLLGRP_MAINDIV_L4SPCLK_MASK) >>
              CLKMGR_MAINPLLGRP_MAINDIV_L4SPCLK_OFFSET;
        clock = clock / (1 << reg);
-
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       clock = cm_get_l4_noc_hz(CLKMGR_MAINPLL_NOCDIV_L4SPCLK_LSB);
+#endif
        return clock;
 }
 
-unsigned int cm_get_mmc_controller_clk_hz(void)
+/* function to poll in the fsm busy bit */
+void cm_wait_for_fsm(void)
 {
-       uint32_t reg, clock = 0;
-
-       /* identify the source of MMC clock */
-       reg = readl(&clock_manager_base->per_pll.src);
-       reg = (reg & CLKMGR_PERPLLGRP_SRC_SDMMC_MASK) >>
-             CLKMGR_PERPLLGRP_SRC_SDMMC_OFFSET;
-
-       if (reg == CLKMGR_SDMMC_CLK_SRC_F2S) {
-               clock = cm_get_f2s_per_ref_clk_hz();
-       } else if (reg == CLKMGR_SDMMC_CLK_SRC_MAIN) {
-               clock = cm_get_main_vco_clk_hz();
-
-               /* get the SDMMC clock */
-               reg = readl(&clock_manager_base->main_pll.mainnandsdmmcclk);
-               clock /= (reg + 1);
-       } else if (reg == CLKMGR_SDMMC_CLK_SRC_PER) {
-               clock = cm_get_per_vco_clk_hz();
-
-               /* get the SDMMC clock */
-               reg = readl(&clock_manager_base->per_pll.pernandsdmmcclk);
-               clock /= (reg + 1);
-       }
-
-       /* further divide by 4 as we have fixed divider at wrapper */
-       clock /= 4;
-       return clock;
+       while (readl(&clock_manager_base->stat) &
+               CLKMGR_CLKMGR_STAT_BUSY_SET_MSK);
 }
 
-unsigned int cm_get_qspi_controller_clk_hz(void)
+unsigned int cm_get_mmc_controller_clk_hz(void)
 {
-       uint32_t reg, clock = 0;
-
-       /* identify the source of QSPI clock */
-       reg = readl(&clock_manager_base->per_pll.src);
-       reg = (reg & CLKMGR_PERPLLGRP_SRC_QSPI_MASK) >>
-             CLKMGR_PERPLLGRP_SRC_QSPI_OFFSET;
+       uint32_t clk_hz = 0;
+       uint32_t clk_input = 0;
+
+#if defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       clk_input = readl(&clock_manager_base->per_pll.cntr6clk);
+       clk_input = (clk_input >> CLKMGR_PERPLL_CNTR6CLK_SRC_LSB) &
+               CLKMGR_PERPLLGRP_SRC_MSK;
+#elif defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       clk_input = readl(&clock_manager_base->per_pll.src);
+       clk_input = (clk_input & CLKMGR_PERPLLGRP_SRC_SDMMC_MASK) >>
+             CLKMGR_PERPLLGRP_SRC_SDMMC_OFFSET;
+#endif
+
+       switch (clk_input) {
+#if defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       case CLKMGR_PERPLLGRP_SRC_MAIN:
+               clk_hz = cm_get_main_vco_clk_hz();
+               clk_hz /= 1 +
+                       (readl
+                       (&clock_manager_base->main_pll.cntr6clk) &
+                       CLKMGR_MAINPLL_CNTRCLK_MSK);
+               break;
+
+       case CLKMGR_PERPLLGRP_SRC_PERI:
+               clk_hz = cm_get_per_vco_clk_hz();
+               clk_hz /= 1 + (readl
+                       (&clock_manager_base->per_pll.cntr6clk) &
+                       CLKMGR_PERPLL_CNTRCLK_MSK);
+               break;
+
+       case CLKMGR_PERPLLGRP_SRC_OSC1:
+               clk_hz = eosc1_hz;
+               break;
+
+       case CLKMGR_PERPLLGRP_SRC_INTOSC:
+               clk_hz = cb_intosc_hz;
+               break;
+
+       case CLKMGR_PERPLLGRP_SRC_FPGA:
+               clk_hz = f2s_free_hz;
+               break;
+#elif defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       case CLKMGR_SDMMC_CLK_SRC_F2S:
+               clk_hz = cm_get_f2s_per_ref_clk_hz();
+               break;
+
+       case CLKMGR_SDMMC_CLK_SRC_MAIN:
+               clk_hz = cm_get_main_vco_clk_hz();
 
-       if (reg == CLKMGR_QSPI_CLK_SRC_F2S) {
-               clock = cm_get_f2s_per_ref_clk_hz();
-       } else if (reg == CLKMGR_QSPI_CLK_SRC_MAIN) {
-               clock = cm_get_main_vco_clk_hz();
+               /* get the SDMMC clock */
+               clk_input =
+                       readl(&clock_manager_base->main_pll.mainnandsdmmcclk);
+               clk_hz /= (clk_input + 1);
+               break;
 
-               /* get the qspi clock */
-               reg = readl(&clock_manager_base->main_pll.mainqspiclk);
-               clock /= (reg + 1);
-       } else if (reg == CLKMGR_QSPI_CLK_SRC_PER) {
-               clock = cm_get_per_vco_clk_hz();
+       case CLKMGR_SDMMC_CLK_SRC_PER:
+               clk_hz = cm_get_per_vco_clk_hz();
 
-               /* get the qspi clock */
-               reg = readl(&clock_manager_base->per_pll.perqspiclk);
-               clock /= (reg + 1);
+               /* get the SDMMC clock */
+               clk_input =
+                       readl(&clock_manager_base->per_pll.pernandsdmmcclk);
+               clk_hz /= (clk_input + 1);
+               break;
+#endif
        }
-
-       return clock;
-}
-
-unsigned int cm_get_spi_controller_clk_hz(void)
-{
-       uint32_t reg, clock = 0;
-
-       clock = cm_get_per_vco_clk_hz();
-
-       /* get the clock prior L4 SP divider (periph_base_clk) */
-       reg = readl(&clock_manager_base->per_pll.perbaseclk);
-       clock /= (reg + 1);
-
-       return clock;
+       return clk_hz/4;
 }
 
 static void cm_print_clock_quick_summary(void)
 {
        printf("MPU       %10ld kHz\n", cm_get_mpu_clk_hz() / 1000);
+       printf("MMC         %8d kHz\n", cm_get_mmc_controller_clk_hz() / 1000);
+       printf("QSPI        %8d kHz\n",
+               cm_get_qspi_controller_clk_hz() / 1000);
+       printf("SPI         %8d kHz\n", cm_get_spi_controller_clk_hz() / 1000);
+#if defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       printf("EOSC1       %8d kHz\n", eosc1_hz / 1000);
+       printf("cb_intosc   %8d kHz\n", cb_intosc_hz / 1000);
+       printf("f2s_free    %8d kHz\n", f2s_free_hz / 1000);
+       printf("Main VCO    %8d kHz\n", cm_get_main_vco_clk_hz()/1000);
+       printf("NOC         %8d kHz\n", cm_get_noc_clk_hz()/1000);
+       printf("L4 Main     %8d kHz\n",
+              cm_get_l4_noc_hz(CLKMGR_MAINPLL_NOCDIV_L4MAINCLK_LSB)/1000);
+       printf("L4 MP       %8d kHz\n",
+              cm_get_l4_noc_hz(CLKMGR_MAINPLL_NOCDIV_L4MPCLK_LSB)/1000);
+       printf("L4 SP       %8d kHz\n",
+              cm_get_l4_sp_clk_hz()/1000);
+       printf("L4 sys free %8d kHz\n", cm_l4_sys_free_clk_hz/1000);
+#elif defined(CONFIG_TARGET_SOCFPGA_GEN5)
        printf("DDR       %10ld kHz\n", cm_get_sdram_clk_hz() / 1000);
        printf("EOSC1       %8d kHz\n", cm_get_osc_clk_hz(1) / 1000);
        printf("EOSC2       %8d kHz\n", cm_get_osc_clk_hz(2) / 1000);
        printf("F2S_SDR_REF %8d kHz\n", cm_get_f2s_sdr_ref_clk_hz() / 1000);
        printf("F2S_PER_REF %8d kHz\n", cm_get_f2s_per_ref_clk_hz() / 1000);
-       printf("MMC         %8d kHz\n", cm_get_mmc_controller_clk_hz() / 1000);
-       printf("QSPI        %8d kHz\n", cm_get_qspi_controller_clk_hz() / 1000);
        printf("UART        %8d kHz\n", cm_get_l4_sp_clk_hz() / 1000);
-       printf("SPI         %8d kHz\n", cm_get_spi_controller_clk_hz() / 1000);
-}
-
-int set_cpu_clk_info(void)
-{
-       /* Calculate the clock frequencies required for drivers */
-       cm_get_l4_sp_clk_hz();
-       cm_get_mmc_controller_clk_hz();
-
-       gd->bd->bi_arm_freq = cm_get_mpu_clk_hz() / 1000000;
-       gd->bd->bi_dsp_freq = 0;
-       gd->bd->bi_ddr_freq = cm_get_sdram_clk_hz() / 1000000;
-
-       return 0;
+#endif
 }
 
 int do_showclocks(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
diff --git a/arch/arm/mach-socfpga/clock_manager_arria10.c 
b/arch/arm/mach-socfpga/clock_manager_arria10.c
new file mode 100644
index 0000000..93165b4
--- /dev/null
+++ b/arch/arm/mach-socfpga/clock_manager_arria10.c
@@ -0,0 +1,954 @@
+/*
+ * Copyright (C) 2016, Intel Corporation
+ *
+ * SPDX-License-Identifier:    GPL-2.0
+ */
+
+#include <common.h>
+#include <asm/io.h>
+#include <asm/arch/clock_manager.h>
+#include <fdtdec.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+int cm_basic_init(const void* blob);
+uint32_t eosc1_hz;
+uint32_t cb_intosc_hz;
+uint32_t f2s_free_hz;
+unsigned int cm_l4_main_clk_hz;
+unsigned int cm_l4_sp_clk_hz;
+unsigned int cm_l4_mp_clk_hz;
+unsigned int cm_l4_sys_free_clk_hz;
+
+struct strtopu32 {
+       const char *str;
+       uint32_t *p;
+};
+
+struct mainpll_cfg {
+       uint32_t vco0_psrc;
+       uint32_t vco1_denom;
+       uint32_t vco1_numer;
+       uint32_t mpuclk;
+       uint32_t mpuclk_cnt;
+       uint32_t mpuclk_src;
+       uint32_t nocclk;
+       uint32_t nocclk_cnt;
+       uint32_t nocclk_src;
+       uint32_t cntr2clk_cnt;
+       uint32_t cntr3clk_cnt;
+       uint32_t cntr4clk_cnt;
+       uint32_t cntr5clk_cnt;
+       uint32_t cntr6clk_cnt;
+       uint32_t cntr7clk_cnt;
+       uint32_t cntr7clk_src;
+       uint32_t cntr8clk_cnt;
+       uint32_t cntr9clk_cnt;
+       uint32_t cntr9clk_src;
+       uint32_t cntr15clk_cnt;
+       uint32_t nocdiv_l4mainclk;
+       uint32_t nocdiv_l4mpclk;
+       uint32_t nocdiv_l4spclk;
+       uint32_t nocdiv_csatclk;
+       uint32_t nocdiv_cstraceclk;
+       uint32_t nocdiv_cspdbclk;
+};
+
+struct perpll_cfg {
+       uint32_t vco0_psrc;
+       uint32_t vco1_denom;
+       uint32_t vco1_numer;
+       uint32_t cntr2clk_cnt;
+       uint32_t cntr2clk_src;
+       uint32_t cntr3clk_cnt;
+       uint32_t cntr3clk_src;
+       uint32_t cntr4clk_cnt;
+       uint32_t cntr4clk_src;
+       uint32_t cntr5clk_cnt;
+       uint32_t cntr5clk_src;
+       uint32_t cntr6clk_cnt;
+       uint32_t cntr6clk_src;
+       uint32_t cntr7clk_cnt;
+       uint32_t cntr8clk_cnt;
+       uint32_t cntr8clk_src;
+       uint32_t cntr9clk_cnt;
+       uint32_t emacctl_emac0sel;
+       uint32_t emacctl_emac1sel;
+       uint32_t emacctl_emac2sel;
+       uint32_t gpiodiv_gpiodbclk;
+};
+
+struct alteragrp_cfg {
+       uint32_t nocclk;
+       uint32_t mpuclk;
+};
+
+unsigned int cm_get_noc_clk_hz(void);
+unsigned int cm_get_l4_noc_hz(unsigned int nocdivshift);
+static int of_to_struct(const void *blob, int node, int cfg__len, void *cfg);
+static int of_get_input_clks(const void *blob, int node, void *cfg);
+static int of_get_clk_cfg(const void *blob, struct mainpll_cfg *main_cfg,
+        struct perpll_cfg *per_cfg, struct alteragrp_cfg *altrgrp_cfg);
+static unsigned int cm_calc_handoff_main_vco_clk_hz(
+        struct mainpll_cfg *main_cfg);
+static unsigned int cm_calc_handoff_periph_vco_clk_hz(
+        struct mainpll_cfg *main_cfg, struct perpll_cfg *per_cfg);
+static unsigned int cm_calc_handoff_mpu_clk_hz(struct mainpll_cfg *main_cfg,
+        struct perpll_cfg *per_cfg);
+static unsigned int cm_calc_handoff_noc_clk_hz(struct mainpll_cfg *main_cfg,
+        struct perpll_cfg *per_cfg);
+static int cm_is_pll_ramp_required(int main0periph1,
+        struct mainpll_cfg *main_cfg, struct perpll_cfg *per_cfg);
+static unsigned int cm_calc_safe_pll_numer(int main0periph1,
+        struct mainpll_cfg *main_cfg, struct perpll_cfg *per_cfg,
+        unsigned int safe_hz);
+static void cm_pll_ramp_main(struct mainpll_cfg *main_cfg,
+        struct perpll_cfg *per_cfg, unsigned int pll_ramp_main_hz);
+static void cm_pll_ramp_periph(struct mainpll_cfg *main_cfg,
+        struct perpll_cfg *per_cfg, unsigned int pll_ramp_periph_hz);
+static int cm_full_cfg(struct mainpll_cfg *main_cfg,
+        struct perpll_cfg *per_cfg);
+
+static const struct socfpga_clock_manager *clock_manager_base =
+       (struct socfpga_clock_manager *)SOCFPGA_CLKMGR_ADDRESS;
+
+void cm_use_intosc(void)
+{
+       setbits_le32(&clock_manager_base->ctrl,
+                    CLKMGR_CLKMGR_CTL_BOOTCLK_INTOSC_SET_MSK);
+}
+
+unsigned int cm_get_noc_clk_hz(void)
+{
+       unsigned int clk_src, dividor, nocclk, src_hz;
+
+       nocclk = readl(&clock_manager_base->main_pll.nocclk);
+       clk_src = (nocclk >> CLKMGR_MAINPLL_NOCCLK_SRC_LSB) &
+               CLKMGR_MAINPLL_NOCCLK_SRC_MSK;
+
+       dividor = 1 + (nocclk & CLKMGR_MAINPLL_NOCDIV_MSK);
+
+       if (clk_src == CLKMGR_PERPLLGRP_SRC_MAIN) {
+               src_hz = cm_get_main_vco_clk_hz();
+               src_hz /= 1 +
+               (readl(SOCFPGA_CLKMGR_ADDRESS+CLKMGR_MAINPLL_NOC_CLK_OFFSET)&
+               CLKMGR_MAINPLL_NOCCLK_CNT_MSK);
+       } else if (clk_src == CLKMGR_PERPLLGRP_SRC_PERI) {
+               src_hz = cm_get_per_vco_clk_hz();
+               src_hz /= 1 +
+               ((readl(SOCFPGA_CLKMGR_ADDRESS+CLKMGR_MAINPLL_NOC_CLK_OFFSET)>>
+                       CLKMGR_MAINPLL_NOCCLK_PERICNT_LSB)&
+                       CLKMGR_MAINPLL_NOCCLK_CNT_MSK);
+       } else if (clk_src == CLKMGR_PERPLLGRP_SRC_OSC1) {
+               src_hz = eosc1_hz;
+       } else if (clk_src == CLKMGR_PERPLLGRP_SRC_INTOSC) {
+               src_hz = cb_intosc_hz;
+       } else if (clk_src == CLKMGR_PERPLLGRP_SRC_FPGA) {
+               src_hz = f2s_free_hz;
+       } else {
+               src_hz = 0;
+       }
+       return src_hz/dividor;
+}
+
+unsigned int cm_get_l4_noc_hz(unsigned int nocdivshift)
+{
+       unsigned int dividor2 = 1 <<
+               ((readl(&clock_manager_base->main_pll.nocdiv) >>
+                       nocdivshift) & CLKMGR_MAINPLL_NOCDIV_MSK);
+
+       return cm_get_noc_clk_hz()/dividor2;
+}
+
+int of_to_struct(const void *blob, int node, int cfg_len, void *cfg)
+{
+       if (fdtdec_get_int_array(blob, node, "altr,of_reg_value",
+               (u32*)cfg, cfg_len)) {
+               /* could not find required property */
+               return 100;
+       }
+
+       return 0;
+}
+
+static int of_get_input_clks(const void *blob, int node, void *cfg)
+{
+       if (fdtdec_get_int_array(blob, node, "clock-frequency",
+               (u32*)cfg, 1)) {
+               /* could not find required property */
+               return 100;
+       }
+
+       return 0;
+}
+
+int of_get_clk_cfg(const void *blob, struct mainpll_cfg *main_cfg,
+                         struct perpll_cfg *per_cfg, struct alteragrp_cfg 
*altrgrp_cfg)
+{
+       int node, child, len;
+       const char *node_name;
+
+       node = fdtdec_next_compatible(blob, 0, COMPAT_ALTERA_SOCFPGA_CLK);
+
+       if (node < 0)
+               return 1;
+
+       child = fdt_first_subnode(blob, node);
+
+       if (child < 0)
+               return 2;
+
+       child = fdt_first_subnode(blob, child);
+
+       if (child < 0)
+               return 3;
+
+       node_name = fdt_get_name(blob, child, &len);
+
+       while (node_name) {
+               if (!strcmp(node_name, "osc1")) {
+                       if (of_get_input_clks(blob, child, &eosc1_hz))
+                               return 101;
+               } else if (!strcmp(node_name, "cb_intosc_ls_clk")) {
+                       if (of_get_input_clks(blob, child, &cb_intosc_hz))
+                               return 102;
+               } else if (!strcmp(node_name, "f2s_free_clk")) {
+                       if (of_get_input_clks(blob, child, &f2s_free_hz))
+                               return 103;
+               } else if (!strcmp(node_name, "main_pll")) {
+                       if (of_to_struct(blob, child, 
sizeof(*main_cfg)/sizeof(uint32_t),
+                               main_cfg))
+                               return 104;
+               } else if (!strcmp(node_name, "periph_pll")) {
+                       if (of_to_struct(blob, child, 
sizeof(*per_cfg)/sizeof(uint32_t),
+                               per_cfg))
+                               return 105;
+               } else if (!strcmp(node_name, "altera")) {
+                       if (of_to_struct(blob, child,
+                               sizeof(*altrgrp_cfg)/sizeof(uint32_t), 
altrgrp_cfg))
+                               return 106;
+
+                       main_cfg->mpuclk = altrgrp_cfg->mpuclk;
+                       main_cfg->nocclk = altrgrp_cfg->nocclk;
+               }
+               child = fdt_next_subnode(blob, child);
+
+               if (child < 0)
+                       break;
+
+               node_name = fdt_get_name(blob, child, &len);
+       }
+
+       return 0;
+}
+
+/* calculate the intended main VCO frequency based on handoff */
+static unsigned int cm_calc_handoff_main_vco_clk_hz
+       (struct mainpll_cfg *main_cfg)
+{
+       unsigned int clk_hz;
+
+       /* Check main VCO clock source: eosc, intosc or f2s? */
+       switch (main_cfg->vco0_psrc) {
+       case CLKMGR_MAINPLL_VCO0_PSRC_EOSC:
+               clk_hz = eosc1_hz;
+               break;
+       case CLKMGR_MAINPLL_VCO0_PSRC_E_INTOSC:
+               clk_hz = cb_intosc_hz;
+               break;
+       case CLKMGR_MAINPLL_VCO0_PSRC_F2S:
+               clk_hz = f2s_free_hz;
+               break;
+       default:
+               return 0;
+       }
+
+       /* calculate the VCO frequency */
+       clk_hz /= (1 + main_cfg->vco1_denom);
+       clk_hz *= (1 + main_cfg->vco1_numer);
+
+       return clk_hz;
+}
+
+/* calculate the intended periph VCO frequency based on handoff */
+static unsigned int cm_calc_handoff_periph_vco_clk_hz
+       (struct mainpll_cfg *main_cfg, struct perpll_cfg *per_cfg)
+{
+       unsigned int clk_hz;
+
+       /* Check periph VCO clock source: eosc, intosc, f2s or mainpll? */
+       switch (per_cfg->vco0_psrc) {
+       case CLKMGR_PERPLL_VCO0_PSRC_EOSC:
+               clk_hz = eosc1_hz;
+               break;
+       case CLKMGR_PERPLL_VCO0_PSRC_E_INTOSC:
+               clk_hz = cb_intosc_hz;
+               break;
+       case CLKMGR_PERPLL_VCO0_PSRC_F2S:
+               clk_hz = f2s_free_hz;
+               break;
+       case CLKMGR_PERPLL_VCO0_PSRC_MAIN:
+               clk_hz = cm_calc_handoff_main_vco_clk_hz(main_cfg);
+               clk_hz /= main_cfg->cntr15clk_cnt;
+               break;
+       default:
+               return 0;
+       }
+
+       /* calculate the VCO frequency */
+       clk_hz /= (1 + per_cfg->vco1_denom);
+       clk_hz *= (1 + per_cfg->vco1_numer);
+
+       return clk_hz;
+}
+
+/* calculate the intended MPU clock frequency based on handoff */
+static unsigned int cm_calc_handoff_mpu_clk_hz(struct mainpll_cfg *main_cfg,
+                              struct perpll_cfg *per_cfg)
+{
+       unsigned int clk_hz;
+
+       /* Check MPU clock source: main, periph, osc1, intosc or f2s? */
+       switch (main_cfg->mpuclk_src) {
+       case CLKMGR_MAINPLL_MPUCLK_SRC_MAIN:
+               clk_hz = cm_calc_handoff_main_vco_clk_hz(main_cfg);
+               clk_hz /= ((main_cfg->mpuclk & CLKMGR_MAINPLL_MPUCLK_CNT_MSK)
+                          + 1);
+               break;
+       case CLKMGR_MAINPLL_MPUCLK_SRC_PERI:
+               clk_hz = cm_calc_handoff_periph_vco_clk_hz(main_cfg, per_cfg);
+               clk_hz /= (((main_cfg->mpuclk >>
+                          CLKMGR_MAINPLL_MPUCLK_PERICNT_LSB) &
+                          CLKMGR_MAINPLL_MPUCLK_CNT_MSK) + 1);
+               break;
+       case CLKMGR_MAINPLL_MPUCLK_SRC_OSC1:
+               clk_hz = eosc1_hz;
+               break;
+       case CLKMGR_MAINPLL_MPUCLK_SRC_INTOSC:
+               clk_hz = cb_intosc_hz;
+               break;
+       case CLKMGR_MAINPLL_MPUCLK_SRC_FPGA:
+               clk_hz = f2s_free_hz;
+               break;
+       default:
+               return 0;
+       }
+
+       clk_hz /= (main_cfg->mpuclk_cnt + 1);
+       return clk_hz;
+}
+
+/* calculate the intended NOC clock frequency based on handoff */
+static unsigned int cm_calc_handoff_noc_clk_hz(struct mainpll_cfg *main_cfg,
+                              struct perpll_cfg *per_cfg)
+{
+       unsigned int clk_hz;
+
+       /* Check MPU clock source: main, periph, osc1, intosc or f2s? */
+       switch (main_cfg->nocclk_src) {
+       case CLKMGR_MAINPLL_NOCCLK_SRC_MAIN:
+               clk_hz = cm_calc_handoff_main_vco_clk_hz(main_cfg);
+               clk_hz /= ((main_cfg->nocclk & CLKMGR_MAINPLL_NOCCLK_CNT_MSK)
+                          + 1);
+               break;
+       case CLKMGR_MAINPLL_NOCCLK_SRC_PERI:
+               clk_hz = cm_calc_handoff_periph_vco_clk_hz(main_cfg, per_cfg);
+               clk_hz /= (((main_cfg->nocclk >>
+                          CLKMGR_MAINPLL_NOCCLK_PERICNT_LSB) &
+                          CLKMGR_MAINPLL_NOCCLK_CNT_MSK) + 1);
+               break;
+       case CLKMGR_MAINPLL_NOCCLK_SRC_OSC1:
+               clk_hz = eosc1_hz;
+               break;
+       case CLKMGR_MAINPLL_NOCCLK_SRC_INTOSC:
+               clk_hz = cb_intosc_hz;
+               break;
+       case CLKMGR_MAINPLL_NOCCLK_SRC_FPGA:
+               clk_hz = f2s_free_hz;
+               break;
+       default:
+               return 0;
+       }
+
+       clk_hz /= (main_cfg->nocclk_cnt + 1);
+       return clk_hz;
+}
+
+/* return 1 if PLL ramp is required */
+static int cm_is_pll_ramp_required(int main0periph1,
+                                  struct mainpll_cfg *main_cfg,
+                                  struct perpll_cfg *per_cfg)
+{
+
+       /* Check for main PLL */
+       if (main0periph1 == 0) {
+               /*
+                * PLL ramp is not required if both MPU clock and NOC clock are
+                * not sourced from main PLL
+                */
+               if (main_cfg->mpuclk_src != CLKMGR_MAINPLL_MPUCLK_SRC_MAIN &&
+                   main_cfg->nocclk_src != CLKMGR_MAINPLL_NOCCLK_SRC_MAIN)
+                       return 0;
+
+               /*
+                * PLL ramp is required if MPU clock is sourced from main PLL
+                * and MPU clock is over 900MHz (as advised by HW team)
+                */
+               if (main_cfg->mpuclk_src == CLKMGR_MAINPLL_MPUCLK_SRC_MAIN &&
+                   (cm_calc_handoff_mpu_clk_hz(main_cfg, per_cfg) >
+                    CLKMGR_PLL_RAMP_MPUCLK_THRESHOLD_HZ))
+                       return 1;
+
+               /*
+                * PLL ramp is required if NOC clock is sourced from main PLL
+                * and NOC clock is over 300MHz (as advised by HW team)
+                */
+               if (main_cfg->nocclk_src == CLKMGR_MAINPLL_NOCCLK_SRC_MAIN &&
+                   (cm_calc_handoff_noc_clk_hz(main_cfg, per_cfg) >
+                    CLKMGR_PLL_RAMP_NOCCLK_THRESHOLD_HZ))
+                       return 2;
+
+       } else if (main0periph1 == 1) {
+               /*
+                * PLL ramp is not required if both MPU clock and NOC clock are
+                * not sourced from periph PLL
+                */
+               if (main_cfg->mpuclk_src != CLKMGR_MAINPLL_MPUCLK_SRC_PERI &&
+                   main_cfg->nocclk_src != CLKMGR_MAINPLL_NOCCLK_SRC_PERI)
+                       return 0;
+
+               /*
+                * PLL ramp is required if MPU clock are source from periph PLL
+                * and MPU clock is over 900MHz (as advised by HW team)
+                */
+               if (main_cfg->mpuclk_src == CLKMGR_MAINPLL_MPUCLK_SRC_PERI &&
+                   (cm_calc_handoff_mpu_clk_hz(main_cfg, per_cfg) >
+                    CLKMGR_PLL_RAMP_MPUCLK_THRESHOLD_HZ))
+                       return 1;
+
+               /*
+                * PLL ramp is required if NOC clock are source from periph PLL
+                * and NOC clock is over 300MHz (as advised by HW team)
+                */
+               if (main_cfg->nocclk_src == CLKMGR_MAINPLL_NOCCLK_SRC_PERI &&
+                   (cm_calc_handoff_noc_clk_hz(main_cfg, per_cfg) >
+                    CLKMGR_PLL_RAMP_NOCCLK_THRESHOLD_HZ))
+                       return 2;
+       }
+       return 0;
+}
+
+/*
+ * Calculate the new PLL numerator which is based on existing DTS hand off and
+ * intended safe frequency (safe_hz). Note that PLL ramp is only modifying the
+ * numerator while maintaining denominator as denominator will influence the
+ * jitter condition. Please refer A10 HPS TRM for the jitter guide. Note final
+ * value for numerator is minus with 1 to cater our register value
+ * representation.
+ */
+static unsigned int cm_calc_safe_pll_numer(int main0periph1,
+                                 struct mainpll_cfg *main_cfg,
+                                 struct perpll_cfg *per_cfg,
+                                 unsigned int safe_hz)
+{
+       unsigned int clk_hz = 0;
+
+       /* Check for main PLL */
+       if (main0periph1 == 0) {
+               /* Check main VCO clock source: eosc, intosc or f2s? */
+               switch (main_cfg->vco0_psrc) {
+               case CLKMGR_MAINPLL_VCO0_PSRC_EOSC:
+                       clk_hz = eosc1_hz;
+                       break;
+               case CLKMGR_MAINPLL_VCO0_PSRC_E_INTOSC:
+                       clk_hz = cb_intosc_hz;
+                       break;
+               case CLKMGR_MAINPLL_VCO0_PSRC_F2S:
+                       clk_hz = f2s_free_hz;
+                       break;
+               default:
+                       return 0;
+               }
+               /* Applicable if MPU clock is from main PLL */
+               if (main_cfg->mpuclk_src == CLKMGR_MAINPLL_MPUCLK_SRC_MAIN) {
+                       /* calculate the safe numer value */
+                       clk_hz = (safe_hz / clk_hz) *
+                               (main_cfg->mpuclk_cnt + 1) *
+                               ((main_cfg->mpuclk &
+                                 CLKMGR_MAINPLL_MPUCLK_CNT_MSK) + 1) *
+                               (1 + main_cfg->vco1_denom) - 1;
+               }
+               /* Reach here if MPU clk not from main PLL but NOC clk is */
+               else if (main_cfg->nocclk_src ==
+                        CLKMGR_MAINPLL_NOCCLK_SRC_MAIN) {
+                       /* calculate the safe numer value */
+                       clk_hz = (safe_hz / clk_hz) *
+                               (main_cfg->nocclk_cnt + 1) *
+                               ((main_cfg->nocclk &
+                                 CLKMGR_MAINPLL_NOCCLK_CNT_MSK) + 1) *
+                               (1 + main_cfg->vco1_denom) - 1;
+               } else
+                       clk_hz = 0;
+
+       } else if (main0periph1 == 1) {
+               /* Check periph VCO clock source: eosc, intosc, f2s, mainpll */
+               switch (per_cfg->vco0_psrc) {
+               case CLKMGR_PERPLL_VCO0_PSRC_EOSC:
+                       clk_hz = eosc1_hz;
+                       break;
+               case CLKMGR_PERPLL_VCO0_PSRC_E_INTOSC:
+                       clk_hz = cb_intosc_hz;
+                       break;
+               case CLKMGR_PERPLL_VCO0_PSRC_F2S:
+                       clk_hz = f2s_free_hz;
+                       break;
+               case CLKMGR_PERPLL_VCO0_PSRC_MAIN:
+                       clk_hz = cm_calc_handoff_main_vco_clk_hz(
+                                main_cfg);
+                       clk_hz /= main_cfg->cntr15clk_cnt;
+                       break;
+               default:
+                       return 0;
+               }
+               /* Applicable if MPU clock is from periph PLL */
+               if (main_cfg->mpuclk_src == CLKMGR_MAINPLL_MPUCLK_SRC_PERI) {
+                       /* calculate the safe numer value */
+                       clk_hz = (safe_hz / clk_hz) *
+                               (main_cfg->mpuclk_cnt + 1) *
+                               (((main_cfg->mpuclk >>
+                                 CLKMGR_MAINPLL_MPUCLK_PERICNT_LSB) &
+                                 CLKMGR_MAINPLL_MPUCLK_CNT_MSK) + 1) *
+                               (1 + per_cfg->vco1_denom) - 1;
+               }
+               /* Reach here if MPU clk not from periph PLL but NOC clk is */
+               else if (main_cfg->nocclk_src ==
+                        CLKMGR_MAINPLL_NOCCLK_SRC_PERI) {
+                       /* calculate the safe numer value */
+                       clk_hz = (safe_hz / clk_hz) *
+                               (main_cfg->nocclk_cnt + 1) *
+                               (((main_cfg->nocclk >>
+                                 CLKMGR_MAINPLL_NOCCLK_PERICNT_LSB) &
+                                 CLKMGR_MAINPLL_NOCCLK_CNT_MSK) + 1) *
+                               (1 + per_cfg->vco1_denom) - 1;
+               } else
+                       clk_hz = 0;
+       }
+       return clk_hz;
+}
+
+/* ramping the main PLL to final value */
+static void cm_pll_ramp_main(struct mainpll_cfg *main_cfg,
+                           struct perpll_cfg *per_cfg,
+                           unsigned int pll_ramp_main_hz)
+{
+       unsigned int clk_hz = 0, clk_incr_hz = 0, clk_final_hz = 0;
+
+       /* find out the increment value */
+       if (main_cfg->mpuclk_src == CLKMGR_MAINPLL_MPUCLK_SRC_MAIN) {
+               clk_incr_hz = CLKMGR_PLL_RAMP_MPUCLK_INCREMENT_HZ;
+               clk_final_hz = cm_calc_handoff_mpu_clk_hz(main_cfg, per_cfg);
+       } else if (main_cfg->nocclk_src == CLKMGR_MAINPLL_NOCCLK_SRC_MAIN) {
+               clk_incr_hz = CLKMGR_PLL_RAMP_NOCCLK_INCREMENT_HZ;
+               clk_final_hz = cm_calc_handoff_noc_clk_hz(main_cfg, per_cfg);
+       }
+       /* execute the ramping here */
+       for (clk_hz = pll_ramp_main_hz + clk_incr_hz;
+            clk_hz < clk_final_hz; clk_hz += clk_incr_hz) {
+               writel((main_cfg->vco1_denom <<
+                       CLKMGR_MAINPLL_VCO1_DENOM_LSB) |
+                       cm_calc_safe_pll_numer(0, main_cfg, per_cfg, clk_hz),
+                       &clock_manager_base->main_pll.vco1);
+               udelay(1000);
+               cm_wait_for_lock(LOCKED_MASK);
+       }
+       writel((main_cfg->vco1_denom << CLKMGR_MAINPLL_VCO1_DENOM_LSB) |
+               main_cfg->vco1_numer,
+                       &clock_manager_base->main_pll.vco1);
+       udelay(1000);
+       cm_wait_for_lock(LOCKED_MASK);
+}
+
+/* ramping the periph PLL to final value */
+static void cm_pll_ramp_periph(struct mainpll_cfg *main_cfg,
+                             struct perpll_cfg *per_cfg,
+                             unsigned int pll_ramp_periph_hz)
+{
+       unsigned int clk_hz = 0, clk_incr_hz = 0, clk_final_hz = 0;
+
+       /* find out the increment value */
+       if (main_cfg->mpuclk_src == CLKMGR_MAINPLL_MPUCLK_SRC_PERI) {
+               clk_incr_hz = CLKMGR_PLL_RAMP_MPUCLK_INCREMENT_HZ;
+               clk_final_hz = cm_calc_handoff_mpu_clk_hz(main_cfg, per_cfg);
+       } else if (main_cfg->nocclk_src == CLKMGR_MAINPLL_NOCCLK_SRC_PERI) {
+               clk_incr_hz = CLKMGR_PLL_RAMP_NOCCLK_INCREMENT_HZ;
+               clk_final_hz = cm_calc_handoff_noc_clk_hz(main_cfg, per_cfg);
+       }
+       /* execute the ramping here */
+       for (clk_hz = pll_ramp_periph_hz + clk_incr_hz;
+            clk_hz < clk_final_hz; clk_hz += clk_incr_hz) {
+               writel((per_cfg->vco1_denom << CLKMGR_PERPLL_VCO1_DENOM_LSB) |
+                       cm_calc_safe_pll_numer(1, main_cfg, per_cfg, clk_hz),
+                       &clock_manager_base->per_pll.vco1);
+               udelay(1000);
+               cm_wait_for_lock(LOCKED_MASK);
+       }
+       writel((per_cfg->vco1_denom << CLKMGR_PERPLL_VCO1_DENOM_LSB) |
+               per_cfg->vco1_numer,
+               &clock_manager_base->per_pll.vco1);
+       udelay(1000);
+       cm_wait_for_lock(LOCKED_MASK);
+}
+
+/*
+ * Setup clocks while making no assumptions of the
+ * previous state of the clocks.
+ *
+ * Start by being paranoid and gate all sw managed clocks
+ *
+ * Put all plls in bypass
+ *
+ * Put all plls VCO registers back to reset value (bgpwr dwn).
+ *
+ * Put peripheral and main pll src to reset value to avoid glitch.
+ *
+ * Delay 5 us.
+ *
+ * Deassert bg pwr dn and set numerator and denominator
+ *
+ * Start 7 us timer.
+ *
+ * set internal dividers
+ *
+ * Wait for 7 us timer.
+ *
+ * Enable plls
+ *
+ * Set external dividers while plls are locking
+ *
+ * Wait for pll lock
+ *
+ * Assert/deassert outreset all.
+ *
+ * Take all pll's out of bypass
+ *
+ * Clear safe mode
+ *
+ * set source main and peripheral clocks
+ *
+ * Ungate clocks
+ */
+
+static int cm_full_cfg(struct mainpll_cfg *main_cfg, struct perpll_cfg 
*per_cfg)
+{
+       unsigned int pll_ramp_main_hz = 0, pll_ramp_periph_hz = 0,
+               ramp_required;
+
+       /* gate off all mainpll clock excpet HW managed clock */
+       writel(CLKMGR_MAINPLL_EN_S2FUSER0CLKEN_SET_MSK |
+               CLKMGR_MAINPLL_EN_HMCPLLREFCLKEN_SET_MSK,
+               &clock_manager_base->main_pll.enr);
+
+       /* now we can gate off the rest of the peripheral clocks */
+       writel(0, &clock_manager_base->per_pll.en);
+
+       /* Put all plls in external bypass */
+       writel(CLKMGR_MAINPLL_BYPASS_RESET,
+               &clock_manager_base->main_pll.bypasss);
+       writel(CLKMGR_PERPLL_BYPASS_RESET,
+               &clock_manager_base->per_pll.bypasss);
+
+       /*
+        * Put all plls VCO registers back to reset value.
+        * Some code might have messed with them. At same time set the
+        * desired clock source
+        */
+       writel(CLKMGR_MAINPLL_VCO0_RESET |
+               CLKMGR_MAINPLL_VCO0_REGEXTSEL_SET_MSK |
+               (main_cfg->vco0_psrc <<
+                       CLKMGR_MAINPLL_VCO0_PSRC_LSB),
+               &clock_manager_base->main_pll.vco0);
+
+       writel(CLKMGR_PERPLL_VCO0_RESET |
+               CLKMGR_PERPLL_VCO0_REGEXTSEL_SET_MSK |
+               (per_cfg->vco0_psrc <<
+                       CLKMGR_PERPLL_VCO0_PSRC_LSB),
+               &clock_manager_base->per_pll.vco0);
+
+       writel(CLKMGR_MAINPLL_VCO1_RESET,
+               &clock_manager_base->main_pll.vco1);
+       writel(CLKMGR_PERPLL_VCO1_RESET,
+               &clock_manager_base->per_pll.vco1);
+
+       /* clear the interrupt register status register */
+       writel(CLKMGR_CLKMGR_INTR_MAINPLLLOST_SET_MSK |
+               CLKMGR_CLKMGR_INTR_PERPLLLOST_SET_MSK |
+               CLKMGR_CLKMGR_INTR_MAINPLLRFSLIP_SET_MSK |
+               CLKMGR_CLKMGR_INTR_PERPLLRFSLIP_SET_MSK |
+               CLKMGR_CLKMGR_INTR_MAINPLLFBSLIP_SET_MSK |
+               CLKMGR_CLKMGR_INTR_PERPLLFBSLIP_SET_MSK |
+               CLKMGR_CLKMGR_INTR_MAINPLLACHIEVED_SET_MSK |
+               CLKMGR_CLKMGR_INTR_PERPLLACHIEVED_SET_MSK,
+               &clock_manager_base->intr);
+
+       /* Program VCO �Numerator� and �Denominator� for main PLL */
+       ramp_required = cm_is_pll_ramp_required(0, main_cfg, per_cfg);
+       if (ramp_required) {
+               /* set main PLL to safe starting threshold frequency */
+               if (ramp_required == 1)
+                       pll_ramp_main_hz = CLKMGR_PLL_RAMP_MPUCLK_THRESHOLD_HZ;
+               else if (ramp_required == 2)
+                       pll_ramp_main_hz = CLKMGR_PLL_RAMP_NOCCLK_THRESHOLD_HZ;
+
+               writel((main_cfg->vco1_denom << CLKMGR_MAINPLL_VCO1_DENOM_LSB) |
+                       cm_calc_safe_pll_numer(0, main_cfg, per_cfg,
+                       pll_ramp_main_hz),
+                       &clock_manager_base->main_pll.vco1);
+       } else
+               writel((main_cfg->vco1_denom << CLKMGR_MAINPLL_VCO1_DENOM_LSB) |
+                       main_cfg->vco1_numer,
+                       &clock_manager_base->main_pll.vco1);
+
+       /* Program VCO �Numerator� and �Denominator� for periph PLL */
+       ramp_required = cm_is_pll_ramp_required(1, main_cfg, per_cfg);
+       if (ramp_required) {
+               /* set periph PLL to safe starting threshold frequency */
+               if (ramp_required == 1)
+                       pll_ramp_periph_hz =
+                               CLKMGR_PLL_RAMP_MPUCLK_THRESHOLD_HZ;
+               else if (ramp_required == 2)
+                       pll_ramp_periph_hz =
+                               CLKMGR_PLL_RAMP_NOCCLK_THRESHOLD_HZ;
+
+               writel((per_cfg->vco1_denom << CLKMGR_PERPLL_VCO1_DENOM_LSB) |
+                       cm_calc_safe_pll_numer(1, main_cfg, per_cfg,
+                       pll_ramp_periph_hz),
+                       &clock_manager_base->per_pll.vco1);
+       } else
+               writel((per_cfg->vco1_denom << CLKMGR_PERPLL_VCO1_DENOM_LSB) |
+                       per_cfg->vco1_numer,
+                       &clock_manager_base->per_pll.vco1);
+
+       /* Wait for at least 5 us */
+       udelay(5);
+
+       /* Now deassert BGPWRDN and PWRDN */
+       clrbits_le32(&clock_manager_base->main_pll.vco0,
+               CLKMGR_MAINPLL_VCO0_BGPWRDN_SET_MSK |
+               CLKMGR_MAINPLL_VCO0_PWRDN_SET_MSK);
+       clrbits_le32(&clock_manager_base->per_pll.vco0,
+               CLKMGR_PERPLL_VCO0_BGPWRDN_SET_MSK |
+               CLKMGR_PERPLL_VCO0_PWRDN_SET_MSK);
+
+       /* Wait for at least 7 us */
+       udelay(7);
+
+       /* enable the VCO and disable the external regulator to PLL */
+       writel((readl(&clock_manager_base->main_pll.vco0) &
+               ~CLKMGR_MAINPLL_VCO0_REGEXTSEL_SET_MSK) |
+               CLKMGR_MAINPLL_VCO0_EN_SET_MSK,
+               &clock_manager_base->main_pll.vco0);
+       writel((readl(&clock_manager_base->per_pll.vco0) &
+               ~CLKMGR_PERPLL_VCO0_REGEXTSEL_SET_MSK) |
+               CLKMGR_PERPLL_VCO0_EN_SET_MSK,
+               &clock_manager_base->per_pll.vco0);
+
+       /* setup all the main PLL counter and clock source */
+       writel(main_cfg->nocclk,
+              SOCFPGA_CLKMGR_ADDRESS + CLKMGR_MAINPLL_NOC_CLK_OFFSET);
+       writel(main_cfg->mpuclk,
+              SOCFPGA_CLKMGR_ADDRESS + CLKMGR_ALTERAGRP_MPU_CLK_OFFSET);
+
+       /* main_emaca_clk divider */
+       writel(main_cfg->cntr2clk_cnt,
+               &clock_manager_base->main_pll.cntr2clk);
+       /* main_emacb_clk divider */
+       writel(main_cfg->cntr3clk_cnt,
+               &clock_manager_base->main_pll.cntr3clk);
+       /* main_emac_ptp_clk divider */
+       writel(main_cfg->cntr4clk_cnt,
+               &clock_manager_base->main_pll.cntr4clk);
+       /* main_gpio_db_clk divider */
+       writel(main_cfg->cntr5clk_cnt,
+               &clock_manager_base->main_pll.cntr5clk);
+       /* main_sdmmc_clk divider */
+       writel(main_cfg->cntr6clk_cnt,
+               &clock_manager_base->main_pll.cntr6clk);
+       /* main_s2f_user0_clk divider */
+       writel(main_cfg->cntr7clk_cnt |
+               (main_cfg->cntr7clk_src <<
+                       CLKMGR_MAINPLL_CNTR7CLK_SRC_LSB),
+               &clock_manager_base->main_pll.cntr7clk);
+       /* main_s2f_user1_clk divider */
+       writel(main_cfg->cntr8clk_cnt,
+               &clock_manager_base->main_pll.cntr8clk);
+       /* main_hmc_pll_clk divider */
+       writel(main_cfg->cntr9clk_cnt |
+               (main_cfg->cntr9clk_src <<
+                       CLKMGR_MAINPLL_CNTR9CLK_SRC_LSB),
+               &clock_manager_base->main_pll.cntr9clk);
+       /* main_periph_ref_clk divider */
+       writel(main_cfg->cntr15clk_cnt,
+               &clock_manager_base->main_pll.cntr15clk);
+
+       /* setup all the peripheral PLL counter and clock source */
+       /* peri_emaca_clk divider */
+       writel(per_cfg->cntr2clk_cnt |
+               (per_cfg->cntr2clk_src << CLKMGR_PERPLL_CNTR2CLK_SRC_LSB),
+               &clock_manager_base->per_pll.cntr2clk);
+       /* peri_emacb_clk divider */
+       writel(per_cfg->cntr3clk_cnt |
+               (per_cfg->cntr3clk_src << CLKMGR_PERPLL_CNTR3CLK_SRC_LSB),
+               &clock_manager_base->per_pll.cntr3clk);
+       /* peri_emac_ptp_clk divider */
+       writel(per_cfg->cntr4clk_cnt |
+               (per_cfg->cntr4clk_src << CLKMGR_PERPLL_CNTR4CLK_SRC_LSB),
+               &clock_manager_base->per_pll.cntr4clk);
+       /* peri_gpio_db_clk divider */
+       writel(per_cfg->cntr5clk_cnt |
+               (per_cfg->cntr5clk_src << CLKMGR_PERPLL_CNTR5CLK_SRC_LSB),
+               &clock_manager_base->per_pll.cntr5clk);
+       /* peri_sdmmc_clk divider */
+       writel(per_cfg->cntr6clk_cnt |
+               (per_cfg->cntr6clk_src << CLKMGR_PERPLL_CNTR6CLK_SRC_LSB),
+               &clock_manager_base->per_pll.cntr6clk);
+       /* peri_s2f_user0_clk divider */
+       writel(per_cfg->cntr7clk_cnt,
+               &clock_manager_base->per_pll.cntr7clk);
+       /* peri_s2f_user1_clk divider */
+       writel(per_cfg->cntr8clk_cnt |
+               (per_cfg->cntr8clk_src << CLKMGR_PERPLL_CNTR8CLK_SRC_LSB),
+               &clock_manager_base->per_pll.cntr8clk);
+       /* peri_hmc_pll_clk divider */
+       writel(per_cfg->cntr9clk_cnt,
+               &clock_manager_base->per_pll.cntr9clk);
+
+       /* setup all the external PLL counter */
+       /* mpu wrapper / external divider */
+       writel(main_cfg->mpuclk_cnt |
+               (main_cfg->mpuclk_src <<
+                       CLKMGR_MAINPLL_MPUCLK_SRC_LSB),
+               &clock_manager_base->main_pll.mpuclk);
+       /* NOC wrapper / external divider */
+       writel(main_cfg->nocclk_cnt |
+               (main_cfg->nocclk_src << CLKMGR_MAINPLL_NOCCLK_SRC_LSB),
+               &clock_manager_base->main_pll.nocclk);
+       /* NOC subclock divider such as l4 */
+       writel(main_cfg->nocdiv_l4mainclk |
+               (main_cfg->nocdiv_l4mpclk <<
+                       CLKMGR_MAINPLL_NOCDIV_L4MPCLK_LSB) |
+               (main_cfg->nocdiv_l4spclk <<
+                       CLKMGR_MAINPLL_NOCDIV_L4SPCLK_LSB) |
+               (main_cfg->nocdiv_csatclk <<
+                       CLKMGR_MAINPLL_NOCDIV_CSATCLK_LSB) |
+               (main_cfg->nocdiv_cstraceclk <<
+                       CLKMGR_MAINPLL_NOCDIV_CSTRACECLK_LSB) |
+               (main_cfg->nocdiv_cspdbclk <<
+                       CLKMGR_MAINPLL_NOCDIV_CSPDBGCLK_LSB),
+               &clock_manager_base->main_pll.nocdiv);
+       /* gpio_db external divider */
+       writel(per_cfg->gpiodiv_gpiodbclk,
+               &clock_manager_base->per_pll.gpiodiv);
+
+       /* setup the EMAC clock mux select */
+       writel((per_cfg->emacctl_emac0sel <<
+                       CLKMGR_PERPLL_EMACCTL_EMAC0SEL_LSB) |
+               (per_cfg->emacctl_emac1sel <<
+                       CLKMGR_PERPLL_EMACCTL_EMAC1SEL_LSB) |
+               (per_cfg->emacctl_emac2sel <<
+                       CLKMGR_PERPLL_EMACCTL_EMAC2SEL_LSB),
+               &clock_manager_base->per_pll.emacctl);
+
+       /* at this stage, check for PLL lock status */
+       cm_wait_for_lock(LOCKED_MASK);
+
+       /*
+        * after locking, but before taking out of bypass,
+        * assert/deassert outresetall
+        */
+       /* assert mainpll outresetall */
+       setbits_le32(&clock_manager_base->main_pll.vco0,
+               CLKMGR_MAINPLL_VCO0_OUTRSTALL_SET_MSK);
+       /* assert perpll outresetall */
+       setbits_le32(&clock_manager_base->per_pll.vco0,
+               CLKMGR_PERPLL_VCO0_OUTRSTALL_SET_MSK);
+       /* de-assert mainpll outresetall */
+       clrbits_le32(&clock_manager_base->main_pll.vco0,
+               CLKMGR_MAINPLL_VCO0_OUTRSTALL_SET_MSK);
+       /* de-assert perpll outresetall */
+       clrbits_le32(&clock_manager_base->per_pll.vco0,
+               CLKMGR_PERPLL_VCO0_OUTRSTALL_SET_MSK);
+
+       /* Take all PLLs out of bypass when boot mode is cleared. */
+       /* release mainpll from bypass */
+       writel(CLKMGR_MAINPLL_BYPASS_RESET,
+               &clock_manager_base->main_pll.bypassr);
+       /* wait till Clock Manager is not busy */
+       cm_wait_for_fsm();
+
+       /* release perpll from bypass */
+       writel(CLKMGR_PERPLL_BYPASS_RESET,
+               &clock_manager_base->per_pll.bypassr);
+       /* wait till Clock Manager is not busy */
+       cm_wait_for_fsm();
+
+       /* clear boot mode */
+       clrbits_le32(&clock_manager_base->ctrl,
+               CLKMGR_CLKMGR_CTL_BOOTMOD_SET_MSK);
+       /* wait till Clock Manager is not busy */
+       cm_wait_for_fsm();
+
+       /* At here, we need to ramp to final value if needed */
+       if (pll_ramp_main_hz != 0)
+               cm_pll_ramp_main(main_cfg, per_cfg, pll_ramp_main_hz);
+       if (pll_ramp_periph_hz != 0)
+               cm_pll_ramp_periph(main_cfg, per_cfg, pll_ramp_periph_hz);
+
+       /* Now ungate non-hw-managed clocks */
+       writel(CLKMGR_MAINPLL_EN_S2FUSER0CLKEN_SET_MSK |
+               CLKMGR_MAINPLL_EN_HMCPLLREFCLKEN_SET_MSK,
+               &clock_manager_base->main_pll.ens);
+       writel(CLKMGR_PERPLL_EN_RESET,
+               &clock_manager_base->per_pll.ens);
+
+       /* Clear the loss lock and slip bits as they might set during
+       clock reconfiguration */
+       writel(CLKMGR_CLKMGR_INTR_MAINPLLLOST_SET_MSK |
+               CLKMGR_CLKMGR_INTR_PERPLLLOST_SET_MSK |
+               CLKMGR_CLKMGR_INTR_MAINPLLRFSLIP_SET_MSK |
+               CLKMGR_CLKMGR_INTR_PERPLLRFSLIP_SET_MSK |
+               CLKMGR_CLKMGR_INTR_MAINPLLFBSLIP_SET_MSK |
+               CLKMGR_CLKMGR_INTR_PERPLLFBSLIP_SET_MSK,
+               &clock_manager_base->intr);
+
+       return 0;
+}
+
+int cm_basic_init(const void *blob)
+{
+       struct mainpll_cfg main_cfg;
+       struct perpll_cfg per_cfg;
+       struct alteragrp_cfg altrgrp_cfg;
+       int rval;
+
+       /* initialize to zero for use case of optional node */
+       memset(&main_cfg, 0, sizeof(main_cfg));
+       memset(&per_cfg, 0, sizeof(per_cfg));
+       memset(&altrgrp_cfg, 0, sizeof(altrgrp_cfg));
+
+       if (of_get_clk_cfg(blob, &main_cfg, &per_cfg, &altrgrp_cfg)) {
+               return 1;
+       }
+
+       rval =  cm_full_cfg(&main_cfg, &per_cfg);
+
+       cm_l4_main_clk_hz =
+               cm_get_l4_noc_hz(CLKMGR_MAINPLL_NOCDIV_L4MAINCLK_LSB);
+
+       cm_l4_mp_clk_hz = cm_get_l4_noc_hz(CLKMGR_MAINPLL_NOCDIV_L4MPCLK_LSB);
+
+       cm_l4_sp_clk_hz = cm_get_l4_sp_clk_hz();
+
+       cm_l4_sys_free_clk_hz = cm_get_noc_clk_hz()/4;
+
+       return rval;
+}
diff --git a/arch/arm/mach-socfpga/clock_manager.c 
b/arch/arm/mach-socfpga/clock_manager_gen5.c
similarity index 62%
copy from arch/arm/mach-socfpga/clock_manager.c
copy to arch/arm/mach-socfpga/clock_manager_gen5.c
index aa71636..f4bb02b 100644
--- a/arch/arm/mach-socfpga/clock_manager.c
+++ b/arch/arm/mach-socfpga/clock_manager_gen5.c
@@ -1,7 +1,7 @@
 /*
- *  Copyright (C) 2013 Altera Corporation <www.altera.com>
+ * Copyright (C) 2016, Intel Corporation
  *
- * SPDX-License-Identifier:    GPL-2.0+
+ * SPDX-License-Identifier:    GPL-2.0
  */
 
 #include <common.h>
@@ -10,31 +10,19 @@
 
 DECLARE_GLOBAL_DATA_PTR;
 
+const unsigned int cm_get_osc_clk_hz(const int osc);
+const unsigned int cm_get_f2s_per_ref_clk_hz(void);
+const unsigned int cm_get_f2s_sdr_ref_clk_hz(void);
+static void cm_write_bypass(uint32_t val);
+static void cm_write_ctrl(uint32_t val);
+static void cm_write_with_phase(uint32_t value,
+         uint32_t reg_address, uint32_t mask);
+unsigned long cm_get_sdram_clk_hz(void);
+int set_cpu_clk_info(void);
+
 static const struct socfpga_clock_manager *clock_manager_base =
        (struct socfpga_clock_manager *)SOCFPGA_CLKMGR_ADDRESS;
 
-static void cm_wait_for_lock(uint32_t mask)
-{
-       register uint32_t inter_val;
-       uint32_t retry = 0;
-       do {
-               inter_val = readl(&clock_manager_base->inter) & mask;
-               if (inter_val == mask)
-                       retry++;
-               else
-                       retry = 0;
-               if (retry >= 10)
-                       break;
-       } while (1);
-}
-
-/* function to poll in the fsm busy bit */
-static void cm_wait_for_fsm(void)
-{
-       while (readl(&clock_manager_base->stat) & CLKMGR_STAT_BUSY)
-               ;
-}
-
 /*
  * function to write the bypass register which requires a poll of the
  * busy bit
@@ -87,7 +75,6 @@ static void cm_write_with_phase(uint32_t value,
  * set source main and peripheral clocks
  * Ungate clocks
  */
-
 void cm_basic_init(const struct cm_config * const cfg)
 {
        unsigned long end;
@@ -230,11 +217,6 @@ void cm_basic_init(const struct cm_config * const cfg)
 
        writel(cfg->gpiodiv, &clock_manager_base->per_pll.gpiodiv);
 
-#define LOCKED_MASK \
-       (CLKMGR_INTER_SDRPLLLOCKED_MASK  | \
-       CLKMGR_INTER_PERPLLLOCKED_MASK  | \
-       CLKMGR_INTER_MAINPLLLOCKED_MASK)
-
        cm_wait_for_lock(LOCKED_MASK);
 
        /* write the sdram clock counters before toggling outreset all */
@@ -328,60 +310,6 @@ void cm_basic_init(const struct cm_config * const cfg)
               &clock_manager_base->inter);
 }
 
-static unsigned int cm_get_main_vco_clk_hz(void)
-{
-       uint32_t reg, clock;
-
-       /* get the main VCO clock */
-       reg = readl(&clock_manager_base->main_pll.vco);
-       clock = cm_get_osc_clk_hz(1);
-       clock /= ((reg & CLKMGR_MAINPLLGRP_VCO_DENOM_MASK) >>
-                 CLKMGR_MAINPLLGRP_VCO_DENOM_OFFSET) + 1;
-       clock *= ((reg & CLKMGR_MAINPLLGRP_VCO_NUMER_MASK) >>
-                 CLKMGR_MAINPLLGRP_VCO_NUMER_OFFSET) + 1;
-
-       return clock;
-}
-
-static unsigned int cm_get_per_vco_clk_hz(void)
-{
-       uint32_t reg, clock = 0;
-
-       /* identify PER PLL clock source */
-       reg = readl(&clock_manager_base->per_pll.vco);
-       reg = (reg & CLKMGR_PERPLLGRP_VCO_SSRC_MASK) >>
-             CLKMGR_PERPLLGRP_VCO_SSRC_OFFSET;
-       if (reg == CLKMGR_VCO_SSRC_EOSC1)
-               clock = cm_get_osc_clk_hz(1);
-       else if (reg == CLKMGR_VCO_SSRC_EOSC2)
-               clock = cm_get_osc_clk_hz(2);
-       else if (reg == CLKMGR_VCO_SSRC_F2S)
-               clock = cm_get_f2s_per_ref_clk_hz();
-
-       /* get the PER VCO clock */
-       reg = readl(&clock_manager_base->per_pll.vco);
-       clock /= ((reg & CLKMGR_PERPLLGRP_VCO_DENOM_MASK) >>
-                 CLKMGR_PERPLLGRP_VCO_DENOM_OFFSET) + 1;
-       clock *= ((reg & CLKMGR_PERPLLGRP_VCO_NUMER_MASK) >>
-                 CLKMGR_PERPLLGRP_VCO_NUMER_OFFSET) + 1;
-
-       return clock;
-}
-
-unsigned long cm_get_mpu_clk_hz(void)
-{
-       uint32_t reg, clock;
-
-       clock = cm_get_main_vco_clk_hz();
-
-       /* get the MPU clock */
-       reg = readl(&clock_manager_base->altera.mpuclk);
-       clock /= (reg + 1);
-       reg = readl(&clock_manager_base->main_pll.mpuclk);
-       clock /= (reg + 1);
-       return clock;
-}
-
 unsigned long cm_get_sdram_clk_hz(void)
 {
        uint32_t reg, clock = 0;
@@ -412,147 +340,3 @@ unsigned long cm_get_sdram_clk_hz(void)
 
        return clock;
 }
-
-unsigned int cm_get_l4_sp_clk_hz(void)
-{
-       uint32_t reg, clock = 0;
-
-       /* identify the source of L4 SP clock */
-       reg = readl(&clock_manager_base->main_pll.l4src);
-       reg = (reg & CLKMGR_MAINPLLGRP_L4SRC_L4SP) >>
-             CLKMGR_MAINPLLGRP_L4SRC_L4SP_OFFSET;
-
-       if (reg == CLKMGR_L4_SP_CLK_SRC_MAINPLL) {
-               clock = cm_get_main_vco_clk_hz();
-
-               /* get the clock prior L4 SP divider (main clk) */
-               reg = readl(&clock_manager_base->altera.mainclk);
-               clock /= (reg + 1);
-               reg = readl(&clock_manager_base->main_pll.mainclk);
-               clock /= (reg + 1);
-       } else if (reg == CLKMGR_L4_SP_CLK_SRC_PERPLL) {
-               clock = cm_get_per_vco_clk_hz();
-
-               /* get the clock prior L4 SP divider (periph_base_clk) */
-               reg = readl(&clock_manager_base->per_pll.perbaseclk);
-               clock /= (reg + 1);
-       }
-
-       /* get the L4 SP clock which supplied to UART */
-       reg = readl(&clock_manager_base->main_pll.maindiv);
-       reg = (reg & CLKMGR_MAINPLLGRP_MAINDIV_L4SPCLK_MASK) >>
-             CLKMGR_MAINPLLGRP_MAINDIV_L4SPCLK_OFFSET;
-       clock = clock / (1 << reg);
-
-       return clock;
-}
-
-unsigned int cm_get_mmc_controller_clk_hz(void)
-{
-       uint32_t reg, clock = 0;
-
-       /* identify the source of MMC clock */
-       reg = readl(&clock_manager_base->per_pll.src);
-       reg = (reg & CLKMGR_PERPLLGRP_SRC_SDMMC_MASK) >>
-             CLKMGR_PERPLLGRP_SRC_SDMMC_OFFSET;
-
-       if (reg == CLKMGR_SDMMC_CLK_SRC_F2S) {
-               clock = cm_get_f2s_per_ref_clk_hz();
-       } else if (reg == CLKMGR_SDMMC_CLK_SRC_MAIN) {
-               clock = cm_get_main_vco_clk_hz();
-
-               /* get the SDMMC clock */
-               reg = readl(&clock_manager_base->main_pll.mainnandsdmmcclk);
-               clock /= (reg + 1);
-       } else if (reg == CLKMGR_SDMMC_CLK_SRC_PER) {
-               clock = cm_get_per_vco_clk_hz();
-
-               /* get the SDMMC clock */
-               reg = readl(&clock_manager_base->per_pll.pernandsdmmcclk);
-               clock /= (reg + 1);
-       }
-
-       /* further divide by 4 as we have fixed divider at wrapper */
-       clock /= 4;
-       return clock;
-}
-
-unsigned int cm_get_qspi_controller_clk_hz(void)
-{
-       uint32_t reg, clock = 0;
-
-       /* identify the source of QSPI clock */
-       reg = readl(&clock_manager_base->per_pll.src);
-       reg = (reg & CLKMGR_PERPLLGRP_SRC_QSPI_MASK) >>
-             CLKMGR_PERPLLGRP_SRC_QSPI_OFFSET;
-
-       if (reg == CLKMGR_QSPI_CLK_SRC_F2S) {
-               clock = cm_get_f2s_per_ref_clk_hz();
-       } else if (reg == CLKMGR_QSPI_CLK_SRC_MAIN) {
-               clock = cm_get_main_vco_clk_hz();
-
-               /* get the qspi clock */
-               reg = readl(&clock_manager_base->main_pll.mainqspiclk);
-               clock /= (reg + 1);
-       } else if (reg == CLKMGR_QSPI_CLK_SRC_PER) {
-               clock = cm_get_per_vco_clk_hz();
-
-               /* get the qspi clock */
-               reg = readl(&clock_manager_base->per_pll.perqspiclk);
-               clock /= (reg + 1);
-       }
-
-       return clock;
-}
-
-unsigned int cm_get_spi_controller_clk_hz(void)
-{
-       uint32_t reg, clock = 0;
-
-       clock = cm_get_per_vco_clk_hz();
-
-       /* get the clock prior L4 SP divider (periph_base_clk) */
-       reg = readl(&clock_manager_base->per_pll.perbaseclk);
-       clock /= (reg + 1);
-
-       return clock;
-}
-
-static void cm_print_clock_quick_summary(void)
-{
-       printf("MPU       %10ld kHz\n", cm_get_mpu_clk_hz() / 1000);
-       printf("DDR       %10ld kHz\n", cm_get_sdram_clk_hz() / 1000);
-       printf("EOSC1       %8d kHz\n", cm_get_osc_clk_hz(1) / 1000);
-       printf("EOSC2       %8d kHz\n", cm_get_osc_clk_hz(2) / 1000);
-       printf("F2S_SDR_REF %8d kHz\n", cm_get_f2s_sdr_ref_clk_hz() / 1000);
-       printf("F2S_PER_REF %8d kHz\n", cm_get_f2s_per_ref_clk_hz() / 1000);
-       printf("MMC         %8d kHz\n", cm_get_mmc_controller_clk_hz() / 1000);
-       printf("QSPI        %8d kHz\n", cm_get_qspi_controller_clk_hz() / 1000);
-       printf("UART        %8d kHz\n", cm_get_l4_sp_clk_hz() / 1000);
-       printf("SPI         %8d kHz\n", cm_get_spi_controller_clk_hz() / 1000);
-}
-
-int set_cpu_clk_info(void)
-{
-       /* Calculate the clock frequencies required for drivers */
-       cm_get_l4_sp_clk_hz();
-       cm_get_mmc_controller_clk_hz();
-
-       gd->bd->bi_arm_freq = cm_get_mpu_clk_hz() / 1000000;
-       gd->bd->bi_dsp_freq = 0;
-       gd->bd->bi_ddr_freq = cm_get_sdram_clk_hz() / 1000000;
-
-       return 0;
-}
-
-int do_showclocks(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
-{
-       cm_print_clock_quick_summary();
-       return 0;
-}
-
-U_BOOT_CMD(
-       clocks, CONFIG_SYS_MAXARGS, 1, do_showclocks,
-       "display clocks",
-       ""
-);
diff --git a/arch/arm/mach-socfpga/include/mach/clock_manager.h 
b/arch/arm/mach-socfpga/include/mach/clock_manager.h
index 2675951..45943ea 100644
--- a/arch/arm/mach-socfpga/include/mach/clock_manager.h
+++ b/arch/arm/mach-socfpga/include/mach/clock_manager.h
@@ -1,5 +1,5 @@
 /*
- *  Copyright (C) 2013 Altera Corporation <www.altera.com>
+ *  Copyright (C) 2013-2016 Altera Corporation <www.altera.com>
  *
  * SPDX-License-Identifier:    GPL-2.0+
  */
@@ -8,21 +8,9 @@
 #define        _CLOCK_MANAGER_H_
 
 #ifndef __ASSEMBLER__
-/* Clock speed accessors */
-unsigned long cm_get_mpu_clk_hz(void);
-unsigned long cm_get_sdram_clk_hz(void);
-unsigned int cm_get_l4_sp_clk_hz(void);
-unsigned int cm_get_mmc_controller_clk_hz(void);
-unsigned int cm_get_qspi_controller_clk_hz(void);
-unsigned int cm_get_spi_controller_clk_hz(void);
-const unsigned int cm_get_osc_clk_hz(const int osc);
-const unsigned int cm_get_f2s_per_ref_clk_hz(void);
-const unsigned int cm_get_f2s_sdr_ref_clk_hz(void);
-
-/* Clock configuration accessors */
-const struct cm_config * const cm_get_default_config(void);
-#endif
+#include <linux/types.h>
 
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
 struct cm_config {
        /* main group */
        uint32_t main_vco_base;
@@ -57,74 +45,196 @@ struct cm_config {
        uint32_t s2fuser2clk;
 };
 
+struct socfpga_clock_manager_sdr_pll {
+       uint32_t        vco;
+       uint32_t        ctrl;
+       uint32_t        ddrdqsclk;
+       uint32_t        ddr2xdqsclk;
+       uint32_t        ddrdqclk;
+       uint32_t        s2fuser2clk;
+       uint32_t        en;
+       uint32_t        stat;
+};
+#endif
+
+/* Common prototypes */
+unsigned int cm_get_l4_sp_clk_hz(void);
+unsigned int cm_get_qspi_controller_clk_hz(void);
+unsigned int cm_get_mmc_controller_clk_hz(void);
+unsigned int cm_get_spi_controller_clk_hz(void);
+void cm_use_intosc(void);
+void cm_wait_for_lock(uint32_t mask);
+void cm_wait_for_fsm(void);
+unsigned int cm_get_main_vco_clk_hz(void);
+unsigned int cm_get_per_vco_clk_hz(void);
+unsigned long cm_get_mpu_clk_hz(void);
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+/* Clock speed accessors */
+const unsigned int cm_get_osc_clk_hz(const int osc);
+const unsigned int cm_get_f2s_per_ref_clk_hz(void);
+const unsigned int cm_get_f2s_sdr_ref_clk_hz(void);
 void cm_basic_init(const struct cm_config * const cfg);
+unsigned long cm_get_sdram_clk_hz(void);
+/* Clock configuration accessors */
+const struct cm_config * const cm_get_default_config(void);
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+unsigned int cm_get_noc_clk_hz(void);
+unsigned int cm_get_l4_noc_hz(unsigned int nocdivshift);
+int cm_basic_init(const void* blob);
+extern unsigned int cm_l4_main_clk_hz;
+extern unsigned int cm_l4_sp_clk_hz;
+extern unsigned int cm_l4_mp_clk_hz;
+extern unsigned int cm_l4_sys_free_clk_hz;
+extern uint32_t eosc1_hz;
+extern uint32_t cb_intosc_hz;
+extern uint32_t f2s_free_hz;
+#endif
+#endif
 
 struct socfpga_clock_manager_main_pll {
-       u32     vco;
-       u32     misc;
-       u32     mpuclk;
-       u32     mainclk;
-       u32     dbgatclk;
-       u32     mainqspiclk;
-       u32     mainnandsdmmcclk;
-       u32     cfgs2fuser0clk;
-       u32     en;
-       u32     maindiv;
-       u32     dbgdiv;
-       u32     tracediv;
-       u32     l4src;
-       u32     stat;
-       u32     _pad_0x38_0x40[2];
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       uint32_t        vco;
+       uint32_t        misc;
+       uint32_t        mpuclk;
+       uint32_t        mainclk;
+       uint32_t        dbgatclk;
+       uint32_t        mainqspiclk;
+       uint32_t        mainnandsdmmcclk;
+       uint32_t        cfgs2fuser0clk;
+       uint32_t        en;
+       uint32_t        maindiv;
+       uint32_t        dbgdiv;
+       uint32_t        tracediv;
+       uint32_t        l4src;
+       uint32_t        stat;
+       uint32_t        _pad_0x38_0x40[2];
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       uint32_t  vco0;
+       uint32_t  vco1;
+       uint32_t  en;
+       uint32_t  ens;
+       uint32_t  enr;
+       uint32_t  bypass;
+       uint32_t  bypasss;
+       uint32_t  bypassr;
+       uint32_t  mpuclk;
+       uint32_t  nocclk;
+       uint32_t  cntr2clk;
+       uint32_t  cntr3clk;
+       uint32_t  cntr4clk;
+       uint32_t  cntr5clk;
+       uint32_t  cntr6clk;
+       uint32_t  cntr7clk;
+       uint32_t  cntr8clk;
+       uint32_t  cntr9clk;
+       uint32_t  pad_0x48_0x5b[5];
+       uint32_t  cntr15clk;
+       uint32_t  outrst;
+       uint32_t  outrststat;
+       uint32_t  nocdiv;
+       uint32_t  pad_0x6c_0x80[5];
+#endif
 };
 
 struct socfpga_clock_manager_per_pll {
-       u32     vco;
-       u32     misc;
-       u32     emac0clk;
-       u32     emac1clk;
-       u32     perqspiclk;
-       u32     pernandsdmmcclk;
-       u32     perbaseclk;
-       u32     s2fuser1clk;
-       u32     en;
-       u32     div;
-       u32     gpiodiv;
-       u32     src;
-       u32     stat;
-       u32     _pad_0x34_0x40[3];
-};
-
-struct socfpga_clock_manager_sdr_pll {
-       u32     vco;
-       u32     ctrl;
-       u32     ddrdqsclk;
-       u32     ddr2xdqsclk;
-       u32     ddrdqclk;
-       u32     s2fuser2clk;
-       u32     en;
-       u32     stat;
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       uint32_t        vco;
+       uint32_t        misc;
+       uint32_t        emac0clk;
+       uint32_t        emac1clk;
+       uint32_t        perqspiclk;
+       uint32_t        pernandsdmmcclk;
+       uint32_t        perbaseclk;
+       uint32_t        s2fuser1clk;
+       uint32_t        en;
+       uint32_t        div;
+       uint32_t        gpiodiv;
+       uint32_t        src;
+       uint32_t        stat;
+       uint32_t        _pad_0x34_0x40[3];
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       uint32_t  vco0;
+       uint32_t  vco1;
+       uint32_t  en;
+       uint32_t  ens;
+       uint32_t  enr;
+       uint32_t  bypass;
+       uint32_t  bypasss;
+       uint32_t  bypassr;
+       uint32_t  pad_0x20_0x27[2];
+       uint32_t  cntr2clk;
+       uint32_t  cntr3clk;
+       uint32_t  cntr4clk;
+       uint32_t  cntr5clk;
+       uint32_t  cntr6clk;
+       uint32_t  cntr7clk;
+       uint32_t  cntr8clk;
+       uint32_t  cntr9clk;
+       uint32_t  pad_0x48_0x5f[6];
+       uint32_t  outrst;
+       uint32_t  outrststat;
+       uint32_t  emacctl;
+       uint32_t  gpiodiv;
+       uint32_t  pad_0x70_0x80[4];
+#endif
 };
 
 struct socfpga_clock_manager_altera {
-       u32     mpuclk;
-       u32     mainclk;
+       uint32_t        mpuclk;
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       uint32_t        mainclk;
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       uint32_t        nocclk;
+       uint32_t        mainmisc0;
+       uint32_t        mainmisc1;
+       uint32_t        perimisc0;
+       uint32_t        perimisc1;
+#endif
 };
 
 struct socfpga_clock_manager {
-       u32     ctrl;
-       u32     bypass;
-       u32     inter;
-       u32     intren;
-       u32     dbctrl;
-       u32     stat;
-       u32     _pad_0x18_0x3f[10];
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+       uint32_t        ctrl;
+       uint32_t        bypass;
+       uint32_t        inter;
+       uint32_t        intren;
+       uint32_t        dbctrl;
+       uint32_t        stat;
+       uint32_t        _pad_0x18_0x3f[10];
        struct socfpga_clock_manager_main_pll main_pll;
        struct socfpga_clock_manager_per_pll per_pll;
        struct socfpga_clock_manager_sdr_pll sdr_pll;
        struct socfpga_clock_manager_altera altera;
-       u32     _pad_0xe8_0x200[70];
+       uint32_t        _pad_0xe8_0x200[70];
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+       /* clkmgr */
+       uint32_t  ctrl;
+       uint32_t  intr;
+       uint32_t  intrs;
+       uint32_t  intrr;
+       uint32_t  intren;
+       uint32_t  intrens;
+       uint32_t  intrenr;
+       uint32_t  stat;
+       uint32_t  testioctrl;
+       uint32_t  _pad_0x24_0x40[7];
+       /* mainpllgrp */
+       struct socfpga_clock_manager_main_pll main_pll;
+       /* perpllgrp */
+       struct socfpga_clock_manager_per_pll per_pll;
+       struct socfpga_clock_manager_altera altera;
+#endif
 };
 
+/* Common mask */
+#define CLKMGR_CLKMGR_STAT_BUSY_SET_MSK                        0x00000001
+
+#if defined(CONFIG_TARGET_SOCFPGA_GEN5)
+#define LOCKED_MASK \
+       (CLKMGR_INTER_SDRPLLLOCKED_MASK  | \
+       CLKMGR_INTER_PERPLLLOCKED_MASK  | \
+       CLKMGR_INTER_MAINPLLLOCKED_MASK)
+
 #define CLKMGR_CTRL_SAFEMODE                           (1 << 0)
 #define CLKMGR_CTRL_SAFEMODE_OFFSET                    0
 
@@ -310,5 +420,119 @@ struct socfpga_clock_manager {
 #define CLKMGR_SDRPLLGRP_S2FUSER2CLK_CNT_MASK          0x000001ff
 #define CLKMGR_SDRPLLGRP_S2FUSER2CLK_PHASE_OFFSET      9
 #define CLKMGR_SDRPLLGRP_S2FUSER2CLK_PHASE_MASK                0x00000e00
-
+#elif defined(CONFIG_TARGET_SOCFPGA_ARRIA10)
+#define CLKMGR_ALTERAGRP_MPU_CLK_OFFSET                        0x140
+#define CLKMGR_MAINPLL_NOC_CLK_OFFSET                  0x144
+#define LOCKED_MASK \
+       (CLKMGR_CLKMGR_STAT_MAINPLLLOCKED_SET_MSK  | \
+       CLKMGR_CLKMGR_STAT_PERPLLLOCKED_SET_MSK)
+
+/* value */
+#define CLKMGR_MAINPLL_BYPASS_RESET                    0x0000003f
+#define CLKMGR_PERPLL_BYPASS_RESET                     0x000000ff
+#define CLKMGR_MAINPLL_VCO0_RESET                      0x00010053
+#define CLKMGR_MAINPLL_VCO1_RESET                      0x00010001
+#define CLKMGR_PERPLL_VCO0_RESET                       0x00010053
+#define CLKMGR_PERPLL_VCO1_RESET                       0x00010001
+#define CLKMGR_MAINPLL_VCO0_PSRC_EOSC                  0x0
+#define CLKMGR_MAINPLL_VCO0_PSRC_E_INTOSC              0x1
+#define CLKMGR_MAINPLL_VCO0_PSRC_F2S                   0x2
+#define CLKMGR_PERPLL_VCO0_PSRC_EOSC                   0x0
+#define CLKMGR_PERPLL_VCO0_PSRC_E_INTOSC               0x1
+#define CLKMGR_PERPLL_VCO0_PSRC_F2S                    0x2
+#define CLKMGR_PERPLL_VCO0_PSRC_MAIN                   0x3
+
+/* mask */
+#define CLKMGR_MAINPLL_EN_S2FUSER0CLKEN_SET_MSK                0x00000040
+#define CLKMGR_MAINPLL_EN_HMCPLLREFCLKEN_SET_MSK       0x00000080
+#define CLKMGR_CLKMGR_STAT_MAINPLLLOCKED_SET_MSK       0x00000100
+#define CLKMGR_CLKMGR_STAT_PERPLLLOCKED_SET_MSK                0x00000200
+#define CLKMGR_CLKMGR_STAT_BOOTCLKSRC_SET_MSK          0x00020000
+#define CLKMGR_MAINPLL_VCO0_BGPWRDN_SET_MSK            0x00000001
+#define CLKMGR_MAINPLL_VCO0_PWRDN_SET_MSK              0x00000002
+#define CLKMGR_MAINPLL_VCO0_EN_SET_MSK                 0x00000004
+#define CLKMGR_MAINPLL_VCO0_OUTRSTALL_SET_MSK          0x00000008
+#define CLKMGR_MAINPLL_VCO0_REGEXTSEL_SET_MSK          0x00000010
+#define CLKMGR_PERPLL_VCO0_BGPWRDN_SET_MSK             0x00000001
+#define CLKMGR_PERPLL_VCO0_PWRDN_SET_MSK               0x00000002
+#define CLKMGR_PERPLL_VCO0_EN_SET_MSK                  0x00000004
+#define CLKMGR_PERPLL_VCO0_OUTRSTALL_SET_MSK           0x00000008
+#define CLKMGR_PERPLL_VCO0_REGEXTSEL_SET_MSK           0x00000010
+#define CLKMGR_CLKMGR_INTR_PERPLLFBSLIP_SET_MSK                0x00000800
+#define CLKMGR_CLKMGR_INTR_MAINPLLFBSLIP_SET_MSK       0x00000400
+#define CLKMGR_CLKMGR_INTR_PERPLLRFSLIP_SET_MSK                0x00000200
+#define CLKMGR_CLKMGR_INTR_MAINPLLRFSLIP_SET_MSK       0x00000100
+#define CLKMGR_CLKMGR_INTR_PERPLLLOST_SET_MSK          0x00000008
+#define CLKMGR_CLKMGR_INTR_MAINPLLLOST_SET_MSK         0x00000004
+#define CLKMGR_CLKMGR_INTR_MAINPLLACHIEVED_SET_MSK     0x00000001
+#define CLKMGR_CLKMGR_INTR_PERPLLACHIEVED_SET_MSK      0x00000002
+#define CLKMGR_CLKMGR_CTL_BOOTMOD_SET_MSK              0x00000001
+#define CLKMGR_CLKMGR_CTL_BOOTCLK_INTOSC_SET_MSK       0x00000300
+#define CLKMGR_PERPLL_EN_RESET                         0x00000f7f
+#define CLKMGR_PERPLLGRP_EN_SDMMCCLK_MASK              0x00000020
+#define CLKMGR_MAINPLL_VCO0_PSRC_MSK                   0x00000003
+#define CLKMGR_MAINPLL_VCO1_NUMER_MSK                  0x00001fff
+#define CLKMGR_MAINPLL_VCO1_DENOM_MSK                  0x0000003f
+#define CLKMGR_MAINPLL_CNTRCLK_MSK                     0x000003ff
+#define CLKMGR_PERPLL_VCO0_PSRC_MSK                    0x00000003
+#define CLKMGR_PERPLL_VCO1_NUMER_MSK                   0x00001fff
+#define CLKMGR_PERPLL_VCO1_DENOM_MSK                   0x0000003f
+#define CLKMGR_PERPLL_CNTRCLK_MSK                      0x000003ff
+#define CLKMGR_MAINPLL_MPUCLK_SRC_MSK                  0x00000007
+#define CLKMGR_MAINPLL_MPUCLK_CNT_MSK                  0x000003ff
+#define CLKMGR_MAINPLL_MPUCLK_SRC_MAIN                 0
+#define CLKMGR_MAINPLL_MPUCLK_SRC_PERI                 1
+#define CLKMGR_MAINPLL_MPUCLK_SRC_OSC1                 2
+#define CLKMGR_MAINPLL_MPUCLK_SRC_INTOSC               3
+#define CLKMGR_MAINPLL_MPUCLK_SRC_FPGA                 4
+#define CLKMGR_MAINPLL_NOCDIV_MSK                      0x00000003
+#define CLKMGR_MAINPLL_NOCCLK_CNT_MSK                  0x000003ff
+#define CLKMGR_MAINPLL_NOCCLK_SRC_MSK                  0x00000007
+#define CLKMGR_MAINPLL_NOCCLK_SRC_MAIN         0
+#define CLKMGR_MAINPLL_NOCCLK_SRC_PERI         1
+#define CLKMGR_MAINPLL_NOCCLK_SRC_OSC1         2
+#define CLKMGR_MAINPLL_NOCCLK_SRC_INTOSC       3
+#define CLKMGR_MAINPLL_NOCCLK_SRC_FPGA         4
+
+#define CLKMGR_PERPLLGRP_SRC_MSK                       0x00000007
+#define CLKMGR_PERPLLGRP_SRC_MAIN      0
+#define CLKMGR_PERPLLGRP_SRC_PERI      1
+#define CLKMGR_PERPLLGRP_SRC_OSC1      2
+#define CLKMGR_PERPLLGRP_SRC_INTOSC    3
+#define CLKMGR_PERPLLGRP_SRC_FPGA      4
+
+/* bit shifting macro */
+#define CLKMGR_MAINPLL_VCO0_PSRC_LSB           8
+#define CLKMGR_PERPLL_VCO0_PSRC_LSB            8
+#define CLKMGR_MAINPLL_VCO1_DENOM_LSB          16
+#define CLKMGR_PERPLL_VCO1_DENOM_LSB           16
+#define CLKMGR_MAINPLL_NOCCLK_PERICNT_LSB              16
+#define CLKMGR_MAINPLL_NOCCLK_SRC_LSB          16
+#define CLKMGR_MAINPLL_NOCDIV_L4MAINCLK_LSB    0
+#define CLKMGR_MAINPLL_NOCDIV_L4MPCLK_LSB      8
+#define CLKMGR_MAINPLL_NOCDIV_L4SPCLK_LSB      16
+#define CLKMGR_MAINPLL_NOCDIV_CSATCLK_LSB      24
+#define CLKMGR_MAINPLL_NOCDIV_CSTRACECLK_LSB   26
+#define CLKMGR_MAINPLL_NOCDIV_CSPDBGCLK_LSB    28
+#define CLKMGR_MAINPLL_MPUCLK_SRC_LSB          16
+#define CLKMGR_MAINPLL_MPUCLK_PERICNT_LSB      16
+#define CLKMGR_MAINPLL_NOCCLK_SRC_LSB          16
+#define CLKMGR_MAINPLL_CNTR7CLK_SRC_LSB                16
+#define CLKMGR_MAINPLL_CNTR9CLK_SRC_LSB                16
+#define CLKMGR_PERPLL_CNTR2CLK_SRC_LSB         16
+#define CLKMGR_PERPLL_CNTR3CLK_SRC_LSB         16
+#define CLKMGR_PERPLL_CNTR4CLK_SRC_LSB         16
+#define CLKMGR_PERPLL_CNTR5CLK_SRC_LSB         16
+#define CLKMGR_PERPLL_CNTR6CLK_SRC_LSB         16
+#define CLKMGR_PERPLL_CNTR8CLK_SRC_LSB         16
+#define CLKMGR_PERPLL_EMACCTL_EMAC0SEL_LSB     26
+#define CLKMGR_PERPLL_EMACCTL_EMAC1SEL_LSB     27
+#define CLKMGR_PERPLL_EMACCTL_EMAC2SEL_LSB     28
+
+/* PLL ramping work around */
+#define CLKMGR_PLL_RAMP_MPUCLK_THRESHOLD_HZ    900000000
+#define CLKMGR_PLL_RAMP_NOCCLK_THRESHOLD_HZ    300000000
+#define CLKMGR_PLL_RAMP_MPUCLK_INCREMENT_HZ    100000000
+#define CLKMGR_PLL_RAMP_NOCCLK_INCREMENT_HZ     33000000
+#endif
 #endif /* _CLOCK_MANAGER_H_ */
-- 
2.2.2

_______________________________________________
U-Boot mailing list
U-Boot@lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

Reply via email to