• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 421
  • Last Modified:

Need help changing a sntp client from using unicast method to anycast

Hiya all, im fairly new to C but have written a sntp client. At the moment I specify a ntp server and it connects with udp checks the time and then checks my system clock and states the offset. Thats all good but it took me alot of searching for tutorials to find how to do that. What I want to do now is change the method that it connects from Unicast which it is now to anycast. But i dont really get how.


#ifndef unix
#define WIN32
#include <signal.h>
#include <time.h>
#include <stdio.h>
#include <windows.h>
#include <winsock.h>
#include <conio.h>
#else
#include <time.h>
#include <signal.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#endif

#define maxlen 1024

int ntpdate(void);

main() {
      ntpdate();

      

}

ntpdate() {
char      *hostname="224.0.1.1";
int      portno=123;            //NTP is port 123
int      i;                  // misc var i
unsigned char msg[48]={010,0,0,0,0,0,0,0,0};      // the packet sent
unsigned long buf[maxlen];      // the buffer we get back
struct protoent *proto;            
struct sockaddr_in server_addr;
int      sd;      // socket descriptor
int      tmit;      // the time -- This is a time_t sort of
FILE *log_file_pointer; //Space for address of log file



#ifdef  WIN32
        WSADATA wsaData;
        WSAStartup(0x0101, &wsaData);
#endif
//use Socket;
//we use the system call to open a UDP socket
proto=getprotobyname("udp");
sd=socket(PF_INET, SOCK_DGRAM, proto->p_proto);


memset( &server_addr, 0, sizeof( server_addr ));
server_addr.sin_family=AF_INET;
server_addr.sin_addr.s_addr = inet_addr(hostname);
server_addr.sin_port=htons(portno);


/*
 * build a message.  The message is all zeros except for a one in the
 * protocol version field
 * msg[] in binary is 00 001 000 00000000
 * it should be a total of 48 bytes long
*/

// send the data
i=sendto(sd,msg,sizeof(msg),0,(struct sockaddr *)&server_addr,sizeof(server_addr));

// get the data back
i=recv(sd,buf,sizeof(buf),0);


/*
 * The high word of transmit time is the 10th word we get back
 * tmit is the time in seconds not accounting for network delays which
 * so be way less than a second sd this is a UK SNTP server
 */

tmit=ntohl((time_t)buf[10]);      // get SNTP time (convert from host byte order to network byte order)
closesocket(sd);

/*
 * Convert time to unix standard time NTP is number of seconds since 0000
 * UT on 1 January 1900 unix time is seconds since 0000 UT on 1 January
 * 1970.
 */

            tmit-= 2208988800U;      

/* use unix library function to show me the local time
 */


//#compare to system time
printf("\tTime: %s",ctime(&tmit)); //convert tmit to local time
i=time(0);

//printf("%d-%d=%d\n",i,tmit,i-tmit);

      if ((i-tmit) > 86400)
      {
            printf("\n\tLocal clock is out by over a day, \n\tplease change it and run this program again.\n\n\t");
      }
      else
      {

            printf("\tSystem time is %d seconds off\n",i-tmit);
            printf("\n\tThis data has been written to 'logfile'\n\tin the current working directory.\n\n\t");

            /*
             * Create a file called 'logfile' and to it write the Current date and time
            * Followed by the number of seconds the system time is off
            */
            log_file_pointer = fopen("logfile","w");
            fprintf(log_file_pointer, "Time: %s \n System time is %d seconds out",ctime(&tmit), i-tmit);  
            fclose(log_file_pointer);
      }
return 0;
}

There is my code at the mo. Cheers guys
0
machoman990
Asked:
machoman990
  • 3
  • 2
1 Solution
 
grg99Commented:
It's not an issue on the program end, I think it all happens in the network routers.

Have you thought about all the gotchas mentioned in:

http://www.kuro5hin.org/story/2003/12/31/173152/86  ??

0
 
machoman990Author Commented:
Cheers for the reply, but as far as i understand it it can be implemented from the client. At the moment I point to a specific ntp server (albeit not the correct one in the code above). But i just want to point to an area. Heres a snippet from the SNTP RFC-2030.

 Anycast mode is designed for use with a set of cooperating servers
   whose addresses are not known beforehand by the client. An anycast
   client sends a request to the designated local broadcast or multicast
   group address as described below. For this purpose, the NTP multicast
   group address assigned by the IANA is used. One or more anycast
   servers listen on the designated local broadcast address or multicast
   group address. Each anycast server, upon receiving a request, sends a
   unicast reply message to the originating client. The client then
   binds to the first such message received and continues operation in
   unicast mode. Subsequent replies from other anycast servers are
   ignored.

Thanks again
0
 
grg99Commented:
Please go and read the link I mentioned.

  Anycast is 99.99% done in the routers, all your client program does is try to connect to an IP address in the Anycast IP ranges defined by the routers.  No coding changes needed on the client end.

0
 
machoman990Author Commented:
Maybe i am just misinterpreting the info I read. But ive read that the IANA has assigned the multicast group address 224.0.1.1 for NTP, which is used both by multicast servers and anycast clients. Obviously that address is not a NTP server. (cannot be pinged or anything). If you can tell me how i find a IP address in the anycast range then ill give you the points.
0
 
grg99Commented:
I don't know much about anycast, but I'd guess your local routers and NTP servers have to cooperate in this.  I don't think that one address "just works" to find the closest NTP server on the Internet.  

Otherwise it would be a real mess if it cascaded up the Internet.

0
Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.

Join & Write a Comment

Featured Post

Improve Your Query Performance Tuning

In this FREE six-day email course, you'll learn from Janis Griffin, Database Performance Evangelist. She'll teach 12 steps that you can use to optimize your queries as much as possible and see measurable results in your work. Get started today!

  • 3
  • 2
Tackle projects and never again get stuck behind a technical roadblock.
Join Now