Relicense "GPLv2 or later" files to "GPLv3 or later".
[gnus] / lisp / parse-time.el
index e6725f3..d35f963 100644 (file)
@@ -1,15 +1,16 @@
 ;;; parse-time.el --- Parsing time strings
 
-;; Copyright (C) 1996 by Free Software Foundation, Inc.
+;; Copyright (C) 1996, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007
+;;   Free Software Foundation, Inc.
 
-;; Author: Erik Naggum <erik@arcana.naggum.no>
+;; Author: Erik Naggum <erik@naggum.no>
 ;; Keywords: util
 
 ;; This file is part of GNU Emacs.
 
 ;; GNU Emacs 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)
+;; the Free Software Foundation; either version 3, or (at your option)
 ;; any later version.
 
 ;; GNU Emacs is distributed in the hope that it will be useful,
@@ -19,8 +20,8 @@
 
 ;; You should have received a copy of the GNU General Public License
 ;; along with GNU Emacs; see the file COPYING.  If not, write to
-;; the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
-;; Boston, MA 02111-1307, USA.
+;; the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+;; Boston, MA 02110-1301, USA.
 
 ;;; Commentary:
 
 ;; `parse-time-string' parses a time in a string and returns a list of 9
 ;; values, just like `decode-time', where unspecified elements in the
 ;; string are returned as nil.  `encode-time' may be applied on these
-;; valuse to obtain an internal time value.
+;; values to obtain an internal time value.
 
 ;;; Code:
 
-(require 'cl)                          ;and ah ain't kiddin' 'bout it
+(eval-when-compile (require 'cl))      ;and ah ain't kiddin' 'bout it
 
-(put 'parse-time-syntax 'char-table-extra-slots 0)
+(defvar parse-time-syntax (make-vector 256 nil))
+(defvar parse-time-digits (make-vector 256 nil))
 
-(defvar parse-time-syntax (make-char-table 'parse-time-syntax))
-(defvar parse-time-digits (make-char-table 'parse-time-syntax))
+;; Byte-compiler warnings
+(defvar elt)
+(defvar val)
 
 (unless (aref parse-time-digits ?0)
   (loop for i from ?0 to ?9
-       do (set-char-table-range parse-time-digits i (- i ?0))))
+    do (aset parse-time-digits i (- i ?0))))
 
 (unless (aref parse-time-syntax ?0)
   (loop for i from ?0 to ?9
-       do (set-char-table-range parse-time-syntax i ?0))
+    do (aset parse-time-syntax i ?0))
   (loop for i from ?A to ?Z
-       do (set-char-table-range parse-time-syntax i ?A))
+    do (aset parse-time-syntax i ?A))
   (loop for i from ?a to ?z
-       do (set-char-table-range parse-time-syntax i ?a))
-  (set-char-table-range parse-time-syntax ?+ 1)
-  (set-char-table-range parse-time-syntax ?- -1)
-  (set-char-table-range parse-time-syntax ?: ?d)
+    do (aset parse-time-syntax i ?a))
+  (aset parse-time-syntax ?+ 1)
+  (aset parse-time-syntax ?- -1)
+  (aset parse-time-syntax ?: ?d)
   )
 
 (defsubst digit-char-p (char)
   (aref parse-time-digits char))
 
 (defsubst parse-time-string-chars (char)
-  (aref parse-time-syntax char))
+  (and (< char (length parse-time-syntax))
+       (aref parse-time-syntax char)))
 
 (put 'parse-error 'error-conditions '(parse-error error))
 (put 'parse-error 'error-message "Parsing error")
@@ -85,7 +89,8 @@
          (setq integer (+ (* integer 10) digit)
                index (1+ index)))
        (if (/= index end)
-           (signal 'parse-error `("not an integer" ,(substring string (or start 0) end)))
+           (signal 'parse-error `("not an integer"
+                                  ,(substring string (or start 0) end)))
          (* sign integer))))))
 
 (defun parse-time-tokenize (string)
                list)))
     (nreverse list)))
 
