Mercurial > hg > xemacs-beta
diff lisp/tm/tm-tar.el @ 4:b82b59fe008d r19-15b3
Import from CVS: tag r19-15b3
author | cvs |
---|---|
date | Mon, 13 Aug 2007 08:46:56 +0200 |
parents | |
children | 4b173ad71786 |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lisp/tm/tm-tar.el Mon Aug 13 08:46:56 2007 +0200 @@ -0,0 +1,344 @@ +;;; +;;; $Id: tm-tar.el,v 1.1.1.1 1996/12/18 03:55:32 steve Exp $ +;;; +;;; tm-tar.el +;;; +;;; Internal viewer for +;;; - application/x-tar +;;; - application/x-gzip, type="tar" +;;; - aplication/octet-stream, type="tar" +;;; - aplication/octet-stream, type="tar+gzip" +;;; +;;; by Hiroshi Ueno <zodiac@ibm.net> +;;; modified by Tomohiko Morioka <morioka@jaist.ac.jp> +;;; + +;;; @ required modules +;;; + +(require 'emu) +(require 'tm-view) + +;;; @ constants +;;; + +(defconst tm-tar/list-buffer "*tm-tar/List*") +(defconst tm-tar/view-buffer "*tm-tar/View*") +(defconst tm-tar/file-search-regexp "[0-9]+\:[0-9\:]+[ ]+[0-9]+[ ]+") +(defconst tm-tar/popup-menu-title "Action Menu") + +;;; @ variables +;;; + +(defvar tm-tar/tar-program "gtar") +(defvar tm-tar/tar-decompress-arg '("-z")) +(defvar tm-tar/gzip-program "gzip") +(defvar tm-tar/mmencode-program "mmencode") +(defvar tm-tar/uudecode-program "uudecode") + +(defvar tm-tar/popup-menu-items + '(("View File" . tm-tar/view-file) + ("Key Help" . tm-tar/helpful-message) + ("Quit tm-tar Mode" . exit-recursive-edit) + )) + +(cond ((string-match "XEmacs\\|Lucid" emacs-version) + (defvar tm-tar/popup-menu + (cons tm-tar/popup-menu-title + (mapcar (function + (lambda (item) + (vector (car item)(cdr item) t) + )) + tm-tar/popup-menu-items))) + + (defun tm-tar/mouse-button-2 (event) + (popup-menu tm-tar/popup-menu) + ) + ) + ((>= emacs-major-version 19) + (defun tm-tar/mouse-button-2 (event) + (let ((menu + (cons tm-tar/popup-menu-title + (list (cons "Menu Items" tm-tar/popup-menu-items)) + ))) + (let ((func (x-popup-menu event menu))) + (if func + (funcall func) + )) + )) + )) + +(defvar tm-tar/tar-mode-map nil) +(if tm-tar/tar-mode-map + nil + (setq tm-tar/tar-mode-map (make-keymap)) + (suppress-keymap tm-tar/tar-mode-map) + (define-key tm-tar/tar-mode-map "\C-c" 'exit-recursive-edit) + (define-key tm-tar/tar-mode-map "q" 'exit-recursive-edit) + (define-key tm-tar/tar-mode-map "n" 'tm-tar/next-line) + (define-key tm-tar/tar-mode-map " " 'tm-tar/next-line) + (define-key tm-tar/tar-mode-map "\C-m" 'tm-tar/next-line) + (define-key tm-tar/tar-mode-map "p" 'tm-tar/previous-line) + (define-key tm-tar/tar-mode-map "\177" 'tm-tar/previous-line) + (define-key tm-tar/tar-mode-map "\C-\M-m" 'tm-tar/previous-line) + (define-key tm-tar/tar-mode-map "v" 'tm-tar/view-file) + (define-key tm-tar/tar-mode-map "\C-h" 'Helper-help) + (define-key tm-tar/tar-mode-map "?" 'tm-tar/helpful-message) + (if mouse-button-2 + (define-key tm-tar/tar-mode-map + mouse-button-2 'tm:button-dispatcher) + ) + ) + +;;; @@ tm-tar mode functions +;;; + +(defun tm-tar/tar-mode (&optional prev-buf) + "Major mode for listing the contents of a tar archive file." + (unwind-protect + (let ((buffer-read-only t) + (mode-name "tm-tar") + (mode-line-buffer-identification '("%17b")) + ) + (goto-char (point-min)) + (tm-tar/move-to-filename) + (catch 'tm-tar/tar-mode (tm-tar/command-loop)) + ) + (if prev-buf + (switch-to-buffer prev-buf) + ) + )) + +(defun tm-tar/command-loop () + (let ((old-local-map (current-local-map)) + ) + (unwind-protect + (progn + (use-local-map tm-tar/tar-mode-map) + (tm-tar/helpful-message) + (recursive-edit) + ) + (save-excursion + (use-local-map old-local-map) + )) + )) + +(defun tm-tar/next-line () + (interactive) + (next-line 1) + (tm-tar/move-to-filename) + ) + +(defun tm-tar/previous-line () + (interactive) + (previous-line 1) + (tm-tar/move-to-filename) + ) + +(defun tm-tar/view-file () + (interactive) + (let ((name (tm-tar/get-filename)) + ) + (save-excursion + (switch-to-buffer tm-tar/view-buffer) + (setq buffer-read-only nil) + (erase-buffer) + (message "Reading a file from an archive. Please wait...") + (apply 'call-process tm-tar/tar-program + nil t nil (append tm-tar/view-args (list name))) + (goto-char (point-min)) + ) + (view-buffer tm-tar/view-buffer) + )) + +(defun tm-tar/get-filename () + (let (eol) + (save-excursion + (end-of-line) + (setq eol (point)) + (beginning-of-line) + (save-excursion + (if (re-search-forward "^d" eol t) + (error "Cannot view a directory")) + ) + (if (re-search-forward tm-tar/file-search-regexp eol t) + (progn (let ((beg (point)) + ) + (skip-chars-forward "^ \n") + (buffer-substring beg (point)) + )) + (error "No file on this line") + )) + )) + +(defun tm-tar/move-to-filename () + (let ((eol (progn (end-of-line) (point))) + ) + (beginning-of-line) + (re-search-forward tm-tar/file-search-regexp eol t) + )) + +(defun tm-tar/set-properties () + (if mouse-button-2 + (let ((beg (point-min)) + (end (point-max)) + ) + (goto-char beg) + (save-excursion + (while (re-search-forward tm-tar/file-search-regexp end t) + (tm:add-button (point) + (progn + (end-of-line) + (point)) + 'tm-tar/view-file) + )) + ))) + +(defun tm-tar/helpful-message () + (interactive) + (message "Type %s, %s, %s, %s, %s, %s." + (substitute-command-keys "\\[Helper-help] for help") + (substitute-command-keys "\\[tm-tar/helpful-message] for keys") + (substitute-command-keys "\\[tm-tar/next-line] to next") + (substitute-command-keys "\\[tm-tar/previous-line] to prev") + (substitute-command-keys "\\[tm-tar/view-file] to view") + (substitute-command-keys "\\[exit-recursive-edit] to quit") + )) + +(defun tm-tar/y-or-n-p (prompt) + (prog1 + (y-or-n-p prompt) + (message "") + )) + +;;; @@ tar message decoder +;; + +(defun mime/decode-message/tar (beg end cal) + (if (tm-tar/y-or-n-p "Do you want to enter tm-tar mode? ") + (let ((coding (cdr (assoc 'encoding cal))) + (cur-buf (current-buffer)) + (tm-tar/tar-file-name (expand-file-name (concat (make-temp-name + (expand-file-name "tm" mime/tmp-dir)) ".tar"))) + (tm-tar/tmp-file-name (expand-file-name (make-temp-name + (expand-file-name "tm" mime/tmp-dir)))) + new-buf + ) + (find-file tm-tar/tmp-file-name) + (setq new-buf (current-buffer)) + (setq buffer-read-only nil) + (erase-buffer) + (save-excursion + (set-buffer cur-buf) + (goto-char beg) + (re-search-forward "^$") + (append-to-buffer new-buf (+ (match-end 0) 1) end) + ) + (if (member coding mime-viewer/uuencode-encoding-name-list) + (progn + (goto-char (point-min)) + (if (re-search-forward "^begin [0-9]+ " nil t) + (progn + (kill-line) + (insert tm-tar/tar-file-name) + ) + (progn + (set-buffer-modified-p nil) + (kill-buffer new-buf) + (error "uuencode file signature was not found") + )))) + (save-buffer) + (kill-buffer new-buf) + (message "Listing the contents of an archive. Please wait...") + (cond ((string-equal coding "base64") + (call-process tm-tar/mmencode-program nil nil nil "-u" + "-o" tm-tar/tar-file-name tm-tar/tmp-file-name) + ) + ((string-equal coding "quoted-printable") + (call-process tm-tar/mmencode-program nil nil nil "-u" "-q" + "-o" tm-tar/tar-file-name tm-tar/tmp-file-name) + ) + ((member coding mime-viewer/uuencode-encoding-name-list) + (call-process tm-tar/uudecode-program nil nil nil + tm-tar/tmp-file-name) + ) + (t + (copy-file tm-tar/tmp-file-name tm-tar/tar-file-name t) + )) + (delete-file tm-tar/tmp-file-name) + (setq tm-tar/list-args (list "-tvf" tm-tar/tar-file-name)) + (setq tm-tar/view-args (list "-xOf" tm-tar/tar-file-name)) + (if (eq 0 (call-process tm-tar/gzip-program + nil nil nil "-t" tm-tar/tar-file-name)) + (progn + (setq tm-tar/list-args + (append tm-tar/tar-decompress-arg tm-tar/list-args)) + (setq tm-tar/view-args + (append tm-tar/tar-decompress-arg tm-tar/view-args)) + )) + (switch-to-buffer tm-tar/view-buffer) + (switch-to-buffer tm-tar/list-buffer) + (setq buffer-read-only nil) + (erase-buffer) + (apply 'call-process tm-tar/tar-program + nil t nil tm-tar/list-args) + (if mouse-button-2 + (progn + (make-local-variable 'tm:mother-button-dispatcher) + (setq tm:mother-button-dispatcher 'tm-tar/mouse-button-2) + )) + (tm-tar/set-properties) + (tm-tar/tar-mode mime::article/preview-buffer) + (kill-buffer tm-tar/view-buffer) + (kill-buffer tm-tar/list-buffer) + (delete-file tm-tar/tar-file-name) + ) + )) + +;;; @@ program/buffer coding system +;;; + +(cond ((boundp 'MULE) + (define-program-coding-system tm-tar/view-buffer nil *autoconv*) + ) + ((boundp 'NEMACS) + (define-program-kanji-code tm-tar/view-buffer nil 1) + )) + +;;; @@ message types to use tm-tar +;;; + +(set-atype 'mime/content-decoding-condition + '((type . "application/octet-stream") + (method . mime/decode-message/tar) + (mode . "play") ("type" . "tar") + )) + +(set-atype 'mime/content-decoding-condition + '((type . "application/octet-stream") + (method . mime/decode-message/tar) + (mode . "play") ("type" . "tar+gzip") + )) + +(set-atype 'mime/content-decoding-condition + '((type . "application/x-gzip") + (method . mime/decode-message/tar) + (mode . "play") ("type" . "tar") + )) + +(set-atype 'mime/content-decoding-condition + '((type . "application/x-tar") + (method . mime/decode-message/tar) + (mode . "play") + )) + +;;; @ end +;;; + +(provide 'tm-tar) + +;;; Local Variables: +;;; mode: emacs-lisp +;;; mode: outline-minor +;;; outline-regexp: ";;; @+\\|(......" +;;; End: