Start line:  
End line:  

Snippet Preview

Snippet HTML Code

Stack Overflow Questions
  /*
   * Copyright (C) 2008 The Android Open Source Project
   *
   * Licensed under the Apache License, Version 2.0 (the "License");
   * you may not use this file except in compliance with the License.
   * You may obtain a copy of the License at
   *
   *      http://www.apache.org/licenses/LICENSE-2.0
   *
  * Unless required by applicable law or agreed to in writing, software
  * distributed under the License is distributed on an "AS IS" BASIS,
  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
 
 package android.net;
 
 
Simple SNTP client class for retrieving network time. Sample usage:
SntpClient client = new SntpClient();
 if (client.requestTime("time.foo.com")) {
     long now = client.getNtpTime() + SystemClock.elapsedRealtime() - client.getNtpTimeReference();
 }
 
 
 public class SntpClient
 {
     private static final String TAG = "SntpClient";
 
     private static final int REFERENCE_TIME_OFFSET = 16;
     private static final int ORIGINATE_TIME_OFFSET = 24;
     private static final int RECEIVE_TIME_OFFSET = 32;
     private static final int TRANSMIT_TIME_OFFSET = 40;
     private static final int NTP_PACKET_SIZE = 48;
 
     private static final int NTP_PORT = 123;
     private static final int NTP_MODE_CLIENT = 3;
     private static final int NTP_VERSION = 3;
 
     // Number of seconds between Jan 1, 1900 and Jan 1, 1970
     // 70 years plus 17 leap days
     private static final long OFFSET_1900_TO_1970 = ((365L * 70L) + 17L) * 24L * 60L * 60L;
 
     // system time computed from NTP server response
     private long mNtpTime;
 
     // value of SystemClock.elapsedRealtime() corresponding to mNtpTime
     private long mNtpTimeReference;
 
     // round trip time in milliseconds
     private long mRoundTripTime;

    
Sends an SNTP request to the given host and processes the response.

Parameters:
host host name of the server.
timeout network timeout in milliseconds.
Returns:
true if the transaction was successful.
 
     public boolean requestTime(String hostint timeout) {
         DatagramSocket socket = null;
         try {
             socket = new DatagramSocket();
             socket.setSoTimeout(timeout);
             InetAddress address = InetAddress.getByName(host);
             byte[] buffer = new byte[];
             DatagramPacket request = new DatagramPacket(bufferbuffer.lengthaddress);
 
             // set mode = 3 (client) and version = 3
             // mode is in low 3 bits of first byte
             // version is in bits 3-5 of first byte
             buffer[0] =  | ( << 3);
 
             // get current time and write it to the request packet
             long requestTime = System.currentTimeMillis();
             long requestTicks = SystemClock.elapsedRealtime();
             writeTimeStamp(bufferrequestTime);
 
             socket.send(request);
 
             // read the response
             DatagramPacket response = new DatagramPacket(bufferbuffer.length);
             socket.receive(response);
             long responseTicks = SystemClock.elapsedRealtime();
             long responseTime = requestTime + (responseTicks - requestTicks);
 
            // extract the results
            long originateTime = readTimeStamp(buffer);
            long receiveTime = readTimeStamp(buffer);
            long transmitTime = readTimeStamp(buffer);
            long roundTripTime = responseTicks - requestTicks - (transmitTime - receiveTime);
            // receiveTime = originateTime + transit + skew
            // responseTime = transmitTime + transit - skew
            // clockOffset = ((receiveTime - originateTime) + (transmitTime - responseTime))/2
            //             = ((originateTime + transit + skew - originateTime) +
            //                (transmitTime - (transmitTime + transit - skew)))/2
            //             = ((transit + skew) + (transmitTime - transmitTime - transit + skew))/2
            //             = (transit + skew - transit + skew)/2
            //             = (2 * skew)/2 = skew
            long clockOffset = ((receiveTime - originateTime) + (transmitTime - responseTime))/2;
            // if (false) Log.d(TAG, "round trip: " + roundTripTime + " ms");
            // if (false) Log.d(TAG, "clock offset: " + clockOffset + " ms");
            // save our results - use the times on this side of the network latency
            // (response rather than request time)
             = responseTime + clockOffset;
             = responseTicks;
             = roundTripTime;
        } catch (Exception e) {
            if (false) Log.d("request time failed: " + e);
            return false;
        } finally {
            if (socket != null) {
                socket.close();
            }
        }
        return true;
    }

    
Returns the time computed from the NTP transaction.

Returns:
time value computed from NTP server response.
    public long getNtpTime() {
        return ;
    }

    
Returns the reference clock value (value of SystemClock.elapsedRealtime()) corresponding to the NTP time.

Returns:
reference clock corresponding to the NTP time.
    public long getNtpTimeReference() {
        return ;
    }

    
Returns the round trip time of the NTP transaction

Returns:
round trip time in milliseconds.
    public long getRoundTripTime() {
        return ;
    }

    
Reads an unsigned 32 bit big endian number from the given offset in the buffer.
    private long read32(byte[] bufferint offset) {
        byte b0 = buffer[offset];
        byte b1 = buffer[offset+1];
        byte b2 = buffer[offset+2];
        byte b3 = buffer[offset+3];
        // convert signed bytes to unsigned values
        int i0 = ((b0 & 0x80) == 0x80 ? (b0 & 0x7F) + 0x80 : b0);
        int i1 = ((b1 & 0x80) == 0x80 ? (b1 & 0x7F) + 0x80 : b1);
        int i2 = ((b2 & 0x80) == 0x80 ? (b2 & 0x7F) + 0x80 : b2);
        int i3 = ((b3 & 0x80) == 0x80 ? (b3 & 0x7F) + 0x80 : b3);
        return ((long)i0 << 24) + ((long)i1 << 16) + ((long)i2 << 8) + (long)i3;
    }

    
Reads the NTP time stamp at the given offset in the buffer and returns it as a system time (milliseconds since January 1, 1970).
    
    private long readTimeStamp(byte[] bufferint offset) {
        long seconds = read32(bufferoffset);
        long fraction = read32(bufferoffset + 4);
        return ((seconds - ) * 1000) + ((fraction * 1000L) / 0x100000000L);        
    }

    
Writes system time (milliseconds since January 1, 1970) as an NTP time stamp at the given offset in the buffer.
    
    private void writeTimeStamp(byte[] bufferint offsetlong time) {
        long seconds = time / 1000L;
        long milliseconds = time - seconds * 1000L;
        seconds += ;
        // write seconds in big endian format
        buffer[offset++] = (byte)(seconds >> 24);
        buffer[offset++] = (byte)(seconds >> 16);
        buffer[offset++] = (byte)(seconds >> 8);
        buffer[offset++] = (byte)(seconds >> 0);
        long fraction = milliseconds * 0x100000000L / 1000L;
        // write fraction in big endian format
        buffer[offset++] = (byte)(fraction >> 24);
        buffer[offset++] = (byte)(fraction >> 16);
        buffer[offset++] = (byte)(fraction >> 8);
        // low order bits should be random data
        buffer[offset++] = (byte)(Math.random() * 255.0);
    }
New to GrepCode? Check out our FAQ X