Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 15 Mar 1999 23:57:10 -0500 (EST)
From:      Brian Haug <haug@hawaii.conterra.com>
To:        FreeBSD-gnats-submit@freebsd.org
Subject:   kern/10609: adjtime bug (tv_sec >2147 ) and enhancement (nil first arg)
Message-ID:  <199903160457.XAA05229@hawaii.conterra.com>

next in thread | raw e-mail | index | archive | help

>Number:         10609
>Category:       kern
>Synopsis:       adjtime bug (tv_sec > 2147) and enhancement (nil first arg)
>Confidential:   no
>Severity:       non-critical
>Priority:       low
>Responsible:    freebsd-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Mon Mar 15 21:00:00 PST 1999
>Closed-Date:
>Last-Modified:
>Originator:     Brian Haug
>Release:        FreeBSD 3.1-RELEASE i386 (?? send-pr from different system)
>Organization:
None
>Environment:

	probably any system with adjtime system call


>Description:

	1. Bug: adjtime can not handle adjustments whos absolute value exceeds
		2148 (or stricly exceeds 2147)
	2. Change request: adjtime does not accept a nil first argument to
		allow the application to determine the current delta being
		applied to the clock.
	3. Documentation doesn't note the first issue (code fix attached).

>How-To-Repeat:

	use "date -a 2148" (code in follow on report) or examine the code.
	Note that 2147 seconds (expressed as microseconds) is real close
	to MAXINT, and 2148 seconds would exceed this.


	Call adjtime with the value NULL for the first argument, note that
	the system call will fail.

>Fix:
	

Hopefully the code diffs are all correct.  I've used BRH_ to diferentiate the
two fixes, and would actually suggest not using the ifdefs.  The two problems
are somewhat intertwined, so I appologize for tying them together.  The man
page only attempts to dealwith the NIL first argument issue since the other
problem is now fixed in the kernel.

*** /usr/src/sys/kern/kern_time.c.old	Sun Oct 25 10:44:51 1998
--- /usr/src/sys/kern/kern_time.c	Sun Mar 14 08:02:31 1999
***************
*** 322,328 ****
--- 322,332 ----
  }
  
  int	tickdelta;			/* current clock skew, us. per tick */
+ #ifdef BRH_ADJTIME_BIG
+ long long	timedelta;		/* unapplied time correction, us. */
+ #else
  long	timedelta;			/* unapplied time correction, us. */
+ #endif
  static long	bigadj = 1000000;	/* use 10x skew above bigadj us. */
  
  #ifndef _SYS_SYSPROTO_H_
***************
*** 338,351 ****
--- 342,370 ----
  	register struct adjtime_args *uap;
  {
  	struct timeval atv;
+ #ifdef BRH_ADJTIME_BIG
+ 	long long ndelta, odelta;
+ 	register long ntickdelta;
+ #else
  	register long ndelta, ntickdelta, odelta;
+ #endif
  	int s, error;
+ #ifdef BRH_ADJTIME_NULL
+ 	int for_real;
+ #endif
  
  	if ((error = suser(p->p_ucred, &p->p_acflag)))
  		return (error);
+ #ifndef BRH_ADJTIME_NULL
  	if ((error =
  	    copyin((caddr_t)uap->delta, (caddr_t)&atv, sizeof(struct timeval))))
  		return (error);
+ #else
+ 	for_real = (caddr_t)NULL != (caddr_t)uap->delta;
+ 	if (for_real && (error =
+ 	    copyin((caddr_t)uap->delta, (caddr_t)&atv, sizeof(struct timeval))))
+ 		return (error);
+ #endif
  
  	/*
  	 * Compute the total correction and the rate at which to apply it.
***************
*** 354,360 ****
--- 373,386 ----
  	 * hardclock(), tickdelta will become zero, lest the correction
  	 * overshoot and start taking us away from the desired final time.
  	 */
+ #ifdef BRH_ADJTIME_NULL
+ 	if (for_real) {
+ #endif
+ #ifdef BRH_ADJTIME_BIG
+ 	ndelta = (long long)atv.tv_sec * 1000000 + atv.tv_usec;
+ #else
  	ndelta = atv.tv_sec * 1000000 + atv.tv_usec;
+ #endif
  	if (ndelta > bigadj || ndelta < -bigadj)
  		ntickdelta = 10 * tickadj;
  	else
***************
*** 369,378 ****
--- 395,413 ----
  	 */
  	if (ndelta < 0)
  		ntickdelta = -ntickdelta;
+ #ifdef BRH_ADJTIME_NULL
+ 	}
+ #endif
  	s = splclock();
  	odelta = timedelta;
+ #ifdef BRH_ADJTIME_NULL
+ 	if (for_real) {
+ #endif
  	timedelta = ndelta;
  	tickdelta = ntickdelta;
+ #ifdef BRH_ADJTIME_NULL
+ 	}
+ #endif
  	splx(s);
  
  	if (uap->olddelta) {
*** /usr/src/sys/sys/kernel.h.old	Sun Mar 14 07:56:11 1999
--- /usr/src/sys/sys/kernel.h	Sun Mar 14 07:57:04 1999
***************
*** 73,79 ****
--- 73,83 ----
  extern int ticks;
  extern int lbolt;			/* once a second sleep address */
  extern int tickdelta;
+ #ifdef BRH_ADJTIME_BIG
+ extern long long timedelta;
+ #else
  extern long timedelta;
+ #endif
  
  #endif /* KERNEL */
  
*** /usr/src/lib/libc/sys/adjtime.2.old	Sun Mar 14 08:08:37 1999
--- /usr/src/lib/libc/sys/adjtime.2	Sun Mar 14 08:14:13 1999
***************
*** 66,71 ****
--- 66,76 ----
  .Fn adjtime
  is called again.
  If
+ .Fa delta
+ is nil, then no changes are made to the clock.
+ This is useful when one wants to determine the amount of adjustment which
+ is yet to be performed.
+ If
  .Fa olddelta
  is non-nil,
  the structure pointed to will contain, upon return, the

>Release-Note:
>Audit-Trail:
>Unformatted:


To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-bugs" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199903160457.XAA05229>