~ubuntu-branches/debian/squeeze/ntp/squeeze-201010051545

« back to all changes in this revision

Viewing changes to ntpd/ntp_intres.c

  • Committer: Bazaar Package Importer
  • Author(s): Matt Zimmerman
  • Date: 2004-10-11 16:10:27 UTC
  • mfrom: (1.1.1 upstream)
  • Revision ID: james.westby@ubuntu.com-20041011161027-icyjbji8ujym633o
Tags: 1:4.2.0a-10ubuntu2
Use ntp.ubuntulinux.org instead of pool.ntp.org

Show diffs side-by-side

added added

removed removed

Lines of Context:
20
20
# include <config.h>
21
21
#endif
22
22
 
 
23
#include "ntp_machine.h"
23
24
#include "ntpd.h"
24
25
#include "ntp_io.h"
25
26
#include "ntp_request.h"
49
50
        struct conf_entry *ce_next;
50
51
        char *ce_name;                  /* name we are trying to resolve */
51
52
        struct conf_peer ce_config;     /* configuration info for peer */
 
53
        struct sockaddr_storage peer_store; /* address info for both fams */
52
54
};
53
55
#define ce_peeraddr     ce_config.peeraddr
 
56
#define ce_peeraddr6    ce_config.peeraddr6
54
57
#define ce_hmode        ce_config.hmode
55
58
#define ce_version      ce_config.version
56
59
#define ce_minpoll      ce_config.minpoll
122
125
/*
123
126
 * File descriptor for ntp request code.
124
127
 */
125
 
static  int sockfd = -1;
126
 
 
 
128
static  SOCKET sockfd = INVALID_SOCKET; /* NT uses SOCKET */
127
129
 
128
130
/* stuff to be filled in by caller */
129
131
 
409
411
        ce = (struct conf_entry *)emalloc(sizeof(struct conf_entry));
410
412
        ce->ce_name = cp;
411
413
        ce->ce_peeraddr = 0;
 
414
        ce->ce_peeraddr6 = in6addr_any;
 
415
        ANYSOCK(&ce->peer_store);
412
416
        ce->ce_hmode = (u_char)mode;
413
417
        ce->ce_version = (u_char)version;
414
418
        ce->ce_minpoll = (u_char)minpoll;
445
449
        struct conf_entry *entry
446
450
        )
