sys_linux: always call TMX_SetLeap() in set_leap()
The optimization avoiding unnecessary setting of the kernel leap status can cause a problem when something outside chronyd sets the status to the new expected value. There will be no TMX_SetLeap() call which would update the saved status and the kernel status will be overwritten with the old (incorrect) value in a later TMX_*() call. Always call TMX_SetLeap() to save the new value and for the log message selection just check if a leap second has been applied.
This commit is contained in:
parent
d73394dde1
commit
770db1fe02
3 changed files with 5 additions and 14 deletions
|
@ -173,15 +173,13 @@ read_frequency(void)
|
||||||
static void
|
static void
|
||||||
set_leap(int leap)
|
set_leap(int leap)
|
||||||
{
|
{
|
||||||
int current_leap, applied;
|
int applied;
|
||||||
|
|
||||||
if (TMX_GetLeap(¤t_leap, &applied) < 0) {
|
applied = 0;
|
||||||
|
if (!leap && TMX_GetLeapApplied(&applied) < 0) {
|
||||||
LOG_FATAL(LOGF_SysLinux, "adjtimex() failed in set_leap");
|
LOG_FATAL(LOGF_SysLinux, "adjtimex() failed in set_leap");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (current_leap == leap)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (TMX_SetLeap(leap) < 0) {
|
if (TMX_SetLeap(leap) < 0) {
|
||||||
LOG_FATAL(LOGF_SysLinux, "adjtimex() failed in set_leap");
|
LOG_FATAL(LOGF_SysLinux, "adjtimex() failed in set_leap");
|
||||||
}
|
}
|
||||||
|
|
|
@ -124,7 +124,7 @@ TMX_SetLeap(int leap)
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
TMX_GetLeap(int *leap, int *applied)
|
TMX_GetLeapApplied(int *applied)
|
||||||
{
|
{
|
||||||
struct timex txc;
|
struct timex txc;
|
||||||
int state;
|
int state;
|
||||||
|
@ -134,13 +134,6 @@ TMX_GetLeap(int *leap, int *applied)
|
||||||
if (state < 0)
|
if (state < 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (txc.status & STA_INS)
|
|
||||||
*leap = 1;
|
|
||||||
else if (txc.status & STA_DEL)
|
|
||||||
*leap = -1;
|
|
||||||
else
|
|
||||||
*leap = 0;
|
|
||||||
|
|
||||||
*applied = state == TIME_WAIT;
|
*applied = state == TIME_WAIT;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -31,7 +31,7 @@ int TMX_ResetOffset(void);
|
||||||
int TMX_SetFrequency(double *freq, long tick);
|
int TMX_SetFrequency(double *freq, long tick);
|
||||||
int TMX_GetFrequency(double *freq, long *tick);
|
int TMX_GetFrequency(double *freq, long *tick);
|
||||||
int TMX_SetLeap(int leap);
|
int TMX_SetLeap(int leap);
|
||||||
int TMX_GetLeap(int *leap, int *applied);
|
int TMX_GetLeapApplied(int *applied);
|
||||||
int TMX_SetSync(int sync, double est_error, double max_error);
|
int TMX_SetSync(int sync, double est_error, double max_error);
|
||||||
int TMX_TestStepOffset(void);
|
int TMX_TestStepOffset(void);
|
||||||
int TMX_ApplyStepOffset(double offset);
|
int TMX_ApplyStepOffset(double offset);
|
||||||
|
|
Loading…
Reference in a new issue