[PATCH] invalid GIC access through VDSO

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Accessing raw timers (currently only CLOCK_MONOTONIC_RAW) through VDSO doesn't
return the correct time when using the GIC as clock source. The address of the
GIC mapped page is in this case not calculated correctly. The GIC mapped page
is calculated from the VDSO data by subtracting PAGE_SIZE:

  void *get_gic(const struct vdso_data *data) {
    return (void __iomem *)data - PAGE_SIZE;
  }

However, the data pointer is not page aligned for raw clock sources. This is
because the VDSO data for raw clock sources (CS_RAW = 1) is stored after the
VDSO data for coarse clock sources (CS_HRES_COARSE = 0). Therefore, only the
VDSO data for CS_HRES_COARSE is page aligned:

  +--------------------+
  |                    |
  | vd[CS_RAW]         | ---+
  | vd[CS_HRES_COARSE] |    |
  +--------------------+    | -PAGE_SIZE
  |                    |    |
  |  GIC mapped page   | <--+
  |                    |
  +--------------------+

When __arch_get_hw_counter() is called with &vd[CS_RAW], get_gic returns the
wrong address (somewhere inside the GIC mapped page). The GIC counter values
are not returned which results in an invalid time.

Signed-off-by: Martin Fäcknitz <faecknitz@xxxxxxxxxxxx>

--- a/arch/mips/include/asm/vdso/vdso.h
+++ b/arch/mips/include/asm/vdso/vdso.h
@@ -67,7 +67,7 @@ static inline const struct vdso_data *get_vdso_data(void)
 
 static inline void __iomem *get_gic(const struct vdso_data *data)
 {
-	return (void __iomem *)data - PAGE_SIZE;
+	return (void __iomem *)((unsigned long)data & PAGE_MASK) - PAGE_SIZE;
 }
 
 #endif /* CONFIG_CLKSRC_MIPS_GIC */

[Index of Archives]     [LKML Archive]     [Linux ARM Kernel]     [Linux ARM]     [Git]     [Yosemite News]     [Linux SCSI]     [Linux Hams]

  Powered by Linux