Date: Mon, 13 Jul 2015 13:55:49 +0200 From: ard.biesheuvel@linaro.org To: haojian.zhuang@outlook.com CC: linaro-uefi@lists.linaro.org Subject: Re: [Linaro-uefi] how to port grub2 on ARM UEFI
On 13 July 2015 at 13:53, Haojian Zhuang haojian.zhuang@outlook.com wrote:
Date: Mon, 13 Jul 2015 13:19:44 +0200 From: ard.biesheuvel@linaro.org To: leif.lindholm@linaro.org CC: linaro-uefi@lists.linaro.org; haojian.zhuang@outlook.com Subject: Re: [Linaro-uefi] how to port grub2 on ARM UEFI
On 13 July 2015 at 13:01, Leif Lindholm leif.lindholm@linaro.org wrote:
Hi Haojian,
On Mon, Jul 13, 2015 at 10:15:09AM +0000, Haojian Zhuang wrote:
There's still something odd... I set a timeout of 3s in grub config and it takes closer to 10s in reality.
Actually it's 30 seconds if you set a timeout of 3s in grub config on hikey. I don't know whether there's the same issue on other ARM platforms.
I have seen this on some other platforms.
After debugging, I found the root cause. Now all ARM platforms set 10ms as timer periods. In grub, it tries to set 1 ms timer notifier. So here's the conflict. Timer notify will only be triggered when timer interrupt occurs. Even grub hope a timer event after 1ms, UEFI will provide the event notification after 10ms. The only way is to fix gEmbeddedTokenSpaceGuid.PcdTimerPeriod in UEFI.
It's not the timer period that is the problem. The timer period is mandated by the UEFI specification. But there may be a mismatch between the timer frequency and the frequency UEFI thinks the timer is running at.
This does indeed smell like a generic timer/EL3 botch. But I checked the HiKey dts, and it uses the same timer frequency there as it does in the HiKey .DSC. This still does not mean that ATF actually programs the correct value, but it suggests that UEFI and the kernel both override CNTFRQ to 12 MHz (IIRC)
If I just check the timeout in Bds boot menu of UEFI, it works well. This issue only exists in timeout of grub.
The timer frequency of hardware is 1.2MHz. If I change it to 12MHz, it will only cause timeout in Bds boot menu inaccurate.
Yes, so the overrides in the DTS and the HiKey .DSC correctly have 1.2 MHz defined, since this is the frequency of the actual hardware timer.
So is CNTFRQ set correctly? And does GRUB for AArch64 make use of the generic timer at all? Or does it only use the delay/timer services of UEFI in this case?
Yes, CNTFRQ is set correctly. Otherwise I'll meet the inaccurate timeout issue in UEFI boot menu.
Grub doesn't care whether generic timer is used in aarch64. It's decided by UEFI. Currently most aarch64 and aarch32 platform are using generic timer in UEFI.
In UEFI, delay/timer service works very well. But the generic timer only provides 10ms interval timer interrupt according PcdTimerPeriod. Grub is using 1ms interval timer event. So we could update PcdTimerPeriod to meet the requirement of grub.
diff --git a/HisiPkg/HiKeyPkg/HiKey.dsc b/HisiPkg/HiKeyPkg/HiKey.dsc index 8b393af..43697ab 100644 --- a/HisiPkg/HiKeyPkg/HiKey.dsc +++ b/HisiPkg/HiKeyPkg/HiKey.dsc @@ -324,6 +324,7 @@ # gArmTokenSpaceGuid.PcdArmArchTimerFreqInHz|1200000 gEmbeddedTokenSpaceGuid.PcdMetronomeTickPeriod|1000 + gEmbeddedTokenSpaceGuid.PcdTimerPeriod|10000
The timer period is using 100ns as unit base. So 10000 * 100ns = 1ms.
Let's check the value of PcdTimerPeriod in other platforms.
EmbeddedPkg/EmbeddedPkg.dec: gEmbeddedTokenSpaceGuid.PcdTimerPeriod|100000|UINT32|0x0000001e ArmPlatformPkg/ArmRealViewEbPkg/ArmRealViewEb-RTSM-A8.dsc: gEmbeddedTokenSpaceGuid.PcdTimerPeriod|100000 # expressed in 100ns units, 100,000 x 100 ns = 10,000,000 ns = 10 ms BeagleBoardPkg/BeagleBoardPkg.dsc: gEmbeddedTokenSpaceGuid.PcdTimerPeriod|100000
Regards Haojian