Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations gkittelson on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Easy *nix Timeserver 1

Status
Not open for further replies.

marsd

IS-IT--Management
Apr 25, 2001
2,218
US
Does anyone have any suggestions or code referrals
for a trivial timeserver that accepts an epoch time
stamp and sets the system date entirely in C without
root privileges throughout?

I've looked at the function defs for a day and have
come up empty since settimeofday() is a little rigid.

Here's the preliminary client code:
Code:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <unistd.h>
#include <sys/socket.h>
#include <arpa/inet.h>



#define DPORT 9001
#define MAXLEN 10

void doUsage(void);
void sendTime(char *, time_t);
void abortWithErr(char *);

int main(int argc , char **argv) {
int i;
time_t mytime;

              if (argc < 2) {
                  doUsage();
                  return -1;
              } else {
                  for (i=1 ; i < argc ; i++) {
                      time(&mytime);
                      printf(&quot;Updating %s\n&quot;, argv[i]);
                      sendTime(argv[i],mytime);
                  }
              }
return 0;
}

void sendTime(char *address, time_t current) {
int sock, port;
struct sockaddr_in remotesrv;


       if ( (sock = socket(PF_INET,SOCK_STREAM,IPPROTO_TCP)) < 0) {
            abortWithErr(&quot;sock()&quot;);
       }

       bzero(&remotesrv, sizeof(remotesrv));
       remotesrv.sin_family = AF_INET;
       remotesrv.sin_addr.s_addr = inet_addr(address);
       remotesrv.sin_port = htons(DPORT);


       if ( (connect(sock,(struct sockaddr *) &remotesrv,sizeof(remotesrv))) < 0) {
            abortWithErr(&quot;connect()&quot;);
       } else {
            if (send(sock,&current,MAXLEN,MSG_DONTWAIT) != MAXLEN) {
                 abortWithErr(&quot;send()&quot;);
            }
         close(sock);
         printf(&quot;Success..opened %s and sent time string %d\n&quot;, address,(int)current);
      }
}
      
void doUsage() {

       printf(&quot;***********************Usage************************\n&quot;);
       printf(&quot;\n&quot;);
       printf(&quot;Please pass the addresses of the hosts you would like to update\n&quot;);
       printf(&quot;as arguments to this program\n&quot;);
       printf(&quot;\n&quot;);
       printf(&quot;***********************Usage************************\n&quot;);
}

void abortWithErr(char *pt) {
          perror(pt);
          abort();
}
 
stime, if available to you, has a friendlier interface for your purposes.

I can't see how the choice of system call would solve the bigger problem of running such a program that doesn't have root privileges, though. stime, and probably any other system call that changes the system date, will require the process to have super-user privileges.

I don't know what you're trying to accomplish exactly, but isn't this sort of thing usually done the other way around? That is, a server running a daytime server (Port 13/TCP) is queried (via root's cron) by each machine on the network that wants to synchronize its clock. I think the rdate command can be invoked on the client side to handle the details of retrieving and setting the time.
 
&quot;I don't know what you're trying to accomplish exactly, but isn't this sort of thing usually done the other way around?&quot;

Exactly. All depends on the server hosts time to be
correct.
I don't like that. It never works.
I'd rather have an easy way to change the time across
multiple servers from any trusted client than have a
single point of failure for the server and multiple
clients.

&quot;I can't see how the choice of system call would solve the bigger problem of running such a program that doesn't have root privileges, though. stime, and probably any other system call that changes the system date, will require the process to have super-user privileges.&quot;

Yes and this was my main question, though I didn't know
about stime(), thanks for that.
I could use sudo via a system call but that would
involve rewriting/padding the members of the tm struct
to correspond to the 10 digit stamp for date....

Thanks again.
 
Rather than set up a timeserver yourself, have you looked into querying a list of Internet servers instead? There are machines out there that have a greater chance of accuracy than a machine you might set up yourself.

The link below contains lists of public NTP servers. Just an idea, but maybe you could build a list of these servers in a text file like this and place it on an HTTP server or NFS server or whatever.

ntp.server1.com
ntp.server2.com
ntp.server3.com
...

And then from cron every night each machine on your network could retrieve the NTP server list, iterate through the list querying each server in turn and recording the time it reports. If n number of servers agree on the time, then you probably have the right time and can go ahead and set it.

Something like that, I'm sure you see what I'm getting at.


Check this out, too:

 
Yes, thats definitely another approach.
I'll take a look at it for feasibility.

Thanks.

 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top