1 #include "config.h" 2 #include "ntp_debug.h" 3 #include "ntp_stdlib.h" 4 #include "ntp_types.h" 5 6 #include "sntptest.h" 7 8 #include "kod_management.h" 9 #include "main.h" 10 #include "networking.h" 11 #include "ntp.h" 12 13 #include "unity.h" 14 15 void setUp(void); 16 int LfpEquality(const l_fp expected, const l_fp actual); 17 void test_GenerateUnauthenticatedPacket(void); 18 void test_GenerateAuthenticatedPacket(void); 19 void test_OffsetCalculationPositiveOffset(void); 20 void test_OffsetCalculationNegativeOffset(void); 21 void test_HandleUnusableServer(void); 22 void test_HandleUnusablePacket(void); 23 void test_HandleServerAuthenticationFailure(void); 24 void test_HandleKodDemobilize(void); 25 void test_HandleKodRate(void); 26 void test_HandleCorrectPacket(void); 27 28 29 void 30 setUp(void) 31 { 32 init_lib(); 33 } 34 35 36 int 37 LfpEquality( 38 const l_fp expected, 39 const l_fp actual 40 ) 41 { 42 return !!(L_ISEQU(&expected, &actual)); 43 } 44 45 46 void 47 test_GenerateUnauthenticatedPacket(void) 48 { 49 struct pkt testpkt; 50 struct timeval xmt; 51 l_fp expected_xmt, actual_xmt; 52 53 GETTIMEOFDAY(&xmt, NULL); 54 xmt.tv_sec += JAN_1970; 55 56 TEST_ASSERT_EQUAL(LEN_PKT_NOMAC, 57 generate_pkt(&testpkt, &xmt, 0, NULL)); 58 59 TEST_ASSERT_EQUAL(LEAP_NOTINSYNC, PKT_LEAP(testpkt.li_vn_mode)); 60 TEST_ASSERT_EQUAL(NTP_VERSION, PKT_VERSION(testpkt.li_vn_mode)); 61 TEST_ASSERT_EQUAL(MODE_CLIENT, PKT_MODE(testpkt.li_vn_mode)); 62 63 TEST_ASSERT_EQUAL(STRATUM_UNSPEC, PKT_TO_STRATUM(testpkt.stratum)); 64 TEST_ASSERT_EQUAL(8, testpkt.ppoll); 65 66 TVTOTS(&xmt, &expected_xmt); 67 NTOHL_FP(&testpkt.xmt, &actual_xmt); 68 TEST_ASSERT_TRUE(LfpEquality(expected_xmt, actual_xmt)); 69 } 70 71 72 void 73 test_GenerateAuthenticatedPacket(void) 74 { 75 static const int EXPECTED_PKTLEN = LEN_PKT_NOMAC + MAX_MD5_LEN; 76 77 struct key testkey; 78 struct pkt testpkt; 79 struct timeval xmt; 80 l_fp expected_xmt, actual_xmt; 81 char expected_mac[MAX_MD5_LEN]; 82 83 testkey.next = NULL; 84 testkey.key_id = 30; 85 testkey.key_len = 9; 86 memcpy(testkey.key_seq, "123456789", testkey.key_len); 87 strlcpy(testkey.typen, "MD5", sizeof(testkey.typen)); 88 testkey.typei = keytype_from_text(testkey.typen, NULL); 89 90 GETTIMEOFDAY(&xmt, NULL); 91 xmt.tv_sec += JAN_1970; 92 93 TEST_ASSERT_EQUAL(EXPECTED_PKTLEN, 94 generate_pkt(&testpkt, &xmt, testkey.key_id, &testkey)); 95 96 TEST_ASSERT_EQUAL(LEAP_NOTINSYNC, PKT_LEAP(testpkt.li_vn_mode)); 97 TEST_ASSERT_EQUAL(NTP_VERSION, PKT_VERSION(testpkt.li_vn_mode)); 98 TEST_ASSERT_EQUAL(MODE_CLIENT, PKT_MODE(testpkt.li_vn_mode)); 99 100 TEST_ASSERT_EQUAL(STRATUM_UNSPEC, PKT_TO_STRATUM(testpkt.stratum)); 101 TEST_ASSERT_EQUAL(8, testpkt.ppoll); 102 103 TVTOTS(&xmt, &expected_xmt); 104 NTOHL_FP(&testpkt.xmt, &actual_xmt); 105 TEST_ASSERT_TRUE(LfpEquality(expected_xmt, actual_xmt)); 106 107 TEST_ASSERT_EQUAL(testkey.key_id, ntohl(testpkt.exten[0])); 108 109 TEST_ASSERT_EQUAL(MAX_MD5_LEN - 4, /* Remove the key_id, only keep the mac. */ 110 make_mac(&testpkt, LEN_PKT_NOMAC, MAX_MD5_LEN-4, &testkey, expected_mac)); 111 TEST_ASSERT_EQUAL_MEMORY(expected_mac, (char*)&testpkt.exten[1], MAX_MD5_LEN -4); 112 } 113 114 115 void 116 test_OffsetCalculationPositiveOffset(void) 117 { 118 struct pkt rpkt; 119 l_fp reftime, tmp; 120 struct timeval dst; 121 double offset, precision, synch_distance; 122 123 rpkt.precision = -16; /* 0,000015259 */ 124 rpkt.rootdelay = HTONS_FP(DTOUFP(0.125)); 125 rpkt.rootdisp = HTONS_FP(DTOUFP(0.25)); 126 127 /* Synch Distance: (0.125+0.25)/2.0 == 0.1875 */ 128 get_systime(&reftime); 129 HTONL_FP(&reftime, &rpkt.reftime); 130 131 /* T1 - Originate timestamp */ 132 tmp.l_ui = 1000000000UL; 133 tmp.l_uf = 0UL; 134 HTONL_FP(&tmp, &rpkt.org); 135 136 /* T2 - Receive timestamp */ 137 tmp.l_ui = 1000000001UL; 138 tmp.l_uf = 2147483648UL; 139 HTONL_FP(&tmp, &rpkt.rec); 140 141 /* T3 - Transmit timestamp */ 142 tmp.l_ui = 1000000002UL; 143 tmp.l_uf = 0UL; 144 HTONL_FP(&tmp, &rpkt.xmt); 145 146 /* T4 - Destination timestamp as standard timeval */ 147 tmp.l_ui = 1000000001UL; 148 tmp.l_uf = 0UL; 149 TSTOTV(&tmp, &dst); 150 dst.tv_sec -= JAN_1970; 151 152 offset_calculation(&rpkt, LEN_PKT_NOMAC, &dst, &offset, &precision, &synch_distance); 153 154 TEST_ASSERT_EQUAL_DOUBLE(1.25, offset); 155 TEST_ASSERT_EQUAL_DOUBLE(1. / ULOGTOD(16), precision); 156 /* 1.1250150000000001 ? */ 157 TEST_ASSERT_EQUAL_DOUBLE(1.125015, synch_distance); 158 } 159 160 161 void 162 test_OffsetCalculationNegativeOffset(void) 163 { 164 struct pkt rpkt; 165 l_fp reftime, tmp; 166 struct timeval dst; 167 double offset, precision, synch_distance; 168 169 rpkt.precision = -1; 170 rpkt.rootdelay = HTONS_FP(DTOUFP(0.5)); 171 rpkt.rootdisp = HTONS_FP(DTOUFP(0.5)); 172 173 /* Synch Distance is (0.5+0.5)/2.0, or 0.5 */ 174 get_systime(&reftime); 175 HTONL_FP(&reftime, &rpkt.reftime); 176 177 /* T1 - Originate timestamp */ 178 tmp.l_ui = 1000000001UL; 179 tmp.l_uf = 0UL; 180 HTONL_FP(&tmp, &rpkt.org); 181 182 /* T2 - Receive timestamp */ 183 tmp.l_ui = 1000000000UL; 184 tmp.l_uf = 2147483648UL; 185 HTONL_FP(&tmp, &rpkt.rec); 186 187 /*/ T3 - Transmit timestamp */ 188 tmp.l_ui = 1000000001UL; 189 tmp.l_uf = 2147483648UL; 190 HTONL_FP(&tmp, &rpkt.xmt); 191 192 /* T4 - Destination timestamp as standard timeval */ 193 tmp.l_ui = 1000000003UL; 194 tmp.l_uf = 0UL; 195 196 TSTOTV(&tmp, &dst); 197 dst.tv_sec -= JAN_1970; 198 199 offset_calculation(&rpkt, LEN_PKT_NOMAC, &dst, &offset, &precision, &synch_distance); 200 201 TEST_ASSERT_EQUAL_DOUBLE(-1, offset); 202 TEST_ASSERT_EQUAL_DOUBLE(1. / ULOGTOD(1), precision); 203 TEST_ASSERT_EQUAL_DOUBLE(1.3333483333333334, synch_distance); 204 } 205 206 207 void 208 test_HandleUnusableServer(void) 209 { 210 struct pkt rpkt; 211 sockaddr_u host; 212 int rpktl; 213 214 ZERO(rpkt); 215 ZERO(host); 216 rpktl = SERVER_UNUSEABLE; 217 TEST_ASSERT_EQUAL(-1, handle_pkt(rpktl, &rpkt, &host, "")); 218 } 219 220 221 void 222 test_HandleUnusablePacket(void) 223 { 224 struct pkt rpkt; 225 sockaddr_u host; 226 int rpktl; 227 228 ZERO(rpkt); 229 ZERO(host); 230 rpktl = PACKET_UNUSEABLE; 231 TEST_ASSERT_EQUAL(1, handle_pkt(rpktl, &rpkt, &host, "")); 232 } 233 234 235 void 236 test_HandleServerAuthenticationFailure(void) 237 { 238 struct pkt rpkt; 239 sockaddr_u host; 240 int rpktl; 241 242 ZERO(rpkt); 243 ZERO(host); 244 rpktl = SERVER_AUTH_FAIL; 245 TEST_ASSERT_EQUAL(1, handle_pkt(rpktl, &rpkt, &host, "")); 246 } 247 248 249 void 250 test_HandleKodDemobilize(void) 251 { 252 static const char * HOSTNAME = "192.0.2.1"; 253 static const char * REASON = "DENY"; 254 struct pkt rpkt; 255 sockaddr_u host; 256 int rpktl; 257 struct kod_entry * entry; 258 259 rpktl = KOD_DEMOBILIZE; 260 ZERO(rpkt); 261 memcpy(&rpkt.refid, REASON, 4); 262 ZERO(host); 263 host.sa4.sin_family = AF_INET; 264 host.sa4.sin_addr.s_addr = inet_addr(HOSTNAME); 265 266 /* Test that the KOD-entry is added to the database. */ 267 kod_init_kod_db("/dev/null", TRUE); 268 269 TEST_ASSERT_EQUAL(1, handle_pkt(rpktl, &rpkt, &host, HOSTNAME)); 270 271 TEST_ASSERT_EQUAL(1, search_entry(HOSTNAME, &entry)); 272 TEST_ASSERT_EQUAL_MEMORY(REASON, entry->type, 4); 273 } 274 275 276 void 277 test_HandleKodRate(void) 278 { 279 struct pkt rpkt; 280 sockaddr_u host; 281 int rpktl; 282 283 ZERO(rpkt); 284 ZERO(host); 285 rpktl = KOD_RATE; 286 TEST_ASSERT_EQUAL(1, handle_pkt(rpktl, &rpkt, &host, "")); 287 } 288 289 290 void 291 test_HandleCorrectPacket(void) 292 { 293 struct pkt rpkt; 294 sockaddr_u host; 295 int rpktl; 296 l_fp now; 297 298 /* We don't want our testing code to actually change the system clock. */ 299 TEST_ASSERT_FALSE(ENABLED_OPT(STEP)); 300 TEST_ASSERT_FALSE(ENABLED_OPT(SLEW)); 301 302 get_systime(&now); 303 HTONL_FP(&now, &rpkt.reftime); 304 HTONL_FP(&now, &rpkt.org); 305 HTONL_FP(&now, &rpkt.rec); 306 HTONL_FP(&now, &rpkt.xmt); 307 rpktl = LEN_PKT_NOMAC; 308 ZERO(host); 309 AF(&host) = AF_INET; 310 311 TEST_ASSERT_EQUAL(0, handle_pkt(rpktl, &rpkt, &host, "")); 312 } 313 314 /* packetHandling.c */ 315