[Git][NTPsec/ntpsec][master] Checkpoint: replay mode before trying to implement full packet parsing.

Eric S. Raymond gitlab at mg.gitlab.com
Tue Dec 15 23:50:21 UTC 2015


Eric S. Raymond pushed to branch master at NTPsec / ntpsec


Commits:
f0a57d5e by Eric S. Raymond at 2015-12-15T18:49:19Z
Checkpoint: replay mode before trying to implement full packet parsing.

- - - - -


3 changed files:

- ntpd/ntp_intercept.c
- ntpd/ntp_intercept.h
- ntpd/ntpd.c


Changes:

=====================================
ntpd/ntp_intercept.c
=====================================
--- a/ntpd/ntp_intercept.c
+++ b/ntpd/ntp_intercept.c
@@ -18,21 +18,19 @@ following kinds:
 
 6. Calls to the host's random-number generator.
 
-7. Alarm events.
+7. Calls to adjtime/ntp_adjtime/adjtime to adjust the system clock.
 
-8. Calls to adjtime/ntp_adjtime/adjtime to adjust the system clock.
+8  Calls to ntp_set_tod to set the system clock.
 
-9  Calls to ntp_set_tod to set the system clock.
+9. Read of the system leapsecond file.
 
-10. Read of the system leapsecond file.
+10. Packets incoming from NTP peers and others.
 
-11. Packets incoming from NTP peers and others.
+11. Packets outgoing to NTP peers and others.
 
-12. Packets outgoing to NTP peers and others.
+12. Read of authkey file
 
-13. Read of authkey file
-
-14. Termination.
+13. Termination.
 
 We must support two modes of operation.  In "capture" mode, ntpd
 operates normally, logging all events.  In "replay" mode, ntpd accepts
@@ -331,16 +329,6 @@ long intercept_ntp_random(const char *legend)
     return roll;
 }
 
