Home | History | Annotate | Line # | Download | only in libntp
timespecops.c revision 1.1.1.4
      1      1.1  christos #include "config.h"
      2      1.1  christos 
      3      1.1  christos #include "ntp_types.h"
      4      1.1  christos #include "ntp_fp.h"
      5      1.1  christos #include "timespecops.h"
      6      1.1  christos 
      7      1.1  christos #include "unity.h"
      8      1.1  christos 
      9  1.1.1.3  christos #include <math.h>
     10      1.1  christos #include <string.h>
     11      1.1  christos 
     12  1.1.1.3  christos 
     13  1.1.1.4  christos #define TEST_ASSERT_EQUAL_timespec(a, b) {				\
     14  1.1.1.4  christos     TEST_ASSERT_EQUAL_MESSAGE(a.tv_sec, b.tv_sec, "Field tv_sec");	\
     15      1.1  christos     TEST_ASSERT_EQUAL_MESSAGE(a.tv_nsec, b.tv_nsec, "Field tv_nsec");	\
     16      1.1  christos }
     17      1.1  christos 
     18  1.1.1.3  christos 
     19  1.1.1.4  christos #define TEST_ASSERT_EQUAL_l_fp(a, b) {					\
     20  1.1.1.4  christos     TEST_ASSERT_EQUAL_MESSAGE(a.l_i, b.l_i, "Field l_i");		\
     21      1.1  christos     TEST_ASSERT_EQUAL_UINT_MESSAGE(a.l_uf, b.l_uf, "Field l_uf");	\
     22      1.1  christos }
     23      1.1  christos 
     24      1.1  christos 
     25      1.1  christos static u_int32 my_tick_to_tsf(u_int32 ticks);
     26      1.1  christos static u_int32 my_tsf_to_tick(u_int32 tsf);
     27      1.1  christos 
     28  1.1.1.3  christos 
     29      1.1  christos // that's it...
     30      1.1  christos struct lfpfracdata {
     31      1.1  christos 	long	nsec;
     32      1.1  christos 	u_int32 frac;
     33      1.1  christos };
     34      1.1  christos 
     35  1.1.1.3  christos 
     36  1.1.1.4  christos void setUp(void);
     37  1.1.1.3  christos void test_Helpers1(void);
     38  1.1.1.3  christos void test_Normalise(void);
     39  1.1.1.3  christos void test_SignNoFrac(void);
     40  1.1.1.3  christos void test_SignWithFrac(void);
     41  1.1.1.3  christos void test_CmpFracEQ(void);
     42  1.1.1.3  christos void test_CmpFracGT(void);
     43  1.1.1.3  christos void test_CmpFracLT(void);
     44  1.1.1.3  christos void test_AddFullNorm(void);
     45  1.1.1.3  christos void test_AddFullOflow1(void);
     46  1.1.1.3  christos void test_AddNsecNorm(void);
     47  1.1.1.3  christos void test_AddNsecOflow1(void);
     48  1.1.1.3  christos void test_SubFullNorm(void);
     49  1.1.1.3  christos void test_SubFullOflow(void);
     50  1.1.1.3  christos void test_SubNsecNorm(void);
     51  1.1.1.3  christos void test_SubNsecOflow(void);
     52  1.1.1.3  christos void test_Neg(void);
     53  1.1.1.3  christos void test_AbsNoFrac(void);
     54  1.1.1.3  christos void test_AbsWithFrac(void);
     55  1.1.1.3  christos void test_Helpers2(void);
     56  1.1.1.3  christos void test_ToLFPbittest(void);
     57  1.1.1.3  christos void test_ToLFPrelPos(void);
     58  1.1.1.3  christos void test_ToLFPrelNeg(void);
     59  1.1.1.3  christos void test_ToLFPabs(void);
     60  1.1.1.3  christos void test_FromLFPbittest(void);
     61  1.1.1.3  christos void test_FromLFPrelPos(void);
     62  1.1.1.3  christos void test_FromLFPrelNeg(void);
     63  1.1.1.3  christos void test_LFProundtrip(void);
     64  1.1.1.3  christos void test_ToString(void);
     65  1.1.1.3  christos 
     66  1.1.1.3  christos typedef int bool;
     67  1.1.1.3  christos 
     68  1.1.1.4  christos const bool	timespec_isValid(struct timespec V);
     69  1.1.1.3  christos struct timespec timespec_init(time_t hi, long lo);
     70  1.1.1.4  christos l_fp		l_fp_init(int32 i, u_int32 f);
     71  1.1.1.4  christos bool		AssertFpClose(const l_fp m, const l_fp n, const l_fp limit);
     72  1.1.1.4  christos bool		AssertTimespecClose(const struct timespec m,
     73  1.1.1.4  christos 				    const struct timespec n,
     74  1.1.1.4  christos 				    const struct timespec limit);
     75  1.1.1.4  christos 
     76  1.1.1.3  christos 
     77  1.1.1.4  christos //***************************MY CUSTOM FUNCTIONS***************************
     78  1.1.1.3  christos 
     79      1.1  christos 
     80  1.1.1.4  christos void
     81  1.1.1.4  christos setUp(void)
     82  1.1.1.4  christos {
     83  1.1.1.4  christos 	init_lib();
     84  1.1.1.4  christos 
     85  1.1.1.4  christos 	return;
     86  1.1.1.4  christos }
     87      1.1  christos 
     88      1.1  christos 
     89  1.1.1.3  christos const bool
     90  1.1.1.4  christos timespec_isValid(struct timespec V)
     91  1.1.1.4  christos {
     92  1.1.1.4  christos 
     93  1.1.1.3  christos 	return V.tv_nsec >= 0 && V.tv_nsec < 1000000000;
     94  1.1.1.3  christos }
     95  1.1.1.3  christos 
     96  1.1.1.3  christos 
     97  1.1.1.3  christos struct timespec
     98  1.1.1.4  christos timespec_init(time_t hi, long lo)
     99  1.1.1.4  christos {
    100  1.1.1.4  christos 	struct timespec V;
    101  1.1.1.4  christos 
    102      1.1  christos 	V.tv_sec = hi;
    103      1.1  christos 	V.tv_nsec = lo;
    104  1.1.1.4  christos 
    105      1.1  christos 	return V;
    106      1.1  christos }
    107      1.1  christos 
    108  1.1.1.3  christos 
    109  1.1.1.3  christos l_fp
    110  1.1.1.4  christos l_fp_init(int32 i, u_int32 f)
    111  1.1.1.4  christos {
    112      1.1  christos 	l_fp temp;
    113  1.1.1.4  christos 
    114      1.1  christos 	temp.l_i  = i;
    115      1.1  christos 	temp.l_uf = f;
    116      1.1  christos 
    117      1.1  christos 	return temp;
    118      1.1  christos }
    119      1.1  christos 
    120  1.1.1.3  christos 
    121  1.1.1.3  christos bool
    122  1.1.1.4  christos AssertFpClose(const l_fp m, const l_fp n, const l_fp limit)
    123  1.1.1.4  christos {
    124      1.1  christos 	l_fp diff;
    125      1.1  christos 
    126      1.1  christos 	if (L_ISGEQ(&m, &n)) {
    127      1.1  christos 		diff = m;
    128      1.1  christos 		L_SUB(&diff, &n);
    129      1.1  christos 	} else {
    130      1.1  christos 		diff = n;
    131      1.1  christos 		L_SUB(&diff, &m);
    132      1.1  christos 	}
    133  1.1.1.4  christos 	if (L_ISGEQ(&limit, &diff)) {
    134      1.1  christos 		return TRUE;
    135      1.1  christos 	}
    136      1.1  christos 	else {
    137  1.1.1.3  christos 		printf("m_expr which is %s \nand\nn_expr which is %s\nare not close; diff=%susec\n", lfptoa(&m, 10), lfptoa(&n, 10), lfptoa(&diff, 10));
    138      1.1  christos 		return FALSE;
    139      1.1  christos 	}
    140      1.1  christos }
    141      1.1  christos 
    142      1.1  christos 
    143  1.1.1.3  christos bool
    144  1.1.1.4  christos AssertTimespecClose(const struct timespec m, const struct timespec n,
    145  1.1.1.4  christos 	const struct timespec limit)
    146  1.1.1.4  christos {
    147      1.1  christos 	struct timespec diff;
    148      1.1  christos 
    149      1.1  christos 	diff = abs_tspec(sub_tspec(m, n));
    150      1.1  christos 	if (cmp_tspec(limit, diff) >= 0)
    151      1.1  christos 		return TRUE;
    152      1.1  christos 	else
    153      1.1  christos 	{
    154  1.1.1.3  christos 		printf("m_expr which is %ld.%lu \nand\nn_expr which is %ld.%lu\nare not close; diff=%ld.%lunsec\n", m.tv_sec, m.tv_nsec, n.tv_sec, n.tv_nsec, diff.tv_sec, diff.tv_nsec);
    155      1.1  christos 		return FALSE;
    156      1.1  christos 	}
    157      1.1  christos }
    158      1.1  christos 
    159      1.1  christos //-----------------------------------------------
    160      1.1  christos 
    161      1.1  christos static const struct lfpfracdata fdata[] = {
    162      1.1  christos 	{	  0, 0x00000000 }, {   2218896, 0x00916ae6 },
    163      1.1  christos 	{  16408100, 0x0433523d }, { 125000000, 0x20000000 },
    164      1.1  christos 	{ 250000000, 0x40000000 }, { 287455871, 0x4996b53d },
    165      1.1  christos 	{ 375000000, 0x60000000 }, { 500000000, 0x80000000 },
    166      1.1  christos 	{ 518978897, 0x84dbcd0e }, { 563730222, 0x90509fb3 },
    167      1.1  christos 	{ 563788007, 0x9054692c }, { 583289882, 0x95527c57 },
    168      1.1  christos 	{ 607074509, 0x9b693c2a }, { 625000000, 0xa0000000 },
    169      1.1  christos 	{ 645184059, 0xa52ac851 }, { 676497788, 0xad2ef583 },
    170      1.1  christos 	{ 678910895, 0xadcd1abb }, { 679569625, 0xadf84663 },
    171      1.1  christos 	{ 690926741, 0xb0e0932d }, { 705656483, 0xb4a5e73d },
    172      1.1  christos 	{ 723553854, 0xb93ad34c }, { 750000000, 0xc0000000 },
    173      1.1  christos 	{ 763550253, 0xc3780785 }, { 775284917, 0xc6791284 },
    174      1.1  christos 	{ 826190764, 0xd3813ce8 }, { 875000000, 0xe0000000 },
    175      1.1  christos 	{ 956805507, 0xf4f134a9 }, { 982570733, 0xfb89c16c }
    176      1.1  christos 	};
    177      1.1  christos 
    178      1.1  christos 
    179  1.1.1.3  christos u_int32
    180  1.1.1.4  christos my_tick_to_tsf(u_int32 ticks)
    181  1.1.1.4  christos {
    182      1.1  christos 	// convert nanoseconds to l_fp fractional units, using double
    183      1.1  christos 	// precision float calculations or, if available, 64bit integer
    184      1.1  christos 	// arithmetic. This should give the precise fraction, rounded to
    185      1.1  christos 	// the nearest representation.
    186  1.1.1.4  christos 
    187      1.1  christos #ifdef HAVE_U_INT64
    188      1.1  christos 	return (u_int32)((( ((u_int64)(ticks)) << 32) + 500000000) / 1000000000);
    189      1.1  christos #else
    190      1.1  christos 	return (u_int32)((double(ticks)) * 4.294967296 + 0.5);
    191      1.1  christos #endif
    192      1.1  christos 	// And before you ask: if ticks >= 1000000000, the result is
    193      1.1  christos 	// truncated nonsense, so don't use it out-of-bounds.
    194      1.1  christos }
    195      1.1  christos 
    196  1.1.1.3  christos 
    197  1.1.1.3  christos u_int32
    198  1.1.1.4  christos my_tsf_to_tick(u_int32 tsf)
    199  1.1.1.4  christos {
    200  1.1.1.4  christos 
    201      1.1  christos 	// Inverse operation: converts fraction to microseconds.
    202      1.1  christos #ifdef HAVE_U_INT64
    203      1.1  christos 	return (u_int32)(( ((u_int64)(tsf)) * 1000000000 + 0x80000000) >> 32);
    204      1.1  christos #else
    205      1.1  christos 	return (u_int32)(double(tsf) / 4.294967296 + 0.5);
    206      1.1  christos #endif
    207      1.1  christos 	// Beware: The result might be 10^9 due to rounding!
    208      1.1  christos }
    209      1.1  christos 
    210      1.1  christos 
    211      1.1  christos 
    212      1.1  christos // ---------------------------------------------------------------------
    213      1.1  christos // test support stuff -- part 1
    214      1.1  christos // ---------------------------------------------------------------------
    215      1.1  christos 
    216  1.1.1.3  christos void
    217  1.1.1.4  christos test_Helpers1(void)
    218  1.1.1.4  christos {
    219      1.1  christos 	struct timespec x;
    220      1.1  christos 
    221      1.1  christos 	for (x.tv_sec = -2; x.tv_sec < 3; x.tv_sec++) {
    222      1.1  christos 		x.tv_nsec = -1;
    223      1.1  christos 		TEST_ASSERT_FALSE(timespec_isValid(x));
    224      1.1  christos 		x.tv_nsec = 0;
    225      1.1  christos 		TEST_ASSERT_TRUE(timespec_isValid(x));
    226      1.1  christos 		x.tv_nsec = 999999999;
    227      1.1  christos 		TEST_ASSERT_TRUE(timespec_isValid(x));
    228      1.1  christos 		x.tv_nsec = 1000000000;
    229      1.1  christos 		TEST_ASSERT_FALSE(timespec_isValid(x));
    230      1.1  christos 	}
    231  1.1.1.4  christos 
    232  1.1.1.4  christos 	return;
    233      1.1  christos }
    234      1.1  christos 
    235      1.1  christos 
    236      1.1  christos //----------------------------------------------------------------------
    237      1.1  christos // test normalisation
    238      1.1  christos //----------------------------------------------------------------------
    239      1.1  christos 
    240  1.1.1.3  christos void
    241  1.1.1.4  christos test_Normalise(void)
    242  1.1.1.4  christos {
    243      1.1  christos 	long ns;
    244  1.1.1.4  christos 
    245      1.1  christos 	for ( ns = -2000000000; ns <= 2000000000; ns += 10000000) {
    246      1.1  christos 		struct timespec x = timespec_init(0, ns);
    247      1.1  christos 
    248      1.1  christos 		x = normalize_tspec(x);
    249      1.1  christos 		TEST_ASSERT_TRUE(timespec_isValid(x));
    250      1.1  christos 	}
    251  1.1.1.4  christos 
    252  1.1.1.4  christos 	return;
    253      1.1  christos }
    254      1.1  christos 
    255      1.1  christos //----------------------------------------------------------------------
    256      1.1  christos // test classification
    257      1.1  christos //----------------------------------------------------------------------
    258      1.1  christos 
    259  1.1.1.3  christos void
    260  1.1.1.4  christos test_SignNoFrac(void)
    261  1.1.1.4  christos {
    262      1.1  christos 	// sign test, no fraction
    263      1.1  christos 	int i;
    264  1.1.1.4  christos 
    265      1.1  christos 	for (i = -4; i <= 4; ++i) {
    266      1.1  christos 		struct timespec a = timespec_init(i, 0);
    267      1.1  christos 		int E = (i > 0) - (i < 0);
    268      1.1  christos 		int r = test_tspec(a);
    269      1.1  christos 
    270      1.1  christos 		TEST_ASSERT_EQUAL(E, r);
    271      1.1  christos 	}
    272  1.1.1.4  christos 
    273  1.1.1.4  christos 	return;
    274      1.1  christos }
    275      1.1  christos 
    276  1.1.1.3  christos 
    277  1.1.1.3  christos void
    278  1.1.1.4  christos test_SignWithFrac(void)
    279  1.1.1.4  christos {
    280      1.1  christos 	// sign test, with fraction
    281      1.1  christos 	int i;
    282  1.1.1.4  christos 
    283      1.1  christos 	for (i = -4; i <= 4; ++i) {
    284      1.1  christos 		struct timespec a = timespec_init(i, 10);
    285      1.1  christos 		int E = (i >= 0) - (i < 0);
    286      1.1  christos 		int r = test_tspec(a);
    287  1.1.1.4  christos 
    288      1.1  christos 		TEST_ASSERT_EQUAL(E, r);
    289      1.1  christos 	}
    290  1.1.1.4  christos 
    291  1.1.1.4  christos 	return;
    292      1.1  christos }
    293      1.1  christos 
    294      1.1  christos //----------------------------------------------------------------------
    295      1.1  christos // test compare
    296      1.1  christos //----------------------------------------------------------------------
    297  1.1.1.3  christos void
    298  1.1.1.4  christos test_CmpFracEQ(void)
    299  1.1.1.4  christos {
    300      1.1  christos 	// fractions are equal
    301  1.1.1.3  christos 	int i, j;
    302      1.1  christos 	for (i = -4; i <= 4; ++i)
    303      1.1  christos 		for (j = -4; j <= 4; ++j) {
    304      1.1  christos 			struct timespec a = timespec_init( i , 200);
    305      1.1  christos 			struct timespec b = timespec_init( j , 200);
    306      1.1  christos 			int   E = (i > j) - (i < j);
    307      1.1  christos 			int   r = cmp_tspec_denorm(a, b);
    308  1.1.1.4  christos 
    309      1.1  christos 			TEST_ASSERT_EQUAL(E, r);
    310      1.1  christos 		}
    311  1.1.1.4  christos 
    312  1.1.1.4  christos 	return;
    313      1.1  christos }
    314      1.1  christos 
    315  1.1.1.3  christos 
    316  1.1.1.3  christos void
    317  1.1.1.4  christos test_CmpFracGT(void)
    318  1.1.1.4  christos {
    319      1.1  christos 	// fraction a bigger fraction b
    320  1.1.1.3  christos 	int i, j;
    321  1.1.1.4  christos 
    322      1.1  christos 	for (i = -4; i <= 4; ++i)
    323      1.1  christos 		for (j = -4; j <= 4; ++j) {
    324      1.1  christos 			struct timespec a = timespec_init(i, 999999800);
    325      1.1  christos 			struct timespec b = timespec_init(j, 200);
    326      1.1  christos 			int   E = (i >= j) - (i < j);
    327      1.1  christos 			int   r = cmp_tspec_denorm(a, b);
    328  1.1.1.4  christos 
    329      1.1  christos 			TEST_ASSERT_EQUAL(E, r);
    330      1.1  christos 		}
    331  1.1.1.4  christos 
    332  1.1.1.4  christos 	return;
    333      1.1  christos }
    334      1.1  christos 
    335  1.1.1.3  christos 
    336  1.1.1.3  christos void
    337  1.1.1.4  christos test_CmpFracLT(void)
    338  1.1.1.4  christos {
    339      1.1  christos 	// fraction a less fraction b
    340  1.1.1.3  christos 	int i, j;
    341  1.1.1.4  christos 
    342      1.1  christos 	for (i = -4; i <= 4; ++i)
    343      1.1  christos 		for (j = -4; j <= 4; ++j) {
    344      1.1  christos 			struct timespec a = timespec_init(i, 200);
    345      1.1  christos 			struct timespec b = timespec_init(j, 999999800);
    346      1.1  christos 			int   E = (i > j) - (i <= j);
    347      1.1  christos 			int   r = cmp_tspec_denorm(a, b);
    348  1.1.1.4  christos 
    349      1.1  christos 			TEST_ASSERT_EQUAL(E, r);
    350      1.1  christos 		}
    351  1.1.1.4  christos 
    352  1.1.1.4  christos 	return;
    353      1.1  christos }
    354      1.1  christos 
    355      1.1  christos //----------------------------------------------------------------------
    356      1.1  christos // Test addition (sum)
    357      1.1  christos //----------------------------------------------------------------------
    358      1.1  christos 
    359  1.1.1.3  christos void
    360  1.1.1.4  christos test_AddFullNorm(void)
    361  1.1.1.4  christos {
    362  1.1.1.3  christos 	int i, j;
    363  1.1.1.4  christos 
    364      1.1  christos 	for (i = -4; i <= 4; ++i)
    365      1.1  christos 		for (j = -4; j <= 4; ++j) {
    366      1.1  christos 			struct timespec a = timespec_init(i, 200);
    367      1.1  christos 			struct timespec b = timespec_init(j, 400);
    368      1.1  christos 			struct timespec E = timespec_init(i + j, 200 + 400);
    369      1.1  christos 			struct timespec c;
    370      1.1  christos 
    371      1.1  christos 			c = add_tspec(a, b);
    372      1.1  christos 			TEST_ASSERT_EQUAL_timespec(E, c);
    373      1.1  christos 		}
    374  1.1.1.4  christos 
    375  1.1.1.4  christos 	return;
    376      1.1  christos }
    377      1.1  christos 
    378  1.1.1.3  christos 
    379  1.1.1.3  christos void
    380  1.1.1.4  christos test_AddFullOflow1(void)
    381  1.1.1.4  christos {
    382  1.1.1.3  christos 	int i, j;
    383  1.1.1.4  christos 
    384      1.1  christos 	for (i = -4; i <= 4; ++i)
    385      1.1  christos 		for (j = -4; j <= 4; ++j) {
    386      1.1  christos 			struct timespec a = timespec_init(i, 200);
    387      1.1  christos 			struct timespec b = timespec_init(j, 999999900);
    388      1.1  christos 			struct timespec E = timespec_init(i + j + 1, 100);
    389      1.1  christos 			struct timespec c;
    390      1.1  christos 
    391      1.1  christos 			c = add_tspec(a, b);
    392      1.1  christos 			TEST_ASSERT_EQUAL_timespec(E, c);
    393      1.1  christos 		}
    394  1.1.1.4  christos 
    395  1.1.1.4  christos 	return;
    396      1.1  christos }
    397      1.1  christos 
    398  1.1.1.3  christos 
    399  1.1.1.3  christos void
    400  1.1.1.3  christos test_AddNsecNorm(void) {
    401      1.1  christos 	int i;
    402  1.1.1.4  christos 
    403      1.1  christos 	for (i = -4; i <= 4; ++i) {
    404      1.1  christos 		struct timespec a = timespec_init(i, 200);
    405      1.1  christos 		struct timespec E = timespec_init(i, 600);
    406      1.1  christos 		struct timespec c;
    407      1.1  christos 
    408      1.1  christos 		c = add_tspec_ns(a, 600 - 200);
    409      1.1  christos 		TEST_ASSERT_EQUAL_timespec(E, c);
    410      1.1  christos 	}
    411  1.1.1.4  christos 
    412  1.1.1.4  christos 	return;
    413      1.1  christos }
    414      1.1  christos 
    415  1.1.1.3  christos 
    416  1.1.1.3  christos void
    417  1.1.1.4  christos test_AddNsecOflow1(void)
    418  1.1.1.4  christos {
    419      1.1  christos 	int i;
    420  1.1.1.4  christos 
    421      1.1  christos 	for (i = -4; i <= 4; ++i) {
    422      1.1  christos 		struct timespec a = timespec_init(i, 200);
    423      1.1  christos 		struct timespec E = timespec_init(i + 1, 100);
    424      1.1  christos 		struct timespec c;
    425      1.1  christos 
    426      1.1  christos 		c = add_tspec_ns(a, NANOSECONDS - 100);
    427      1.1  christos 		TEST_ASSERT_EQUAL_timespec(E, c);
    428      1.1  christos 	}
    429  1.1.1.4  christos 
    430  1.1.1.4  christos 	return;
    431      1.1  christos }
    432      1.1  christos 
    433      1.1  christos //----------------------------------------------------------------------
    434      1.1  christos // test subtraction (difference)
    435      1.1  christos //----------------------------------------------------------------------
    436      1.1  christos 
    437  1.1.1.3  christos void
    438  1.1.1.4  christos test_SubFullNorm(void)
    439  1.1.1.4  christos {
    440  1.1.1.3  christos 	int i, j;
    441  1.1.1.4  christos 
    442      1.1  christos 	for (i = -4; i <= 4; ++i)
    443      1.1  christos 		for (j = -4; j <= 4; ++j) {
    444      1.1  christos 			struct timespec a = timespec_init( i , 600);
    445      1.1  christos 			struct timespec b = timespec_init( j , 400);
    446      1.1  christos 			struct timespec E = timespec_init(i-j, 200);
    447      1.1  christos 			struct timespec c;
    448      1.1  christos 
    449      1.1  christos 			c = sub_tspec(a, b);
    450      1.1  christos 			TEST_ASSERT_EQUAL_timespec(E, c);
    451      1.1  christos 		}
    452  1.1.1.4  christos 
    453  1.1.1.4  christos 	return;
    454      1.1  christos }
    455      1.1  christos 
    456  1.1.1.3  christos 
    457  1.1.1.3  christos void
    458  1.1.1.4  christos test_SubFullOflow(void)
    459  1.1.1.4  christos {
    460  1.1.1.3  christos 	int i, j;
    461  1.1.1.4  christos 
    462      1.1  christos 	for (i = -4; i <= 4; ++i)
    463      1.1  christos 		for (j = -4; j <= 4; ++j) {
    464  1.1.1.3  christos 			struct timespec a = timespec_init(i, 100);
    465  1.1.1.3  christos 			struct timespec b = timespec_init(j, 999999900);
    466  1.1.1.3  christos 			struct timespec E = timespec_init(i - j - 1, 200);
    467      1.1  christos 			struct timespec c;
    468      1.1  christos 
    469      1.1  christos 			c = sub_tspec(a, b);
    470      1.1  christos 			TEST_ASSERT_EQUAL_timespec(E, c);
    471      1.1  christos 		}
    472  1.1.1.4  christos 
    473  1.1.1.4  christos 	return;
    474      1.1  christos }
    475      1.1  christos 
    476  1.1.1.3  christos 
    477  1.1.1.3  christos void
    478  1.1.1.4  christos test_SubNsecNorm(void)
    479  1.1.1.4  christos {
    480      1.1  christos 	int i;
    481  1.1.1.4  christos 
    482      1.1  christos 	for (i = -4; i <= 4; ++i) {
    483      1.1  christos 		struct timespec a = timespec_init(i, 600);
    484      1.1  christos 		struct timespec E = timespec_init(i, 200);
    485      1.1  christos 		struct timespec c;
    486      1.1  christos 
    487      1.1  christos 		c = sub_tspec_ns(a, 600 - 200);
    488      1.1  christos 		TEST_ASSERT_EQUAL_timespec(E, c);
    489      1.1  christos 	}
    490  1.1.1.4  christos 
    491  1.1.1.4  christos 	return;
    492      1.1  christos }
    493      1.1  christos 
    494  1.1.1.3  christos 
    495  1.1.1.3  christos void
    496  1.1.1.4  christos test_SubNsecOflow(void)
    497  1.1.1.4  christos {
    498      1.1  christos 	int i;
    499  1.1.1.4  christos 
    500      1.1  christos 	for (i = -4; i <= 4; ++i) {
    501      1.1  christos 		struct timespec a = timespec_init( i , 100);
    502      1.1  christos 		struct timespec E = timespec_init(i-1, 200);
    503      1.1  christos 		struct timespec c;
    504      1.1  christos 
    505      1.1  christos 		c = sub_tspec_ns(a, NANOSECONDS - 100);
    506      1.1  christos 		TEST_ASSERT_EQUAL_timespec(E, c);
    507      1.1  christos 	}
    508  1.1.1.4  christos 
    509  1.1.1.4  christos 	return;
    510      1.1  christos }
    511      1.1  christos 
    512      1.1  christos //----------------------------------------------------------------------
    513      1.1  christos // test negation
    514      1.1  christos //----------------------------------------------------------------------
    515      1.1  christos 
    516  1.1.1.3  christos 
    517  1.1.1.3  christos void
    518  1.1.1.4  christos test_Neg(void)
    519  1.1.1.4  christos {
    520      1.1  christos 	int i;
    521  1.1.1.4  christos 
    522      1.1  christos 	for (i = -4; i <= 4; ++i) {
    523      1.1  christos 		struct timespec a = timespec_init(i, 100);
    524      1.1  christos 		struct timespec b;
    525      1.1  christos 		struct timespec c;
    526      1.1  christos 
    527      1.1  christos 		b = neg_tspec(a);
    528      1.1  christos 		c = add_tspec(a, b);
    529      1.1  christos 		TEST_ASSERT_EQUAL(0, test_tspec(c));
    530      1.1  christos 	}
    531  1.1.1.4  christos 
    532  1.1.1.4  christos 	return;
    533      1.1  christos }
    534      1.1  christos 
    535      1.1  christos //----------------------------------------------------------------------
    536      1.1  christos // test abs value
    537      1.1  christos //----------------------------------------------------------------------
    538      1.1  christos 
    539  1.1.1.3  christos void
    540  1.1.1.4  christos test_AbsNoFrac(void)
    541  1.1.1.4  christos {
    542      1.1  christos 	int i;
    543  1.1.1.4  christos 
    544      1.1  christos 	for (i = -4; i <= 4; ++i) {
    545      1.1  christos 		struct timespec a = timespec_init(i , 0);
    546      1.1  christos 		struct timespec b;
    547      1.1  christos 
    548      1.1  christos 		b = abs_tspec(a);
    549      1.1  christos 		TEST_ASSERT_EQUAL((i != 0), test_tspec(b));
    550      1.1  christos 	}
    551  1.1.1.4  christos 
    552  1.1.1.4  christos 	return;
    553      1.1  christos }
    554      1.1  christos 
    555  1.1.1.3  christos 
    556  1.1.1.3  christos void
    557  1.1.1.4  christos test_AbsWithFrac(void)
    558  1.1.1.4  christos {
    559      1.1  christos 	int i;
    560  1.1.1.4  christos 
    561      1.1  christos 	for (i = -4; i <= 4; ++i) {
    562      1.1  christos 		struct timespec a = timespec_init(i, 100);
    563      1.1  christos 		struct timespec b;
    564      1.1  christos 
    565      1.1  christos 		b = abs_tspec(a);
    566      1.1  christos 		TEST_ASSERT_EQUAL(1, test_tspec(b));
    567      1.1  christos 	}
    568  1.1.1.4  christos 
    569  1.1.1.4  christos 	return;
    570      1.1  christos }
    571      1.1  christos 
    572      1.1  christos // ---------------------------------------------------------------------
    573      1.1  christos // test support stuff -- part 2
    574      1.1  christos // ---------------------------------------------------------------------
    575      1.1  christos 
    576  1.1.1.3  christos void
    577  1.1.1.4  christos test_Helpers2(void)
    578  1.1.1.4  christos {
    579  1.1.1.3  christos 	struct timespec limit = timespec_init(0, 2);
    580      1.1  christos 	struct timespec x, y;
    581      1.1  christos 	long i;
    582      1.1  christos 
    583      1.1  christos 	for (x.tv_sec = -2; x.tv_sec < 3; x.tv_sec++)
    584      1.1  christos 		for (x.tv_nsec = 1;
    585      1.1  christos 		     x.tv_nsec < 1000000000;
    586      1.1  christos 		     x.tv_nsec += 499999999) {
    587  1.1.1.3  christos 			for (i = -4; i < 5; ++i) {
    588      1.1  christos 				y = x;
    589      1.1  christos 				y.tv_nsec += i;
    590  1.1.1.4  christos 				if (i >= -2 && i <= 2) {
    591  1.1.1.3  christos 					TEST_ASSERT_TRUE(AssertTimespecClose(x, y, limit));
    592      1.1  christos 				}
    593      1.1  christos 				else
    594      1.1  christos 				{
    595  1.1.1.3  christos 					TEST_ASSERT_FALSE(AssertTimespecClose(x, y, limit));
    596      1.1  christos 				}
    597      1.1  christos 			}
    598      1.1  christos 		}
    599  1.1.1.4  christos 
    600  1.1.1.4  christos 	return;
    601      1.1  christos }
    602      1.1  christos 
    603      1.1  christos //----------------------------------------------------------------------
    604      1.1  christos // conversion to l_fp
    605      1.1  christos //----------------------------------------------------------------------
    606      1.1  christos 
    607  1.1.1.3  christos void
    608  1.1.1.4  christos test_ToLFPbittest(void)
    609  1.1.1.4  christos {
    610  1.1.1.3  christos 	l_fp lfpClose =  l_fp_init(0, 1);
    611      1.1  christos 	u_int32 i;
    612  1.1.1.4  christos 
    613      1.1  christos 	for (i = 0; i < 1000000000; i+=1000) {
    614      1.1  christos 		struct timespec a = timespec_init(1, i);
    615      1.1  christos 		l_fp E= l_fp_init(1, my_tick_to_tsf(i));
    616      1.1  christos 		l_fp r;
    617      1.1  christos 
    618      1.1  christos 		r = tspec_intv_to_lfp(a);
    619  1.1.1.3  christos 		TEST_ASSERT_TRUE(AssertFpClose(E, r, lfpClose));
    620      1.1  christos 	}
    621  1.1.1.4  christos 
    622  1.1.1.4  christos 	return;
    623      1.1  christos }
    624      1.1  christos 
    625  1.1.1.3  christos 
    626  1.1.1.3  christos void
    627  1.1.1.4  christos test_ToLFPrelPos(void)
    628  1.1.1.4  christos {
    629      1.1  christos 	int i;
    630  1.1.1.4  christos 
    631  1.1.1.3  christos 	for (i = 0; i < COUNTOF(fdata); ++i) {
    632      1.1  christos 		struct timespec a = timespec_init(1, fdata[i].nsec);
    633      1.1  christos 		l_fp E = l_fp_init(1, fdata[i].frac);
    634      1.1  christos 		l_fp r;
    635      1.1  christos 
    636      1.1  christos 		r = tspec_intv_to_lfp(a);
    637      1.1  christos 		TEST_ASSERT_EQUAL_l_fp(E, r);
    638      1.1  christos 	}
    639  1.1.1.4  christos 
    640  1.1.1.4  christos 	return;
    641      1.1  christos }
    642      1.1  christos 
    643  1.1.1.3  christos 
    644  1.1.1.3  christos void
    645  1.1.1.4  christos test_ToLFPrelNeg(void)
    646  1.1.1.4  christos {
    647      1.1  christos 	int i;
    648  1.1.1.4  christos 
    649  1.1.1.3  christos 	for (i = 0; i < COUNTOF(fdata); ++i) {
    650      1.1  christos 		struct timespec a = timespec_init(-1, fdata[i].nsec);
    651      1.1  christos 		l_fp E = l_fp_init(~0, fdata[i].frac);
    652      1.1  christos 		l_fp r;
    653      1.1  christos 
    654      1.1  christos 		r = tspec_intv_to_lfp(a);
    655      1.1  christos 		TEST_ASSERT_EQUAL_l_fp(E, r);
    656      1.1  christos 	}
    657  1.1.1.4  christos 
    658  1.1.1.4  christos 	return;
    659      1.1  christos }
    660      1.1  christos 
    661  1.1.1.3  christos 
    662  1.1.1.3  christos void
    663  1.1.1.4  christos test_ToLFPabs(void)
    664  1.1.1.4  christos {
    665      1.1  christos 	int i;
    666  1.1.1.4  christos 
    667  1.1.1.3  christos 	for (i = 0; i < COUNTOF(fdata); ++i) {
    668      1.1  christos 		struct timespec a = timespec_init(1, fdata[i].nsec);
    669      1.1  christos 		l_fp E = l_fp_init(1 + JAN_1970, fdata[i].frac);
    670      1.1  christos 		l_fp r;
    671      1.1  christos 
    672      1.1  christos 		r = tspec_stamp_to_lfp(a);
    673      1.1  christos 		TEST_ASSERT_EQUAL_l_fp(E, r);
    674      1.1  christos 	}
    675  1.1.1.4  christos 
    676  1.1.1.4  christos 	return;
    677      1.1  christos }
    678      1.1  christos 
    679      1.1  christos //----------------------------------------------------------------------
    680      1.1  christos // conversion from l_fp
    681      1.1  christos //----------------------------------------------------------------------
    682  1.1.1.3  christos 
    683  1.1.1.3  christos void
    684  1.1.1.4  christos test_FromLFPbittest(void)
    685  1.1.1.4  christos {
    686  1.1.1.3  christos 	struct timespec limit = timespec_init(0, 2);
    687      1.1  christos 
    688      1.1  christos 	// Not *exactly* a bittest, because 2**32 tests would take a
    689      1.1  christos 	// really long time even on very fast machines! So we do test
    690      1.1  christos 	// every 1000 fractional units.
    691      1.1  christos 	u_int32 tsf;
    692      1.1  christos 	for (tsf = 0; tsf < ~((u_int32)(1000)); tsf += 1000) {
    693      1.1  christos 		struct timespec E = timespec_init(1, my_tsf_to_tick(tsf));
    694      1.1  christos 		l_fp a = l_fp_init(1, tsf);
    695      1.1  christos 		struct timespec r;
    696      1.1  christos 
    697      1.1  christos 		r = lfp_intv_to_tspec(a);
    698      1.1  christos 		// The conversion might be off by one nanosecond when
    699      1.1  christos 		// comparing to calculated value.
    700  1.1.1.3  christos 		TEST_ASSERT_TRUE(AssertTimespecClose(E, r, limit));
    701      1.1  christos 	}
    702  1.1.1.4  christos 
    703  1.1.1.4  christos 	return;
    704      1.1  christos }
    705      1.1  christos 
    706  1.1.1.3  christos 
    707  1.1.1.3  christos void
    708  1.1.1.4  christos test_FromLFPrelPos(void)
    709  1.1.1.4  christos {
    710  1.1.1.3  christos 	struct timespec limit = timespec_init(0, 2);
    711      1.1  christos 	int i;
    712  1.1.1.4  christos 
    713  1.1.1.3  christos 	for (i = 0; i < COUNTOF(fdata); ++i) {
    714      1.1  christos 		l_fp a = l_fp_init(1, fdata[i].frac);
    715      1.1  christos 		struct timespec E = timespec_init(1, fdata[i].nsec);
    716      1.1  christos 		struct timespec r;
    717      1.1  christos 
    718      1.1  christos 		r = lfp_intv_to_tspec(a);
    719  1.1.1.3  christos 		TEST_ASSERT_TRUE(AssertTimespecClose(E, r, limit));
    720      1.1  christos 	}
    721  1.1.1.4  christos 
    722  1.1.1.4  christos 	return;
    723      1.1  christos }
    724      1.1  christos 
    725  1.1.1.3  christos 
    726  1.1.1.3  christos void
    727  1.1.1.4  christos test_FromLFPrelNeg(void)
    728  1.1.1.4  christos {
    729  1.1.1.3  christos 	struct timespec limit = timespec_init(0, 2);
    730      1.1  christos 	int i;
    731  1.1.1.4  christos 
    732  1.1.1.3  christos 	for (i = 0; i < COUNTOF(fdata); ++i) {
    733      1.1  christos 		l_fp a = l_fp_init(~0, fdata[i].frac);
    734      1.1  christos 		struct timespec E = timespec_init(-1, fdata[i].nsec);
    735      1.1  christos 		struct timespec r;
    736      1.1  christos 
    737      1.1  christos 		r = lfp_intv_to_tspec(a);
    738  1.1.1.3  christos 		TEST_ASSERT_TRUE(AssertTimespecClose(E, r, limit));
    739      1.1  christos 	}
    740  1.1.1.4  christos 
    741  1.1.1.4  christos 	return;
    742      1.1  christos }
    743      1.1  christos 
    744      1.1  christos 
    745      1.1  christos // nsec -> frac -> nsec roundtrip, using a prime start and increment
    746  1.1.1.3  christos void
    747  1.1.1.4  christos test_LFProundtrip(void)
    748  1.1.1.4  christos {
    749      1.1  christos 	int32_t t;
    750      1.1  christos 	u_int32 i;
    751  1.1.1.4  christos 
    752      1.1  christos 	for (t = -1; t < 2; ++t)
    753  1.1.1.3  christos 		for (i = 4999; i < 1000000000; i += 10007) {
    754      1.1  christos 			struct timespec E = timespec_init(t, i);
    755      1.1  christos 			l_fp a;
    756      1.1  christos 			struct timespec r;
    757      1.1  christos 
    758      1.1  christos 			a = tspec_intv_to_lfp(E);
    759      1.1  christos 			r = lfp_intv_to_tspec(a);
    760      1.1  christos 			TEST_ASSERT_EQUAL_timespec(E, r);
    761      1.1  christos 		}
    762  1.1.1.4  christos 
    763  1.1.1.4  christos 	return;
    764      1.1  christos }
    765      1.1  christos 
    766      1.1  christos //----------------------------------------------------------------------
    767      1.1  christos // string formatting
    768      1.1  christos //----------------------------------------------------------------------
    769      1.1  christos 
    770  1.1.1.3  christos void
    771  1.1.1.4  christos test_ToString(void)
    772  1.1.1.4  christos {
    773      1.1  christos 	static const struct {
    774      1.1  christos 		time_t		sec;
    775      1.1  christos 		long		nsec;
    776      1.1  christos 		const char *	repr;
    777      1.1  christos 	} data [] = {
    778      1.1  christos 		{ 0, 0,	 "0.000000000" },
    779      1.1  christos 		{ 2, 0,	 "2.000000000" },
    780      1.1  christos 		{-2, 0, "-2.000000000" },
    781      1.1  christos 		{ 0, 1,	 "0.000000001" },
    782      1.1  christos 		{ 0,-1,	"-0.000000001" },
    783      1.1  christos 		{ 1,-1,	 "0.999999999" },
    784      1.1  christos 		{-1, 1, "-0.999999999" },
    785      1.1  christos 		{-1,-1, "-1.000000001" },
    786      1.1  christos 	};
    787      1.1  christos 	int i;
    788  1.1.1.4  christos 
    789  1.1.1.3  christos 	for (i = 0; i < COUNTOF(data); ++i) {
    790      1.1  christos 		struct timespec a = timespec_init(data[i].sec, data[i].nsec);
    791      1.1  christos 		const char * E = data[i].repr;
    792      1.1  christos 		const char * r = tspectoa(a);
    793      1.1  christos 		TEST_ASSERT_EQUAL_STRING(E, r);
    794      1.1  christos 	}
    795  1.1.1.4  christos 
    796  1.1.1.4  christos 	return;
    797      1.1  christos }
    798      1.1  christos 
    799      1.1  christos // -*- EOF -*-
    800