• Home
  • History
  • Annotate
  • Raw
  • Download
  • only in /macosx-10.10.1/emacs-93/emacs/lisp/

Lines Matching +defs:tar +defs:mode

0 ;;; tar-mode.el --- simple editing of tar files from GNU emacs
30 ;; This package attempts to make dealing with Unix 'tar' archives easier.
31 ;; When this code is loaded, visiting a file whose name ends in '.tar' will
36 ;; It is also possible to delete sub-files from within the tar file and write
39 ;; string of tar-mode for more info.
41 ;; This code now understands the extra fields that GNU tar adds to tar files.
47 ;; (setq auto-mode-alist (cons '("\\.Z$" . uncompress-while-visiting)
48 ;; auto-mode-alist))
50 ;; Do not attempt to use tar-mode.el with crypt.el, you will lose.
56 ;; o It's not possible to add a NEW file to a tar archive; not that
67 ;; o Sometimes (but not always) reverting the tar-file buffer does not
68 ;; re-grind the listing, and you are staring at the binary tar data.
72 ;; o Tar-mode interacts poorly with crypt.el and zcat.el because the tar
76 ;; might be a problem if the tar write-file-hook does not come *first* on
84 ;; Why does tar-mode edit the file itself instead of using tar?
86 ;; That means that you can edit tar files which you don't have room for
89 ;; I don't know about recent features in gnu tar, but old versions of tar
90 ;; can't replace a file in the middle of a tar file with a new version.
91 ;; Tar-mode can. I don't think tar can do things like chmod the subfiles.
98 (defgroup tar nil
99 "Simple editing of tar files."
100 :prefix "tar-"
103 (defcustom tar-anal-blocksize 20
104 "The blocksize of tar files written by Emacs, or nil, meaning don't care.
105 The blocksize of a tar file is not really the size of the blocks; rather, it is
108 matter much. The only noticeable difference is that if a tar file does not
109 have a blocksize of 20, tar will tell you that; all this really controls is
110 how many null padding bytes go on the end of the tar file."
112 :group 'tar)
114 (defcustom tar-update-datestamp nil
115 "Non-nil means Tar mode should play fast and loose with sub-file datestamps.
116 If this is true, then editing and saving a tar file entry back into its
117 tar file will update its datestamp. If false, the datestamp is unchanged.
119 in a tar archive has been changed, but it is bad for the same reason that
120 editing a file in the tar archive at all is bad - the changed version of
123 :group 'tar)
125 (defcustom tar-mode-show-date nil
126 "Non-nil means Tar mode should show the date/time of each subfile.
129 :group 'tar)
131 (defvar tar-parse-info nil)
133 (defvar tar-header-offset nil)
134 (defvar tar-superior-buffer nil)
135 (defvar tar-superior-descriptor nil)
136 (defvar tar-subfile-mode nil)
138 (put 'tar-parse-info 'permanent-local t)
139 (put 'tar-header-offset 'permanent-local t)
140 (put 'tar-superior-buffer 'permanent-local t)
141 (put 'tar-superior-descriptor 'permanent-local t)
144 (defmacro tar-setf (form val)
161 (defmacro make-tar-header (name mode uid git size date ck lt ln
163 (list 'vector name mode uid git size date ck lt ln
166 (defmacro tar-header-name (x) (list 'aref x 0))
167 (defmacro tar-header-mode (x) (list 'aref x 1))
168 (defmacro tar-header-uid (x) (list 'aref x 2))
169 (defmacro tar-header-gid (x) (list 'aref x 3))
170 (defmacro tar-header-size (x) (list 'aref x 4))
171 (defmacro tar-header-date (x) (list 'aref x 5))
172 (defmacro tar-header-checksum (x) (list 'aref x 6))
173 (defmacro tar-header-link-type (x) (list 'aref x 7))
174 (defmacro tar-header-link-name (x) (list 'aref x 8))
175 (defmacro tar-header-magic (x) (list 'aref x 9))
176 (defmacro tar-header-uname (x) (list 'aref x 10))
177 (defmacro tar-header-gname (x) (list 'aref x 11))
178 (defmacro tar-header-dmaj (x) (list 'aref x 12))
179 (defmacro tar-header-dmin (x) (list 'aref x 13))
181 (defmacro make-tar-desc (data-start tokens)
184 (defmacro tar-desc-data-start (x) (list 'car x))
185 (defmacro tar-desc-tokens (x) (list 'cdr x))
187 (defconst tar-name-offset 0)
188 (defconst tar-mode-offset (+ tar-name-offset 100))
189 (defconst tar-uid-offset (+ tar-mode-offset 8))
190 (defconst tar-gid-offset (+ tar-uid-offset 8))
191 (defconst tar-size-offset (+ tar-gid-offset 8))
192 (defconst tar-time-offset (+ tar-size-offset 12))
193 (defconst tar-chk-offset (+ tar-time-offset 12))
194 (defconst tar-linkp-offset (+ tar-chk-offset 8))
195 (defconst tar-link-offset (+ tar-linkp-offset 1))
196 ;;; GNU-tar specific slots.
197 (defconst tar-magic-offset (+ tar-link-offset 100))
198 (defconst tar-uname-offset (+ tar-magic-offset 8))
199 (defconst tar-gname-offset (+ tar-uname-offset 32))
200 (defconst tar-dmaj-offset (+ tar-gname-offset 32))
201 (defconst tar-dmin-offset (+ tar-dmaj-offset 8))
202 (defconst tar-end-offset (+ tar-dmin-offset 8))
204 (defun tar-header-block-tokenize (string)
205 "Return a `tar-header' structure.
206 This is a list of name, mode, uid, gid, size,
212 (let* ((name-end (1- tar-mode-offset))
213 (link-end (1- tar-magic-offset))
214 (uname-end (1- tar-gname-offset))
215 (gname-end (1- tar-dmaj-offset))
216 (link-p (aref string tar-linkp-offset))
217 (magic-str (substring string tar-magic-offset (1- tar-uname-offset)))
221 (when (string-match nulsexp string tar-name-offset)
223 (when (string-match nulsexp string tar-link-offset)
225 (when (string-match nulsexp string tar-uname-offset)
227 (when (string-match nulsexp string tar-gname-offset)
229 (setq name (substring string tar-name-offset name-end)
233 (setq linkname (substring string tar-link-offset link-end))
246 (make-tar-header
248 (tar-parse-octal-integer string tar-mode-offset tar-uid-offset)
249 (tar-parse-octal-integer string tar-uid-offset tar-gid-offset)
250 (tar-parse-octal-integer string tar-gid-offset tar-size-offset)
251 (tar-parse-octal-integer string tar-size-offset tar-time-offset)
252 (tar-parse-octal-long-integer string tar-time-offset tar-chk-offset)
253 (tar-parse-octal-integer string tar-chk-offset tar-linkp-offset)
257 (and uname-valid-p (substring string tar-uname-offset uname-end))
258 (and uname-valid-p (substring string tar-gname-offset gname-end))
259 (tar-parse-octal-integer string tar-dmaj-offset tar-dmin-offset)
260 (tar-parse-octal-integer string tar-dmin-offset tar-end-offset)
262 (t 'empty-tar-block)))
265 (defun tar-parse-octal-integer (string &optional start end)
277 (defun tar-parse-octal-long-integer (string &optional start end)
292 (defun tar-parse-octal-integer-safe (string)
298 (tar-parse-octal-integer string))
301 (defun tar-header-block-checksum (string)
302 "Compute and return a tar-acceptable checksum for this block."
303 (let* ((chk-field-start tar-chk-offset)
318 (defun tar-header-block-check-checksum (hblock desired-checksum file-name)
320 (if (not (= desired-checksum (tar-header-block-checksum hblock)))
323 (defun tar-clip-time-string (time)
327 (defun tar-grind-file-mode (mode)
329 MODE should be an integer which is a file mode value."
331 (if (zerop (logand 256 mode)) ?- ?r)
332 (if (zerop (logand 128 mode)) ?- ?w)
333 (if (zerop (logand 1024 mode)) (if (zerop (logand 64 mode)) ?- ?x) ?s)
334 (if (zerop (logand 32 mode)) ?- ?r)
335 (if (zerop (logand 16 mode)) ?- ?w)
336 (if (zerop (logand 2048 mode)) (if (zerop (logand 8 mode)) ?- ?x) ?s)
337 (if (zerop (logand 4 mode)) ?- ?r)
338 (if (zerop (logand 2 mode)) ?- ?w)
339 (if (zerop (logand 1 mode)) ?- ?x)))
341 (defun tar-header-block-summarize (tar-hblock &optional mod-p)
342 "Return a line similar to the output of `tar -vtf'."
343 (let ((name (tar-header-name tar-hblock))
344 (mode (tar-header-mode tar-hblock))
345 (uid (tar-header-uid tar-hblock))
346 (gid (tar-header-gid tar-hblock))
347 (uname (tar-header-uname tar-hblock))
348 (gname (tar-header-gname tar-hblock))
349 (size (tar-header-size tar-hblock))
350 (time (tar-header-date tar-hblock))
351 ;; (ck (tar-header-checksum tar-hblock))
352 (type (tar-header-link-type tar-hblock))
353 (link-name (tar-header-link-name tar-hblock)))
370 (tar-grind-file-mode mode)
374 (if tar-mode-show-date (tar-clip-time-string time) "")
382 (defun tar-untar-buffer ()
383 "Extract all archive members in the tar-file into the current directory."
390 (dolist (descriptor tar-parse-info)
391 (let* ((tokens (tar-desc-tokens descriptor))
392 (name (tar-header-name tokens))
394 (start (+ (tar-desc-data-start descriptor)
395 (- tar-header-offset (point-min))))
396 (end (+ start (tar-header-size tokens))))
403 (set-file-modes name (tar-header-mode tokens))))))
406 (defun tar-summarize-buffer ()
407 "Parse the contents of the tar file in the current buffer.
416 (make-progress-reporter "Parsing tar file..."
420 (not (eq 'empty-tar-block
422 (tar-header-block-tokenize
426 (if (eq (tar-header-link-type tokens) 20)
429 (let ((size (tar-header-size tokens)))
432 (tar-header-name tokens) size))
435 ;(tar-header-block-check-checksum
436 ; hblock (tar-header-block-checksum hblock)
437 ; (tar-header-name tokens))
439 (push (make-tar-desc pos tokens) result)
441 (and (null (tar-header-link-type tokens))
447 (make-local-variable 'tar-parse-info)
448 (setq tar-parse-info (nreverse result))
449 ;; A tar file should end with a block or two of nulls,
451 (if (eq tokens 'empty-tar-block)
453 (message "Warning: premature EOF parsing tar file")))
457 ;; Collect summary lines and insert them all at once since tar files
461 (lambda (tar-desc)
462 (tar-header-block-summarize (tar-desc-tokens tar-desc)))
463 tar-parse-info
467 (set (make-local-variable 'tar-header-offset) (position-bytes (point)))
472 (defvar tar-mode-map
475 (define-key map " " 'tar-next-line)
476 (define-key map "C" 'tar-copy)
477 (define-key map "d" 'tar-flag-deleted)
478 (define-key map "\^D" 'tar-flag-deleted)
479 (define-key map "e" 'tar-extract)
480 (define-key map "f" 'tar-extract)
481 (define-key map "\C-m" 'tar-extract)
482 (define-key map [mouse-2] 'tar-mouse-extract)
484 (define-key map "h" 'describe-mode)
485 (define-key map "n" 'tar-next-line)
486 (define-key map "\^N" 'tar-next-line)
487 (define-key map [down] 'tar-next-line)
488 (define-key map "o" 'tar-extract-other-window)
489 (define-key map "p" 'tar-previous-line)
491 (define-key map "\^P" 'tar-previous-line)
492 (define-key map [up] 'tar-previous-line)
493 (define-key map "R" 'tar-rename-entry)
494 (define-key map "u" 'tar-unflag)
495 (define-key map "v" 'tar-view)
496 (define-key map "x" 'tar-expunge)
497 (define-key map "\177" 'tar-unflag-backwards)
498 (define-key map "E" 'tar-extract-other-window)
499 (define-key map "M" 'tar-chmod-entry)
500 (define-key map "G" 'tar-chgrp-entry)
501 (define-key map "O" 'tar-chown-entry)
512 '("View This File" . tar-view))
514 '("Display in Other Window" . tar-display-other-window))
516 '("Find in Other Window" . tar-extract-other-window))
518 '("Find This File" . tar-extract))
524 '("Unmark All" . tar-clear-modification-flags))
526 '("Flag" . tar-flag-deleted))
528 '("Unflag" . tar-unflag))
534 '("Change Owner..." . tar-chown-entry))
536 '("Change Group..." . tar-chgrp-entry))
538 '("Change Mode..." . tar-chmod-entry))
540 '("Rename to..." . tar-rename-entry))
542 '("Copy to..." . tar-copy))
544 '("Expunge Marked Files" . tar-expunge))
547 "Local keymap for Tar mode listings.")
551 ;; tar mode is suitable only for specially formatted data.
552 (put 'tar-mode 'mode-class 'special)
553 (put 'tar-subfile-mode 'mode-class 'special)
556 (define-derived-mode tar-mode nil "Tar"
557 "Major mode for viewing a tar file as a dired-like listing of its contents.
560 Type `e' to pull a file out of the tar file and into its own buffer;
561 or click mouse-2 on the file's line in the Tar mode buffer.
562 Type `c' to copy an entry from the tar file into another file on disk.
566 saved back into the tar-file buffer; in this way you can edit a file
567 inside of a tar archive without extracting it and re-archiving it.
569 See also: variables `tar-update-datestamp' and `tar-anal-blocksize'.
570 \\{tar-mode-map}"
572 ;; mode on and off. You can corrupt things that way.
575 (make-local-variable 'tar-header-offset)
576 (make-local-variable 'tar-parse-info)
578 (set (make-local-variable 'revert-buffer-function) 'tar-mode-revert)
583 (auto-save-mode 0)
584 (set (make-local-variable 'write-contents-functions) '(tar-mode-write-file))
587 (if (and (boundp 'tar-header-offset) tar-header-offset)
588 (narrow-to-region (point-min) (byte-to-position tar-header-offset))
589 (tar-summarize-buffer)
590 (tar-next-line 0)))
593 (defun tar-subfile-mode (p)
594 "Minor mode for editing an element of a tar-file.
595 This mode arranges for \"saving\" this buffer to write the data
596 into the tar-file buffer that it came from. The changes will actually
597 appear on disk when you save the tar-file's buffer."
599 (or (and (boundp 'tar-superior-buffer) tar-superior-buffer)
600 (error "This buffer is not an element of a tar file"))
601 ;; Don't do this, because it is redundant and wastes mode line space.
602 ;; (or (assq 'tar-subfile-mode minor-mode-alist)
603 ;; (setq minor-mode-alist (append minor-mode-alist
604 ;; (list '(tar-subfile-mode " TarFile")))))
605 (make-local-variable 'tar-subfile-mode)
606 (setq tar-subfile-mode
608 (not tar-subfile-mode)
610 (cond (tar-subfile-mode
611 (add-hook 'write-file-functions 'tar-subfile-save-buffer nil t)
613 (auto-save-mode -1)
615 (run-hooks 'tar-subfile-mode-hook))
617 (remove-hook 'write-file-functions 'tar-subfile-save-buffer t))))
621 (defun tar-mode-revert (&optional no-auto-save no-confirm)
623 (old-offset tar-header-offset)
625 (setq tar-header-offset nil)
630 (tar-mode)))
632 ;; put back the old value of tar-header-offset.
634 (setq tar-header-offset old-offset)))))
637 (defun tar-next-line (arg)
641 (if (eobp) nil (forward-char (if tar-mode-show-date 54 36))))
643 (defun tar-previous-line (arg)
646 (tar-next-line (- arg)))
648 (defun tar-current-descriptor (&optional noerror)
649 "Return the tar-descriptor of the current line, or signals an error."
653 tar-parse-info)
656 (error "This line does not describe a tar-file entry"))))
658 (defun tar-get-descriptor ()
659 (let* ((descriptor (tar-current-descriptor))
660 (tokens (tar-desc-tokens descriptor))
661 (size (tar-header-size tokens))
662 (link-p (tar-header-link-type tokens)))
666 ((eq link-p 20) "tar directory header")
675 (defun tar-mouse-extract (event)
676 "Extract a file whose tar directory line you click on."
683 (tar-get-descriptor)))
686 (tar-extract))
688 (defun tar-file-name-handler (op &rest args)
689 "Helper function for `tar-extract'."
694 (defun tar-extract (&optional other-window-p)
695 "In Tar mode, extract this entry of the tar file into its own buffer."
698 (descriptor (tar-get-descriptor))
699 (tokens (tar-desc-tokens descriptor))
700 (name (tar-header-name tokens))
701 (size (tar-header-size tokens))
702 (start (+ (tar-desc-data-start descriptor)
703 (- tar-header-offset (point-min))))
705 (let* ((tar-buffer (current-buffer))
706 (tar-buffer-multibyte enable-multibyte-characters)
733 (insert-buffer-substring tar-buffer start end)
735 (insert-buffer-substring tar-buffer start end))
756 '(("" . tar-file-name-handler))
788 (set-buffer tar-buffer)
790 (normal-mode) ; pick a mode.
792 (make-local-variable 'tar-superior-buffer)
793 (make-local-variable 'tar-superior-descriptor)
794 (setq tar-superior-buffer tar-buffer)
795 (setq tar-superior-descriptor descriptor)
798 (tar-subfile-mode 1))
799 (set-buffer tar-buffer))
800 (narrow-to-region (point-min) tar-header-offset)
801 (set-buffer-multibyte tar-buffer-multibyte)))
811 (defun tar-extract-other-window ()
812 "In Tar mode, find this entry of the tar file in another window."
814 (tar-extract t))
816 (defun tar-display-other-window ()
817 "In Tar mode, display this entry of the tar file in another window."
819 (tar-extract 'display))
821 (defun tar-view ()
822 "In Tar mode, view the tar file entry on this line."
824 (tar-extract 'view))
827 (defun tar-read-file-name (&optional prompt)
831 (tar-header-name (tar-desc-tokens
832 (tar-current-descriptor)))))
847 (defun tar-copy (&optional to-file)
848 "In Tar mode, extract this entry of the tar file into a file on disk.
850 the current tar-entry."
851 (interactive (list (tar-read-file-name)))
852 (let* ((descriptor (tar-get-descriptor))
853 (tokens (tar-desc-tokens descriptor))
854 (name (tar-header-name tokens))
855 (size (tar-header-size tokens))
856 (start (+ (tar-desc-data-start descriptor)
857 (- tar-header-offset (point-min))))
878 (message "Copied tar entry %s to %s" name to-file)))
880 (defun tar-flag-deleted (p &optional unflag)
881 "In Tar mode, mark this sub-file to be deleted from the tar file.
886 (if (tar-current-descriptor unflag) ; barf if we're not on an entry-line.
893 (defun tar-unflag (p)
894 "In Tar mode, un-mark this sub-file if it is marked to be deleted.
897 (tar-flag-deleted p t))
899 (defun tar-unflag-backwards (p)
900 "In Tar mode, un-mark this sub-file if it is marked to be deleted.
903 (tar-flag-deleted (- p) t))
907 (defun tar-expunge-internal ()
908 "Expunge the tar-entry specified by the current line."
909 (let* ((descriptor (tar-current-descriptor))
910 (tokens (tar-desc-tokens descriptor))
911 ;; (line (tar-desc-data-start descriptor))
912 (name (tar-header-name tokens))
913 (size (tar-header-size tokens))
914 (link-p (tar-header-link-type tokens))
915 (start (tar-desc-data-start descriptor))
916 (following-descs (cdr (memq descriptor tar-parse-info))))
924 (setq tar-header-offset (- tar-header-offset (- (point) line-start)))
928 (setq tar-parse-info (delq descriptor tar-parse-info))
932 (let* ((data-start (+ start (- tar-header-offset (point-min)) -512))
943 (tar-setf (tar-desc-data-start desc)
944 (- (tar-desc-data-start desc) data-length))))
946 (narrow-to-region (point-min) tar-header-offset))
949 (defun tar-expunge (&optional noconfirm)
950 "In Tar mode, delete all the archived files flagged for deletion.
951 This does not modify the disk image; you must save the tar file itself
964 (progn (tar-expunge-internal)
968 (tar-pad-to-blocksize)
971 (narrow-to-region (point-min) tar-header-offset))
977 (defun tar-clear-modification-flags ()
982 (while (< (position-bytes (point)) tar-header-offset)
988 (defun tar-chown-entry (new-uid)
989 "Change the user-id associated with this entry in the tar file.
990 If this tar file was written by GNU tar, then you will be able to edit
993 This does not modify the disk image; you must save the tar file itself
996 (let ((tokens (tar-desc-tokens (tar-current-descriptor))))
998 (not (tar-header-magic tokens)))
1002 (format "%s" (tar-header-uid tokens)))))))
1004 (read-string "New UID string: " (tar-header-uname tokens))))))
1006 (tar-setf (tar-header-uname (tar-desc-tokens (tar-current-descriptor)))
1008 (tar-alter-one-field tar-uname-offset (concat new-uid "\000")))
1010 (tar-setf (tar-header-uid (tar-desc-tokens (tar-current-descriptor)))
1012 (tar-alter-one-field tar-uid-offset
1016 (defun tar-chgrp-entry (new-gid)
1017 "Change the group-id associated with this entry in the tar file.
1018 If this tar file was written by GNU tar, then you will be able to edit
1021 This does not modify the disk image; you must save the tar file itself
1024 (let ((tokens (tar-desc-tokens (tar-current-descriptor))))
1026 (not (tar-header-magic tokens)))
1030 (format "%s" (tar-header-gid tokens)))))))
1032 (read-string "New GID string: " (tar-header-gname tokens))))))
1034 (tar-setf (tar-header-gname (tar-desc-tokens (tar-current-descriptor)))
1036 (tar-alter-one-field tar-gname-offset
1039 (tar-setf (tar-header-gid (tar-desc-tokens (tar-current-descriptor)))
1041 (tar-alter-one-field tar-gid-offset
1044 (defun tar-rename-entry (new-name)
1045 "Change the name associated with this entry in the tar file.
1046 This does not modify the disk image; you must save the tar file itself
1050 (tar-header-name (tar-desc-tokens (tar-current-descriptor))))))
1053 (tar-setf (tar-header-name (tar-desc-tokens (tar-current-descriptor)))
1059 (tar-alter-one-field 0
1063 (defun tar-chmod-entry (new-mode)
1064 "Change the protection bits associated with this entry in the tar file.
1065 This does not modify the disk image; you must save the tar file itself
1067 (interactive (list (tar-parse-octal-integer-safe
1069 (tar-setf (tar-header-mode (tar-desc-tokens (tar-current-descriptor)))
1070 new-mode)
1071 (tar-alter-one-field tar-mode-offset
1072 (concat (substring (format "%6o" new-mode) 0 6) "\000 ")))
1075 (defun tar-alter-one-field (data-position new-data-string)
1076 (let* ((descriptor (tar-current-descriptor))
1077 (tokens (tar-desc-tokens descriptor))
1087 (insert (tar-header-block-summarize tokens) "\n")
1088 (setq tar-header-offset (position-bytes (point-max))))
1092 (let* ((start (+ (tar-desc-data-start descriptor)
1093 (- tar-header-offset (point-min))
1102 (let ((chk (tar-header-block-checksum
1104 (goto-char (+ start tar-chk-offset))
1109 (tar-setf (tar-header-checksum tokens) chk)
1112 (tar-header-block-check-checksum
1114 chk (tar-header-name tokens))
1116 (narrow-to-region (point-min) tar-header-offset)
1118 (tar-next-line 0))))
1121 (defun tar-octal-time (timeval)
1131 (defun tar-subfile-save-buffer ()
1132 "In tar subfile mode, save this buffer into its parent tar-file buffer.
1133 This doesn't write anything to disk; you must save the parent tar-file buffer
1136 (if (not (and (boundp 'tar-superior-buffer) tar-superior-buffer))
1137 (error "This buffer has no superior tar file buffer"))
1138 (if (not (and (boundp 'tar-superior-descriptor) tar-superior-descriptor))
1139 (error "This buffer doesn't have an index into its superior tar file!"))
1144 (descriptor tar-superior-descriptor)
1150 (set-buffer tar-superior-buffer)
1151 (let* ((tokens (tar-desc-tokens descriptor))
1152 (start (tar-desc-data-start descriptor))
1153 (name (tar-header-name tokens))
1154 (size (tar-header-size tokens))
1156 (head (memq descriptor tar-parse-info))
1158 (tar-buffer-multibyte enable-multibyte-characters))
1160 (error "Can't find this tar file entry in its parent tar file!"))
1166 (let* ((data-start (+ start (- tar-header-offset (point-min))))
1182 (tar-setf (tar-header-size tokens) subfile-size)
1185 (tar-setf (tar-desc-data-start desc)
1186 (+ (tar-desc-data-start desc) difference))))
1190 (goto-char (+ header-start tar-size-offset))
1196 (if (not tar-update-datestamp)
1198 (goto-char (+ header-start tar-time-offset))
1200 (insert (tar-octal-time (current-time)))
1204 (let ((chk (tar-header-block-checksum
1206 (goto-char (+ header-start tar-chk-offset))
1211 (tar-setf (tar-header-checksum tokens) chk)))
1215 (let ((position (- (length tar-parse-info) (length head))))
1221 (m (set-marker (make-marker) tar-header-offset)))
1226 (let ((line (tar-header-block-summarize tokens t)))
1229 (setq tar-header-offset (marker-position m)))
1232 (tar-pad-to-blocksize))
1233 (narrow-to-region (point-min) tar-header-offset)
1234 (set-buffer-multibyte tar-buffer-multibyte)))
1235 (set-buffer-modified-p t) ; mark the tar file as modified
1236 (tar-next-line 0)
1240 (set-buffer-modified-p nil) ; mark the tar subfile as unmodified
1241 (message "Saved into tar-buffer `%s'. Be sure to save that buffer!"
1242 (buffer-name tar-superior-buffer))
1250 (defun tar-pad-to-blocksize ()
1251 "If we are being anal about tar file blocksizes, fix up the current buffer.
1253 (if (null tar-anal-blocksize)
1256 (let* ((last-desc (nth (1- (length tar-parse-info)) tar-parse-info))
1257 (start (tar-desc-data-start last-desc))
1258 (tokens (tar-desc-tokens last-desc))
1259 (link-p (tar-header-link-type tokens))
1260 (size (if link-p 0 (tar-header-size tokens)))
1262 (bbytes (ash tar-anal-blocksize 9))
1269 (let ((goal-end (+ (or tar-header-offset 0) pad-to)))
1276 ;; Used in write-file-hook to write tar-files out correctly.
1277 (defun tar-mode-write-file ()
1283 ;; (tar-pad-to-blocksize)
1284 ;; tar-header-offset turns out to be null for files fetched with W3,
1287 (write-region (if tar-header-offset
1288 (byte-to-position tar-header-offset)
1292 (tar-clear-modification-flags)
1294 (narrow-to-region (point-min) (byte-to-position tar-header-offset)))
1299 (provide 'tar-mode)
1302 ;;; tar-mode.el ends here