uml: virtualized time fix
With the current timekeeping, !CONFIG_UML_REAL_TIME_CLOCK has inconsistent behavior. Previously, gettimeofday could be (and was) isolated from the clock ticking. Now, it's not, so when CONFIG_UML_REAL_TIME_CLOCK is disabled, gettimeofday must progress in lockstep with the clock, making it fully virtual. Signed-off-by: Jeff Dike <jdike@linux.intel.com> Cc: Paolo 'Blaisorblade' Giarrusso <blaisorblade@yahoo.it> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
This commit is contained in:
Родитель
83ff7df5f1
Коммит
b7ec15bd00
|
@ -34,8 +34,8 @@ unsigned long long sched_clock(void)
|
||||||
return (unsigned long long)jiffies_64 * (1000000000 / HZ);
|
return (unsigned long long)jiffies_64 * (1000000000 / HZ);
|
||||||
}
|
}
|
||||||
|
|
||||||
static unsigned long long prev_nsecs[NR_CPUS];
|
|
||||||
#ifdef CONFIG_UML_REAL_TIME_CLOCK
|
#ifdef CONFIG_UML_REAL_TIME_CLOCK
|
||||||
|
static unsigned long long prev_nsecs[NR_CPUS];
|
||||||
static long long delta[NR_CPUS]; /* Deviation per interval */
|
static long long delta[NR_CPUS]; /* Deviation per interval */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -94,7 +94,12 @@ irqreturn_t um_timer(int irq, void *dev)
|
||||||
|
|
||||||
do_timer(1);
|
do_timer(1);
|
||||||
|
|
||||||
|
#ifdef CONFIG_UML_REAL_TIME_CLOCK
|
||||||
nsecs = get_time();
|
nsecs = get_time();
|
||||||
|
#else
|
||||||
|
nsecs = (unsigned long long) xtime.tv_sec * BILLION + xtime.tv_nsec +
|
||||||
|
BILLION / HZ;
|
||||||
|
#endif
|
||||||
xtime.tv_sec = nsecs / NSEC_PER_SEC;
|
xtime.tv_sec = nsecs / NSEC_PER_SEC;
|
||||||
xtime.tv_nsec = nsecs - xtime.tv_sec * NSEC_PER_SEC;
|
xtime.tv_nsec = nsecs - xtime.tv_sec * NSEC_PER_SEC;
|
||||||
|
|
||||||
|
@ -127,13 +132,18 @@ void time_init(void)
|
||||||
nsecs = os_nsecs();
|
nsecs = os_nsecs();
|
||||||
set_normalized_timespec(&wall_to_monotonic, -nsecs / BILLION,
|
set_normalized_timespec(&wall_to_monotonic, -nsecs / BILLION,
|
||||||
-nsecs % BILLION);
|
-nsecs % BILLION);
|
||||||
|
set_normalized_timespec(&xtime, nsecs / BILLION, nsecs % BILLION);
|
||||||
late_time_init = register_timer;
|
late_time_init = register_timer;
|
||||||
}
|
}
|
||||||
|
|
||||||
void do_gettimeofday(struct timeval *tv)
|
void do_gettimeofday(struct timeval *tv)
|
||||||
{
|
{
|
||||||
|
#ifdef CONFIG_UML_REAL_TIME_CLOCK
|
||||||
unsigned long long nsecs = get_time();
|
unsigned long long nsecs = get_time();
|
||||||
|
#else
|
||||||
|
unsigned long long nsecs = (unsigned long long) xtime.tv_sec * BILLION +
|
||||||
|
xtime.tv_nsec;
|
||||||
|
#endif
|
||||||
tv->tv_sec = nsecs / NSEC_PER_SEC;
|
tv->tv_sec = nsecs / NSEC_PER_SEC;
|
||||||
/* Careful about calculations here - this was originally done as
|
/* Careful about calculations here - this was originally done as
|
||||||
* (nsecs - tv->tv_sec * NSEC_PER_SEC) / NSEC_PER_USEC
|
* (nsecs - tv->tv_sec * NSEC_PER_SEC) / NSEC_PER_USEC
|
||||||
|
|
Загрузка…
Ссылка в новой задаче