void xmlrpc_read_datetime_sec(xmlrpc_env *const envP, const xmlrpc_value *const valueP, time_t *const timeValueP) { unsigned int usecs; xmlrpc_read_datetime_usec(envP, valueP, timeValueP, &usecs); }
void xmlrpc_read_datetime_timespec(xmlrpc_env * const envP, const xmlrpc_value * const valueP, struct timespec * const timeValueP) { time_t secs; unsigned int usecs; xmlrpc_read_datetime_usec(envP, valueP, &secs, &usecs); timeValueP->tv_sec = secs; timeValueP->tv_nsec = usecs * 1000; }
void xmlrpc_read_datetime_str(xmlrpc_env *const envP, const xmlrpc_value *const valueP, const char **const stringValueP) { /*---------------------------------------------------------------------------- This exists for backward compatibility. No normal modern program would want to see a datetime value in this format. Note that the format isn't even ISO 8601 -- it's a bizarre hybrid of two ISO 8601 formats. Do not extend this. This exists because Xmlrpc-c was at one time lazy and this was the only way to extract the value. An xmlrpc_value in those days represented a datetime with the actual XML-RPC wire format of a datetime, and this function simply returned a copy of it. -----------------------------------------------------------------------------*/ validateDatetimeType(envP, valueP); if (!envP->fault_occurred) { time_t secs; unsigned int usecs; xmlrpc_read_datetime_usec(envP, valueP, &secs, &usecs); if (!envP->fault_occurred) { struct tm brokenTime; char dtString[64]; xmlrpc_gmtime(secs, &brokenTime); /* Note that this format is NOT ISO 8601 -- it's a bizarre hybrid of two ISO 8601 formats. */ strftime(dtString, sizeof(dtString), "%Y%m%dT%H:%M:%S", &brokenTime); if (usecs != 0) { char usecString[64]; assert(usecs < 1000000); snprintf(usecString, sizeof(usecString), ".%06u", usecs); STRSCAT(dtString, usecString); } *stringValueP = strdup(dtString); if (*stringValueP == NULL) xmlrpc_faultf(envP, "Unable to allocate memory for datetime string"); } } }
static void test_value_datetime_varytime(const char * const datestring, time_t const datetime, unsigned int const usec) { xmlrpc_value * v; xmlrpc_env env; const char * readBackString; time_t readBackDt; unsigned int readBackUsec; const char * datestringSec; #if XMLRPC_HAVE_TIMEVAL struct timeval const dtTimeval = makeTv(datetime, usec); struct timeval readBackTv; #endif #if XMLRPC_HAVE_TIMESPEC struct timespec const dtTimespec = makeTs(datetime, usec); struct timespec readBackTs; #endif const char * const dt8601 = make8601(datetime, usec); const char * readBack8601; datestringSec = truncateFracSec(datestring); xmlrpc_env_init(&env); /* Test xmlrpc_datetime_new_str and time read functions*/ v = xmlrpc_datetime_new_str(&env, datestring); TEST_NO_FAULT(&env); TEST(XMLRPC_TYPE_DATETIME == xmlrpc_value_type(v)); xmlrpc_read_datetime_sec(&env, v, &readBackDt); TEST_NO_FAULT(&env); TEST(readBackDt == datetime); xmlrpc_read_datetime_usec(&env, v, &readBackDt, &readBackUsec); TEST_NO_FAULT(&env); TEST(readBackDt == datetime); TEST(readBackUsec == usec); #if XMLRPC_HAVE_TIMEVAL xmlrpc_read_datetime_timeval(&env, v, &readBackTv); TEST_NO_FAULT(&env); TEST(tvIsEqual(dtTimeval, readBackTv)); #endif #if XMLRPC_HAVE_TIMESPEC xmlrpc_read_datetime_timespec(&env, v, &readBackTs); TEST_NO_FAULT(&env); TEST(tsIsEqual(dtTimespec, readBackTs)); #endif xmlrpc_read_datetime_8601(&env, v, &readBack8601); TEST_NO_FAULT(&env); TEST(xmlrpc_streq(dt8601, readBack8601)); strfree(readBack8601); xmlrpc_DECREF(v); /* Test xmlrpc_datetime_new_sec */ v = xmlrpc_datetime_new_sec(&env, datetime); TEST_NO_FAULT(&env); TEST(XMLRPC_TYPE_DATETIME == xmlrpc_value_type(v)); xmlrpc_read_datetime_str(&env, v, &readBackString); TEST_NO_FAULT(&env); TEST(streq(readBackString, datestringSec)); strfree(readBackString); xmlrpc_DECREF(v); /* Test xmlrpc_datetime_new_usec */ v = xmlrpc_datetime_new_usec(&env, datetime, usec); TEST_NO_FAULT(&env); TEST(XMLRPC_TYPE_DATETIME == xmlrpc_value_type(v)); xmlrpc_read_datetime_str(&env, v, &readBackString); TEST_NO_FAULT(&env); TEST(streq(readBackString, datestring)); strfree(readBackString); xmlrpc_DECREF(v); #if XMLRPC_HAVE_TIMEVAL /* Test xmlrpc_datetime_new_timeval */ v = xmlrpc_datetime_new_timeval(&env, dtTimeval); TEST_NO_FAULT(&env); TEST(XMLRPC_TYPE_DATETIME == xmlrpc_value_type(v)); xmlrpc_read_datetime_str(&env, v, &readBackString); TEST_NO_FAULT(&env); TEST(streq(readBackString, datestring)); strfree(readBackString); xmlrpc_DECREF(v); #endif #if XMLRPC_HAVE_TIMESPEC /* Test xmlrpc_datetime_new_timespec */ v = xmlrpc_datetime_new_timespec(&env, dtTimespec); TEST_NO_FAULT(&env); TEST(XMLRPC_TYPE_DATETIME == xmlrpc_value_type(v)); xmlrpc_read_datetime_str(&env, v, &readBackString); TEST_NO_FAULT(&env); TEST(streq(readBackString, datestring)); strfree(readBackString); xmlrpc_DECREF(v); #endif xmlrpc_env_clean(&env); strfree(datestringSec); }