447
451
{
448
 
        struct hostent *hp;
449
 
        struct in_addr in;
 
452
        struct addrinfo *addr;
 
453
        int error;
450
454
 
451
455
        checkparent();          /* make sure our guy is still running */
452
456
 
453
 
        if (entry->ce_name && entry->ce_peeraddr) {
 
457
        if (entry->ce_name != NULL && SOCKNUL(&entry->peer_store)) {
454
458
                /* HMS: Squawk? */
455
459
                msyslog(LOG_ERR, "findhostaddr: both ce_name and ce_peeraddr are defined...");
456
460
                return 1;
457
461
        }
458
462
 
459
 
        if (!entry->ce_name && !entry->ce_peeraddr) {
 
463
        if (entry->ce_name == NULL && !SOCKNUL(&entry->peer_store)) {
460
464
                msyslog(LOG_ERR, "findhostaddr: both ce_name and ce_peeraddr are undefined!");
461
465
                return 0;
462
466
        }
467
471
                        msyslog(LOG_INFO, "findhostaddr: Resolving <%s>",
468
472
                                entry->ce_name);
469
473
#endif /* DEBUG */
470
 
                hp = gethostbyname(entry->ce_name);
 
474
                error = getaddrinfo(entry->ce_name, NULL, NULL, &addr);
 
475
                if (error == 0) {
 
476
                        entry->peer_store = *((struct sockaddr_storage*)(addr->ai_addr));
 
477
                        if (entry->peer_store.ss_family == AF_INET) {
 
478
                                entry->ce_peeraddr =
 
479
                                    GET_INADDR(entry->peer_store);
 
480
                                entry->ce_config.v6_flag = 0;
 
481
                        } else {
 
482
                                entry->ce_peeraddr6 =
 
483
                                    GET_INADDR6(entry->peer_store);
 
484
                                entry->ce_config.v6_flag = 1;
 
485
                        }
 
486
                }
471
487
        } else {
472
488
#ifdef DEBUG
473
489
                if (debug > 2)
474
 
                        msyslog(LOG_INFO, "findhostaddr: Resolving %x>",
475
 
                                entry->ce_peeraddr);
 
490
                        msyslog(LOG_INFO, "findhostaddr: Resolving %s>",
 
491
                                stoa(&entry->peer_store));
476
492
#endif
477
 
                in.s_addr = entry->ce_peeraddr;
478
 
                hp = gethostbyaddr((const char *)&in,
479
 
                                   sizeof entry->ce_peeraddr,
480
 
                                   AF_INET);
 
493
                entry->ce_name = emalloc(MAXHOSTNAMELEN);
 
494
                error = getnameinfo((const struct sockaddr *)&entry->peer_store,
 
495
                                   SOCKLEN(&entry->peer_store),
 
496
                                   (char *)&entry->ce_name, MAXHOSTNAMELEN,
 
497
                                   NULL, 0, 0);
481
498
        }
482
499
 
483
 
        if (hp == NULL) {
 
500
        if (error != 0) {
484
501
                /*
485
502
                 * If the resolver is in use, see if the failure is
486
503
                 * temporary.  If so, return success.
495
512
                if (debug > 2)
496
513
                        msyslog(LOG_INFO, "findhostaddr: name resolved.");
497
514
#endif
498
 
                /*
499
 
                 * Use the first address.  We don't have any way to tell
500
 
                 * preferences and older gethostbyname() implementations
501
 
                 * only return one.
502
 
                 */
503
 
                memmove((char *)&(entry->ce_peeraddr),
504
 
                        (char *)hp->h_addr,
505
 
                        sizeof(struct in_addr));
506
 
                if (entry->ce_keystr[0] == '*')
507
 
                        strncpy((char *)&(entry->ce_keystr), hp->h_name,
508
 
                                MAXFILENAME);
509
 
        } else {
510
 
                char *cp;
511
 
                size_t s;
512
515
 
513
516
#ifdef DEBUG
514
517
                if (debug > 2)
515
518
                        msyslog(LOG_INFO, "findhostaddr: address resolved.");
516
519
#endif
517
 
                s = strlen(hp->h_name) + 1;
518
 
                cp = emalloc(s);
519
 
                strcpy(cp, hp->h_name);
520
 
                entry->ce_name = cp;
521
520
        }
522
521
                   
523
522
        return (1);
530
529
static void
531
530
openntp(void)
532
531
{
533
 
        struct sockaddr_in saddr;
 
532
        struct addrinfo hints;
 
533
        struct addrinfo *addrResult;
534
534
 
535
535
        if (sockfd >= 0)
536
536
            return;
537
 
        
538
 
        sockfd = socket(AF_INET, SOCK_DGRAM, 0);
 
537
 
 
538
        memset(&hints, 0, sizeof(hints));
 
539
        hints.ai_family = AF_UNSPEC;
 
540
        hints.ai_socktype = SOCK_DGRAM;
 
541
        if (getaddrinfo(NULL, "ntp", &hints, &addrResult)!=0) {
 
542
                msyslog(LOG_ERR, "getaddrinfo failed: %m");
 
543
                exit(1);
 
544
        }
 
545
        sockfd = socket(addrResult->ai_family, addrResult->ai_socktype, 0);
 
546
 
539
547
        if (sockfd == -1) {
540
548
                msyslog(LOG_ERR, "socket() failed: %m");
541
549
                exit(1);
542
550
        }
543
551
 
544
 
        memset((char *)&saddr, 0, sizeof(saddr));
545
 
        saddr.sin_family = AF_INET;
546
 
        saddr.sin_port = htons(NTP_PORT);               /* trash */
547
 
        saddr.sin_addr.s_addr = htonl(LOCALHOST);       /* garbage */
548
 
 
549
552
        /*
550
553
         * Make the socket non-blocking.  We'll wait with select()
551
554
         */
574
577
                }
575
578
        }
576
579
#endif /* SYS_WINNT */
577
 
 
578
 
 
579
 
        if (connect(sockfd, (struct sockaddr *)&saddr, sizeof(saddr)) == -1) {
 
580
        if (connect(sockfd, addrResult->ai_addr, addrResult->ai_addrlen) == -1) {
580
581
                msyslog(LOG_ERR, "openntp: connect() failed: %m");
581
582
                exit(1);
582
583
        }
 
584
        freeaddrinfo(addrResult);
583
585
}
584
586
 
585
587
 
676
678
        overlap.Offset = overlap.OffsetHigh = (DWORD)0;
677
679
        overlap.hEvent = hReadWriteEvent;
678
680
        ret = WriteFile((HANDLE)sockfd, (char *)&reqpkt, REQ_LEN_NOMAC + n,
679
 
                        (LPDWORD)&NumberOfBytesWritten, (LPOVERLAPPED)&overlap);
 
681
                        NULL, (LPOVERLAPPED)&overlap);
680
682
        if ((ret == FALSE) && (GetLastError() != ERROR_IO_PENDING)) {
681
683
                msyslog(LOG_ERR, "send to NTP server failed: %m");
682
684
                return 0;
687
689
                    msyslog(LOG_ERR, "WaitForSingleObject failed: %m");
688
690
                return 0;
689
691
        }
 
692
        if (!GetOverlappedResult((HANDLE)sockfd, (LPOVERLAPPED)&overlap,
 
693
                                (LPDWORD)&NumberOfBytesWritten, FALSE)) {
 
694
                msyslog(LOG_ERR, "GetOverlappedResult for WriteFile fails: %m");
 
695
                return 0;
 
696
        }
690
697
#endif /* SYS_WINNT */
691
698
    
692
699
 
710
717
 
711
718
                if (n < 0)
712
719
                {
713
 
                        msyslog(LOG_ERR, "select() fails: %m");
 
720
                        if (errno != EINTR)
 
721
                            msyslog(LOG_ERR, "select() fails: %m");
714
722
                        return 0;
715
723
                }
716
724
                else if (n == 0)
731
739
                }
