]> code.delx.au - gnu-emacs/blobdiff - lisp/vc.el
* window.c (Fwindow_height): Doc fix (bug#6518).
[gnu-emacs] / lisp / vc.el
index 9bd6e338f372be733737c81c5b4b684b968a85eb..a7d4ec663917963fb290d34feafed37f007aac11 100644 (file)
@@ -1,7 +1,7 @@
 ;;; vc.el --- drive a version-control system from within Emacs
 
 ;; Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 2000,
-;;   2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
+;;   2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
 ;;   Free Software Foundation, Inc.
 
 ;; Author:     FSF (see below for full credits)
 ;;
 ;; HISTORY FUNCTIONS
 ;;
-;; * print-log (files buffer &optional shortlog limit)
+;; * print-log (files buffer &optional shortlog start-revision limit)
 ;;
 ;;   Insert the revision log for FILES into BUFFER.
 ;;   If SHORTLOG is true insert a short version of the log.
 ;;   If LIMIT is true insert only insert LIMIT log entries.  If the
 ;;   backend does not support limiting the number of entries to show
 ;;   it should return `limit-unsupported'.
+;;   If START-REVISION is given, then show the log starting from the
+;;   revision.  At this point START-REVISION is only required to work
+;;   in conjunction with LIMIT = 1.
 ;;
 ;; - log-view-mode ()
 ;;
@@ -788,13 +791,23 @@ in their implementation of vc-BACKEND-diff.")
 
 (defmacro with-vc-properties (files form settings)
   "Execute FORM, then maybe set per-file properties for FILES.
+If any of FILES is actually a directory, then do the same for all
+buffers for files in that directory.
 SETTINGS is an association list of property/value pairs.  After
 executing FORM, set those properties from SETTINGS that have not yet
 been updated to their corresponding values."
   (declare (debug t))
-  `(let ((vc-touched-properties (list t)))
-     ,form
+  `(let ((vc-touched-properties (list t))
+        (flist nil))
      (dolist (file ,files)
+       (if (file-directory-p file)
+          (dolist (buffer (buffer-list))
+            (let ((fname (buffer-file-name buffer)))
+              (when (and fname (vc-string-prefix-p file fname))
+                (push fname flist))))
+        (push file flist)))
+     ,form
+     (dolist (file flist)
        (dolist (setting ,settings)
          (let ((property (car setting)))
            (unless (memq property vc-touched-properties)
@@ -1385,6 +1398,16 @@ Runs the normal hooks `vc-before-checkin-hook' and `vc-checkin-hook'."
 ;;          (vc-call-backend ',(vc-backend f)
 ;;                           'diff (list ',f) ',rev1 ',rev2))))))
 
+(defvar vc-coding-system-inherit-eol t
+  "When non-nil, inherit the EOL format for reading Diff output from the file.
+
+Used in `vc-coding-system-for-diff' to determine the EOL format to use
+for reading Diff output for a file.  If non-nil, the EOL format is
+inherited from the file itself.
+Set this variable to nil if your Diff tool might use a different
+EOL.  Then Emacs will auto-detect the EOL format in Diff output, which
+gives better results.") ;; Cf. bug#4451.
+
 (defun vc-coding-system-for-diff (file)
   "Return the coding system for reading diff output for FILE."
   (or coding-system-for-read
@@ -1392,7 +1415,12 @@ Runs the normal hooks `vc-before-checkin-hook' and `vc-checkin-hook'."
       ;; use the buffer's coding system
       (let ((buf (find-buffer-visiting file)))
         (when buf (with-current-buffer buf
-                   buffer-file-coding-system)))
+                   (if vc-coding-system-inherit-eol
+                       buffer-file-coding-system
+                     ;; Don't inherit the EOL part of the coding-system,
+                     ;; because some Diff tools may choose to use
+                     ;; a different one.  bug#4451.
+                     (coding-system-base buffer-file-coding-system)))))
       ;; otherwise, try to find one based on the file name
       (car (find-operation-coding-system 'insert-file-contents file))
       ;; and a final fallback
@@ -1596,9 +1624,10 @@ saving the buffer."
 
 ;;;###autoload
 (defun vc-root-diff (historic &optional not-urgent)
-  "Display diffs between file revisions.
-Normally this compares the currently selected fileset with their
-working revisions.  With a prefix argument HISTORIC, it reads two revision
+  "Display diffs between VC-controlled whole tree revisions.
+Normally, this compares the tree corresponding to the current
+fileset with the working revision.
+With a prefix argument HISTORIC, prompt for two revision
 designators specifying which revisions to compare.
 
 The optional argument NOT-URGENT non-nil means it is ok to say no to
@@ -1641,8 +1670,9 @@ If `F.~REV~' already exists, use it instead of checking it out again."
                    rev)))
     (switch-to-buffer-other-window (vc-find-revision file revision))))
 
-(defun vc-find-revision (file revision)
-  "Read REVISION of FILE into a buffer and return the buffer."
+(defun vc-find-revision (file revision &optional backend)
+  "Read REVISION of FILE into a buffer and return the buffer.
+Use BACKEND as the VC backend if specified."
   (let ((automatic-backup (vc-version-backup-file-name file revision))
        (filebuf (or (get-file-buffer file) (current-buffer)))
         (filename (vc-version-backup-file-name file revision 'manual)))
@@ -1660,7 +1690,9 @@ If `F.~REV~' already exists, use it instead of checking it out again."
                      ;; Change buffer to get local value of
                      ;; vc-checkout-switches.
                      (with-current-buffer filebuf
-                       (vc-call find-revision file revision outbuf))))
+                       (if backend
+                           (vc-call-backend backend 'find-revision file revision outbuf)
+                         (vc-call find-revision file revision outbuf)))))
                  (setq failed nil))
              (when (and failed (file-exists-p filename))
                (delete-file filename))))
