I am new to ARM.
I am using Xilinx RFSOC which in particular comprises 4 A53 cores (Armv8-A) running Linux in SMP configuration.
I need a real-time clock with 1 us (or better) resolution that can be accessed from user-level code (running in AArch64 mode) and yield consistent readings across all cores.
I would like to be able to read the clock from application (EL0) code with minimal overhead, which implies that such reads should not be trapped by the O/S.
Preferably the counter should be readable via an atomic 64-bit read.
Browsing the various documents I found on the net, it seems that the ARM system counter provides the necessary functionality. The question is how to read it from user code. I found the following registers:
CNTCV, (supports reads via CNTReadBase)
CNTVCT, (accessible via 32-bit reads?)
CNTPCT_EL0 (probably trapped by the O/S?)
I have the following questions:
a) Does any of the above counters comply with my requirements (i.e. it is directly readable from EL0 code and provides consistent time stamps across the 4 A53 cores)? If not, is there another counter that I could use?
b) How exactly do I read the counter from user-level C code running under Linux?
Thanks,
AFAIK, CNTPCT_EL0 refers to the local hardware timer and its frequency should be 1-50Mhz. So the time resolution is enough for you.
"The CNTPCT_EL0 register reports the current count value. CNTKCTL_EL1 controls whether EL0 can access the system timer." Probably Yes, but for more detail, you should check the manual.
Yes, I'm sure the hardware local timer has a consistent frequency across all the core, as this is the prerequisite to feasible the OS's scheduling.
If is accessible from EL0, you can just use assembly in C code to read the register like
asm volatile ("mrs %0, cntp_tval_el0":"=r" (value));
btw, I'm not sure you should read the value of cntp_tval or cntpct, please see the manual for their meaning.