1 /* $NetBSD: calendar.c,v 1.1.1.6 2016/11/22 01:35:19 christos Exp $ */ 2 3 #include "config.h" 4 5 #include "ntp_stdlib.h" /* test fail without this include, for some reason */ 6 #include "ntp_calendar.h" 7 #include "ntp_unixtime.h" 8 #include "unity.h" 9 10 #include <string.h> 11 12 static int leapdays(int year); 13 14 void setUp(void); 15 int isGT(int first, int second); 16 int leapdays(int year); 17 char * CalendarFromCalToString(const struct calendar *cal); 18 char * CalendarFromIsoToString(const struct isodate *iso); 19 int IsEqualCal(const struct calendar *expected, const struct calendar *actual); 20 int IsEqualIso(const struct isodate *expected, const struct isodate *actual); 21 char * DateFromCalToString(const struct calendar *cal); 22 char * DateFromIsoToString(const struct isodate *iso); 23 int IsEqualDateCal(const struct calendar *expected, const struct calendar *actual); 24 int IsEqualDateIso(const struct isodate *expected, const struct isodate *actual); 25 26 void test_DaySplitMerge(void); 27 void test_SplitYearDays1(void); 28 void test_SplitYearDays2(void); 29 void test_RataDie1(void); 30 void test_LeapYears1(void); 31 void test_LeapYears2(void); 32 void test_RoundTripDate(void); 33 void test_RoundTripYearStart(void); 34 void test_RoundTripMonthStart(void); 35 void test_RoundTripWeekStart(void); 36 void test_RoundTripDayStart(void); 37 void test_IsoCalYearsToWeeks(void); 38 void test_IsoCalWeeksToYearStart(void); 39 void test_IsoCalWeeksToYearEnd(void); 40 void test_DaySecToDate(void); 41 42 void test_NtpToNtp(void); 43 void test_NtpToTime(void); 44 45 void 46 setUp(void) 47 { 48 init_lib(); 49 50 return; 51 } 52 53 54 /* 55 * --------------------------------------------------------------------- 56 * test support stuff 57 * --------------------------------------------------------------------- 58 */ 59 int 60 isGT(int first, int second) 61 { 62 if(first > second) { 63 return TRUE; 64 } else { 65 return FALSE; 66 } 67 } 68 69 int 70 leapdays(int year) 71 { 72 if (year % 400 == 0) 73 return 1; 74 if (year % 100 == 0) 75 return 0; 76 if (year % 4 == 0) 77 return 1; 78 return 0; 79 } 80 81 char * 82 CalendarFromCalToString( 83 const struct calendar *cal) 84 { 85 char * str = malloc(sizeof (char) * 100); 86 snprintf(str, 100, "%u-%02u-%02u (%u) %02u:%02u:%02u", 87 cal->year, (u_int)cal->month, (u_int)cal->monthday, 88 cal->yearday, 89 (u_int)cal->hour, (u_int)cal->minute, (u_int)cal->second); 90 str[99] = '\0'; /* paranoia rulez! */ 91 return str; 92 } 93 94 char * 95 CalendarFromIsoToString( 96 const struct isodate *iso) 97 { 98 char * str = emalloc (sizeof (char) * 100); 99 snprintf(str, 100, "%u-W%02u-%02u %02u:%02u:%02u", 100 iso->year, (u_int)iso->week, (u_int)iso->weekday, 101 (u_int)iso->hour, (u_int)iso->minute, (u_int)iso->second); 102 str[99] = '\0'; /* paranoia rulez! */ 103 return str; 104 } 105 106 int 107 IsEqualCal( 108 const struct calendar *expected, 109 const struct calendar *actual) 110 { 111 if (expected->year == actual->year && 112 (!expected->yearday || expected->yearday == actual->yearday) && 113 expected->month == actual->month && 114 expected->monthday == actual->monthday && 115 expected->hour == actual->hour && 116 expected->minute == actual->minute && 117 expected->second == actual->second) { 118 return TRUE; 119 } else { 120 char *p_exp = CalendarFromCalToString(expected); 121 char *p_act = CalendarFromCalToString(actual); 122 123 printf("expected: %s but was %s", p_exp, p_act); 124 125 free(p_exp); 126 free(p_act); 127 128 return FALSE; 129 } 130 } 131 132 int 133 IsEqualIso( 134 const struct isodate *expected, 135 const struct isodate *actual) 136 { 137 if (expected->year == actual->year && 138 expected->week == actual->week && 139 expected->weekday == actual->weekday && 140 expected->hour == actual->hour && 141 expected->minute == actual->minute && 142 expected->second == actual->second) { 143 return TRUE; 144 } else { 145 printf("expected: %s but was %s", 146 CalendarFromIsoToString(expected), 147 CalendarFromIsoToString(actual)); 148 return FALSE; 149 } 150 } 151 152 char * 153 DateFromCalToString( 154 const struct calendar *cal) 155 { 156 157 char * str = emalloc (sizeof (char) * 100); 158 snprintf(str, 100, "%u-%02u-%02u (%u)", 159 cal->year, (u_int)cal->month, (u_int)cal->monthday, 160 cal->yearday); 161 str[99] = '\0'; /* paranoia rulez! */ 162 return str; 163 } 164 165 char * 166 DateFromIsoToString( 167 const struct isodate *iso) 168 { 169 170 char * str = emalloc (sizeof (char) * 100); 171 snprintf(str, 100, "%u-W%02u-%02u", 172 iso->year, (u_int)iso->week, (u_int)iso->weekday); 173 str[99] = '\0'; /* paranoia rulez! */ 174 return str; 175 } 176 177 int/*BOOL*/ 178 IsEqualDateCal( 179 const struct calendar *expected, 180 const struct calendar *actual) 181 { 182 if (expected->year == actual->year && 183 (!expected->yearday || expected->yearday == actual->yearday) && 184 expected->month == actual->month && 185 expected->monthday == actual->monthday) { 186 return TRUE; 187 } else { 188 printf("expected: %s but was %s", 189 DateFromCalToString(expected), 190 DateFromCalToString(actual)); 191 return FALSE; 192 } 193 } 194 195 int/*BOOL*/ 196 IsEqualDateIso( 197 const struct isodate *expected, 198 const struct isodate *actual) 199 { 200 if (expected->year == actual->year && 201 expected->week == actual->week && 202 expected->weekday == actual->weekday) { 203 return TRUE; 204 } else { 205 printf("expected: %s but was %s", 206 DateFromIsoToString(expected), 207 DateFromIsoToString(actual)); 208 return FALSE; 209 } 210 } 211 212 213 /* 214 * --------------------------------------------------------------------- 215 * test cases 216 * --------------------------------------------------------------------- 217 */ 218 219 /* days before month, with a full-year pad at the upper end */ 220 static const u_short real_month_table[2][13] = { 221 /* -*- table for regular years -*- */ 222 { 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365 }, 223 /* -*- table for leap years -*- */ 224 { 0, 31, 60, 91, 121, 152, 182, 213, 244, 274, 305, 335, 366 } 225 }; 226 227 /* days in month, with one month wrap-around at both ends */ 228 static const u_short real_month_days[2][14] = { 229 /* -*- table for regular years -*- */ 230 { 31, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31, 31 }, 231 /* -*- table for leap years -*- */ 232 { 31, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31, 31 } 233 }; 234 235 /* test the day/sec join & split ops, making sure that 32bit 236 * intermediate results would definitely overflow and the hi DWORD of 237 * the 'vint64' is definitely needed. 238 */ 239 void 240 test_DaySplitMerge(void) 241 { 242 int32 day,sec; 243 244 for (day = -1000000; day <= 1000000; day += 100) { 245 for (sec = -100000; sec <= 186400; sec += 10000) { 246 vint64 merge; 247 ntpcal_split split; 248 int32 eday; 249 int32 esec; 250 251 merge = ntpcal_dayjoin(day, sec); 252 split = ntpcal_daysplit(&merge); 253 eday = day; 254 esec = sec; 255 256 while (esec >= 86400) { 257 eday += 1; 258 esec -= 86400; 259 } 260 while (esec < 0) { 261 eday -= 1; 262 esec += 86400; 263 } 264 265 TEST_ASSERT_EQUAL(eday, split.hi); 266 TEST_ASSERT_EQUAL(esec, split.lo); 267 } 268 } 269 270 return; 271 } 272 273 void 274 test_SplitYearDays1(void) 275 { 276 int32 eyd; 277 278 for (eyd = -1; eyd <= 365; eyd++) { 279 ntpcal_split split = ntpcal_split_yeardays(eyd, 0); 280 if (split.lo >= 0 && split.hi >= 0) { 281 TEST_ASSERT_TRUE(isGT(12,split.hi)); 282 TEST_ASSERT_TRUE(isGT(real_month_days[0][split.hi+1], split.lo)); 283 int32 tyd = real_month_table[0][split.hi] + split.lo; 284 TEST_ASSERT_EQUAL(eyd, tyd); 285 } else 286 TEST_ASSERT_TRUE(eyd < 0 || eyd > 364); 287 } 288 289 return; 290 } 291 292 void 293 test_SplitYearDays2(void) 294 { 295 int32 eyd; 296 297 for (eyd = -1; eyd <= 366; eyd++) { 298 ntpcal_split split = ntpcal_split_yeardays(eyd, 1); 299 if (split.lo >= 0 && split.hi >= 0) { 300 /* basic checks do not work on compunds :( */ 301 /* would like: TEST_ASSERT_TRUE(12 > split.hi); */ 302 TEST_ASSERT_TRUE(isGT(12,split.hi)); 303 TEST_ASSERT_TRUE(isGT(real_month_days[1][split.hi+1], split.lo)); 304 int32 tyd = real_month_table[1][split.hi] + split.lo; 305 TEST_ASSERT_EQUAL(eyd, tyd); 306 } else 307 TEST_ASSERT_TRUE(eyd < 0 || eyd > 365); 308 } 309 310 return; 311 } 312 313 void 314 test_RataDie1(void) 315 { 316 int32 testDate = 1; /* 0001-01-01 (proleptic date) */ 317 struct calendar expected = { 1, 1, 1, 1 }; 318 struct calendar actual; 319 320 ntpcal_rd_to_date(&actual, testDate); 321 TEST_ASSERT_TRUE(IsEqualDateCal(&expected, &actual)); 322 323 return; 324 } 325 326 /* check last day of february for first 10000 years */ 327 void 328 test_LeapYears1(void) 329 { 330 struct calendar dateIn, dateOut; 331 332 for (dateIn.year = 1; dateIn.year < 10000; ++dateIn.year) { 333 dateIn.month = 2; 334 dateIn.monthday = 28 + leapdays(dateIn.year); 335 dateIn.yearday = 31 + dateIn.monthday; 336 337 ntpcal_rd_to_date(&dateOut, ntpcal_date_to_rd(&dateIn)); 338 339 TEST_ASSERT_TRUE(IsEqualDateCal(&dateIn, &dateOut)); 340 } 341 342 return; 343 } 344 345 /* check first day of march for first 10000 years */ 346 void 347 test_LeapYears2(void) 348 { 349 struct calendar dateIn, dateOut; 350 351 for (dateIn.year = 1; dateIn.year < 10000; ++dateIn.year) { 352 dateIn.month = 3; 353 dateIn.monthday = 1; 354 dateIn.yearday = 60 + leapdays(dateIn.year); 355 356 ntpcal_rd_to_date(&dateOut, ntpcal_date_to_rd(&dateIn)); 357 TEST_ASSERT_TRUE(IsEqualDateCal(&dateIn, &dateOut)); 358 } 359 360 return; 361 } 362 363 /* Full roundtrip from 1601-01-01 to 2400-12-31 364 * checks sequence of rata die numbers and validates date output 365 * (since the input is all nominal days of the calendar in that range 366 * and the result of the inverse calculation must match the input no 367 * invalid output can occur.) 368 */ 369 void 370 test_RoundTripDate(void) 371 { 372 struct calendar truDate, expDate = { 1600, 0, 12, 31 };; 373 int leaps; 374 int32 truRdn, expRdn = ntpcal_date_to_rd(&expDate); 375 376 while (expDate.year < 2400) { 377 expDate.year++; 378 expDate.month = 0; 379 expDate.yearday = 0; 380 leaps = leapdays(expDate.year); 381 while (expDate.month < 12) { 382 expDate.month++; 383 expDate.monthday = 0; 384 while (expDate.monthday < real_month_days[leaps][expDate.month]) { 385 expDate.monthday++; 386 expDate.yearday++; 387 expRdn++; 388 389 truRdn = ntpcal_date_to_rd(&expDate); 390 TEST_ASSERT_EQUAL(expRdn, truRdn); 391 392 ntpcal_rd_to_date(&truDate, truRdn); 393 TEST_ASSERT_TRUE(IsEqualDateCal(&expDate, &truDate)); 394 } 395 } 396 } 397 398 return; 399 } 400 401 /* Roundtrip testing on calyearstart */ 402 void 403 test_RoundTripYearStart(void) 404 { 405 static const time_t pivot = 0; 406 u_int32 ntp, expys, truys; 407 struct calendar date; 408 409 for (ntp = 0; ntp < 0xFFFFFFFFu - 30000000u; ntp += 30000000u) { 410 truys = calyearstart(ntp, &pivot); 411 ntpcal_ntp_to_date(&date, ntp, &pivot); 412 date.month = date.monthday = 1; 413 date.hour = date.minute = date.second = 0; 414 expys = ntpcal_date_to_ntp(&date); 415 TEST_ASSERT_EQUAL(expys, truys); 416 } 417 418 return; 419 } 420 421 /* Roundtrip testing on calmonthstart */ 422 void 423 test_RoundTripMonthStart(void) 424 { 425 static const time_t pivot = 0; 426 u_int32 ntp, expms, trums; 427 struct calendar date; 428 429 for (ntp = 0; ntp < 0xFFFFFFFFu - 2000000u; ntp += 2000000u) { 430 trums = calmonthstart(ntp, &pivot); 431 ntpcal_ntp_to_date(&date, ntp, &pivot); 432 date.monthday = 1; 433 date.hour = date.minute = date.second = 0; 434 expms = ntpcal_date_to_ntp(&date); 435 TEST_ASSERT_EQUAL(expms, trums); 436 } 437 438 return; 439 } 440 441 /* Roundtrip testing on calweekstart */ 442 void 443 test_RoundTripWeekStart(void) 444 { 445 static const time_t pivot = 0; 446 u_int32 ntp, expws, truws; 447 struct isodate date; 448 449 for (ntp = 0; ntp < 0xFFFFFFFFu - 600000u; ntp += 600000u) { 450 truws = calweekstart(ntp, &pivot); 451 isocal_ntp_to_date(&date, ntp, &pivot); 452 date.hour = date.minute = date.second = 0; 453 date.weekday = 1; 454 expws = isocal_date_to_ntp(&date); 455 TEST_ASSERT_EQUAL(expws, truws); 456 } 457 458 return; 459 } 460 461 /* Roundtrip testing on caldaystart */ 462 void 463 test_RoundTripDayStart(void) 464 { 465 static const time_t pivot = 0; 466 u_int32 ntp, expds, truds; 467 struct calendar date; 468 469 for (ntp = 0; ntp < 0xFFFFFFFFu - 80000u; ntp += 80000u) { 470 truds = caldaystart(ntp, &pivot); 471 ntpcal_ntp_to_date(&date, ntp, &pivot); 472 date.hour = date.minute = date.second = 0; 473 expds = ntpcal_date_to_ntp(&date); 474 TEST_ASSERT_EQUAL(expds, truds); 475 } 476 477 return; 478 } 479 480 /* --------------------------------------------------------------------- 481 * ISO8601 week calendar internals 482 * 483 * The ISO8601 week calendar implementation is simple in the terms of 484 * the math involved, but the implementation of the calculations must 485 * take care of a few things like overflow, floor division, and sign 486 * corrections. 487 * 488 * Most of the functions are straight forward, but converting from years 489 * to weeks and from weeks to years warrants some extra tests. These use 490 * an independent reference implementation of the conversion from years 491 * to weeks. 492 * --------------------------------------------------------------------- 493 */ 494 495 /* helper / reference implementation for the first week of year in the 496 * ISO8601 week calendar. This is based on the reference definition of 497 * the ISO week calendar start: The Monday closest to January,1st of the 498 * corresponding year in the Gregorian calendar. 499 */ 500 static int32_t 501 refimpl_WeeksInIsoYears( 502 int32_t years) 503 { 504 int32_t days, weeks; 505 506 days = ntpcal_weekday_close( 507 ntpcal_days_in_years(years) + 1, 508 CAL_MONDAY) - 1; 509 /* the weekday functions operate on RDN, while we want elapsed 510 * units here -- we have to add / sub 1 in the midlle / at the 511 * end of the operation that gets us the first day of the ISO 512 * week calendar day. 513 */ 514 weeks = days / 7; 515 days = days % 7; 516 TEST_ASSERT_EQUAL(0, days); /* paranoia check... */ 517 518 return weeks; 519 } 520 521 /* The next tests loop over 5000yrs, but should still be very fast. If 522 * they are not, the calendar needs a better implementation... 523 */ 524 void 525 test_IsoCalYearsToWeeks(void) 526 { 527 int32_t years; 528 int32_t wref, wcal; 529 530 for (years = -1000; years < 4000; ++years) { 531 /* get number of weeks before years (reference) */ 532 wref = refimpl_WeeksInIsoYears(years); 533 /* get number of weeks before years (object-under-test) */ 534 wcal = isocal_weeks_in_years(years); 535 TEST_ASSERT_EQUAL(wref, wcal); 536 } 537 538 return; 539 } 540 541 void 542 test_IsoCalWeeksToYearStart(void) 543 { 544 int32_t years; 545 int32_t wref; 546 ntpcal_split ysplit; 547 548 for (years = -1000; years < 4000; ++years) { 549 /* get number of weeks before years (reference) */ 550 wref = refimpl_WeeksInIsoYears(years); 551 /* reverse split */ 552 ysplit = isocal_split_eraweeks(wref); 553 /* check invariants: same year, week 0 */ 554 TEST_ASSERT_EQUAL(years, ysplit.hi); 555 TEST_ASSERT_EQUAL(0, ysplit.lo); 556 } 557 558 return; 559 } 560 561 void 562 test_IsoCalWeeksToYearEnd(void) 563 { 564 int32_t years; 565 int32_t wref; 566 ntpcal_split ysplit; 567 568 for (years = -1000; years < 4000; ++years) { 569 /* get last week of previous year */ 570 wref = refimpl_WeeksInIsoYears(years) - 1; 571 /* reverse split */ 572 ysplit = isocal_split_eraweeks(wref); 573 /* check invariants: previous year, week 51 or 52 */ 574 TEST_ASSERT_EQUAL(years-1, ysplit.hi); 575 TEST_ASSERT(ysplit.lo == 51 || ysplit.lo == 52); 576 } 577 578 return; 579 } 580 581 void 582 test_DaySecToDate(void) 583 { 584 struct calendar cal; 585 int32_t days; 586 587 days = ntpcal_daysec_to_date(&cal, -86400); 588 TEST_ASSERT_MESSAGE((days==-1 && cal.hour==0 && cal.minute==0 && cal.second==0), 589 "failed for -86400"); 590 591 days = ntpcal_daysec_to_date(&cal, -86399); 592 TEST_ASSERT_MESSAGE((days==-1 && cal.hour==0 && cal.minute==0 && cal.second==1), 593 "failed for -86399"); 594 595 days = ntpcal_daysec_to_date(&cal, -1); 596 TEST_ASSERT_MESSAGE((days==-1 && cal.hour==23 && cal.minute==59 && cal.second==59), 597 "failed for -1"); 598 599 days = ntpcal_daysec_to_date(&cal, 0); 600 TEST_ASSERT_MESSAGE((days==0 && cal.hour==0 && cal.minute==0 && cal.second==0), 601 "failed for 0"); 602 603 days = ntpcal_daysec_to_date(&cal, 1); 604 TEST_ASSERT_MESSAGE((days==0 && cal.hour==0 && cal.minute==0 && cal.second==1), 605 "failed for 1"); 606 607 days = ntpcal_daysec_to_date(&cal, 86399); 608 TEST_ASSERT_MESSAGE((days==0 && cal.hour==23 && cal.minute==59 && cal.second==59), 609 "failed for 86399"); 610 611 days = ntpcal_daysec_to_date(&cal, 86400); 612 TEST_ASSERT_MESSAGE((days==1 && cal.hour==0 && cal.minute==0 && cal.second==0), 613 "failed for 86400"); 614 615 return; 616 } 617 618 /* -------------------------------------------------------------------- 619 * unfolding of (truncated) NTP time stamps to full 64bit values. 620 * 621 * Note: These tests need a 64bit time_t to be useful. 622 */ 623 624 void 625 test_NtpToNtp(void) 626 { 627 # if SIZEOF_TIME_T <= 4 628 629 TEST_IGNORE_MESSAGE("test only useful for sizeof(time_t) > 4, skipped"); 630 631 # else 632 633 static const uint32_t ntp_vals[6] = { 634 UINT32_C(0x00000000), 635 UINT32_C(0x00000001), 636 UINT32_C(0x7FFFFFFF), 637 UINT32_C(0x80000000), 638 UINT32_C(0x80000001), 639 UINT32_C(0xFFFFFFFF) 640 }; 641 642 static char lbuf[128]; 643 vint64 hold; 644 time_t pivot, texp, diff; 645 int loops, iloop; 646 647 pivot = 0; 648 for (loops = 0; loops < 16; ++loops) { 649 for (iloop = 0; iloop < 6; ++iloop) { 650 hold = ntpcal_ntp_to_ntp( 651 ntp_vals[iloop], &pivot); 652 texp = vint64_to_time(&hold); 653 654 /* constraint 1: texp must be in the 655 * (right-open) intervall [p-(2^31), p+(2^31)[, 656 * but the pivot 'p' must be taken in full NTP 657 * time scale! 658 */ 659 diff = texp - (pivot + JAN_1970); 660 snprintf(lbuf, sizeof(lbuf), 661 "bounds check: piv=%lld exp=%lld dif=%lld", 662 (long long)pivot, 663 (long long)texp, 664 (long long)diff); 665 TEST_ASSERT_MESSAGE((diff >= INT32_MIN) && (diff <= INT32_MAX), 666 lbuf); 667 668 /* constraint 2: low word must be equal to 669 * input 670 */ 671 snprintf(lbuf, sizeof(lbuf), 672 "low check: ntp(in)=$%08lu ntp(out[0:31])=$%08lu", 673 (unsigned long)ntp_vals[iloop], 674 (unsigned long)hold.D_s.lo); 675 TEST_ASSERT_EQUAL_MESSAGE(ntp_vals[iloop], hold.D_s.lo, lbuf); 676 } 677 pivot += 0x20000000; 678 } 679 # endif 680 } 681 682 void 683 test_NtpToTime(void) 684 { 685 # if SIZEOF_TIME_T <= 4 686 687 TEST_IGNORE_MESSAGE("test only useful for sizeof(time_t) > 4, skipped"); 688 689 # else 690 691 static const uint32_t ntp_vals[6] = { 692 UINT32_C(0x00000000), 693 UINT32_C(0x00000001), 694 UINT32_C(0x7FFFFFFF), 695 UINT32_C(0x80000000), 696 UINT32_C(0x80000001), 697 UINT32_C(0xFFFFFFFF) 698 }; 699 700 static char lbuf[128]; 701 vint64 hold; 702 time_t pivot, texp, diff; 703 uint32_t back; 704 int loops, iloop; 705 706 pivot = 0; 707 for (loops = 0; loops < 16; ++loops) { 708 for (iloop = 0; iloop < 6; ++iloop) { 709 hold = ntpcal_ntp_to_time( 710 ntp_vals[iloop], &pivot); 711 texp = vint64_to_time(&hold); 712 713 /* constraint 1: texp must be in the 714 * (right-open) intervall [p-(2^31), p+(2^31)[ 715 */ 716 diff = texp - pivot; 717 snprintf(lbuf, sizeof(lbuf), 718 "bounds check: piv=%lld exp=%lld dif=%lld", 719 (long long)pivot, 720 (long long)texp, 721 (long long)diff); 722 TEST_ASSERT_MESSAGE((diff >= INT32_MIN) && (diff <= INT32_MAX), 723 lbuf); 724 725 /* constraint 2: conversion from full time back 726 * to truncated NTP time must yield same result 727 * as input. 728 */ 729 back = (uint32_t)texp + JAN_1970; 730 snprintf(lbuf, sizeof(lbuf), 731 "modulo check: ntp(in)=$%08lu ntp(out)=$%08lu", 732 (unsigned long)ntp_vals[iloop], 733 (unsigned long)back); 734 TEST_ASSERT_EQUAL_MESSAGE(ntp_vals[iloop], back, lbuf); 735 } 736 pivot += 0x20000000; 737 } 738 # endif 739 } 740