Annotation of 43BSDReno/contrib/emacs-18.55/lisp/rmail.el, revision 1.1

1.1     ! root        1: ;; "RMAIL" mail reader for Emacs.
        !             2: ;; Copyright (C) 1985, 1986, 1987, 1988 Free Software Foundation, Inc.
        !             3: 
        !             4: ;; This file is part of GNU Emacs.
        !             5: 
        !             6: ;; GNU Emacs is distributed in the hope that it will be useful,
        !             7: ;; but WITHOUT ANY WARRANTY.  No author or distributor
        !             8: ;; accepts responsibility to anyone for the consequences of using it
        !             9: ;; or for whether it serves any particular purpose or works at all,
        !            10: ;; unless he says so in writing.  Refer to the GNU Emacs General Public
        !            11: ;; License for full details.
        !            12: 
        !            13: ;; Everyone is granted permission to copy, modify and redistribute
        !            14: ;; GNU Emacs, but only under the conditions described in the
        !            15: ;; GNU Emacs General Public License.   A copy of this license is
        !            16: ;; supposed to have been given to you along with GNU Emacs so you
        !            17: ;; can know your rights and responsibilities.  It should be in a
        !            18: ;; file named COPYING.  Among other things, the copyright notice
        !            19: ;; and this notice must be preserved on all copies.
        !            20: 
        !            21: 
        !            22: ;; Souped up by shane@mit-ajax based on ideas of [email protected]
        !            23: ;;   New features include attribute and keyword support, message
        !            24: ;;   selection by dispatch table, summary by attributes and keywords,
        !            25: ;;   expunging by dispatch table, sticky options for file commands.
        !            26: 
        !            27: (require 'mail-utils)
        !            28: (provide 'rmail)
        !            29: 
        !            30: ; these variables now declared in loaddefs or paths.el
        !            31: ;(defvar rmail-spool-directory "/usr/spool/mail/"
        !            32: ;  "This is the name of the directory used by the system mailer for\n\
        !            33: ;delivering new mail.  It's name should end with a slash.")
        !            34: ;(defvar rmail-dont-reply-to-names
        !            35: ;  nil
        !            36: ;  "*A regexp specifying names to prune of reply to messages.
        !            37: ;nil means dont reply to yourself.")
        !            38: ;(defvar rmail-ignored-headers
        !            39: ;   "^via:\\|^mail-from:\\|^origin:\\|^status:\\|^received:\\|^message-id:\\|^summary-line:"
        !            40: ;   "*Gubbish headers one would rather not see.")
        !            41: ;(defvar rmail-file-name
        !            42: ;  (expand-file-name "~/RMAIL")
        !            43: ;  "")
        !            44: ;
        !            45: ;(defvar rmail-delete-after-output nil
        !            46: ;  "*Non-nil means automatically delete a message that is copied to a file.")
        !            47: ;
        !            48: ;(defvar rmail-primary-inbox-list 
        !            49: ;  '("/usr/spool/mail/$USER" "~/mbox")
        !            50: ; "")
        !            51: 
        !            52: ;; these may be altered by site-init.el to match the format of mmdf files
        !            53: ;;  delimitation used on a given host (delim1 and delim2 from the config
        !            54: ;;  files)
        !            55: 
        !            56: (defvar mmdf-delim1 "^\001\001\001\001\n"
        !            57:   "Regexp marking the start of an mmdf message")
        !            58: (defvar mmdf-delim2 "^\001\001\001\001\n"
        !            59:   "Regexp marking the end of an mmdf message")
        !            60: 
        !            61: (defvar rmail-message-filter nil
        !            62:   "If non nil, is a filter function for new headers in RMAIL.
        !            63: Called with region narrowed to unformatted header.")
        !            64: 
        !            65: (defvar rmail-mode-map nil)
        !            66: 
        !            67: ;; Message counters and markers.  Deleted flags.
        !            68: 
        !            69: (defvar rmail-current-message nil)
        !            70: (defvar rmail-total-messages nil)
        !            71: (defvar rmail-message-vector nil)
        !            72: (defvar rmail-deleted-vector nil)
        !            73: 
        !            74: ;; These are used by autoloaded rmail-summary.
        !            75: 
        !            76: (defvar rmail-summary-buffer nil)
        !            77: (defvar rmail-summary-vector nil)
        !            78: 
        !            79: ;; `Sticky' default variables.
        !            80: 
        !            81: ;; Last individual label specified to a or k.
        !            82: (defvar rmail-last-label nil)
        !            83: ;; Last set of labels specified to C-M-n or C-M-p or C-M-l.
        !            84: (defvar rmail-last-multi-labels nil)
        !            85: (defvar rmail-last-file nil)
        !            86: (defvar rmail-last-rmail-file nil)
        !            87: 
        !            88: ;;;; *** Rmail Mode ***
        !            89: 
        !            90: (defun rmail (&optional file-name-arg)
        !            91:   "Read and edit incoming mail.
        !            92: Moves messages into file named by  rmail-file-name  (a babyl format file)
        !            93:  and edits that file in RMAIL Mode.
        !            94: Type \\[describe-mode] once editing that file, for a list of RMAIL commands.
        !            95: 
        !            96: May be called with filename as argument;
        !            97: then performs rmail editing on that file,
        !            98: but does not copy any new mail into the file."
        !            99:   (interactive (if current-prefix-arg
        !           100:                   (list (read-file-name "Run rmail on RMAIL file: "
        !           101:                                         nil nil t))))
        !           102:   (or rmail-last-file
        !           103:       (setq rmail-last-file (expand-file-name "~/xmail")))
        !           104:   (or rmail-last-rmail-file
        !           105:       (setq rmail-last-rmail-file (expand-file-name "~/XMAIL")))
        !           106:   (let* ((file-name (expand-file-name (or file-name-arg rmail-file-name)))
        !           107:         (existed (get-file-buffer file-name)))
        !           108:     ;; Like find-file, but in the case where a buffer existed
        !           109:     ;; and the file was reverted, recompute the message-data.
        !           110:     (if (and existed (not (verify-visited-file-modtime existed)))
        !           111:        (progn
        !           112:          (find-file file-name)
        !           113:          (if (verify-visited-file-modtime existed)
        !           114:              (progn (rmail-forget-messages)
        !           115:                     (rmail-set-message-counters))))
        !           116:       (find-file file-name))
        !           117:     (if existed
        !           118:        nil
        !           119:       (rmail-mode)
        !           120:       ;; Provide default set of inboxes for primary mail file ~/RMAIL.
        !           121:       (and (null rmail-inbox-list)
        !           122:           (null file-name-arg)
        !           123:           (setq rmail-inbox-list
        !           124:                 (or rmail-primary-inbox-list
        !           125:                     (list "~/mbox"
        !           126:                           (concat rmail-spool-directory
        !           127:                                   (or (getenv "LOGNAME")
        !           128:                                       (getenv "USER")
        !           129:                                       (user-login-name)))))))
        !           130:       ;; Convert all or part to Babyl file if possible.
        !           131:       (rmail-convert-file)
        !           132:       (goto-char (point-max))
        !           133:       (if (null rmail-inbox-list)
        !           134:          (progn
        !           135:            (rmail-set-message-counters)
        !           136:            (rmail-show-message))))
        !           137:     (rmail-get-new-mail)))
        !           138: 
        !           139: (defun rmail-convert-file ()
        !           140:   (let (convert)
        !           141:     (widen)
        !           142:     (goto-char (point-min))
        !           143:     ;; If file doesn't start like a Babyl file,
        !           144:     ;; convert it to one, by adding a header and converting each message.
        !           145:     (cond ((looking-at "BABYL OPTIONS:"))
        !           146:          ((looking-at "Version: 5\n")
        !           147:           ;; Losing babyl file made by old version of Rmail.
        !           148:           ;; Just fix the babyl file header; don't make a new one,
        !           149:           ;; so we don't lose the Labels: file attribute, etc.
        !           150:           (let ((buffer-read-only nil))
        !           151:             (insert "BABYL OPTIONS:\n")))
        !           152:          (t
        !           153:           (setq convert t)
        !           154:           (rmail-insert-rmail-file-header)))
        !           155:     ;; If file was not a Babyl file or if there are
        !           156:     ;; Unix format messages added at the end,
        !           157:     ;; convert file as necessary.
        !           158:     (if (or convert
        !           159:            (progn (goto-char (point-max))
        !           160:                   (search-backward "\^_")
        !           161:                   (forward-char 1)
        !           162:                   (looking-at "\n*From ")))
        !           163:        (let ((buffer-read-only nil))
        !           164:          (message "Converting to Babyl format...")
        !           165:          (narrow-to-region (point) (point-max))
        !           166:          (rmail-convert-to-babyl-format)
        !           167:          (message "Converting to Babyl format...done")))))
        !           168: 
        !           169: (defun rmail-insert-rmail-file-header ()
        !           170:   (let ((buffer-read-only nil))
        !           171:     (insert "BABYL OPTIONS:
        !           172: Version: 5
        !           173: Labels:
        !           174: Note:   This is the header of an rmail file.
        !           175: Note:   If you are seeing it in rmail,
        !           176: Note:    it means the file has no messages in it.\n\^_")))
        !           177: 
        !           178: (if rmail-mode-map
        !           179:     nil
        !           180:   (setq rmail-mode-map (make-keymap))
        !           181:   (suppress-keymap rmail-mode-map)
        !           182:   (define-key rmail-mode-map "." 'rmail-beginning-of-message)
        !           183:   (define-key rmail-mode-map " " 'scroll-up)
        !           184:   (define-key rmail-mode-map "\177" 'scroll-down)
        !           185:   (define-key rmail-mode-map "n" 'rmail-next-undeleted-message)
        !           186:   (define-key rmail-mode-map "p" 'rmail-previous-undeleted-message)
        !           187:   (define-key rmail-mode-map "\en" 'rmail-next-message)
        !           188:   (define-key rmail-mode-map "\ep" 'rmail-previous-message)
        !           189:   (define-key rmail-mode-map "\e\C-n" 'rmail-next-labeled-message)
        !           190:   (define-key rmail-mode-map "\e\C-p" 'rmail-previous-labeled-message)
        !           191:   (define-key rmail-mode-map "a" 'rmail-add-label)
        !           192:   (define-key rmail-mode-map "k" 'rmail-kill-label)
        !           193:   (define-key rmail-mode-map "d" 'rmail-delete-forward)
        !           194:   (define-key rmail-mode-map "u" 'rmail-undelete-previous-message)
        !           195:   (define-key rmail-mode-map "e" 'rmail-expunge)
        !           196:   (define-key rmail-mode-map "x" 'rmail-expunge)
        !           197:   (define-key rmail-mode-map "s" 'rmail-expunge-and-save)
        !           198:   (define-key rmail-mode-map "g" 'rmail-get-new-mail)
        !           199:   (define-key rmail-mode-map "h" 'rmail-summary)
        !           200:   (define-key rmail-mode-map "\e\C-h" 'rmail-summary)
        !           201:   (define-key rmail-mode-map "l" 'rmail-summary-by-labels)
        !           202:   (define-key rmail-mode-map "\e\C-l" 'rmail-summary-by-labels)
        !           203:   (define-key rmail-mode-map "\e\C-r" 'rmail-summary-by-recipients)
        !           204:   (define-key rmail-mode-map "t" 'rmail-toggle-header)
        !           205:   (define-key rmail-mode-map "m" 'rmail-mail)
        !           206:   (define-key rmail-mode-map "r" 'rmail-reply)
        !           207:   (define-key rmail-mode-map "c" 'rmail-continue)
        !           208:   (define-key rmail-mode-map "f" 'rmail-forward)
        !           209:   (define-key rmail-mode-map "\es" 'rmail-search)
        !           210:   (define-key rmail-mode-map "j" 'rmail-show-message)
        !           211:   (define-key rmail-mode-map "o" 'rmail-output-to-rmail-file)
        !           212:   (define-key rmail-mode-map "\C-o" 'rmail-output)
        !           213:   (define-key rmail-mode-map "i" 'rmail-input)
        !           214:   (define-key rmail-mode-map "q" 'rmail-quit)
        !           215:   (define-key rmail-mode-map ">" 'rmail-last-message)
        !           216:   (define-key rmail-mode-map "?" 'describe-mode)
        !           217:   (define-key rmail-mode-map "w" 'rmail-edit-current-message)
        !           218:   (define-key rmail-mode-map "\C-d" 'rmail-delete-backward))
        !           219: 
        !           220: ;; Rmail mode is suitable only for specially formatted data.
        !           221: (put 'rmail-mode 'mode-class 'special)
        !           222: 
        !           223: (defun rmail-mode ()
        !           224:   "Rmail Mode is used by \\[rmail] for editing Rmail files.
        !           225: All normal editing commands are turned off.
        !           226: Instead, these commands are available:
        !           227: 
        !           228: .      Move point to front of this message (same as \\[beginning-of-buffer]).
        !           229: SPC    Scroll to next screen of this message.
        !           230: DEL    Scroll to previous screen of this message.
        !           231: n      Move to Next non-deleted message.
        !           232: p      Move to Previous non-deleted message.
        !           233: M-n    Move to Next message whether deleted or not.
        !           234: M-p    Move to Previous message whether deleted or not.
        !           235: >      Move to the last message in Rmail file.
        !           236: j      Jump to message specified by numeric position in file.
        !           237: M-s    Search for string and show message it is found in.
        !           238: d      Delete this message, move to next nondeleted.
        !           239: C-d    Delete this message, move to previous nondeleted.
        !           240: u      Undelete message.  Tries current message, then earlier messages
        !           241:        till a deleted message is found.
        !           242: e      Expunge deleted messages.
        !           243: s      Expunge and save the file.
        !           244: q       Quit Rmail: expunge, save, then switch to another buffer.
        !           245: C-x C-s Save without expunging.
        !           246: g      Move new mail from system spool directory or mbox into this file.
        !           247: m      Mail a message (same as \\[mail-other-window]).
        !           248: c      Continue composing outgoing message started before.
        !           249: r      Reply to this message.  Like m but initializes some fields.
        !           250: f      Forward this message to another user.
        !           251: o       Output this message to an Rmail file (append it).
        !           252: C-o    Output this message to a Unix-format mail file (append it).
        !           253: i      Input Rmail file.  Run Rmail on that file.
        !           254: a      Add label to message.  It will be displayed in the mode line.
        !           255: k      Kill label.  Remove a label from current message.
        !           256: C-M-n   Move to Next message with specified label
        !           257:           (label defaults to last one specified).
        !           258:           Standard labels: filed, unseen, answered, forwarded, deleted.
        !           259:           Any other label is present only if you add it with `a'.
        !           260: C-M-p   Move to Previous message with specified label
        !           261: C-M-h  Show headers buffer, with a one line summary of each message.
        !           262: C-M-l  Like h only just messages with particular label(s) are summarized.
        !           263: C-M-r   Like h only just messages with particular recipient(s) are summarized.
        !           264: t      Toggle header, show Rmail header if unformatted or vice versa.
        !           265: w      Edit the current message.  C-c C-c to return to Rmail."
        !           266:   (interactive)
        !           267:   (kill-all-local-variables)
        !           268:   (rmail-mode-1)
        !           269:   (rmail-variables)
        !           270:   (run-hooks 'rmail-mode-hook))
        !           271: 
        !           272: (defun rmail-mode-1 ()
        !           273:   (setq major-mode 'rmail-mode)
        !           274:   (setq mode-name "RMAIL")
        !           275:   (setq buffer-read-only t)
        !           276:   ;; No need to auto save RMAIL files.
        !           277:   (setq buffer-auto-save-file-name nil)
        !           278:   (if (boundp 'mode-line-modified)
        !           279:       (setq mode-line-modified "--- ")
        !           280:     (setq mode-line-format
        !           281:          (cons "--- " (cdr (default-value 'mode-line-format)))))
        !           282:   (use-local-map rmail-mode-map)
        !           283:   (set-syntax-table text-mode-syntax-table)
        !           284:   (setq local-abbrev-table text-mode-abbrev-table))
        !           285: 
        !           286: (defun rmail-variables ()
        !           287:   (make-local-variable 'revert-buffer-function)
        !           288:   (setq revert-buffer-function 'rmail-revert)
        !           289:   (make-local-variable 'rmail-last-label)
        !           290:   (make-local-variable 'rmail-deleted-vector)
        !           291:   (make-local-variable 'rmail-keywords)
        !           292:   (make-local-variable 'rmail-summary-buffer)
        !           293:   (make-local-variable 'rmail-summary-vector)
        !           294:   (make-local-variable 'rmail-current-message)
        !           295:   (make-local-variable 'rmail-total-messages)
        !           296:   (make-local-variable 'require-final-newline)
        !           297:   (setq require-final-newline nil)
        !           298:   (make-local-variable 'version-control)
        !           299:   (setq version-control 'never)
        !           300:   (make-local-variable 'file-precious-flag)
        !           301:   (setq file-precious-flag t)
        !           302:   (make-local-variable 'rmail-message-vector)
        !           303:   (make-local-variable 'rmail-last-file)
        !           304:   (make-local-variable 'rmail-inbox-list)
        !           305:   (setq rmail-inbox-list (rmail-parse-file-inboxes))
        !           306:   (make-local-variable 'rmail-keywords)
        !           307:   ;; this gets generated as needed
        !           308:   (setq rmail-keywords nil))
        !           309: 
        !           310: ;; Handle M-x revert-buffer done in an rmail-mode buffer.
        !           311: (defun rmail-revert (arg noconfirm)
        !           312:   (let (revert-buffer-function)
        !           313:     ;; Call our caller again, but this time it does the default thing.
        !           314:     (if (revert-buffer arg noconfirm)
        !           315:        ;; If the user said "yes", and we changed something,
        !           316:        ;; reparse the messages.
        !           317:        (progn
        !           318:          (rmail-convert-file)
        !           319:          (goto-char (point-max))
        !           320:          (rmail-set-message-counters)
        !           321:          (rmail-show-message)))))
        !           322: 
        !           323: ;; Return a list of files from this buffer's Mail: option.
        !           324: ;; Does not assume that messages have been parsed.
        !           325: ;; Just returns nil if buffer does not look like Babyl format.
        !           326: (defun rmail-parse-file-inboxes ()
        !           327:   (save-excursion
        !           328:     (save-restriction
        !           329:       (widen)
        !           330:       (goto-char 1)
        !           331:       (cond ((looking-at "Babyl options:")
        !           332:             (search-forward "\^_" nil 'move)
        !           333:             (narrow-to-region 1 (point))
        !           334:             (goto-char 1)
        !           335:             (if (search-forward "\nMail:" nil t)
        !           336:                 (progn
        !           337:                   (narrow-to-region (point) (progn (end-of-line) (point)))
        !           338:                   (goto-char (point-min))
        !           339:                   (mail-parse-comma-list))))))))
        !           340: 
        !           341: (defun rmail-expunge-and-save ()
        !           342:   "Expunge and save RMAIL file."
        !           343:   (interactive)
        !           344:   (rmail-expunge)
        !           345:   (save-buffer))
        !           346: 
        !           347: (defun rmail-quit ()
        !           348:   "Quit out of RMAIL."
        !           349:   (interactive)
        !           350:   (rmail-expunge-and-save)
        !           351:   ;; Don't switch to the summary buffer even if it was recently visible.
        !           352:   (if rmail-summary-buffer
        !           353:       (bury-buffer rmail-summary-buffer))
        !           354:   (let ((obuf (current-buffer)))
        !           355:     (switch-to-buffer (other-buffer))
        !           356:     (bury-buffer obuf)))
        !           357: 
        !           358: (defun rmail-input (filename)
        !           359:   "Run RMAIL on file FILENAME."
        !           360:   (interactive "FRun rmail on RMAIL file: ")
        !           361:   (rmail filename))
        !           362: 
        !           363: 
        !           364: ;;;; *** Rmail input ***
        !           365: 
        !           366: ;; RLK feature not added in this version:
        !           367: ;; argument specifies inbox file or files in various ways.
        !           368: 
        !           369: (defun rmail-get-new-mail (&optional file-name)
        !           370:   "Move any new mail from this RMAIL file's inbox files.
        !           371: The inbox files can be specified with the file's Mail: option.
        !           372: The variable rmail-primary-inbox-list specifies the inboxes for
        !           373: your primary RMAIL file if it has no Mail: option.
        !           374: These are normally your ~/mbox and your /usr/spool/mail/$USER.
        !           375: 
        !           376: You can also specify the file to get new mail from.  In this
        !           377: case, the file of new mail is not changed or deleted.
        !           378: Noninteractively, you can pass the inbox file name as an argument.
        !           379: Interactively, a prefix argument causes us to read a file name
        !           380: and use that file as the inbox."
        !           381:   (interactive
        !           382:    (list (if current-prefix-arg
        !           383:             (read-file-name "Get new mail from file: "))))
        !           384:   (or (verify-visited-file-modtime (current-buffer))
        !           385:       (progn
        !           386:        (find-file (buffer-file-name))
        !           387:        (if (verify-visited-file-modtime (current-buffer))
        !           388:            (rmail-forget-messages))))
        !           389:   (rmail-maybe-set-message-counters)
        !           390:   (widen)
        !           391:   (unwind-protect
        !           392:       (let ((opoint (point))
        !           393:            (new-messages 0)
        !           394:            (delete-files ())
        !           395:            ;; If buffer has not changed yet, and has not been saved yet,
        !           396:            ;; don't replace the old backup file now.
        !           397:            (make-backup-files (and make-backup-files (buffer-modified-p)))
        !           398:            (buffer-read-only nil))
        !           399:        (goto-char (point-max))
        !           400:        (skip-chars-backward " \t\n")   ; just in case of brain damage
        !           401:        (delete-region (point) (point-max))     ; caused by require-final-newline
        !           402:        (save-excursion
        !           403:          (save-restriction
        !           404:            (narrow-to-region (point) (point))
        !           405:            ;; Read in the contents of the inbox files,
        !           406:            ;; renaming them as necessary,
        !           407:            ;; and adding to the list of files to delete eventually.
        !           408:            (if file-name
        !           409:                (rmail-insert-inbox-text (list file-name) nil)
        !           410:              (setq delete-files (rmail-insert-inbox-text rmail-inbox-list t)))
        !           411:            ;; Scan the new text and convert each message to babyl format.
        !           412:            (goto-char (point-min))
        !           413:            (save-excursion
        !           414:              (setq new-messages (rmail-convert-to-babyl-format)))
        !           415:            (or (zerop new-messages)
        !           416:                (let (success)
        !           417:                  (widen)
        !           418:                  (search-backward "\^_")
        !           419:                  (narrow-to-region (point) (point-max))
        !           420:                  (goto-char (1+ (point-min)))
        !           421:                  (rmail-count-new-messages)
        !           422:                  (save-buffer)))
        !           423:            ;; Delete the old files, now that babyl file is saved.
        !           424:            (while delete-files
        !           425:              (condition-case ()
        !           426:                  (delete-file (car delete-files))
        !           427:                (file-error nil))
        !           428:              (setq delete-files (cdr delete-files)))))
        !           429:        (if (= new-messages 0)
        !           430:            (progn (goto-char opoint)
        !           431:                   (if (or file-name rmail-inbox-list)
        !           432:                       (message "(No new mail has arrived)")))
        !           433:            (message "%d new message%s read"
        !           434:                     new-messages (if (= 1 new-messages) "" "s"))))
        !           435:     ;; Don't leave the buffer screwed up if we get a disk-full error.
        !           436:     (rmail-show-message)))
        !           437: 
        !           438: (defun rmail-insert-inbox-text (files renamep)
        !           439:   (let (file tofile delete-files movemail)
        !           440:     (while files
        !           441:       (setq file (expand-file-name (substitute-in-file-name (car files)))
        !           442:            ;;>> un*x specific <<
        !           443:            tofile (concat file "~"))
        !           444:       ;; If getting from mail spool directory,
        !           445:       ;; use movemail to move rather than renaming.
        !           446:       (setq movemail (equal (file-name-directory file) rmail-spool-directory))
        !           447:       (if movemail
        !           448:          (progn
        !           449:            (setq tofile (expand-file-name
        !           450:                           ".newmail"
        !           451:                           (file-name-directory
        !           452:                             (expand-file-name rmail-file-name))))
        !           453:            ;; On some systems, /usr/spool/mail/foo is a directory
        !           454:            ;; and the actual inbox is /usr/spool/mail/foo/foo.
        !           455:            (if (file-directory-p file)
        !           456:                (setq file (expand-file-name (or (getenv "LOGNAME")
        !           457:                                                 (getenv "USER")
        !           458:                                                 (user-login-name))
        !           459:                                             file)))))
        !           460:       (if (or (file-exists-p tofile) (file-exists-p file))
        !           461:          (message "Getting mail from %s..." file))
        !           462:       ;; Set TOFILE if have not already done so, and
        !           463:       ;; rename or copy the file FILE to TOFILE if and as appropriate.
        !           464:       (cond ((not renamep)
        !           465:             (setq tofile file))
        !           466:            ((or (file-exists-p tofile) (not (file-exists-p file)))
        !           467:             nil)
        !           468:            ((not movemail)
        !           469:             (rename-file file tofile nil))
        !           470:            (t
        !           471:             (let ((errors nil))
        !           472:               (unwind-protect
        !           473:                   (save-excursion
        !           474:                     (setq errors (generate-new-buffer " *rmail loss*"))
        !           475:                     (buffer-flush-undo errors)
        !           476:                     (call-process
        !           477:                       (expand-file-name "movemail" exec-directory)
        !           478:                       nil errors nil file tofile)
        !           479:                     (if (not (buffer-modified-p errors))
        !           480:                         ;; No output => movemail won
        !           481:                         nil
        !           482:                       (set-buffer errors)
        !           483:                       (subst-char-in-region (point-min) (point-max)
        !           484:                                             ?\n ?\  )
        !           485:                       (goto-char (point-max))
        !           486:                       (skip-chars-backward " \t")
        !           487:                       (delete-region (point) (point-max))
        !           488:                       (goto-char (point-min))
        !           489:                       (if (looking-at "movemail: ")
        !           490:                           (delete-region (point-min) (match-end 0)))
        !           491:                       (signal 'file-error
        !           492:                               (list "movemail"
        !           493:                                     (buffer-substring (point-min)
        !           494:                                                       (point-max))
        !           495:                                     ;file tofile
        !           496:                                     ))))
        !           497:                 (if errors (kill-buffer errors))))))
        !           498:       ;; At this point, TOFILE contains the name to read:
        !           499:       ;; Either the alternate name (if we renamed)
        !           500:       ;; or the actual inbox (if not renaming).
        !           501:       (if (file-exists-p tofile)
        !           502:          (progn (goto-char (point-max))
        !           503:                 (insert-file-contents tofile)
        !           504:                 (goto-char (point-max))
        !           505:                 (or (= (preceding-char) ?\n)
        !           506:                     (insert ?\n))
        !           507:                 (setq delete-files (cons tofile delete-files))))
        !           508:       (message "")
        !           509:       (setq files (cdr files)))
        !           510:     delete-files))
        !           511: 
        !           512: ;; the  rmail-break-forwarded-messages  feature is not implemented
        !           513: (defun rmail-convert-to-babyl-format ()
        !           514:   (let ((count 0) start
        !           515:        (case-fold-search nil))
        !           516:     (goto-char (point-min))
        !           517:     (save-restriction
        !           518:       (while (not (eobp))
        !           519:        (cond ((looking-at "Babyl Options:");Babyl header
        !           520:               (search-forward "\n\^_")
        !           521:               (delete-region (point-min) (point)))
        !           522:              ;; Babyl format message
        !           523:              ((looking-at "\^L")
        !           524:               (or (search-forward "\n\^_" nil t)
        !           525:                   (progn
        !           526:                     (message "Invalid Babyl format in inbox!")
        !           527:                     (sit-for 1)
        !           528:                     (goto-char (point-max))))
        !           529:               (setq count (1+ count))
        !           530:               (skip-chars-forward " \t\n")
        !           531:               (narrow-to-region (point) (point-max)))
        !           532:              ;;*** MMDF format
        !           533:              ((let ((case-fold-search t))
        !           534:                 (looking-at mmdf-delim1))
        !           535:               (let ((case-fold-search t))
        !           536:                 (replace-match "\^L\n0, unseen,,\n*** EOOH ***\n")
        !           537:                 (setq start (point))
        !           538:                 (re-search-forward mmdf-delim2 nil t)
        !           539:                 (replace-match "\^_"))
        !           540:               (save-excursion
        !           541:                 (save-restriction
        !           542:                   (narrow-to-region start (1- (point)))
        !           543:                   (goto-char (point-min))
        !           544:                   (while (search-forward "\n\^_" nil t) ; single char "\^_"
        !           545:                     (replace-match "\n^_")))) ; 2 chars: "^" and "_"
        !           546:               (narrow-to-region (point) (point-max))
        !           547:               (setq count (1+ count)))
        !           548:              ;;*** Mail format
        !           549:              ((looking-at "^From ")
        !           550:               (setq start (point))
        !           551:               (insert "\^L\n0, unseen,,\n*** EOOH ***\n")
        !           552:               (rmail-nuke-pinhead-header)
        !           553:               (if (re-search-forward
        !           554:                    (concat "^[\^_]?\\("
        !           555:                            "From [^ \n]*\\(\\|\".*\"[^ \n]*\\)  ?[^ \n]* [^ \n]* *"
        !           556:                            "[0-9]* [0-9:]*\\( ?[A-Z]?[A-Z][A-Z]T\\| ?[-+]?[0-9][0-9][0-9][0-9]\\|\\) " ; EDT, -0500
        !           557:                            "19[0-9]* *$\\|"
        !           558:                            mmdf-delim1 "\\|"
        !           559:                            "^Babyl Options:\\|"
        !           560:                            "\^L\n[01],\\)") nil t)
        !           561:                   (goto-char (match-beginning 1))
        !           562:                 (goto-char (point-max)))
        !           563:               (setq count (1+ count))
        !           564:               (save-excursion
        !           565:                 (save-restriction
        !           566:                   (narrow-to-region start (point))
        !           567:                   (goto-char (point-min))
        !           568:                   (while (search-forward "\n\^_" nil t); single char
        !           569:                     (replace-match "\n^_")))); 2 chars: "^" and "_"
        !           570:               (insert ?\^_)
        !           571:               (narrow-to-region (point) (point-max)))
        !           572:              ;;
        !           573:              ;;This is a kludge, in case we're wrong about mmdf not
        !           574:              ;;allowing anything in between.  If it loses, we'll have
        !           575:              ;;to look for something else
        !           576:              (t (delete-char 1)))))
        !           577:     count))
        !           578: 
        !           579: (defun rmail-nuke-pinhead-header ()
        !           580:   (save-excursion
        !           581:     (save-restriction
        !           582:       (let ((start (point))
        !           583:            (end (progn
        !           584:                   (condition-case ()
        !           585:                       (search-forward "\n\n")
        !           586:                     (error
        !           587:                      (goto-char (point-max))
        !           588:                      (insert "\n\n")))
        !           589:                   (point)))
        !           590:            has-from has-date)
        !           591:        (narrow-to-region start end)
        !           592:        (let ((case-fold-search t))
        !           593:          (goto-char start)
        !           594:          (setq has-from (search-forward "\nFrom:" nil t))
        !           595:          (goto-char start)
        !           596:          (setq has-date (and (search-forward "\nDate:" nil t) (point)))
        !           597:          (goto-char start))
        !           598:        (let ((case-fold-search nil))
        !           599:          (if (re-search-forward
        !           600:               "^From \\([^ ]*\\(\\|\".*\"[^ ]*\\)\\)  ?\\([^ ]*\\) \\([^ ]*\\) *\\([0-9]*\\) \\([0-9:]*\\)\\( ?[A-Z]?[A-Z][A-Z]T\\| ?[-+]?[0-9][0-9][0-9][0-9]\\|\\) 19\\([0-9]*\\) *\n" nil t)
        !           601:              (replace-match
        !           602:                (concat
        !           603:                  ;; Keep and reformat the date if we don't
        !           604:                  ;;  have a Date: field.
        !           605:                  (if has-date
        !           606:                      ""
        !           607:                    ;; If no time zone specified, assume est.
        !           608:                    (if (= (match-beginning 7) (match-end 7))
        !           609:                        "Date: \\3, \\5 \\4 \\8 \\6 EST\n"
        !           610:                        "Date: \\3, \\5 \\4 \\8 \\6\\7\n"))
        !           611:                  ;; Keep and reformat the sender if we don't
        !           612:                  ;; have a From: field.
        !           613:                  (if has-from
        !           614:                      ""
        !           615:                    "From: \\1\n")))))))))
        !           616: 
        !           617: ;;;; *** Rmail Message Formatting and Header Manipulation ***
        !           618: 
        !           619: (defun rmail-reformat-message (beg end)
        !           620:   (goto-char beg)
        !           621:   (forward-line 1)
        !           622:   (if (/= (following-char) ?0)
        !           623:       (error "Bad format in RMAIL file."))
        !           624:   (let ((buffer-read-only nil)
        !           625:        (delta (- (buffer-size) end)))
        !           626:     (delete-char 1)
        !           627:     (insert ?1)
        !           628:     (forward-line 1)
        !           629:     (if (looking-at "Summary-line: ")
        !           630:        (forward-line 1))
        !           631:     (if (looking-at "\\*\\*\\* EOOH \\*\\*\\*\n")
        !           632:        (delete-region (point)
        !           633:                       (progn (forward-line 1) (point))))
        !           634:     (let ((str (buffer-substring (point)
        !           635:                                 (save-excursion (search-forward "\n\n" end 'move)
        !           636:                                                 (point)))))
        !           637:       (insert str "*** EOOH ***\n")
        !           638:       (narrow-to-region (point) (- (buffer-size) delta)))
        !           639:     (goto-char (point-min))
        !           640:     (if rmail-ignored-headers (rmail-clear-headers))
        !           641:     (if rmail-message-filter (funcall rmail-message-filter))))
        !           642: 
        !           643: (defun rmail-clear-headers ()
        !           644:   (if (search-forward "\n\n" nil t)
        !           645:       (save-restriction
        !           646:         (narrow-to-region (point-min) (point))
        !           647:        (let ((buffer-read-only nil))
        !           648:          (while (let ((case-fold-search t))
        !           649:                   (goto-char (point-min))
        !           650:                   (re-search-forward rmail-ignored-headers nil t))
        !           651:            (beginning-of-line)
        !           652:            (delete-region (point)
        !           653:                           (progn (re-search-forward "\n[^ \t]")
        !           654:                                  (forward-char -1)
        !           655:                                  (point))))))))
        !           656: 
        !           657: (defun rmail-toggle-header ()
        !           658:   "Show original message header if pruned header currently shown, or vice versa."
        !           659:   (interactive)
        !           660:   (rmail-maybe-set-message-counters)
        !           661:   (narrow-to-region (rmail-msgbeg rmail-current-message) (point-max))
        !           662:   (let ((buffer-read-only nil))
        !           663:     (goto-char (point-min))
        !           664:     (forward-line 1)
        !           665:     (if (= (following-char) ?1)
        !           666:        (progn (delete-char 1)
        !           667:               (insert ?0)
        !           668:               (forward-line 1)
        !           669:               (if (looking-at "Summary-Line:")
        !           670:                   (forward-line 1))
        !           671:               (insert "*** EOOH ***\n")
        !           672:               (forward-char -1)
        !           673:               (search-forward "\n*** EOOH ***\n")
        !           674:               (forward-line -1)
        !           675:               (let ((temp (point)))
        !           676:                 (and (search-forward "\n\n" nil t)
        !           677:                      (delete-region temp (point))))
        !           678:               (goto-char (point-min))
        !           679:               (search-forward "\n*** EOOH ***\n")
        !           680:               (narrow-to-region (point) (point-max)))
        !           681:       (rmail-reformat-message (point-min) (point-max)))))
        !           682: 
        !           683: ;;;; *** Rmail Attributes and Keywords ***
        !           684: 
        !           685: ;; Make a string describing current message's attributes and keywords
        !           686: ;; and set it up as the name of a minor mode
        !           687: ;; so it will appear in the mode line.
        !           688: (defun rmail-display-labels ()
        !           689:   (let ((blurb "") (beg (point-min-marker)) (end (point-max-marker)))
        !           690:     (save-excursion
        !           691:       (unwind-protect
        !           692:          (progn
        !           693:            (widen)
        !           694:            (goto-char (rmail-msgbeg rmail-current-message))
        !           695:            (forward-line 1)
        !           696:            (if (looking-at "[01],")
        !           697:                (progn
        !           698:                  (narrow-to-region (point) (progn (end-of-line) (point)))
        !           699:                  ;; Truly valid BABYL format requires a space before each
        !           700:                  ;; attribute or keyword name.  Put them in if missing.
        !           701:                  (let (buffer-read-only)
        !           702:                    (goto-char (point-min))
        !           703:                    (while (search-forward "," nil t)
        !           704:                      (or (looking-at "[ ,]") (eobp)
        !           705:                          (insert " "))))
        !           706:                  (goto-char (point-max))
        !           707:                  (if (search-backward ",," nil 'move)
        !           708:                      (progn
        !           709:                        (if (> (point) (1+ (point-min)))
        !           710:                            (setq blurb (buffer-substring (+ 1 (point-min)) (point))))
        !           711:                        (if (> (- (point-max) (point)) 2)
        !           712:                            (setq blurb
        !           713:                                  (concat blurb
        !           714:                                          ";"
        !           715:                                          (buffer-substring (+ (point) 3)
        !           716:                                                            (1- (point-max)))))))))))
        !           717:        (narrow-to-region beg end)
        !           718:        (set-marker beg nil)
        !           719:        (set-marker end nil)))
        !           720:     (while (string-match " +," blurb)
        !           721:       (setq blurb (concat (substring blurb 0 (match-beginning 0)) ","
        !           722:                          (substring blurb (match-end 0)))))
        !           723:     (while (string-match ", +" blurb)
        !           724:       (setq blurb (concat (substring blurb 0 (match-beginning 0)) ","
        !           725:                          (substring blurb (match-end 0)))))
        !           726:     (setq mode-line-process
        !           727:          (concat " " rmail-current-message "/" rmail-total-messages
        !           728:                  blurb))))
        !           729: 
        !           730: ;; Turn an attribute of the current message on or off according to STATE.
        !           731: ;; ATTR is the name of the attribute, as a string.
        !           732: (defun rmail-set-attribute (attr state)
        !           733:   (let ((omax (- (buffer-size) (point-max)))
        !           734:        (omin (- (buffer-size) (point-min)))
        !           735:        (buffer-read-only nil))
        !           736:     (unwind-protect
        !           737:        (save-excursion
        !           738:          (widen)
        !           739:          (goto-char (+ 3 (rmail-msgbeg rmail-current-message)))
        !           740:          (let ((curstate (search-backward (concat ", " attr ",")
        !           741:                                           (prog1 (point) (end-of-line)) t)))
        !           742:            (or (eq curstate (not (not state)))
        !           743:                (if curstate
        !           744:                    (delete-region (point) (1- (match-end 0)))
        !           745:                  (beginning-of-line)
        !           746:                  (forward-char 2)
        !           747:                  (insert " " attr ","))))
        !           748:          (if (string= attr "deleted")
        !           749:              (rmail-set-message-deleted-p rmail-current-message state)))
        !           750:       (narrow-to-region (max 1 (- (buffer-size) omin))
        !           751:                        (- (buffer-size) omax))
        !           752:       (rmail-display-labels))))
        !           753: 
        !           754: ;; Return t if the attributes/keywords line of msg number MSG
        !           755: ;; contains a match for the regexp LABELS.
        !           756: (defun rmail-message-labels-p (msg labels)
        !           757:   (goto-char (rmail-msgbeg msg))
        !           758:   (forward-char 3)
        !           759:   (re-search-backward labels (prog1 (point) (end-of-line)) t))
        !           760: 
        !           761: ;;;; *** Rmail Message Selection And Support ***
        !           762: 
        !           763: (defun rmail-msgend (n)
        !           764:   (marker-position (aref rmail-message-vector (1+ n))))
        !           765: 
        !           766: (defun rmail-msgbeg (n)
        !           767:   (marker-position (aref rmail-message-vector n)))
        !           768: 
        !           769: (defun rmail-widen-to-current-msgbeg (function)
        !           770:   "Call FUNCTION with point at start of internal data of current message.
        !           771: Assumes that bounds were previously narrowed to display the message in Rmail.
        !           772: The bounds are widened enough to move point where desired,
        !           773: then narrowed again afterward.
        !           774: Assumes that the visible text of the message is not changed by FUNCTION."
        !           775:   (save-excursion
        !           776:     (let ((obeg (- (point-max) (point-min)))
        !           777:       (unwind-protect
        !           778:          (progn
        !           779:            (narrow-to-region (rmail-msgbeg rmail-current-message)
        !           780:                              (point-max))
        !           781:            (goto-char (point-min))
        !           782:            (funcall function))
        !           783:        (narrow-to-region (- (point-max) obeg) (point-max)))))))
        !           784: 
        !           785: (defun rmail-forget-messages ()
        !           786:   (unwind-protect
        !           787:       (if (vectorp rmail-message-vector)
        !           788:          (let* ((i 0)
        !           789:                 (v rmail-message-vector)
        !           790:                 (n (length v)))
        !           791:            (while (< i n)
        !           792:              (move-marker (aref v i)  nil)
        !           793:              (setq i (1+ i)))))
        !           794:     (setq rmail-message-vector nil)
        !           795:     (setq rmail-deleted-vector nil)))
        !           796: 
        !           797: (defun rmail-maybe-set-message-counters ()
        !           798:   (if (not (and rmail-deleted-vector
        !           799:                rmail-message-vector
        !           800:                rmail-current-message
        !           801:                rmail-total-messages))
        !           802:       (rmail-set-message-counters)))
        !           803: 
        !           804: (defun rmail-count-new-messages (&optional nomsg)
        !           805:   (let* ((case-fold-search nil)
        !           806:         (total-messages 0)
        !           807:         (messages-head nil)
        !           808:         (deleted-head nil))
        !           809:     (or nomsg (message "Counting new messages..."))
        !           810:     (goto-char (point-max))
        !           811:     ;; Put at the end of messages-head
        !           812:     ;; the entry for message N+1, which marks
        !           813:     ;; the end of message N.  (N = number of messages).
        !           814:     (search-backward "\^_")
        !           815:     (setq messages-head (list (point-marker)))
        !           816:     (rmail-set-message-counters-counter (point-min))
        !           817:     (setq rmail-current-message (1+ rmail-total-messages))
        !           818:     (setq rmail-total-messages
        !           819:          (+ rmail-total-messages total-messages))
        !           820:     (setq rmail-message-vector
        !           821:          (vconcat rmail-message-vector (cdr messages-head)))
        !           822:     (aset rmail-message-vector
        !           823:          rmail-current-message (car messages-head))
        !           824:     (setq rmail-deleted-vector
        !           825:          (concat rmail-deleted-vector deleted-head))
        !           826:     (setq rmail-summary-vector
        !           827:          (vconcat rmail-summary-vector (make-vector total-messages nil)))
        !           828:     (goto-char (point-min))
        !           829:     (or nomsg (message "Counting new messages...done (%d)" total-messages))))
        !           830: 
        !           831: (defun rmail-set-message-counters ()
        !           832:   (rmail-forget-messages)
        !           833:   (save-excursion
        !           834:     (save-restriction
        !           835:       (widen)
        !           836:       (let* ((point-save (point))
        !           837:             (total-messages 0)
        !           838:             (messages-after-point)
        !           839:             (case-fold-search nil)
        !           840:             (messages-head nil)
        !           841:             (deleted-head nil))
        !           842:        (message "Counting messages...")
        !           843:        (goto-char (point-max))
        !           844:        ;; Put at the end of messages-head
        !           845:        ;; the entry for message N+1, which marks
        !           846:        ;; the end of message N.  (N = number of messages).
        !           847:        (search-backward "\^_")
        !           848:        (setq messages-head (list (point-marker)))
        !           849:        (rmail-set-message-counters-counter (min (point) point-save))
        !           850:        (setq messages-after-point total-messages)
        !           851:        (rmail-set-message-counters-counter)
        !           852:        (setq rmail-total-messages total-messages)
        !           853:        (setq rmail-current-message
        !           854:              (min total-messages
        !           855:                   (max 1 (- total-messages messages-after-point))))
        !           856:        (setq rmail-message-vector
        !           857:              (apply 'vector (cons (point-min-marker) messages-head))
        !           858:              rmail-deleted-vector (concat "D" deleted-head)
        !           859:              rmail-summary-vector (make-vector rmail-total-messages nil))
        !           860:        (message "Counting messages...done")))))
        !           861:        
        !           862: (defun rmail-set-message-counters-counter (&optional stop)
        !           863:   (while (search-backward "\^_\^L\n" stop t)
        !           864:     (setq messages-head (cons (point-marker) messages-head))
        !           865:     (save-excursion
        !           866:       (setq deleted-head
        !           867:            (cons (if (search-backward ", deleted,"
        !           868:                                       (prog1 (point)
        !           869:                                         (forward-line 2))
        !           870:                                       t)
        !           871:                      ?D ?\ )
        !           872:                  deleted-head)))
        !           873:     (if (zerop (% (setq total-messages (1+ total-messages)) 20))
        !           874:        (message "Counting messages...%d" total-messages))))
        !           875: 
        !           876: (defun rmail-beginning-of-message ()
        !           877:   "Show current message starting from the beginning."
        !           878:   (interactive)
        !           879:   (rmail-show-message rmail-current-message))
        !           880: 
        !           881: (defun rmail-show-message (&optional n)
        !           882:   "Show message number N (prefix argument), counting from start of file."
        !           883:   (interactive "p")
        !           884:   (rmail-maybe-set-message-counters)
        !           885:   (widen)
        !           886:   (if (zerop rmail-total-messages)
        !           887:       (progn (narrow-to-region (point-min) (1- (point-max)))
        !           888:             (goto-char (point-min))
        !           889:             (setq mode-line-process nil))
        !           890:     (let (blurb)
        !           891:       (if (not n)
        !           892:          (setq n rmail-current-message)
        !           893:        (cond ((<= n 0)
        !           894:               (setq n 1
        !           895:                     rmail-current-message 1
        !           896:                     blurb "No previous message"))
        !           897:              ((> n rmail-total-messages)
        !           898:               (setq n rmail-total-messages
        !           899:                     rmail-current-message rmail-total-messages
        !           900:                     blurb "No following message"))
        !           901:              (t
        !           902:               (setq rmail-current-message n))))
        !           903:       (let ((beg (rmail-msgbeg n))
        !           904:            (end (rmail-msgend n)))
        !           905:        (goto-char beg)
        !           906:        (forward-line 1)
        !           907:        (if (= (following-char) ?0)
        !           908:            (progn
        !           909:              (rmail-reformat-message beg end)
        !           910:              (rmail-set-attribute "unseen" nil))
        !           911:          (search-forward "\n*** EOOH ***\n" end t)
        !           912:          (narrow-to-region (point) end))
        !           913:        (goto-char (point-min))
        !           914:        (rmail-display-labels)
        !           915:        (run-hooks 'rmail-show-message-hook)
        !           916:        (if blurb
        !           917:            (message blurb))))))
        !           918: 
        !           919: (defun rmail-next-message (n)
        !           920:   "Show following message whether deleted or not.
        !           921: With prefix argument N, moves forward N messages,
        !           922: or backward if N is negative."
        !           923:   (interactive "p")
        !           924:   (rmail-maybe-set-message-counters)
        !           925:   (rmail-show-message (+ rmail-current-message n)))
        !           926: 
        !           927: (defun rmail-previous-message (n)
        !           928:   "Show previous message whether deleted or not.
        !           929: With prefix argument N, moves backward N messages,
        !           930: or forward if N is negative."
        !           931:   (interactive "p")
        !           932:   (rmail-next-message (- n)))  
        !           933: 
        !           934: (defun rmail-next-undeleted-message (n)
        !           935:   "Show following non-deleted message.
        !           936: With prefix argument N, moves forward N non-deleted messages,
        !           937: or backward if N is negative."
        !           938:   (interactive "p")
        !           939:   (rmail-maybe-set-message-counters)
        !           940:   (let ((lastwin rmail-current-message)
        !           941:        (current rmail-current-message))
        !           942:     (while (and (> n 0) (< current rmail-total-messages))
        !           943:       (setq current (1+ current))
        !           944:       (if (not (rmail-message-deleted-p current))
        !           945:          (setq lastwin current n (1- n))))
        !           946:     (while (and (< n 0) (> current 1))
        !           947:       (setq current (1- current))
        !           948:       (if (not (rmail-message-deleted-p current))
        !           949:          (setq lastwin current n (1+ n))))
        !           950:     (if (/= lastwin rmail-current-message)
        !           951:        (rmail-show-message lastwin))
        !           952:     (if (< n 0)
        !           953:        (message "No previous nondeleted message"))
        !           954:     (if (> n 0)
        !           955:        (message "No following nondeleted message"))))
        !           956: 
        !           957: (defun rmail-previous-undeleted-message (n)
        !           958:   "Show previous non-deleted message.
        !           959: With prefix argument N, moves backward N non-deleted messages,
        !           960: or forward if N is negative."
        !           961:   (interactive "p")
        !           962:   (rmail-next-undeleted-message (- n)))
        !           963: 
        !           964: (defun rmail-last-message ()
        !           965:   "Show last message in file."
        !           966:   (interactive)
        !           967:   (rmail-maybe-set-message-counters)
        !           968:   (rmail-show-message rmail-total-messages))
        !           969: 
        !           970: (defun rmail-what-message ()
        !           971:   (let ((where (point))
        !           972:        (low 1)
        !           973:        (high rmail-total-messages)
        !           974:        (mid (/ rmail-total-messages 2)))
        !           975:     (while (> (- high low) 1)
        !           976:       (if (>= where (rmail-msgbeg mid))
        !           977:          (setq low mid)
        !           978:        (setq high mid))
        !           979:       (setq mid (+ low (/ (- high low) 2))))
        !           980:     (if (>= where (rmail-msgbeg high)) high low)))
        !           981: 
        !           982: (defvar rmail-search-last-regexp nil)
        !           983: (defun rmail-search (regexp &optional reversep)
        !           984:   "Show message containing next match for REGEXP.
        !           985: Search in reverse (earlier messages) with non-nil 2nd arg REVERSEP.
        !           986: Interactively, empty argument means use same regexp used last time,
        !           987: and reverse search is specified by a negative numeric arg."
        !           988:   (interactive
        !           989:     (let* ((reversep (< (prefix-numeric-value current-prefix-arg) 0))
        !           990:           (prompt (concat (if reversep "Reverse " "") "Rmail search (regexp): "))
        !           991:           regexp)
        !           992:       (if rmail-search-last-regexp
        !           993:          (setq prompt (concat prompt
        !           994:                               "(default "
        !           995:                               rmail-search-last-regexp
        !           996:                               ") ")))
        !           997:       (setq regexp (read-string prompt))
        !           998:       (cond ((not (equal regexp ""))
        !           999:             (setq rmail-search-last-regexp regexp))
        !          1000:            ((not rmail-search-last-regexp)
        !          1001:             (error "No previous Rmail search string")))
        !          1002:       (list rmail-search-last-regexp reversep)))
        !          1003:   (message "%sRmail search for %s..."
        !          1004:           (if reversep "Reverse " "")
        !          1005:           regexp)
        !          1006:   (let ((omin (point-min))
        !          1007:        (omax (point-max))
        !          1008:        (opoint (point))
        !          1009:        win
        !          1010:        (msg rmail-current-message))
        !          1011:     (unwind-protect
        !          1012:        (progn
        !          1013:          (widen)
        !          1014:          ;; Check messages one by one, advancing message number up or down
        !          1015:          ;; but searching forward through each message.
        !          1016:          (if reversep
        !          1017:              (while (and (null win) (> msg 1))
        !          1018:                (goto-char (rmail-msgbeg (setq msg (1- msg))))
        !          1019:                (setq win (re-search-forward
        !          1020:                           regexp (rmail-msgend msg) t)))
        !          1021:            (while (and (null win) (< msg rmail-total-messages))
        !          1022:              (goto-char (rmail-msgbeg (setq msg (1+ msg))))
        !          1023:              (setq win (re-search-forward regexp (rmail-msgend msg) t)))))
        !          1024:       (if win
        !          1025:          (progn
        !          1026:            ;; If this is a reverse search and we found a message,
        !          1027:            ;; search backward thru this message to position point.
        !          1028:            (if reversep
        !          1029:                (progn
        !          1030:                  (goto-char (rmail-msgend msg))
        !          1031:                  (re-search-backward
        !          1032:                   regexp (rmail-msgbeg msg) t)))
        !          1033:            (setq win (point))
        !          1034:            (rmail-show-message msg)
        !          1035:            (message "%sRmail search for %s...done"
        !          1036:                     (if reversep "Reverse " "")
        !          1037:                     regexp)
        !          1038:            (goto-char win))
        !          1039:        (goto-char opoint)
        !          1040:        (narrow-to-region omin omax)
        !          1041:        (ding)
        !          1042:        (message "Searched failed: %s" regexp)))))
        !          1043: 
        !          1044: ;;;; *** Rmail Message Deletion Commands ***
        !          1045: 
        !          1046: (defun rmail-message-deleted-p (n)
        !          1047:   (= (aref rmail-deleted-vector n) ?D))
        !          1048: 
        !          1049: (defun rmail-set-message-deleted-p (n state)
        !          1050:   (aset rmail-deleted-vector n (if state ?D ?\ )))
        !          1051: 
        !          1052: (defun rmail-delete-message ()
        !          1053:   "Delete this message and stay on it."
        !          1054:   (interactive)
        !          1055:   (rmail-set-attribute "deleted" t))
        !          1056: 
        !          1057: (defun rmail-undelete-previous-message ()
        !          1058:   "Back up to deleted message, select it, and undelete it."
        !          1059:   (interactive)
        !          1060:   (let ((msg rmail-current-message))
        !          1061:     (while (and (> msg 0)
        !          1062:                (not (rmail-message-deleted-p msg)))
        !          1063:       (setq msg (1- msg)))
        !          1064:     (if (= msg 0)
        !          1065:        (error "No previous deleted message")
        !          1066:       (if (/= msg rmail-current-message)
        !          1067:          (rmail-show-message msg))
        !          1068:       (rmail-set-attribute "deleted" nil))))
        !          1069: 
        !          1070: (defun rmail-delete-forward (&optional backward)
        !          1071:   "Delete this message and move to next nondeleted one.
        !          1072: Deleted messages stay in the file until the \\[rmail-expunge] command is given.
        !          1073: With prefix argument, delete and move backward."
        !          1074:   (interactive "P")
        !          1075:   (rmail-set-attribute "deleted" t)
        !          1076:   (rmail-next-undeleted-message (if backward -1 1)))
        !          1077: 
        !          1078: (defun rmail-delete-backward ()
        !          1079:   "Delete this message and move to previous nondeleted one.
        !          1080: Deleted messages stay in the file until the \\[rmail-expunge] command is given."
        !          1081:   (interactive)
        !          1082:   (rmail-delete-forward t))
        !          1083: 
        !          1084: (defun rmail-expunge ()
        !          1085:   "Actually erase all deleted messages in the file."
        !          1086:   (interactive)
        !          1087:   (message "Expunging deleted messages...")
        !          1088:   (rmail-maybe-set-message-counters)
        !          1089:   (let* ((omax (- (buffer-size) (point-max)))
        !          1090:         (omin (- (buffer-size) (point-min)))
        !          1091:         (opoint (if (and (> rmail-current-message 0)
        !          1092:                          (= ?D (aref rmail-deleted-vector rmail-current-message)))
        !          1093:                     0 (- (point) (point-min))))
        !          1094:         (messages-head (cons (aref rmail-message-vector 0) nil))
        !          1095:         (messages-tail messages-head)
        !          1096:         (win))
        !          1097:     (unwind-protect
        !          1098:        (save-excursion
        !          1099:          (widen)
        !          1100:          (goto-char (point-min))
        !          1101:          (let ((counter 0)
        !          1102:                (number 1)
        !          1103:                (total rmail-total-messages)
        !          1104:                (new-message-number rmail-current-message)
        !          1105:                (new-summary nil)
        !          1106:                (buffer-read-only nil)
        !          1107:                (messages rmail-message-vector)
        !          1108:                (deleted rmail-deleted-vector)
        !          1109:                (summary rmail-summary-vector))
        !          1110:            (setq rmail-total-messages nil
        !          1111:                  rmail-current-message nil
        !          1112:                  rmail-message-vector nil
        !          1113:                  rmail-deleted-vector nil
        !          1114:                  rmail-summary-vector nil)
        !          1115:            (while (<= number total)
        !          1116:              (if (= (aref deleted number) ?D)
        !          1117:                  (progn
        !          1118:                    (delete-region
        !          1119:                      (marker-position (aref messages number))
        !          1120:                      (marker-position (aref messages (1+ number))))
        !          1121:                    (move-marker (aref messages number) nil)
        !          1122:                    (if (> new-message-number counter)
        !          1123:                        (setq new-message-number (1- new-message-number))))
        !          1124:                (setq counter (1+ counter))
        !          1125:                (setq messages-tail
        !          1126:                      (setcdr messages-tail
        !          1127:                              (cons (aref messages number) nil)))
        !          1128:                (setq new-summary
        !          1129:                      (cons (if (= counter number) (aref summary (1- number)))
        !          1130:                            new-summary)))
        !          1131:              (if (zerop (% (setq number (1+ number)) 20))
        !          1132:                  (message "Expunging deleted messages...%d" number)))
        !          1133:            (setq messages-tail
        !          1134:                  (setcdr messages-tail
        !          1135:                          (cons (aref messages number) nil)))
        !          1136:            (setq rmail-current-message new-message-number
        !          1137:                  rmail-total-messages counter
        !          1138:                  rmail-message-vector (apply 'vector messages-head)
        !          1139:                  rmail-deleted-vector (make-string (1+ counter) ?\ )
        !          1140:                  rmail-summary-vector (vconcat (nreverse new-summary))
        !          1141:                  win t)))
        !          1142:       (message "Expunging deleted messages...done")
        !          1143:       (if (not win)
        !          1144:          (narrow-to-region (- (buffer-size) omin) (- (buffer-size) omax)))
        !          1145:       (rmail-show-message
        !          1146:        (if (zerop rmail-current-message) 1 nil))
        !          1147:       (forward-char opoint))))
        !          1148: 
        !          1149: ;;;; *** Rmail Mailing Commands ***
        !          1150: 
        !          1151: (defun rmail-mail ()
        !          1152:   "Send mail in another window.
        !          1153: While composing the message, use \\[mail-yank-original] to yank the
        !          1154: original message into it."
        !          1155:   (interactive)
        !          1156:   (mail-other-window nil nil nil nil nil (current-buffer)))
        !          1157: 
        !          1158: (defun rmail-continue ()
        !          1159:   "Continue composing outgoing message previously being composed."
        !          1160:   (interactive)
        !          1161:   (mail-other-window t))
        !          1162: 
        !          1163: (defun rmail-reply (just-sender)
        !          1164:   "Reply to the current message.
        !          1165: Normally include CC: to all other recipients of original message;
        !          1166: prefix argument means ignore them.
        !          1167: While composing the reply, use \\[mail-yank-original] to yank the
        !          1168: original message into it."
        !          1169:   (interactive "P")
        !          1170:   ;;>> this gets set even if we abort. Can't do anything about it, though.
        !          1171:   (rmail-set-attribute "answered" t)
        !          1172:   (rmail-display-labels)
        !          1173:   (let (from reply-to cc subject date to message-id resent-reply-to)
        !          1174:     (save-excursion
        !          1175:       (save-restriction
        !          1176:        (widen)
        !          1177:        (goto-char (rmail-msgbeg rmail-current-message))
        !          1178:        (forward-line 1)
        !          1179:        (if (= (following-char) ?0)
        !          1180:            (narrow-to-region
        !          1181:             (progn (forward-line 2)
        !          1182:                    (point))
        !          1183:             (progn (search-forward "\n\n" (rmail-msgend rmail-current-message)
        !          1184:                                    'move)
        !          1185:                    (point)))
        !          1186:          (narrow-to-region (point)
        !          1187:                            (progn (search-forward "\n*** EOOH ***\n")
        !          1188:                                   (beginning-of-line) (point))))
        !          1189:        (setq resent-reply-to (mail-fetch-field "resent-reply-to" t)
        !          1190:              from (mail-fetch-field "from")
        !          1191:              reply-to (or resent-reply-to
        !          1192:                           (mail-fetch-field "reply-to" nil t)
        !          1193:                           from)
        !          1194:              cc (cond (just-sender nil)
        !          1195:                       (resent-reply-to (mail-fetch-field "resent-cc" t))
        !          1196:                       (t (mail-fetch-field "cc" nil t)))
        !          1197:              subject (or (and resent-reply-to
        !          1198:                               (mail-fetch-field "resent-subject" t))
        !          1199:                          (mail-fetch-field "subject"))
        !          1200:              date (cond (resent-reply-to
        !          1201:                          (mail-fetch-field "resent-date" t))
        !          1202:                         ((mail-fetch-field "date")))
        !          1203:              to (cond (resent-reply-to
        !          1204:                        (mail-fetch-field "resent-to" t))
        !          1205:                       ((mail-fetch-field "to" nil t))
        !          1206:                       ;((mail-fetch-field "apparently-to")) ack gag barf
        !          1207:                       (t ""))
        !          1208:              message-id (cond (resent-reply-to
        !          1209:                                (mail-fetch-field "resent-message-id" t))
        !          1210:                               ((mail-fetch-field "message-id"))))))
        !          1211:     (and subject
        !          1212:         (string-match "\\`Re: " subject)
        !          1213:         (setq subject (substring subject 4)))
        !          1214:     (mail-other-window nil
        !          1215:       (mail-strip-quoted-names reply-to)
        !          1216:       subject
        !          1217:       (rmail-make-in-reply-to-field from date message-id)
        !          1218:       (if just-sender
        !          1219:          nil
        !          1220:        (let* ((cc-list (rmail-dont-reply-to
        !          1221:                          (mail-strip-quoted-names
        !          1222:                            (if (null cc) to (concat to ", " cc))))))
        !          1223:          (if (string= cc-list "") nil cc-list)))
        !          1224:       (current-buffer))))
        !          1225: 
        !          1226: (defun rmail-make-in-reply-to-field (from date message-id)
        !          1227:   (if mail-use-rfc822 (require 'rfc822))
        !          1228:   (let (field)
        !          1229:     (if (and mail-use-rfc822 from)
        !          1230:        (let ((tem (car (rfc822-addresses from))))
        !          1231:          (and message-id
        !          1232:               (setq field (if (string-match
        !          1233:                                 (regexp-quote
        !          1234:                                   (if (string-match "@[^@]*\\'" tem)
        !          1235:                                       (substring tem
        !          1236:                                                  0 (match-beginning 0))
        !          1237:                                       tem))
        !          1238:                                 message-id)
        !          1239:                               message-id
        !          1240:                               (concat message-id " \"" tem "\""))
        !          1241:                     message-id nil date nil))
        !          1242:          (or field
        !          1243:              (setq field (prin1-to-string tem))))
        !          1244: ;      (if message-id
        !          1245: ;          (setq field message-id message-id nil date nil)
        !          1246: ;          (setq field (car (rfc882-addresses from))))
        !          1247:        )
        !          1248:     (or field
        !          1249:        (not from)
        !          1250:        ;; Compute the sender for the in-reply-to; prefer full name.
        !          1251:        (let* ((stop-pos (string-match "  *at \\|  *@ \\|  *<" from))
        !          1252:               (start-pos (if stop-pos 0
        !          1253:                            ;;>> this loses on nested ()'s
        !          1254:                            (let ((pos (string-match " *(" from)))
        !          1255:                              (if (not pos) nil
        !          1256:                                (setq stop-pos (string-match ")" from pos))
        !          1257:                                (if (zerop pos) 0 (+ 2 pos)))))))
        !          1258:          (setq field (if stop-pos
        !          1259:                          (substring from start-pos stop-pos)
        !          1260:                          from))))
        !          1261:     (if date (setq field (concat field "'s message of " date)))
        !          1262:     (if message-id (setq field (concat field " " message-id)))
        !          1263:     field))
        !          1264: 
        !          1265: (defun rmail-forward ()
        !          1266:   "Forward the current message to another user."
        !          1267:   (interactive)
        !          1268:   ;;>> this gets set even if we abort. Can't do anything about it, though.
        !          1269:   (rmail-set-attribute "forwarded" t)
        !          1270:   (let ((forward-buffer (current-buffer))
        !          1271:        (subject (concat "["
        !          1272:                         (mail-strip-quoted-names (mail-fetch-field "From"))
        !          1273:                         ": " (or (mail-fetch-field "Subject") "") "]")))
        !          1274:     ;; If only one window, use it for the mail buffer.
        !          1275:     ;; Otherwise, use another window for the mail buffer
        !          1276:     ;; so that the Rmail buffer remains visible
        !          1277:     ;; and sending the mail will get back to it.
        !          1278:     (if (if (one-window-p t)
        !          1279:            (mail nil nil subject)
        !          1280:          (mail-other-window nil nil subject))
        !          1281:        (save-excursion
        !          1282:          (goto-char (point-max))
        !          1283:          (forward-line 1)
        !          1284:          (insert-buffer forward-buffer)))))
        !          1285: 
        !          1286: ;;;; *** Rmail Specify Inbox Files ***
        !          1287: 
        !          1288: (autoload 'set-rmail-inbox-list "rmailmsc"
        !          1289:   "Set the inbox list of the current RMAIL file to FILE-NAME.
        !          1290: This may be a list of file names separated by commas.
        !          1291: If FILE-NAME is empty, remove any inbox list."
        !          1292:   t)
        !          1293: 
        !          1294: ;;;; *** Rmail Commands for Labels ***
        !          1295: 
        !          1296: (autoload 'rmail-add-label "rmailkwd"
        !          1297:   "Add LABEL to labels associated with current RMAIL message.
        !          1298: Completion is performed over known labels when reading."
        !          1299:   t)
        !          1300: 
        !          1301: (autoload 'rmail-kill-label "rmailkwd"
        !          1302:   "Remove LABEL from labels associated with current RMAIL message.
        !          1303: Completion is performed over known labels when reading."
        !          1304:   t)
        !          1305: 
        !          1306: (autoload 'rmail-next-labeled-message "rmailkwd"
        !          1307:   "Show next message with LABEL.  Defaults to last label used.
        !          1308: With prefix argument N moves forward N messages with this label."
        !          1309:   t)
        !          1310: 
        !          1311: (autoload 'rmail-previous-labeled-message "rmailkwd"
        !          1312:   "Show previous message with LABEL.  Defaults to last label used.
        !          1313: With prefix argument N moves backward N messages with this label."
        !          1314:   t)
        !          1315: 
        !          1316: ;;;; *** Rmail Edit Mode ***
        !          1317: 
        !          1318: (autoload 'rmail-edit-current-message "rmailedit"
        !          1319:   "Edit the contents of the current message"
        !          1320:   t)
        !          1321: 
        !          1322: ;;;; *** Rmail Summary Mode ***
        !          1323: 
        !          1324: (autoload 'rmail-summary "rmailsum"
        !          1325:   "Display a summary of all messages, one line per message."
        !          1326:   t)
        !          1327: 
        !          1328: (autoload 'rmail-summary-by-labels "rmailsum"
        !          1329:   "Display a summary of all messages with one or more LABELS.
        !          1330: LABELS should be a string containing the desired labels, separated by commas."
        !          1331:   t)
        !          1332: 
        !          1333: (autoload 'rmail-summary-by-recipients "rmailsum"
        !          1334:   "Display a summary of all messages with the given RECIPIENTS.
        !          1335: Normally checks the To, From and Cc fields of headers;
        !          1336: but if PRIMARY-ONLY is non-nil (prefix arg given),
        !          1337:  only look in the To and From fields.
        !          1338: RECIPIENTS is a string of names separated by commas."
        !          1339:   t)
        !          1340: 
        !          1341: ;;;; *** Rmail output messages to files ***
        !          1342: 
        !          1343: (autoload 'rmail-output-to-rmail-file "rmailout"
        !          1344:   "Append the current message to an Rmail file named FILE-NAME.
        !          1345: If the file does not exist, ask if it should be created.
        !          1346: If file is being visited, the message is appended to the Emacs
        !          1347: buffer visiting that file."
        !          1348:   t)
        !          1349: 
        !          1350: (autoload 'rmail-output "rmailout"
        !          1351:   "Append this message to Unix mail file named FILE-NAME."
        !          1352:   t)
        !          1353: 
        !          1354: ;;;; *** Rmail undigestification ***
        !          1355: 
        !          1356: (autoload 'undigestify-rmail-message "undigest"
        !          1357:   "Break up a digest message into its constituent messages.
        !          1358: Leaves original message, deleted, before the undigestified messages."
        !          1359:   t)

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.