FileDocCategorySizeDatePackage
TimeInfo.javaAPI DocApache Commons NET 1.4.1 API10626Sat Dec 03 10:05:48 GMT 2005org.apache.commons.net.ntp

TimeInfo

public class TimeInfo extends Object
Wrapper class to network time packet messages (NTP, etc) that computes related timing info and stats.
author
Jason Mathews, MITRE Corp
version
$Revision: 165675 $ $Date: 2005-05-02 15:09:55 -0500 (Mon, 02 May 2005) $

Fields Summary
private NtpV3Packet
_message
private List
_comments
private Long
_delay
private Long
_offset
private long
_returnTime
time at which time message packet was received by local machine
private boolean
_detailsComputed
flag indicating that the TimeInfo details was processed and delay/offset were computed
Constructors Summary
public TimeInfo(NtpV3Packet message, long returnTime)
Create TimeInfo object with raw packet message and destination time received.

param
message NTP message packet
param
returnTime destination receive time
throws
IllegalArgumentException if message is null

        this(message, returnTime, null, true);
    
public TimeInfo(NtpV3Packet message, long returnTime, List comments)
Create TimeInfo object with raw packet message and destination time received.

param
message NTP message packet
param
returnTime destination receive time
param
comments List of errors/warnings identified during processing
throws
IllegalArgumentException if message is null

            this(message, returnTime, comments, true);
    
public TimeInfo(NtpV3Packet msgPacket, long returnTime, boolean doComputeDetails)
Create TimeInfo object with raw packet message and destination time received. Auto-computes details if computeDetails flag set otherwise this is delayed until computeDetails() is called. Delayed computation is for fast intialization when sub-millisecond timing is needed.

param
msgPacket NTP message packet
param
returnTime destination receive time
param
doComputeDetails flag to pre-compute delay/offset values
throws
IllegalArgumentException if message is null

            this(msgPacket, returnTime, null, doComputeDetails);
    
public TimeInfo(NtpV3Packet message, long returnTime, List comments, boolean doComputeDetails)
Create TimeInfo object with raw packet message and destination time received. Auto-computes details if computeDetails flag set otherwise this is delayed until computeDetails() is called. Delayed computation is for fast intialization when sub-millisecond timing is needed.

param
message NTP message packet
param
returnTime destination receive time
param
comments list of comments used to store errors/warnings with message
param
doComputeDetails flag to pre-compute delay/offset values
throws
IllegalArgumentException if message is null

        if (message == null)
            throw new IllegalArgumentException("message cannot be null");
        this._returnTime = returnTime;
        this._message = message;
        this._comments = comments;
        if (doComputeDetails)
            computeDetails();
    
Methods Summary
public voidaddComment(java.lang.String comment)
Add comment (error/warning) to list of comments associated with processing of NTP parameters. If comment list not create then one will be created.

param
comment

        if (_comments == null) {
            _comments = new ArrayList();
        }
        _comments.add(comment);
    
