Re: [U-Boot] [PATCH v2 04/28] armv8/ls2085a: Fix generic timer clock source

2015-03-20 Thread Mark Rutland
  +int timer_init(void)
  +{
  +  u32 __iomem *cntcr = (u32 *)CONFIG_SYS_FSL_TIMER_ADDR;
  +  u32 __iomem *cltbenr = (u32 *)CONFIG_SYS_FSL_PMU_CLTBENR;
  +#ifdef COUNTER_FREQUENCY_REAL
  +  unsigned long cntfrq = COUNTER_FREQUENCY_REAL;
  +
  +  /* Update with accurate clock frequency */
  +  asm volatile(msr cntfrq_el0, %0 : : r (cntfrq) : memory);
  
  The commit message says that this can only be determined at runtime, but
  this looks like we're writing a compile-time static value.
  
 
 The macro COUNTER_FREQUENCY_REA is (CONFIG_SYS_CLK_FREQ/4), where
 CONFIG_SYS_CLK_FREQ is a function call get_board_sys_clk().

Ah, that sounds fine to me then.

  +  __real_cntfrq = cntfrq; /* update for secondary cores */
  
  Do we need anything in the way or barriers and/or cache flushing to
  ensure that this is visible to the secondary CPUs? Or is the MMU off at
  this point?
 
 It is flushed before booting secondary cores. But I am relying on the trick of
 enabling cache on flash. It may not be as reliable if someone decide to 
 disable
 the cache to begin with. I will move the code to somewhere safe in next 
 version.

Ok.

  +  .global __real_cntfrq
  +__real_cntfrq:
  +  .quad 0x17d7840 /* 25MHz */
  
  I think this would be better as COUNTER_FREQUENCY, so as to avoid
  duplicating the value.
 
 Good idea. Will fix in next version.

Great!

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


Re: [U-Boot] [PATCH v2 04/28] armv8/ls2085a: Fix generic timer clock source

2015-03-20 Thread Mark Rutland
Hi,

On Thu, Mar 19, 2015 at 08:34:22PM +, York Sun wrote:
 The timer clock is system clock divided by 4, not fixed 12MHz. This is
 common to the SoC, not board specific.
 
 Signed-off-by: York Sun york...@freescale.com
 
 ---
 
 Changes in v2:
   Fix CNTFRQ for secondary cores when COUNTER_FREQUENCY_REAL is defined.
 
  README  |8 
  arch/arm/cpu/armv8/fsl-lsch3/cpu.c  |   26 ++
  arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S |6 ++
  arch/arm/cpu/armv8/fsl-lsch3/mp.h   |1 +
  board/freescale/ls2085a/ls2085a.c   |   18 --
  include/configs/ls2085a_common.h|6 +-
  6 files changed, 46 insertions(+), 19 deletions(-)
 
 diff --git a/README b/README
 index f473515..776ebf4 100644
 --- a/README
 +++ b/README
 @@ -690,6 +690,14 @@ The following options need to be configured:
   exists, unlike the similar options in the Linux kernel. Do not
   set these options unless they apply!
  
 + COUNTER_FREQUENCY
 + Generic timer clock source frequency.
 +
 + COUNTER_FREQUENCY_REAL
 + Generic timer clock source frequency if the real clock is
 + different from COUNTER_FREQUENCY, and can only be determined
 + at run time.
 +
   NOTE: The following can be machine specific errata. These
   do have ability to provide rudimentary version and machine
   specific checks, but expect no product checks.
 diff --git a/arch/arm/cpu/armv8/fsl-lsch3/cpu.c 
 b/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
 index 94fd147..f75b21d 100644
 --- a/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
 +++ b/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
 @@ -395,3 +395,29 @@ int arch_early_init_r(void)
  
   return 0;
  }
 +
 +int timer_init(void)
 +{
 + u32 __iomem *cntcr = (u32 *)CONFIG_SYS_FSL_TIMER_ADDR;
 + u32 __iomem *cltbenr = (u32 *)CONFIG_SYS_FSL_PMU_CLTBENR;
 +#ifdef COUNTER_FREQUENCY_REAL
 + unsigned long cntfrq = COUNTER_FREQUENCY_REAL;
 +
 + /* Update with accurate clock frequency */
 + asm volatile(msr cntfrq_el0, %0 : : r (cntfrq) : memory);

The commit message says that this can only be determined at runtime, but
this looks like we're writing a compile-time static value.

 +
 + __real_cntfrq = cntfrq; /* update for secondary cores */

Do we need anything in the way or barriers and/or cache flushing to
ensure that this is visible to the secondary CPUs? Or is the MMU off at
this point?

 +#endif
 +
 + /* Enable timebase for all clusters.
 +  * It is safe to do so even some clusters are not enabled.
 +  */
 + out_le32(cltbenr, 0xf);
 +
 + /* Enable clock for timer
 +  * This is a global setting.
 +  */
 + out_le32(cntcr, 0x1);
 +
 + return 0;
 +}
 diff --git a/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S 
 b/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
 index 886576e..8d330ff 100644
 --- a/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
 +++ b/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
 @@ -224,6 +224,9 @@ ENTRY(secondary_boot_func)
   /* physical address of this cpus spin table element */
   add x11, x1, x0
  
 + ldr x0, =__real_cntfrq
 + ldr x0, [x0]
 + msr cntfrq_el0, x0  /* set with real frequency */
   str x9, [x11, #16]  /* LPID */
   mov x4, #1
   str x4, [x11, #8]   /* STATUS */
 @@ -275,6 +278,9 @@ ENDPROC(secondary_switch_to_el1)
  
   /* 64 bit alignment for elements accessed as data */
   .align 4
 + .global __real_cntfrq
 +__real_cntfrq:
 + .quad 0x17d7840 /* 25MHz */

I think this would be better as COUNTER_FREQUENCY, so as to avoid
duplicating the value.

Thanks,
Mark.
___
U-Boot mailing list
U-Boot@lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot


Re: [U-Boot] [PATCH v2 04/28] armv8/ls2085a: Fix generic timer clock source

2015-03-20 Thread York Sun
On 03/20/2015 10:34 AM, Mark Rutland wrote:
 Hi,
 
 On Thu, Mar 19, 2015 at 08:34:22PM +, York Sun wrote:
 The timer clock is system clock divided by 4, not fixed 12MHz. This is
 common to the SoC, not board specific.

 Signed-off-by: York Sun york...@freescale.com

 ---

 Changes in v2:
   Fix CNTFRQ for secondary cores when COUNTER_FREQUENCY_REAL is defined.

  README  |8 
  arch/arm/cpu/armv8/fsl-lsch3/cpu.c  |   26 ++
  arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S |6 ++
  arch/arm/cpu/armv8/fsl-lsch3/mp.h   |1 +
  board/freescale/ls2085a/ls2085a.c   |   18 --
  include/configs/ls2085a_common.h|6 +-
  6 files changed, 46 insertions(+), 19 deletions(-)

 diff --git a/README b/README
 index f473515..776ebf4 100644
 --- a/README
 +++ b/README
 @@ -690,6 +690,14 @@ The following options need to be configured:
  exists, unlike the similar options in the Linux kernel. Do not
  set these options unless they apply!
  
 +COUNTER_FREQUENCY
 +Generic timer clock source frequency.
 +
 +COUNTER_FREQUENCY_REAL
 +Generic timer clock source frequency if the real clock is
 +different from COUNTER_FREQUENCY, and can only be determined
 +at run time.
 +
  NOTE: The following can be machine specific errata. These
  do have ability to provide rudimentary version and machine
  specific checks, but expect no product checks.
 diff --git a/arch/arm/cpu/armv8/fsl-lsch3/cpu.c 
 b/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
 index 94fd147..f75b21d 100644
 --- a/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
 +++ b/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
 @@ -395,3 +395,29 @@ int arch_early_init_r(void)
  
  return 0;
  }
 +
 +int timer_init(void)
 +{
 +u32 __iomem *cntcr = (u32 *)CONFIG_SYS_FSL_TIMER_ADDR;
 +u32 __iomem *cltbenr = (u32 *)CONFIG_SYS_FSL_PMU_CLTBENR;
 +#ifdef COUNTER_FREQUENCY_REAL
 +unsigned long cntfrq = COUNTER_FREQUENCY_REAL;
 +
 +/* Update with accurate clock frequency */
 +asm volatile(msr cntfrq_el0, %0 : : r (cntfrq) : memory);
 
 The commit message says that this can only be determined at runtime, but
 this looks like we're writing a compile-time static value.
 

The macro COUNTER_FREQUENCY_REA is (CONFIG_SYS_CLK_FREQ/4), where
CONFIG_SYS_CLK_FREQ is a function call get_board_sys_clk().

 +
 +__real_cntfrq = cntfrq; /* update for secondary cores */
 
 Do we need anything in the way or barriers and/or cache flushing to
 ensure that this is visible to the secondary CPUs? Or is the MMU off at
 this point?

It is flushed before booting secondary cores. But I am relying on the trick of
enabling cache on flash. It may not be as reliable if someone decide to disable
the cache to begin with. I will move the code to somewhere safe in next version.

 
 +#endif
 +
 +/* Enable timebase for all clusters.
 + * It is safe to do so even some clusters are not enabled.
 + */
 +out_le32(cltbenr, 0xf);
 +
 +/* Enable clock for timer
 + * This is a global setting.
 + */
 +out_le32(cntcr, 0x1);
 +
 +return 0;
 +}
 diff --git a/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S 
 b/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
 index 886576e..8d330ff 100644
 --- a/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
 +++ b/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
 @@ -224,6 +224,9 @@ ENTRY(secondary_boot_func)
  /* physical address of this cpus spin table element */
  add x11, x1, x0
  
 +ldr x0, =__real_cntfrq
 +ldr x0, [x0]
 +msr cntfrq_el0, x0  /* set with real frequency */
  str x9, [x11, #16]  /* LPID */
  mov x4, #1
  str x4, [x11, #8]   /* STATUS */
 @@ -275,6 +278,9 @@ ENDPROC(secondary_switch_to_el1)
  
  /* 64 bit alignment for elements accessed as data */
  .align 4
 +.global __real_cntfrq
 +__real_cntfrq:
 +.quad 0x17d7840 /* 25MHz */
 
 I think this would be better as COUNTER_FREQUENCY, so as to avoid
 duplicating the value.

Good idea. Will fix in next version.

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


[U-Boot] [PATCH v2 04/28] armv8/ls2085a: Fix generic timer clock source

2015-03-19 Thread York Sun
The timer clock is system clock divided by 4, not fixed 12MHz. This is
common to the SoC, not board specific.

Signed-off-by: York Sun york...@freescale.com

---

Changes in v2:
  Fix CNTFRQ for secondary cores when COUNTER_FREQUENCY_REAL is defined.

 README  |8 
 arch/arm/cpu/armv8/fsl-lsch3/cpu.c  |   26 ++
 arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S |6 ++
 arch/arm/cpu/armv8/fsl-lsch3/mp.h   |1 +
 board/freescale/ls2085a/ls2085a.c   |   18 --
 include/configs/ls2085a_common.h|6 +-
 6 files changed, 46 insertions(+), 19 deletions(-)

diff --git a/README b/README
index f473515..776ebf4 100644
--- a/README
+++ b/README
@@ -690,6 +690,14 @@ The following options need to be configured:
exists, unlike the similar options in the Linux kernel. Do not
set these options unless they apply!
 
+   COUNTER_FREQUENCY
+   Generic timer clock source frequency.
+
+   COUNTER_FREQUENCY_REAL
+   Generic timer clock source frequency if the real clock is
+   different from COUNTER_FREQUENCY, and can only be determined
+   at run time.
+
NOTE: The following can be machine specific errata. These
do have ability to provide rudimentary version and machine
specific checks, but expect no product checks.
diff --git a/arch/arm/cpu/armv8/fsl-lsch3/cpu.c 
b/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
index 94fd147..f75b21d 100644
--- a/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
+++ b/arch/arm/cpu/armv8/fsl-lsch3/cpu.c
@@ -395,3 +395,29 @@ int arch_early_init_r(void)
 
return 0;
 }
+
+int timer_init(void)
+{
+   u32 __iomem *cntcr = (u32 *)CONFIG_SYS_FSL_TIMER_ADDR;
+   u32 __iomem *cltbenr = (u32 *)CONFIG_SYS_FSL_PMU_CLTBENR;
+#ifdef COUNTER_FREQUENCY_REAL
+   unsigned long cntfrq = COUNTER_FREQUENCY_REAL;
+
+   /* Update with accurate clock frequency */
+   asm volatile(msr cntfrq_el0, %0 : : r (cntfrq) : memory);
+
+   __real_cntfrq = cntfrq; /* update for secondary cores */
+#endif
+
+   /* Enable timebase for all clusters.
+* It is safe to do so even some clusters are not enabled.
+*/
+   out_le32(cltbenr, 0xf);
+
+   /* Enable clock for timer
+* This is a global setting.
+*/
+   out_le32(cntcr, 0x1);
+
+   return 0;
+}
diff --git a/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S 
b/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
index 886576e..8d330ff 100644
--- a/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
+++ b/arch/arm/cpu/armv8/fsl-lsch3/lowlevel.S
@@ -224,6 +224,9 @@ ENTRY(secondary_boot_func)
/* physical address of this cpus spin table element */
add x11, x1, x0
 
+   ldr x0, =__real_cntfrq
+   ldr x0, [x0]
+   msr cntfrq_el0, x0  /* set with real frequency */
str x9, [x11, #16]  /* LPID */
mov x4, #1
str x4, [x11, #8]   /* STATUS */
@@ -275,6 +278,9 @@ ENDPROC(secondary_switch_to_el1)
 
/* 64 bit alignment for elements accessed as data */
.align 4
+   .global __real_cntfrq
+__real_cntfrq:
+   .quad 0x17d7840 /* 25MHz */
.globl __secondary_boot_code_size
.type __secondary_boot_code_size, %object
/* Secondary Boot Code ends here */
diff --git a/arch/arm/cpu/armv8/fsl-lsch3/mp.h 
b/arch/arm/cpu/armv8/fsl-lsch3/mp.h
index 66144d6..c985d6a 100644
--- a/arch/arm/cpu/armv8/fsl-lsch3/mp.h
+++ b/arch/arm/cpu/armv8/fsl-lsch3/mp.h
@@ -26,6 +26,7 @@
 #define id_to_core(x)  ((x  3) | (x  6))
 #ifndef __ASSEMBLY__
 extern u64 __spin_table[];
+extern u64 __real_cntfrq;
 extern u64 *secondary_boot_code;
 extern size_t __secondary_boot_code_size;
 int fsl_lsch3_wake_seconday_cores(void);
diff --git a/board/freescale/ls2085a/ls2085a.c 
b/board/freescale/ls2085a/ls2085a.c
index e78c63a..bd016e9 100644
--- a/board/freescale/ls2085a/ls2085a.c
+++ b/board/freescale/ls2085a/ls2085a.c
@@ -55,24 +55,6 @@ int dram_init(void)
return 0;
 }
 
-int timer_init(void)
-{
-   u32 __iomem *cntcr = (u32 *)CONFIG_SYS_FSL_TIMER_ADDR;
-   u32 __iomem *cltbenr = (u32 *)CONFIG_SYS_FSL_PMU_CLTBENR;
-
-   /* Enable timebase for all clusters.
-* It is safe to do so even some clusters are not enabled.
-*/
-   out_le32(cltbenr, 0xf);
-
-   /* Enable clock for timer
-* This is a global setting.
-*/
-   out_le32(cntcr, 0x1);
-
-   return 0;
-}
-
 /*
  * Board specific reset that is system reset.
  */
diff --git a/include/configs/ls2085a_common.h b/include/configs/ls2085a_common.h
index 339337d..b47cf68 100644
--- a/include/configs/ls2085a_common.h
+++ b/include/configs/ls2085a_common.h
@@ -72,7 +72,11 @@
 #define CONFIG_DP_DDR_NUM_CTRLS1
 
 /* Generic Timer Definitions */
-#define COUNTER_FREQUENCY  1200/* 12MHz */