Merge branch 'for-next/timers' of git://git.kernel.org/pub/scm/linux/kernel/git/arm64...
authorWill Deacon <will.deacon@arm.com>
Wed, 1 May 2019 14:45:36 +0000 (15:45 +0100)
committerWill Deacon <will.deacon@arm.com>
Wed, 1 May 2019 14:45:36 +0000 (15:45 +0100)
Conflicts:
arch/arm64/Kconfig
arch/arm64/include/asm/arch_timer.h

1  2 
arch/arm64/Kconfig
arch/arm64/include/asm/arch_timer.h
arch/arm64/kernel/cpu_errata.c
arch/arm64/kernel/traps.c
drivers/clocksource/arm_arch_timer.c

index b5c6943225ce091b4aef6cf6819b6bb8bd252344,fcda4e21fa8feac47727b8cc7a834ba94edc6897..1c0cb5131c2ab5e75f1411b42eadad32b3d9e19d
@@@ -477,15 -475,17 +477,17 @@@ config ARM64_ERRATUM_102471
          If unsure, say Y.
  
  config ARM64_ERRATUM_1188873
-       bool "Cortex-A76: MRC read following MRRC read of specific Generic Timer in AArch32 might give incorrect result"
+       bool "Cortex-A76/Neoverse-N1: MRC read following MRRC read of specific Generic Timer in AArch32 might give incorrect result"
        default y
+       depends on COMPAT
        select ARM_ARCH_TIMER_OOL_WORKAROUND
        help
-         This option adds a workaround for ARM Cortex-A76 erratum 1188873.
 -        This option adds work arounds for ARM Cortex-A76/Neoverse-N1
 -        erratum 1188873
++        This option adds a workaround for ARM Cortex-A76/Neoverse-N1
++        erratum 1188873.
  
-         Affected Cortex-A76 cores (r0p0, r1p0, r2p0) could cause
-         register corruption when accessing the timer registers from
-         AArch32 userspace.
+         Affected Cortex-A76/Neoverse-N1 cores (r0p0, r1p0, r2p0) could
+         cause register corruption when accessing the timer registers
+         from AArch32 userspace.
  
          If unsure, say Y.
  
index 93e07512b4b61cad3c9fc1832a2c973ab0b6b1ad,48b2100f4aaad0ce63312eaf13bde4ee640f62dc..b7bca1ae09e66df3a096c6b900c7dfe8ccd4ea9e
@@@ -148,47 -174,30 +174,67 @@@ static inline void arch_timer_set_cntkc
        isb();
  }
  
- static inline u64 arch_counter_get_cntpct(void)
 +/*
 + * Ensure that reads of the counter are treated the same as memory reads
 + * for the purposes of ordering by subsequent memory barriers.
 + *
 + * This insanity brought to you by speculative system register reads,
 + * out-of-order memory accesses, sequence locks and Thomas Gleixner.
 + *
 + * http://lists.infradead.org/pipermail/linux-arm-kernel/2019-February/631195.html
 + */
 +#define arch_counter_enforce_ordering(val) do {                               \
 +      u64 tmp, _val = (val);                                          \
 +                                                                      \
 +      asm volatile(                                                   \
 +      "       eor     %0, %1, %1\n"                                   \
 +      "       add     %0, sp, %0\n"                                   \
 +      "       ldr     xzr, [%0]"                                      \
 +      : "=r" (tmp) : "r" (_val));                                     \
 +} while (0)
 +
+ static inline u64 __arch_counter_get_cntpct_stable(void)
  {
 +      u64 cnt;
 +
        isb();
 -      return arch_timer_reg_read_stable(cntpct_el0);
 +      cnt = arch_timer_reg_read_stable(cntpct_el0);
 +      arch_counter_enforce_ordering(cnt);
 +      return cnt;
  }
  
- static inline u64 arch_counter_get_cntvct(void)
+ static inline u64 __arch_counter_get_cntpct(void)
+ {
++      u64 cnt;
++
+       isb();
 -      return read_sysreg(cntpct_el0);
++      cnt = read_sysreg(cntpct_el0);
++      arch_counter_enforce_ordering(cnt);
++      return cnt;
+ }
+ static inline u64 __arch_counter_get_cntvct_stable(void)
  {
 +      u64 cnt;
 +
        isb();
 -      return arch_timer_reg_read_stable(cntvct_el0);
 +      cnt = arch_timer_reg_read_stable(cntvct_el0);
 +      arch_counter_enforce_ordering(cnt);
 +      return cnt;
  }
  
 -      return read_sysreg(cntvct_el0);
+ static inline u64 __arch_counter_get_cntvct(void)
+ {
++      u64 cnt;
++
+       isb();
++      cnt = read_sysreg(cntvct_el0);
++      arch_counter_enforce_ordering(cnt);
++      return cnt;
+ }
 +#undef arch_counter_enforce_ordering
 +
  static inline int arch_timer_arch_init(void)
  {
        return 0;
index 1b9ce0fdd81de87595a15e0440c1e05095ae4fa9,06f1c8aae1dcbf83d9c588384930596a2e1a6a99..e88d4e7bdfc71c0a054f730e6722ae741a761b8e
@@@ -797,14 -731,13 +807,13 @@@ const struct arm64_cpu_capabilities arm
                .capability = ARM64_SSBD,
                .type = ARM64_CPUCAP_LOCAL_CPU_ERRATUM,
                .matches = has_ssbd_mitigation,
 +              .midr_range_list = arm64_ssb_cpus,
        },
 -#endif
  #ifdef CONFIG_ARM64_ERRATUM_1188873
        {
-               /* Cortex-A76 r0p0 to r2p0 */
                .desc = "ARM erratum 1188873",
                .capability = ARM64_WORKAROUND_1188873,
-               ERRATA_MIDR_RANGE(MIDR_CORTEX_A76, 0, 0, 2, 0),
+               ERRATA_MIDR_RANGE_LIST(erratum_1188873_list),
        },
  #endif
  #ifdef CONFIG_ARM64_ERRATUM_1165522
Simple merge
Simple merge