public voidcomputeDetails()
Compute and validate details of the NTP message packet. Computed fields include the offset and delay.

        if (_detailsComputed) {
            return; // details already computed - do nothing
        }
        _detailsComputed = true;
        if (_comments == null) {
            _comments = new ArrayList();
        }

        TimeStamp origNtpTime = _message.getOriginateTimeStamp();
        long origTime = origNtpTime.getTime();

        // Receive Time is time request received by server (t2)
        TimeStamp rcvNtpTime = _message.getReceiveTimeStamp();
        long rcvTime = rcvNtpTime.getTime();

        // Transmit time is time reply sent by server (t3)
        TimeStamp xmitNtpTime = _message.getTransmitTimeStamp();
        long xmitTime = xmitNtpTime.getTime();

        /*
         * Round-trip network delay and local clock offset (or time drift) is calculated
         * according to this standard NTP equation:
         *
         * LocalClockOffset = ((ReceiveTimestamp - OriginateTimestamp) +
         *		        (TransmitTimestamp - DestinationTimestamp)) / 2
         *
         * equations from RFC-1305 (NTPv3)
         *      roundtrip delay = (t4 - t1) - (t3 - t2)
         *      local clock offset = ((t2 - t1) + (t3 - t4)) / 2
         *
         * It takes into account network delays and assumes that they are symmetrical.
         *
         * Note the typo in SNTP RFCs 1769/2030 which state that the delay
         * is (T4 - T1) - (T2 - T3) with the "T2" and "T3" switched.
         */
        if (origNtpTime.ntpValue() == 0)
        {
            // without originate time cannot determine when packet went out
            // might be via a broadcast NTP packet...
            if (xmitNtpTime.ntpValue() != 0)
            {
                _offset = new Long(xmitTime - _returnTime);
                _comments.add("Error: zero orig time -- cannot compute delay");
            } else
                _comments.add("Error: zero orig time -- cannot compute delay/offset");
        } else if (rcvNtpTime.ntpValue() == 0 || xmitNtpTime.ntpValue() == 0)
        {
            _comments.add("Warning: zero rcvNtpTime or xmitNtpTime");
            // assert destTime >= origTime since network delay cannot be negative
            if (origTime > _returnTime)
                _comments.add("Error: OrigTime > DestRcvTime");
            else
            {
                // without receive or xmit time cannot figure out processing time
                // so delay is simply the network travel time
                _delay = new Long(_returnTime - origTime);
            }
            // TODO: is offset still valid if rcvNtpTime=0 || xmitNtpTime=0 ???
            // Could always hash origNtpTime (sendTime) but if host doesn't set it
            // then it's an malformed ntp host anyway and we don't care?
            // If server is in broadcast mode then we never send out a query in first place...
            if (rcvNtpTime.ntpValue() != 0)
            {
                // xmitTime is 0 just use rcv time
                _offset = new Long(rcvTime - origTime);
            } else if (xmitNtpTime.ntpValue() != 0)
            {
                // rcvTime is 0 just use xmitTime time
                _offset = new Long(xmitTime - _returnTime);
            }
        } else
        {
             long delayValue = _returnTime - origTime;
             // assert xmitTime >= rcvTime: difference typically < 1ms
             if (xmitTime < rcvTime)
             {
                 // server cannot send out a packet before receiving it...
                 _comments.add("Error: xmitTime < rcvTime"); // time-travel not allowed
             } else
             {
                 // subtract processing time from round-trip network delay
                 long delta = xmitTime - rcvTime;
                 // in normal cases the processing delta is less than
                 // the total roundtrip network travel time.
                 if (delta <= delayValue)
                 {
                     delayValue -= delta; // delay = (t4 - t1) - (t3 - t2)
                 } else
                 {
                     // if delta - delayValue == 1 ms then it's a round-off error
                     // e.g. delay=3ms, processing=4ms
                     if (delta - delayValue == 1)
                     {
                         // delayValue == 0 -> local clock saw no tick change but destination clock did
                         if (delayValue != 0)
                         {
                             _comments.add("Info: processing time > total network time by 1 ms -> assume zero delay");
                             delayValue = 0;
                         }
                     } else
                         _comments.add("Warning: processing time > total network time");
                 }
             }
             _delay = new Long(delayValue);
            if (origTime > _returnTime) // assert destTime >= origTime
                _comments.add("Error: OrigTime > DestRcvTime");

            _offset = new Long(((rcvTime - origTime) + (xmitTime - _returnTime)) / 2);
        }
    
public java.util.ListgetComments()
Return list of comments (if any) during processing of NTP packet.

return
List or null if not yet computed

        return _comments;
    
public java.lang.LonggetDelay()
Get round-trip network delay. If null then could not compute the delay.

return
Long or null if delay not available.

        return _delay;
    
public NtpV3PacketgetMessage()
Returns NTP message packet.

return
NTP message packet.

        return _message;
    
public java.lang.LonggetOffset()
Get clock offset needed to adjust local clock to match remote clock. If null then could not compute the offset.

return
Long or null if offset not available.

        return _offset;
    
public longgetReturnTime()
Returns time at which time message packet was received by local machine.

return
packet return time.

        return _returnTime;