-void intercept_timer(void)
-{
-    timer();
-    if (mode == capture)
-	printf("timer\n");
-    else if (mode == replay)
-	/* probably is not necessary to record this... */
-	get_operation("timer");
-}
-
 bool intercept_drift_read(const char *drift_file, double *drift)
 {
     if (mode == replay) {
@@ -625,7 +613,7 @@ intercept_leapsec_load_file(
 }
 
 static void packet_dump(char *buf, size_t buflen,
-			sockaddr_u *dest, struct pkt *pkt, int len)
+			sockaddr_u *dest, struct pkt *pkt, size_t len)
 {
     size_t i;
     /*
@@ -650,6 +638,23 @@ static void packet_dump(char *buf, size_t buflen,
 	}
 }
 
+static void recvbuf_dump(char *buf, size_t buflen, struct recvbuf *rbufp)
+{
+    char pkt_dump[BUFSIZ];
+
+    packet_dump(pkt_dump, sizeof(pkt_dump),
+		&rbufp->recv_srcadr, &rbufp->recv_pkt, rbufp->recv_length);
+    /*
+     * Order is: cast flags, receipt time, source address, packet,
+     * MAC.  Cast flags are only kept because they change the ntpq
+     * display, they have no implications for the protocol machine.
+     * We don't dump srcadr because only the parse clock uses that.
+     */
+    snprintf(buf, buflen,
+	     "receive %0x %s %s\n",
+	     rbufp->cast_flags, lfpdump(&rbufp->recv_time), pkt_dump);
+}
+
 void intercept_sendpkt(const char *legend,
 		  sockaddr_u *dest, struct interface *ep, int ttl,
 		  struct pkt *pkt, int len)
@@ -677,31 +682,62 @@ void intercept_sendpkt(const char *legend,
 
 void intercept_receive(struct recvbuf *rbufp)
 {
-    char pkt_dump[BUFSIZ], newpacket[BUFSIZ];
+    /* never called in replay mode */
+    if (mode == capture) {
+	char pkt_dump[BUFSIZ];
 
-    packet_dump(pkt_dump, sizeof(pkt_dump),
-		&rbufp->recv_srcadr,
-		&rbufp->recv_pkt, rbufp->recv_length);
-    /*
-     * Order is: cast flags, receipt time, source address, packet,
-     * MAC.  Cast flags are only kept because they change the ntpq
-     * display, they have no implications for the protocol machine.
-     * We don't dump srcadr because only the parse clock uses that.
-     */
-    snprintf(newpacket, sizeof(newpacket),
-	     "receive %0x %s %s\n",
-	     rbufp->cast_flags, lfpdump(&rbufp->recv_time), pkt_dump);
+	recvbuf_dump(pkt_dump, sizeof(pkt_dump), rbufp);
+	fputs(pkt_dump, stdout);
+    }
 
-    if (mode == replay) {
-	if (strcmp(linebuf, newpacket) != 0) {
-	    fprintf(stderr, "ntpd: line %d, receive mismatch saw %s\n",
-		    lineno, newpacket);
+    receive(rbufp);
+}
+
+void intercept_replay(void)
+{
+    printf("# entering replay loop at line %d\n", lineno);
+    for (;;) {
+	get_operation(NULL);
+	if (strncmp(linebuf, "finish", 6) == 0)
+	    break;
+	else if (strncmp(linebuf, "receive ", 8) == 0)
+	{
+	    struct recvbuf rbuf;
+	    char recvbuf[BUFSIZ], srcbuf[BUFSIZ], pktbuf[BUFSIZ], macbuf[BUFSIZ];
+
+	    if (sscanf(linebuf, "receive %x %s %s %s %s",
+		       &rbuf.cast_flags, recvbuf, srcbuf, pktbuf, macbuf) != 5)
+	    {
+		fprintf(stderr, "ntpd: bad receive format at line %d\n", lineno);
+		exit(1);
+	    }
+
+	    atolfp(recvbuf, &rbuf.recv_time);
+	    /* FIXME: parse source address */
+	    /* FIXME: parse packet and MAC */
+
+	    /*
+	     * If the packet doesn't dump identically to how it came in,
+	     * something is wrong with our packet parsing.
+	     */
+	    recvbuf_dump(recvbuf, sizeof(recvbuf), &rbuf);
+	    if (strcmp(linebuf, recvbuf) != 0)
+	    {
+		fprintf(stderr, "ntpd: round-trip failure at line %d\n", lineno);
+		fprintf(stderr, "old = %s\n", linebuf);
+		fprintf(stderr, "new = %s\n", recvbuf);
+		exit(1);
+	    }
+
+	    /* executing the receive call may pop other things off the queue */
+	    receive(&rbuf);
+	}
+	else
+	{
+	    fprintf(stderr, "ntpd: unexpected operation at line %d\n", lineno);
 	    exit(1);
 	}
-    } else if (mode == capture)
-	fputs(newpacket, stdout);
-
-    receive(rbufp);
+    }
 }
 
 void


=====================================
ntpd/ntp_intercept.h
=====================================
--- a/ntpd/ntp_intercept.h
+++ b/ntpd/ntp_intercept.h
@@ -20,7 +20,6 @@ void intercept_argparse(int *, char ***);
 void intercept_getconfig(const char *);
 void intercept_get_systime(const char *, l_fp *);
 long intercept_ntp_random(const char *);
-void intercept_timer(void);
 void intercept_sendpkt(const char *,
 		       sockaddr_u *, struct interface *, int, struct pkt *, int);
 void intercept_receive(struct recvbuf *);
@@ -34,6 +33,7 @@ int intercept_set_tod(struct timespec *tvs);
 extern bool intercept_leapsec_load_file(const char * fname, struct stat * sb,
 					bool force, bool logall);
 void intercept_getauthkeys(const char *);
+void intercept_replay(void);
 void intercept_exit(const int);
 
 /* end */


=====================================
ntpd/ntpd.c
=====================================
--- a/ntpd/ntpd.c
+++ b/ntpd/ntpd.c
@@ -935,7 +935,10 @@ ntpdmain(
 		msyslog(LOG_INFO, "running as non-root disables dynamic interface tracking");
 	}
 
-	mainloop();
+	if (intercept_get_mode() == replay)
+	    intercept_replay();
+	else
+	    mainloop();
 	return 1;
 }
 
@@ -980,7 +983,7 @@ static void mainloop(void)
 			 * Out here, signals are unblocked.  Call timer routine
 			 * to process expiry.
 			 */
-			intercept_timer();
+			timer();
 			was_alarmed = false;
 			BLOCK_IO_AND_ALARM();
 		}



View it on GitLab: https://gitlab.com/NTPsec/ntpsec/commit/f0a57d5e59c8dda9f3a9ec789bd79ab7fde791cc
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.ntpsec.org/pipermail/vc/attachments/20151215/3f718347/attachment.html>


More information about the vc mailing list