mirror of
https://github.com/apache/nuttx.git
synced 2026-10-10 07:40:27 +00:00
arch/arm64/qemu: Use the PL031 RTC of the virt machine.
The QEMU virt machine has a PL031 RTC at 0x09010000 (SPI 2), which QEMU sets from the host clock. qemu-armv8a did not register it, so the system time started at CONFIG_START_YEAR, and files on a host share (v9fs, hostfs) had times years in the future. With CONFIG_RTC_PL031, up_rtc_initialize() now registers the PL031 as the RTC, so the system time starts at the host's time. The new option QEMU_RTC_PL031_SYNC makes the boot wait (up to a second) for the RTC second to change. The PL031 counts whole seconds, so without the wait the time starts up to a second behind the host. Assisted-by: Claude Code:claude-opus-5-5 Signed-off-by: Marco Casaroli <marco.casaroli@gmail.com>
This commit is contained in:
parent
baa21f197d
commit
7c6307bebf
4 changed files with 101 additions and 0 deletions
|
|
@ -30,4 +30,7 @@ endif()
|
|||
if(CONFIG_PM)
|
||||
list(APPEND SRCS qemu_initialize.c)
|
||||
endif()
|
||||
if(CONFIG_RTC_PL031)
|
||||
list(APPEND SRCS qemu_rtc.c)
|
||||
endif()
|
||||
target_sources(arch PRIVATE ${SRCS})
|
||||
|
|
|
|||
|
|
@ -47,4 +47,29 @@ config ARCH_CHIP_QEMU_WITH_HV
|
|||
|
||||
endmenu # "Qemu Chip Selection"
|
||||
|
||||
config QEMU_RTC_PL031_BASE
|
||||
hex "PL031 RTC base address"
|
||||
default 0x09010000
|
||||
depends on RTC_PL031
|
||||
---help---
|
||||
Physical address of the PL031 RTC of the QEMU virt machine.
|
||||
|
||||
config QEMU_RTC_PL031_IRQ
|
||||
int "PL031 RTC interrupt"
|
||||
default 34
|
||||
depends on RTC_PL031
|
||||
---help---
|
||||
Interrupt of the PL031 RTC of the QEMU virt machine (SPI 2).
|
||||
|
||||
config QEMU_RTC_PL031_SYNC
|
||||
bool "Start the system time at an RTC second boundary"
|
||||
default n
|
||||
depends on RTC_PL031
|
||||
---help---
|
||||
The PL031 counts whole seconds, so the system time starts up to a
|
||||
second behind the host. Files that the host writes then look
|
||||
up to a second in the future, and make warns about clock skew.
|
||||
With this option the boot waits (up to a second) for the RTC
|
||||
second to change, so the time is correct to a few milliseconds.
|
||||
|
||||
endif # ARCH_CHIP_QEMU
|
||||
|
|
|
|||
|
|
@ -36,3 +36,7 @@ endif
|
|||
ifeq ($(CONFIG_PM),y)
|
||||
CHIP_CSRCS += qemu_initialize.c
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_RTC_PL031),y)
|
||||
CHIP_CSRCS += qemu_rtc.c
|
||||
endif
|
||||
|
|
|
|||
69
arch/arm64/src/qemu/qemu_rtc.c
Normal file
69
arch/arm64/src/qemu/qemu_rtc.c
Normal file
|
|
@ -0,0 +1,69 @@
|
|||
/****************************************************************************
|
||||
* arch/arm64/src/qemu/qemu_rtc.c
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership. The
|
||||
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance with the
|
||||
* License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
* License for the specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <nuttx/config.h>
|
||||
|
||||
#include <nuttx/arch.h>
|
||||
#include <nuttx/timers/pl031.h>
|
||||
#include <nuttx/timers/rtc.h>
|
||||
#include <nuttx/timers/arch_rtc.h>
|
||||
|
||||
#include "arm64_internal.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: up_rtc_initialize
|
||||
*
|
||||
* Description:
|
||||
* Register the PL031 RTC of the QEMU virt machine. QEMU sets it from the
|
||||
* host clock (-rtc base=utc by default), so the system time starts at the
|
||||
* host's time.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int up_rtc_initialize(void)
|
||||
{
|
||||
FAR struct rtc_lowerhalf_s *lower;
|
||||
|
||||
#ifdef CONFIG_QEMU_RTC_PL031_SYNC
|
||||
/* The PL031 counts whole seconds, so the system time would start up to a
|
||||
* second late. Wait until the second changes: the time read next is
|
||||
* then correct to a few milliseconds. Register 0 is the data register.
|
||||
*/
|
||||
|
||||
uint32_t second = getreg32(CONFIG_QEMU_RTC_PL031_BASE);
|
||||
|
||||
while (getreg32(CONFIG_QEMU_RTC_PL031_BASE) == second);
|
||||
#endif
|
||||
|
||||
lower = pl031_initialize(CONFIG_QEMU_RTC_PL031_BASE,
|
||||
CONFIG_QEMU_RTC_PL031_IRQ);
|
||||
up_rtc_set_lowerhalf(lower, true);
|
||||
return rtc_initialize(0, lower);
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue