ntp: protect authenticated symmetric associations against DoS attacks

An attacker knowing that NTP hosts A and B are peering with each other
(symmetric association) can send a packet with random timestamps to host
A with source address of B which will set the NTP state variables on A
to the values sent by the attacker. Host A will then send on its next
poll to B a packet with originate timestamp that doesn't match the
transmit timestamp of B and the packet will be dropped. If the attacker
does this periodically for both hosts, they won't be able to synchronize
to each other. It is a denial-of-service attack.

According to [1], NTP authentication is supposed to protect symmetric
associations against this attack, but in the NTPv3 (RFC 1305) and NTPv4
(RFC 5905) specifications the state variables are updated before the
authentication check is performed, which means the association is
vulnerable to the attack even when authentication is enabled.

To fix this problem in chrony, save the originate and local timestamps
only when the authentication check (test5) passed.

[1] https://www.eecis.udel.edu/~mills/onwire.html
This commit is contained in:
Miroslav Lichvar 2015-03-05 12:44:30 +01:00
parent ebab36e859
commit f0c48680fe

View file

@ -1005,9 +1005,6 @@ receive_packet(NTP_Packet *message, struct timeval *now, double now_err, NCR_Ins
/* ==================== */
/* Save local receive timestamp */
inst->local_rx = *now;
pkt_leap = (message->lvm >> 6) & 0x3;
if (pkt_leap == 0x3) {
source_is_synchronized = 0;
@ -1039,14 +1036,6 @@ receive_packet(NTP_Packet *message, struct timeval *now, double now_err, NCR_Ins
test2 = 1; /* Success */
}
/* Regardless of any validity checks we apply, we are required to
save this field from the packet into the ntp source
instance record. See RFC1305 section 3.4.4, peer.org <- pkt.xmt
& peer.peerpoll <- pkt.poll. Note we can't do this assignment
before test1 has been carried out!! */
inst->remote_orig = message->transmit_ts;
/* Test 3 requires that pkt.org != 0 and pkt.rec != 0. If
either of these are true it means the association is not properly
'up'. */
@ -1219,6 +1208,14 @@ receive_packet(NTP_Packet *message, struct timeval *now, double now_err, NCR_Ins
kod_rate = 1;
}
/* The transmit timestamp and local receive timestamp must not be saved when
the authentication test failed to prevent denial-of-service attacks on
symmetric associations using authentication */
if (test5) {
inst->remote_orig = message->transmit_ts;
inst->local_rx = *now;
}
valid_kod = test1 && test2 && test5;
valid_data = test1 && test2 && test3 && test4 && test4a && test4b;