@@ -1863,7 +1895,7 @@ Not all VC backends support short logs!")
 (defvar log-view-vc-fileset)
 
 (defun vc-print-log-internal (backend files working-revision
-                                      &optional limit)
+                                      &optional is-start-revision limit)
   ;; Don't switch to the output buffer before running the command,
   ;; so that any buffer-local settings in the vc-controlled
   ;; buffer can be accessed by the command.
@@ -1878,8 +1910,9 @@ Not all VC backends support short logs!")
                         (memq 'directory vc-log-short-style)
                       (memq 'file vc-log-short-style)))))
 
-    (setq pl-return (vc-call-backend backend 'print-log files "*vc-change-log*"
-                                    vc-short-log limit))
+    (setq pl-return (vc-call-backend
+                    backend 'print-log files "*vc-change-log*"
+                    vc-short-log (when is-start-revision working-revision) limit))
     (pop-to-buffer "*vc-change-log*")
     (let ((inhibit-read-only t))
       ;; log-view-mode used to be called with inhibit-read-only bound
@@ -1890,19 +1923,20 @@ Not all VC backends support short logs!")
 
     (vc-exec-after
      `(let ((inhibit-read-only t))
-       (when (and ,limit (not (eq 'limit-unsupported pl-return)))
+       (when (and ,limit (not ,(eq 'limit-unsupported pl-return))
+                  (not ,is-start-revision))
          (goto-char (point-max))
          (widget-create 'push-button
                         :notify (lambda (&rest ignore)
                                   (vc-print-log-internal
-                                   ',backend ',files ',working-revision (* 2 ,limit)))
+                                   ',backend ',files ',working-revision nil (* 2 ,limit)))
                         :help-echo "Show the log again, and double the number of log entries shown"
                         "Show 2X entries")
          (widget-insert "    ")
          (widget-create 'push-button
                         :notify (lambda (&rest ignore)
                                   (vc-print-log-internal
-                                   ',backend ',files ',working-revision nil))
+                                   ',backend ',files ',working-revision nil nil))
                         :help-echo "Show the log again, showing all entries"
                         "Show unlimited entries")
          (widget-setup))
@@ -1916,7 +1950,12 @@ Not all VC backends support short logs!")
 ;;;###autoload
 (defun vc-print-log (&optional working-revision limit)
   "List the change log of the current fileset in a window.
-If WORKING-REVISION is non-nil, leave the point at that revision."
+If WORKING-REVISION is non-nil, leave point at that revision.
+If LIMIT is non-nil, it should be a number specifying the maximum
+number of revisions to show; the default is `vc-log-show-limit'.
+
+When called interactively with a prefix argument, prompt for
+WORKING-REVISION and LIMIT."
   (interactive
    (cond
     (current-prefix-arg
@@ -1931,16 +1970,19 @@ If WORKING-REVISION is non-nil, leave the point at that revision."
        (when (<= lim 0) (setq lim nil))
        (list rev lim)))
     (t
-     (list nil nil))))
+     (list nil (when (> vc-log-show-limit 0) vc-log-show-limit)))))
   (let* ((vc-fileset (vc-deduce-fileset t)) ;FIXME: Why t? --Stef
         (backend (car vc-fileset))
         (files (cadr vc-fileset))
         (working-revision (or working-revision (vc-working-revision (car files)))))
-    (vc-print-log-internal backend files working-revision limit)))
+    (vc-print-log-internal backend files working-revision nil limit)))
 
 ;;;###autoload
 (defun vc-print-root-log (&optional limit)
-  "List the change log of for the current VC controlled tree in a window."
+  "List the change log for the current VC controlled tree in a window.
+If LIMIT is non-nil, it should be a number specifying the maximum
+number of revisions to show; the default is `vc-log-show-limit'.
+When called interactively with a prefix argument, prompt for LIMIT."
   (interactive
    (cond
     (current-prefix-arg
@@ -1952,7 +1994,7 @@ If WORKING-REVISION is non-nil, leave the point at that revision."
        (when (<= lim 0) (setq lim nil))
        (list lim)))
     (t
-     (list nil))))
+     (list (when (> vc-log-show-limit 0) vc-log-show-limit)))))
   (let ((backend
         (cond ((derived-mode-p 'vc-dir-mode)  vc-dir-backend)
               ((derived-mode-p 'dired-mode) (vc-responsible-backend default-directory))
@@ -1962,7 +2004,7 @@ If WORKING-REVISION is non-nil, leave the point at that revision."
       (error "Buffer is not version controlled"))
     (setq rootdir (vc-call-backend backend 'root default-directory))
     (setq working-revision (vc-working-revision rootdir))
-    (vc-print-log-internal backend (list rootdir) working-revision limit)))
+    (vc-print-log-internal backend (list rootdir) working-revision nil limit)))
 
 ;;;###autoload
 (defun vc-revert ()