1/* 2** This file is in the public domain, so clarified as of 3** 1996-06-05 by Arthur David Olson. 4*/ 5 6/*LINTLIBRARY*/ 7 8#include "private.h" /* for time_t and TYPE_SIGNED */ 9 10double ATTRIBUTE_CONST 11difftime(const time_t time1, const time_t time0) 12{ 13 /* 14 ** If (sizeof (double) > sizeof (time_t)) simply convert and subtract 15 ** (assuming that the larger type has more precision). 16 */ 17 if (sizeof (double) > sizeof (time_t)) 18 return (double) time1 - (double) time0; 19 if (!TYPE_SIGNED(time_t)) { 20 /* 21 ** The difference of two unsigned values can't overflow 22 ** if the minuend is greater than or equal to the subtrahend. 23 */ 24 if (time1 >= time0) 25 return time1 - time0; 26 else return -(double) (time0 - time1); 27 } 28 /* 29 ** Handle cases where both time1 and time0 have the same sign 30 ** (meaning that their difference cannot overflow). 31 */ 32 if ((time1 < 0) == (time0 < 0)) 33 return time1 - time0; 34 /* 35 ** time1 and time0 have opposite signs. 36 ** Punt if uintmax_t is too narrow. 37 ** This suffers from double rounding; attempt to lessen that 38 ** by using long double temporaries. 39 */ 40 if (sizeof (uintmax_t) < sizeof (time_t)) 41 return (long double) time1 - (long double) time0; 42 /* 43 ** Stay calm...decent optimizers will eliminate the complexity below. 44 */ 45 if (time1 >= 0 /* && time0 < 0 */) 46 return (uintmax_t) time1 + (uintmax_t) (-1 - time0) + 1; 47 return -(double) ((uintmax_t) time0 + (uintmax_t) (-1 - time1) + 1); 48} 49