[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [bug-gnulib] gettimeofday() for Win32
From: |
Martin Lambers |
Subject: |
Re: [bug-gnulib] gettimeofday() for Win32 |
Date: |
Thu, 25 Aug 2005 18:02:09 +0200 |
User-agent: |
Mutt/1.5.6+20040907i |
On Thu, 25. Aug 2005, 15:32:00 +0200, Bruno Haible wrote:
> > If so, how can this be done?
>
> It can be done by merging your .m4 file with Jim's one, and put a big
> #if inside lib/gettimeofday.c.
OK, I had no better idea than defining GETTIMEOFDAY_USE_REPLACEMENTS if
the replacement functions should be used, and let the big #if test that.
Besides introducing another constat, this has the disadvantage that
rpl_tzset is compiled even when it is not activated by the tzset module.
There's probably a better way to do it.
> But first, can you please bring your proposed code up to gnulib
> standards?
Done.
> And compare the code with GNU clisp's gettimeofday emulations. (I wrote
> that code => no copyright problems when porting it to gnulib.)
I used your code, with one exception:
> What's the right way to fill the struct timezone?
Newer descriptions of the gettimeofday function replaced 'struct
timezone * tzp' with 'void * tzp' and state that "If tzp is not a null
pointer, the behavior is unspecified." See
http://www.opengroup.org/onlinepubs/009695399/functions/gettimeofday.html
The code below therefore simply ignores the tzp argument.
I also added a test module, using the test code from Jim Meyering's
tests in gettimeofday.m4.
Thanks for your comments,
Martin
diff -uNr gnulib/lib/gettimeofday.c gnulib-gettimeofday-work/lib/gettimeofday.c
--- gnulib/lib/gettimeofday.c 2005-05-14 08:03:58.000000000 +0200
+++ gnulib-gettimeofday-work/lib/gettimeofday.c 2005-08-25 17:01:47.000000000
+0200
@@ -1,8 +1,9 @@
-/* Work around the bug in some systems whereby gettimeofday clobbers the
+/* Provide gettimeofday for systems that don't have it, or
+ work around the bug in some systems whereby gettimeofday clobbers the
static buffer that localtime uses for it's return value. The gettimeofday
function from Mac OS X 10.0.4, i.e. Darwin 1.3.7 has this problem.
The tzset replacement is necessary for at least Solaris 2.5, 2.5.1, and 2.6.
- Copyright (C) 2001, 2002, 2003 Free Software Foundation, Inc.
+ Copyright (C) 2001, 2002, 2003, 2005 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
@@ -31,19 +32,35 @@
#include <sys/types.h>
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
+#include <stdlib.h>
+
+#ifdef _WIN32
+#include <sys/timeb.h>
#endif
-#include <stdlib.h>
+#include "gettimeofday.h"
+
+#ifndef HAVE_GETTIMEOFDAY
+int
+gettimeofday (struct timeval *tp, void *tzp)
+{
+ if (tp != NULL)
+ {
+#ifdef _WIN32
+ struct _timeb timebuf;
+ _ftime (&timebuf);
+ tp->tv_sec = timebuf.time;
+ tp->tv_usec = (long)(timebuf.millitm) * (1000000/1000);
+#else
+ tp->tv_sec = time (NULL);
+ tp->tv_usec = 0;
+#endif
+ }
+ return 0;
+}
+#endif /* HAVE_GETTIMEOFDAY */
+#ifdef GETTIMEOFDAY_USE_REPLACEMENTS
static struct tm *localtime_buffer_addr;
/* This is a wrapper for localtime. It is used only on systems for which
@@ -119,3 +136,4 @@
tzset ();
*localtime_buffer_addr = save;
}
+#endif /* GETTIMEOFDAY_USE_REPLACEMENTS */
diff -uNr gnulib/lib/gettimeofday.h gnulib-gettimeofday-work/lib/gettimeofday.h
--- gnulib/lib/gettimeofday.h 1970-01-01 01:00:00.000000000 +0100
+++ gnulib-gettimeofday-work/lib/gettimeofday.h 2005-08-25 17:28:06.908471216
+0200
@@ -0,0 +1,50 @@
+/* Provide gettimeofday for systems that don't have it, or
+ work around the bug in some systems whereby gettimeofday clobbers the
+ static buffer that localtime uses for it's return value. The gettimeofday
+ function from Mac OS X 10.0.4, i.e. Darwin 1.3.7 has this problem.
+ The tzset replacement is necessary for at least Solaris 2.5, 2.5.1, and 2.6.
+ Copyright (C) 2001, 2002, 2003, 2005 Free Software Foundation, Inc.
+
+ This program 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; either version 2, or (at your option)
+ any later version.
+
+ This program 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, write to the Free Software Foundation,
+ Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */
+
+#ifndef GETTIMEOFDAY_H
+#define GETTIMEOFDAY_H
+
+#include <config.h>
+
+#if TIME_WITH_SYS_TIME
+# include <sys/time.h>
+# include <time.h>
+#else
+# if HAVE_SYS_TIME_H
+# include <sys/time.h>
+# else
+# include <time.h>
+# endif
+#endif
+
+#ifndef HAVE_STRUCT_TIMEVAL
+struct timeval
+{
+ time_t tv_sec;
+ suseconds_t tv_usec;
+};
+#endif
+
+#ifndef HAVE_GETTIMEOFDAY
+int gettimeofday (struct timeval *tp, void *tzp);
+#endif
+
+#endif /* GETTIMEOFDAY_H */
diff -uNr gnulib/m4/gettimeofday.m4 gnulib-gettimeofday-work/m4/gettimeofday.m4
--- gnulib/m4/gettimeofday.m4 2005-05-18 21:47:30.000000000 +0200
+++ gnulib-gettimeofday-work/m4/gettimeofday.m4 2005-08-25 17:57:28.232709232
+0200
@@ -1,10 +1,20 @@
-#serial 7
+#serial 8
# Copyright (C) 2001, 2002, 2003, 2005 Free Software Foundation, Inc.
# This file is free software; the Free Software Foundation
# gives unlimited permission to copy and/or distribute it,
# with or without modifications, as long as this notice is preserved.
+AC_DEFUN([gl_FUNC_GETTIMEOFDAY],
+[
+ AC_LIBSOURCES([gettimeofday.c, gettimeofday.h])
+ gl_PREREQ_GETTIMEOFDAY
+ AC_REPLACE_FUNCS(gettimeofday)
+ if test $ac_cv_func_gettimeofday = yes; then
+ AC_FUNC_GETTIMEOFDAY_CLOBBER
+ fi
+])
+
dnl From Jim Meyering.
dnl
dnl See if gettimeofday clobbers the static buffer that localtime uses
@@ -62,11 +72,12 @@
AC_DEFINE(gettimeofday, rpl_gettimeofday,
[Define to rpl_gettimeofday if the replacement function should be used.])
- gl_PREREQ_GETTIMEOFDAY
fi
])
AC_DEFUN([gl_GETTIMEOFDAY_REPLACE_LOCALTIME], [
+ AC_DEFINE(GETTIMEOFDAY_USE_REPLACEMENTS, 1,
+ [Define if some time related replacement functions should be used.])
AC_LIBOBJ(gettimeofday)
AC_DEFINE(gmtime, rpl_gmtime,
[Define to rpl_gmtime if the replacement function should be used.])
@@ -77,4 +88,45 @@
# Prerequisites of lib/gettimeofday.c.
AC_DEFUN([gl_PREREQ_GETTIMEOFDAY], [
AC_REQUIRE([AC_HEADER_TIME])
+
+ AC_CHECK_TYPE([suseconds_t], ,
+ [AC_DEFINE([suseconds_t], [int],
+ [Define to `int' if `suseconds_t' is missing.])
+ ],
+ [
+# if TIME_WITH_SYS_TIME
+# include <sys/time.h>
+# include <time.h>
+# else
+# if HAVE_SYS_TIME_H
+# include <sys/time.h>
+# else
+# include <time.h>
+# endif
+# endif
+ ])
+
+ AC_CACHE_CHECK([for struct timeval], fu_cv_sys_struct_timeval,
+ [AC_TRY_COMPILE(
+ [
+# if TIME_WITH_SYS_TIME
+# include <sys/time.h>
+# include <time.h>
+# else
+# if HAVE_SYS_TIME_H
+# include <sys/time.h>
+# else
+# include <time.h>
+# endif
+# endif
+ ],
+ [static struct timeval x; x.tv_sec = x.tv_usec;],
+ fu_cv_sys_struct_timeval=yes,
+ fu_cv_sys_struct_timeval=no)
+ ])
+
+ if test $fu_cv_sys_struct_timeval = yes; then
+ AC_DEFINE(HAVE_STRUCT_TIMEVAL, 1,
+ [Define if struct timeval is declared in <time.h> or
<sys/time.h>. ])
+ fi
])
diff -uNr gnulib/modules/gettimeofday
gnulib-gettimeofday-work/modules/gettimeofday
--- gnulib/modules/gettimeofday 2004-09-22 17:11:04.000000000 +0200
+++ gnulib-gettimeofday-work/modules/gettimeofday 2005-08-25
16:46:22.870142904 +0200
@@ -3,17 +3,19 @@
Files:
lib/gettimeofday.c
+lib/gettimeofday.h
m4/gettimeofday.m4
Depends-on:
configure.ac:
-AC_FUNC_GETTIMEOFDAY_CLOBBER
+gl_FUNC_GETTIMEOFDAY
Makefile.am:
Include:
<sys/time.h>
+"gettimeofday.h"
License:
GPL
diff -uNr gnulib/modules/gettimeofday-tests
gnulib-gettimeofday-work/modules/gettimeofday-tests
--- gnulib/modules/gettimeofday-tests 1970-01-01 01:00:00.000000000 +0100
+++ gnulib-gettimeofday-work/modules/gettimeofday-tests 2005-08-25
17:27:35.780203432 +0200
@@ -0,0 +1,11 @@
+Files:
+tests/test-gettimeofday.c
+
+Depends-on:
+
+configure.ac:
+
+Makefile.am:
+TESTS += test-gettimeofday
+test_gettimeofday_SOURCES = test-gettimeofday.c
+
diff -uNr gnulib/tests/test-gettimeofday.c
gnulib-gettimeofday-work/tests/test-gettimeofday.c
--- gnulib/tests/test-gettimeofday.c 1970-01-01 01:00:00.000000000 +0100
+++ gnulib-gettimeofday-work/tests/test-gettimeofday.c 2005-08-25
17:25:15.797484040 +0200
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2005 Free Software Foundation
+ * Written by Jim Meyering.
+ *
+ * This program 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; either version 2, or (at your option)
+ * any later version.
+ *
+ * This program 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, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ * 02110-1301, USA. */
+
+#if HAVE_CONFIG_H
+# include <config.h>
+#endif
+
+#include <stdio.h>
+#include <string.h>
+
+#if TIME_WITH_SYS_TIME
+# include <sys/time.h>
+# include <time.h>
+#else
+# if HAVE_SYS_TIME_H
+# include <sys/time.h>
+# else
+# include <time.h>
+# endif
+#endif
+
+#include "gettimeofday.h"
+
+int
+main (int argc, char *argv[])
+{
+ suseconds_t dummy = 0; /* just to test if this type is available */
+ time_t t = 0;
+ struct tm *lt;
+ struct tm saved_lt;
+ struct timeval tv;
+ lt = localtime (&t);
+ saved_lt = *lt;
+ gettimeofday (&tv, NULL);
+ if (memcmp (lt, &saved_lt, sizeof (struct tm)) != 0)
+ {
+ fprintf (stderr, "gettimeofday still clobbers the localtime buffer!\n");
+ return 1;
+ }
+ else
+ {
+ return 0;
+ }
+}