add helpers for time_t reading/writing

This commit is contained in:
Vincent Sanders 2014-05-15 01:18:52 +01:00
parent a4be7f7d1a
commit ef00272e2f
4 changed files with 143 additions and 49 deletions

View File

@ -35,7 +35,6 @@
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <curl/curl.h>
#include "utils/config.h"
@ -45,6 +44,7 @@
#include "utils/messages.h"
#include "utils/nsurl.h"
#include "utils/utils.h"
#include "utils/time.h"
#include "desktop/gui_factory.h"
#include "content/fetch.h"
@ -1105,7 +1105,6 @@ llcache_serialise_metadata(llcache_object *object,
char *op;
unsigned int hloop;
int use;
struct tm *ltm;
allocsize = 10 + 1; /* object length */
@ -1133,22 +1132,30 @@ llcache_serialise_metadata(llcache_object *object,
datasize = allocsize;
/* the url, used for checking for collisions */
use = snprintf(op, datasize, "%s%c", nsurl_access(object->url), 0);
if (use > datasize)
use = snprintf(op, datasize, "%s", nsurl_access(object->url));
if (use < 0) {
goto operror;
}
use++; /* does not count the null */
if (use > datasize) {
goto overflow;
}
op += use;
datasize -= use;
/* object size */
use = snprintf(op, datasize, "%zu%c", object->source_len, 0);
use = snprintf(op, datasize, "%zu", object->source_len);
if (use < 0) {
goto operror;
}
use++; /* does not count the null */
if (use > datasize)
goto overflow;
op += use;
datasize -= use;
/* Time of request */
ltm = localtime(&object->cache.req_time);
use = strftime(op, datasize, "%s", ltm);
use = nsc_sntimet(op, datasize, &object->cache.req_time);
if (use == 0)
goto overflow;
use++; /* does not count the null */
@ -1156,8 +1163,7 @@ llcache_serialise_metadata(llcache_object *object,
datasize -= use;
/* Time of response */
ltm = localtime(&object->cache.res_time);
use = strftime(op, datasize, "%s", ltm);
use = nsc_sntimet(op, datasize, &object->cache.res_time);
if (use == 0)
goto overflow;
use++; /* does not count the null */
@ -1165,8 +1171,7 @@ llcache_serialise_metadata(llcache_object *object,
datasize -= use;
/* Time of completion */
ltm = localtime(&object->cache.fin_time);
use = strftime(op, datasize, "%s", ltm);
use = nsc_sntimet(op, datasize, &object->cache.fin_time);
if (use == 0)
goto overflow;
use++; /* does not count the null */
@ -1174,7 +1179,11 @@ llcache_serialise_metadata(llcache_object *object,
datasize -= use;
/* number of headers */
use = snprintf(op, datasize, "%zu%c", object->num_headers, 0);
use = snprintf(op, datasize, "%zu", object->num_headers);
if (use < 0) {
goto operror;
}
use++; /* does not count the null */
if (use > datasize)
goto overflow;
op += use;
@ -1183,10 +1192,13 @@ llcache_serialise_metadata(llcache_object *object,
/* headers */
for (hloop = 0 ; hloop < object->num_headers ; hloop++) {
use = snprintf(op, datasize,
"%s:%s%c",
"%s:%s",
object->headers[hloop].name,
object->headers[hloop].value,
0);
object->headers[hloop].value);
if (use < 0) {
goto operror;
}
use++; /* does not count the null */
if (use > datasize)
goto overflow;
op += use;
@ -1205,6 +1217,12 @@ overflow:
LOG(("Overflowed metadata buffer"));
free(data);
return NSERROR_INVALID;
operror:
/* output error */
LOG(("Output error"));
free(data);
return NSERROR_INVALID;
}
/**
@ -1223,7 +1241,6 @@ llcache_process_metadata(llcache_object *object)
int lnsize;
size_t num_headers;
size_t hloop;
struct tm ltm;
enum backing_store_flags flags = BACKING_STORE_META;
LOG(("Retriving metadata"));
@ -1290,31 +1307,24 @@ llcache_process_metadata(llcache_object *object)
ln += lnsize + 1;
lnsize = strlen(ln);
if ((lnsize < 1) ||
(strptime(ln, "%s", &ltm) == NULL))
if (nsc_snptimet(ln, lnsize, &object->cache.req_time) != NSERROR_OK)
goto format_error;
object->cache.req_time = mktime(&ltm);
/* metadata line 4 is the time of response */
line = 4;
ln += lnsize + 1;
lnsize = strlen(ln);
if ((lnsize < 1) ||
(strptime(ln, "%s", &ltm) == NULL))
if (nsc_snptimet(ln, lnsize, &object->cache.res_time) != NSERROR_OK)
goto format_error;
object->cache.res_time = mktime(&ltm);
/* metadata line 5 is the time of request completion */
line = 5;
ln += lnsize + 1;
lnsize = strlen(ln);
if ((lnsize < 1) ||
(strptime(ln, "%s", &ltm) == NULL))
if (nsc_snptimet(ln, lnsize, &object->cache.fin_time) != NSERROR_OK)
goto format_error;
object->cache.fin_time = mktime(&ltm);
/* metadata line 6 is the number of headers */
line = 6;

View File

@ -38,13 +38,15 @@ char *strndup(const char *s, size_t n);
char *strcasestr(const char *haystack, const char *needle);
#endif
#if (defined(riscos) || defined(_WIN32))
/* Although these platforms might have strftime or strptime they
* appear not to support the time_t seconds format specifier.
*/
#if (defined(_WIN32) || defined(riscos) || defined(__HAIKU__) || defined(__BEOS__) || defined(__amigaos4__) || defined(__AMIGA__) || defined(__MINT__))
#undef HAVE_STRPTIME
#define strptime nsc_time_strptime
struct tm;
char *nsc_time_strptime(const char *s, const char *format, struct tm *tm);
#undef HAVE_STRFTIME
#else
#define HAVE_STRPTIME
#define HAVE_STRFTIME
#endif
/* For some reason, UnixLib defines this unconditionally.

53
utils/time.h Normal file
View File

@ -0,0 +1,53 @@
/*
* Copyright 2014 Vincent Sanders <vince@netsurf-browser.org>
*
* This file is part of NetSurf, http://www.netsurf-browser.org/
*
* NetSurf is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; version 2 of the License.
*
* NetSurf is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/**
* \file utils/time.h
* \brief Interface to time operations.
*/
#ifndef _NETSURF_UTILS_TIME_H_
#define _NETSURF_UTILS_TIME_H_
#include <time.h>
/**
* Write the time in seconds since epoch to a buffer.
*
* This is provided as strftime is not generally portable.
*
* @param str The destination buffer.
* @param size The length of the destination buffer.
* @param timep The pointer to the time to write.
* @return The length of the string written.
*/
int nsc_sntimet(char *str, size_t size, time_t *timep);
/**
* Parse time in seconds since epoc.
*
* This is provided as strptime is not generally portable.
*
* @param str The source buffer.
* @param size The length of the source buffer.
* @param timep Pointer to result.
* @return NSERROR_OK on success or error code on faliure.
*/
nserror nsc_snptimet(char *str, size_t size, time_t *timep);
#endif

View File

@ -35,6 +35,7 @@
#include "utils/config.h"
#include "utils/messages.h"
#include "utils/utf8.h"
#include "utils/time.h"
#include "utils/utils.h"
/* exported interface documented in utils/utils.h */
@ -566,29 +567,57 @@ int inet_pton(int af, const char *src, void *dst)
#endif
/* exported function documented in utils/time.h */
int nsc_sntimet(char *str, size_t size, time_t *timep)
{
#ifndef HAVE_STRFTIME
long long val;
val = (long long)*timep;
return snprintf(str, size, "%lld", val);
#else
struct tm *ltm;
ltm = localtime(timep);
if (ltm == NULL) {
return -1;
}
return strftime(str, size, "%s", ltm);
#endif
}
nserror nsc_snptimet(char *str, size_t size, time_t *timep)
{
time_t time_out;
#ifndef HAVE_STRPTIME
/**
* naff strptime implementation for risc os and windows.
*
* @warning only supports %s format
*/
char *nsc_time_strptime(const char *s, const char *format, struct tm *tm)
{
time_t esecs;
struct tm *gtm;
char *endptr;
if ((format[0] != '%') || (format[1] != 's')) {
return NULL;
if (size < 1) {
return NSERROR_BAD_PARAMETER;
}
esecs = (time_t)strtoll(s, &endptr, 10);
time_out = (time_t)strtoll(str, NULL, 10);
gtm = gmtime(esecs);
*tm = *gtm;
return endptr;
if (time_out == 0) {
return NSERROR_BAD_PARAMETER;
}
#else
struct tm ltm;
if (size < 1) {
return NSERROR_BAD_PARAMETER;
}
if (strptime(str, "%s", &ltm) == NULL) {
return NSERROR_BAD_PARAMETER;
}
time_out = mktime(&ltm);
#endif
*timep = time_out;
return NSERROR_OK;
}