um: time: fix initialization in time-travel mode

In time-travel mode, since my previous patch, the start time was
initialized too late, so that the system would read it before we
set it, thus always starting system time at 0 (1970-01-01). This
happens because timekeeping_init() reads the time and is called
before time_init().

Unfortunately, I didn't see this before because I was testing it
only with the RTC patch applied (and enabled), and then the time
is read again by the RTC a little - after time_init() this time.

Fix this by just doing the initialization whenever necessary.

Fixes: 2701c1bd91 ("um: time: Fix read_persistent_clock64() in time-travel")
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Signed-off-by: Richard Weinberger <richard@nod.at>
This commit is contained in:
Johannes Berg 2021-01-15 12:49:45 +01:00 committed by Richard Weinberger
parent 9868c2081d
commit 7f3414226b

View File

@ -535,6 +535,31 @@ invalid_number:
return 1;
}
static void time_travel_set_start(void)
{
if (time_travel_start_set)
return;
switch (time_travel_mode) {
case TT_MODE_EXTERNAL:
time_travel_start = time_travel_ext_req(UM_TIMETRAVEL_GET_TOD, -1);
/* controller gave us the *current* time, so adjust by that */
time_travel_ext_get_time();
time_travel_start -= time_travel_time;
break;
case TT_MODE_INFCPU:
case TT_MODE_BASIC:
if (!time_travel_start_set)
time_travel_start = os_persistent_clock_emulation();
break;
case TT_MODE_OFF:
/* we just read the host clock with os_persistent_clock_emulation() */
break;
}
time_travel_start_set = true;
}
#else /* CONFIG_UML_TIME_TRAVEL_SUPPORT */
#define time_travel_start_set 0
#define time_travel_start 0
@ -553,6 +578,10 @@ static void time_travel_set_interval(unsigned long long interval)
{
}
static inline void time_travel_set_start(void)
{
}
/* fail link if this actually gets used */
extern u64 time_travel_ext_req(u32 op, u64 time);
@ -731,6 +760,8 @@ void read_persistent_clock64(struct timespec64 *ts)
{
long long nsecs;
time_travel_set_start();
if (time_travel_mode != TT_MODE_OFF)
nsecs = time_travel_start + time_travel_time;
else
@ -742,25 +773,6 @@ void read_persistent_clock64(struct timespec64 *ts)
void __init time_init(void)
{
#ifdef CONFIG_UML_TIME_TRAVEL_SUPPORT
switch (time_travel_mode) {
case TT_MODE_EXTERNAL:
time_travel_start = time_travel_ext_req(UM_TIMETRAVEL_GET_TOD, -1);
/* controller gave us the *current* time, so adjust by that */
time_travel_ext_get_time();
time_travel_start -= time_travel_time;
break;
case TT_MODE_INFCPU:
case TT_MODE_BASIC:
if (!time_travel_start_set)
time_travel_start = os_persistent_clock_emulation();
break;
case TT_MODE_OFF:
/* we just read the host clock with os_persistent_clock_emulation() */
break;
}
#endif
timer_set_signal_handler();
late_time_init = um_timer_setup;
}