-(defvar parse-time-months '(("Jan" . 1) ("Feb" . 2) ("Mar" . 3)
-                           ("Apr" . 4) ("May" . 5) ("Jun" . 6)
-                           ("Jul" . 7) ("Aug" . 8) ("Sep" . 9)
-                           ("Oct" . 10) ("Nov" . 11) ("Dec" . 12)))
-(defvar parse-time-weekdays '(("Sun" . 0) ("Mon" . 1) ("Tue" . 2)
-                             ("Wed" . 3) ("Thu" . 4) ("Fri" . 5) ("Sat" . 6)))
-(defvar parse-time-zoneinfo `(("Z" 0) ("UT" 0) ("GMT" 0)
-                             ("PST" ,(* -8 3600)) ("PDT" ,(* -7 3600) t)
-                             ("MST" ,(* -7 3600)) ("MDT" ,(* -6 3600) t)
-                             ("CST" ,(* -6 3600)) ("CDT" ,(* -5 3600) t)
-                             ("EST" ,(* -5 3600)) ("EDT" ,(* -4 3600) t))
+(defvar parse-time-months '(("jan" . 1) ("feb" . 2) ("mar" . 3)
+                           ("apr" . 4) ("may" . 5) ("jun" . 6)
+                           ("jul" . 7) ("aug" . 8) ("sep" . 9)
+                           ("oct" . 10) ("nov" . 11) ("dec" . 12)))
+(defvar parse-time-weekdays '(("sun" . 0) ("mon" . 1) ("tue" . 2)
+                             ("wed" . 3) ("thu" . 4) ("fri" . 5) ("sat" . 6)))
+(defvar parse-time-zoneinfo `(("z" 0) ("ut" 0) ("gmt" 0)
+                             ("pst" ,(* -8 3600)) ("pdt" ,(* -7 3600) t)
+                             ("mst" ,(* -7 3600)) ("mdt" ,(* -6 3600) t)
+                             ("cst" ,(* -6 3600)) ("cdt" ,(* -5 3600) t)
+                             ("est" ,(* -5 3600)) ("edt" ,(* -4 3600) t))
   "(zoneinfo seconds-off daylight-savings-time-p)")
 
 (defvar parse-time-rules
   `(((6) parse-time-weekdays)
     ((3) (1 31))
     ((4) parse-time-months)
-    ((5) (1970 2038))
+    ((5) (100 4038))
     ((2 1 0)
      ,#'(lambda () (and (stringp elt)
                        (= (length elt) 8)
      ,#'(lambda () (car val))
      ,#'(lambda () (cadr val)))
     ((8)
-     ,#'(lambda () 
+     ,#'(lambda ()
          (and (stringp elt)
               (= 5 (length elt))
               (or (= (aref elt 0) ?+) (= (aref elt 0) ?-))))
                            (* 60 (parse-integer elt 1 3)))
                      (if (= (aref elt 0) ?-) -1 1))))
     ((5 4 3)
-     ,#'(lambda () (and (stringp elt) (= (length elt) 10) (= (aref elt 4) ?-) (= (aref elt 7) ?-)))
+     ,#'(lambda () (and (stringp elt)
+                       (= (length elt) 10)
+                       (= (aref elt 4) ?-)
+                       (= (aref elt 7) ?-)))
      [0 4] [5 7] [8 10])
-    ((2 1)
+    ((2 1 0)
      ,#'(lambda () (and (stringp elt) (= (length elt) 5) (= (aref elt 2) ?:)))
-     [0 2] [3 5])
-    ((5) (70 99) ,#'(lambda () (+ 1900 elt))))
+     [0 2] [3 5] ,#'(lambda () 0))
+    ((2 1 0)
+     ,#'(lambda () (and (stringp elt)
+                       (= (length elt) 4)
+                       (= (aref elt 1) ?:)))
+     [0 1] [2 4] ,#'(lambda () 0))
+    ((2 1 0)
+     ,#'(lambda () (and (stringp elt)
+                       (= (length elt) 7)
+                       (= (aref elt 1) ?:)))
+     [0 1] [2 4] [5 7])
+    ((5) (50 110) ,#'(lambda () (+ 1900 elt)))
+    ((5) (0 49) ,#'(lambda () (+ 2000 elt))))
   "(slots predicate extractor...)")
 
 (defun parse-time-string (string)
   "Parse the time-string STRING into (SEC MIN HOUR DAY MON YEAR DOW DST TZ).
 The values are identical to those of `decode-time', but any values that are
 unknown are returned as nil."
-  (let ((time (list nil nil nil nil nil nil nil nil nil nil))
-       (temp (parse-time-tokenize string)))
+  (let ((time (list nil nil nil nil nil nil nil nil nil))
+       (temp (parse-time-tokenize (downcase string))))
     (while temp
       (let ((elt (pop temp))
            (rules parse-time-rules)
@@ -169,27 +188,30 @@ unknown are returned as nil."
                 (slots (pop rule))
                 (predicate (pop rule))
                 (val))
-           (if (and (not (nth (car slots) time)) ;not already set
-                    (setq val (cond ((and (consp predicate)
-                                          (not (eq (car predicate) 'lambda)))
-                                     (and (numberp elt)
-                                          (<= (car predicate) elt)
-                                          (<= elt (cadr predicate))
-                                          elt))
-                                    ((symbolp predicate)
-                                     (cdr (assoc elt (symbol-value predicate))))
-                                    ((funcall predicate)))))
-               (progn
-                 (setq exit t)
-                 (while slots
-                   (let ((new-val (and rule
-                                       (let ((this (pop rule)))
-                                         (if (vectorp this)
-                                             (parse-integer elt (aref this 0) (aref this 1))
-                                           (funcall this))))))
-                     (rplaca (nthcdr (pop slots) time) (or new-val val))))))))))
+           (when (and (not (nth (car slots) time)) ;not already set
+                      (setq val (cond ((and (consp predicate)
+                                            (not (eq (car predicate)
+                                                     'lambda)))
+                                       (and (numberp elt)
+                                            (<= (car predicate) elt)
+                                            (<= elt (cadr predicate))
+                                            elt))
+                                      ((symbolp predicate)
+                                       (cdr (assoc elt
+                                                   (symbol-value predicate))))
+                                      ((funcall predicate)))))
+             (setq exit t)
+             (while slots
+               (let ((new-val (and rule
+                                   (let ((this (pop rule)))
+                                     (if (vectorp this)
+                                         (parse-integer
+                                          elt (aref this 0) (aref this 1))
+                                       (funcall this))))))
+                 (rplaca (nthcdr (pop slots) time) (or new-val val)))))))))
     time))
 
 (provide 'parse-time)
 
+;;; arch-tag: 07066094-45a8-4c68-b307-86195e2c1103
 ;;; parse-time.el ends here