[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Emacs-diffs] /srv/bzr/emacs/trunk r108928: Do not require float-time's
From: |
Paul Eggert |
Subject: |
[Emacs-diffs] /srv/bzr/emacs/trunk r108928: Do not require float-time's arg to fit in time_t (Bug#11825). |
Date: |
Fri, 06 Jul 2012 18:57:42 -0700 |
User-agent: |
Bazaar (2.5.0) |
------------------------------------------------------------
revno: 108928
committer: Paul Eggert <address@hidden>
branch nick: trunk
timestamp: Fri 2012-07-06 18:57:42 -0700
message:
Do not require float-time's arg to fit in time_t (Bug#11825).
This works better on hosts where time_t is unsigned, and where
float-time is applied to the (negative) difference between two times.
* editfns.c (decode_time_components): Last arg is now double *,
not int *, and means to store all the result as a double, without
worrying about whether the seconds part fits in time_t.
All callers changed.
(lisp_time_argument): Remove last int * arg, as it's no longer needed.
All callers changed.
(Ffloat_time): Do not fail merely because the specified time falls
outside of time_t range.
modified:
src/ChangeLog
src/editfns.c
src/fileio.c
src/systime.h
src/undo.c
=== modified file 'src/ChangeLog'
--- a/src/ChangeLog 2012-07-07 01:03:46 +0000
+++ b/src/ChangeLog 2012-07-07 01:57:42 +0000
@@ -1,3 +1,17 @@
+2012-07-07 Paul Eggert <address@hidden>
+
+ Do not require float-time's arg to fit in time_t (Bug#11825).
+ This works better on hosts where time_t is unsigned, and where
+ float-time is applied to the (negative) difference between two times.
+ * editfns.c (decode_time_components): Last arg is now double *,
+ not int *, and means to store all the result as a double, without
+ worrying about whether the seconds part fits in time_t.
+ All callers changed.
+ (lisp_time_argument): Remove last int * arg, as it's no longer needed.
+ All callers changed.
+ (Ffloat_time): Do not fail merely because the specified time falls
+ outside of time_t range.
+
2012-07-07 Glenn Morris <address@hidden>
* s/darwin.h (HAVE_RES_INIT, HAVE_LIBRESOLV):
=== modified file 'src/editfns.c'
--- a/src/editfns.c 2012-07-06 05:07:44 +0000
+++ b/src/editfns.c 2012-07-07 01:57:42 +0000
@@ -1521,16 +1521,20 @@
}
/* From the time components HIGH, LOW, USEC and PSEC taken from a Lisp
- list, generate the corresponding EMACS_TIME value *RESULT, and
- if RESULT_PSEC is not null store into *RESULT_PSEC the
- (nonnegative) difference in picoseconds between the input time and
- the returned time. Return nonzero if successful. */
+ list, generate the corresponding time value.
+
+ If RESULT is not null, store into *RESULT the converted time;
+ this can fail if the converted time does not fit into EMACS_TIME.
+ If *DRESULT is not null, store into *DRESULT the number of
+ seconds since the start of the POSIX Epoch.
+
+ Return nonzero if successful. */
int
decode_time_components (Lisp_Object high, Lisp_Object low, Lisp_Object usec,
- Lisp_Object psec, EMACS_TIME *result, int *result_psec)
+ Lisp_Object psec,
+ EMACS_TIME *result, double *dresult)
{
EMACS_INT hi, lo, us, ps;
- time_t sec;
if (! (INTEGERP (high) && INTEGERP (low)
&& INTEGERP (usec) && INTEGERP (psec)))
return 0;
@@ -1548,27 +1552,38 @@
us = us % 1000000 + 1000000 * (us % 1000000 < 0);
lo &= (1 << 16) - 1;
- /* Check for overflow in the highest-order component. */
- if (! ((TYPE_SIGNED (time_t) ? TIME_T_MIN >> 16 <= hi : 0 <= hi)
- && hi <= TIME_T_MAX >> 16))
- return 0;
-
- sec = hi;
- EMACS_SET_SECS_NSECS (*result, (sec << 16) + lo, us * 1000 + ps / 1000);
- if (result_psec)
- *result_psec = ps % 1000;
+ if (result)
+ {
+ if ((TYPE_SIGNED (time_t) ? TIME_T_MIN >> 16 <= hi : 0 <= hi)
+ && hi <= TIME_T_MAX >> 16)
+ {
+ /* Return the greatest representable time that is not greater
+ than the requested time. */
+ time_t sec = hi;
+ EMACS_SET_SECS_NSECS (*result, (sec << 16) + lo,
+ us * 1000 + ps / 1000);
+ }
+ else
+ {
+ /* Overflow in the highest-order component. */
+ return 0;
+ }
+ }
+
+ if (dresult)
+ *dresult = (us * 1e6 + ps) / 1e12 + lo + hi * 65536.0;
+
return 1;
}
/* Decode a Lisp list SPECIFIED_TIME that represents a time.
If SPECIFIED_TIME is nil, use the current time.
- Round the time down to the nearest EMACS_TIME value, and
- if PPSEC is not null store into *PPSEC the (nonnegative) difference in
- picoseconds between the input time and the returned time.
+
+ Round the time down to the nearest EMACS_TIME value.
Return seconds since the Epoch.
Signal an error if unsuccessful. */
EMACS_TIME
-lisp_time_argument (Lisp_Object specified_time, int *ppsec)
+lisp_time_argument (Lisp_Object specified_time)
{
EMACS_TIME t;
if (NILP (specified_time))
@@ -1577,14 +1592,15 @@
{
Lisp_Object high, low, usec, psec;
if (! (disassemble_lisp_time (specified_time, &high, &low, &usec, &psec)
- && decode_time_components (high, low, usec, psec, &t, ppsec)))
+ && decode_time_components (high, low, usec, psec, &t, 0)))
error ("Invalid time specification");
}
return t;
}
/* Like lisp_time_argument, except decode only the seconds part,
- and do not check the subseconds part, and always round down. */
+ do not allow out-of-range time stamps, do not check the subseconds part,
+ and always round down. */
static time_t
lisp_seconds_argument (Lisp_Object specified_time)
{
@@ -1616,12 +1632,21 @@
or (if you need time as a string) `format-time-string'. */)
(Lisp_Object specified_time)
{
- int psec;
- EMACS_TIME t = lisp_time_argument (specified_time, &psec);
- double ps = (1000 * 1000 * 1000 <= INTMAX_MAX / 1000
- ? EMACS_NSECS (t) * (intmax_t) 1000 + psec
- : EMACS_NSECS (t) * 1e3 + psec);
- return make_float (EMACS_SECS (t) + ps / 1e12);
+ double t;
+ if (NILP (specified_time))
+ {
+ EMACS_TIME now;
+ EMACS_GET_TIME (now);
+ t = EMACS_SECS (now) + EMACS_NSECS (now) / 1e9;
+ }
+ else
+ {
+ Lisp_Object high, low, usec, psec;
+ if (! (disassemble_lisp_time (specified_time, &high, &low, &usec, &psec)
+ && decode_time_components (high, low, usec, psec, 0, &t)))
+ error ("Invalid time specification");
+ }
+ return make_float (t);
}
/* Write information into buffer S of size MAXSIZE, according to the
@@ -1730,7 +1755,7 @@
usage: (format-time-string FORMAT-STRING &optional TIME UNIVERSAL) */)
(Lisp_Object format_string, Lisp_Object timeval, Lisp_Object universal)
{
- EMACS_TIME t = lisp_time_argument (timeval, 0);
+ EMACS_TIME t = lisp_time_argument (timeval);
struct tm tm;
CHECK_STRING (format_string);
=== modified file 'src/fileio.c'
--- a/src/fileio.c 2012-07-05 18:35:48 +0000
+++ b/src/fileio.c 2012-07-07 01:57:42 +0000
@@ -3031,7 +3031,7 @@
{
Lisp_Object absname, encoded_absname;
Lisp_Object handler;
- EMACS_TIME t = lisp_time_argument (timestamp, 0);
+ EMACS_TIME t = lisp_time_argument (timestamp);
absname = Fexpand_file_name (filename, BVAR (current_buffer, directory));
@@ -5159,7 +5159,7 @@
{
if (!NILP (time_list))
{
- current_buffer->modtime = lisp_time_argument (time_list, 0);
+ current_buffer->modtime = lisp_time_argument (time_list);
current_buffer->modtime_size = -1;
}
else
=== modified file 'src/systime.h'
--- a/src/systime.h 2012-06-24 17:21:20 +0000
+++ b/src/systime.h 2012-07-07 01:57:42 +0000
@@ -112,8 +112,8 @@
/* defined in editfns.c */
extern Lisp_Object make_lisp_time (EMACS_TIME);
extern int decode_time_components (Lisp_Object, Lisp_Object, Lisp_Object,
- Lisp_Object, EMACS_TIME *, int *);
-extern EMACS_TIME lisp_time_argument (Lisp_Object, int *);
+ Lisp_Object, EMACS_TIME *, double *);
+extern EMACS_TIME lisp_time_argument (Lisp_Object);
#endif
/* Compare times T1 and T2 for equality, inequality etc. */
=== modified file 'src/undo.c'
--- a/src/undo.c 2012-06-24 17:39:14 +0000
+++ b/src/undo.c 2012-07-07 01:57:42 +0000
@@ -521,7 +521,7 @@
(mod_time, 0,
XINT (XCAR (XCDR (XCDR (XCDR (cdr))))) / 1000);
else
- mod_time = lisp_time_argument (cdr, 0);
+ mod_time = lisp_time_argument (cdr);
if (current_buffer->base_buffer)
base_buffer = current_buffer->base_buffer;
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Emacs-diffs] /srv/bzr/emacs/trunk r108928: Do not require float-time's arg to fit in time_t (Bug#11825).,
Paul Eggert <=