732
740
#else /* Overlapped I/O used on non-blocking sockets on Windows NT */
733
741
                ret = ReadFile((HANDLE)sockfd, (char *)&reqpkt, (DWORD)REQ_LEN_MAC,
734
 
                               (LPDWORD)&NumberOfBytesRead, (LPOVERLAPPED)&overlap);
 
742
                               NULL, (LPOVERLAPPED)&overlap);
735
743
                if ((ret == FALSE) && (GetLastError() != ERROR_IO_PENDING)) {
736
744
                        msyslog(LOG_ERR, "ReadFile() fails: %m");
737
745
                        return 0;
739
747
                dwWait = WaitForSingleObject(hReadWriteEvent, (DWORD) TIMEOUT_SEC * 1000);
740
748
                if ((dwWait == WAIT_FAILED) || (dwWait == WAIT_TIMEOUT)) {
741
749
                        if (dwWait == WAIT_FAILED) {
742
 
                                msyslog(LOG_ERR, "WaitForSingleObject fails: %m");
 
750
                                msyslog(LOG_ERR, "WaitForSingleObject for ReadFile fails: %m");
743
751
                                return 0;
744
752
                        }
745
753
                        continue;
746
754
                }
 
755
                if (!GetOverlappedResult((HANDLE)sockfd, (LPOVERLAPPED)&overlap,
 
756
                                        (LPDWORD)&NumberOfBytesRead, FALSE)) {
 
757
                        msyslog(LOG_ERR, "GetOverlappedResult fails: %m");
 
758
                        return 0;
 
759
                }
747
760
                n = NumberOfBytesRead;
748
761
#endif /* SYS_WINNT */
749
762
 
831
844
                
832
845
                    case INFO_ERR_IMPL:
833
846
                        msyslog(LOG_ERR,
834
 
                                "server reports implementation mismatch!!");
 
847
                                "ntpd reports implementation mismatch!");
835
848
                        return 0;
836
849
                
837
850
                    case INFO_ERR_REQ:
838
851
                        msyslog(LOG_ERR,
839
 
                                "server claims configuration request is unknown");
 
852
                                "ntpd says configuration request is unknown!");
840
853
                        return 0;
841
854
                
842
855
                    case INFO_ERR_FMT:
843
856
                        msyslog(LOG_ERR,
844
 
                                "server indicates a format error occurred(!!)");
 
857
                                "ntpd indicates a format error occurred!");
845
858
                        return 0;
846
859
 
847
860
                    case INFO_ERR_NODATA:
848
861
                        msyslog(LOG_ERR,
849
 
                                "server indicates no data available (shouldn't happen)");
 
862
                                "ntpd indicates no data available!");
850
863
                        return 0;
851
864
                
852
865
                    case INFO_ERR_AUTH:
853
866
                        msyslog(LOG_ERR,
854
 
                                "server returns a permission denied error");
 
867
                                "ntpd returns a permission denied error!");
855
868
                        return 0;
856
869
 
857
870
                    default:
858
871
                        msyslog(LOG_ERR,
859
 
                                "server returns unknown error code %d", n);
 
872
                                "ntpd returns unknown error code %d!", n);
860
873
                        return 0;
861
874
                }
862
875
        }
1028
1041
#ifdef DEBUG
1029
1042
                if (debug > 1)
1030
1043
                        msyslog(LOG_INFO,
1031
 
                            "doconfigure: <%s> has peeraddr %#x",
1032
 
                            ce->ce_name, ce->ce_peeraddr);
 
1044
                            "doconfigure: <%s> has peeraddr %s",
 
1045
                            ce->ce_name, stoa(&ce->peer_store));
1033
1046
#endif
1034
 
                if (dores && ce->ce_peeraddr == 0) {
 
1047
                if (dores && !SOCKNUL(&(ce->peer_store))) {
1035
1048
                        if (!findhostaddr(ce)) {
1036
1049
                                msyslog(LOG_ERR,
1037
1050
                                        "couldn't resolve `%s', giving up on it",
1043
1056
                        }
1044
1057
                }
1045
1058
 
1046
 
                if (ce->ce_peeraddr != 0) {
 
1059
                if (!SOCKNUL(&ce->peer_store)) {
1047
1060
                        if (request(&ce->ce_config)) {
1048
1061
                                ceremove = ce;
1049
1062
                                ce = ceremove->ce_next;