Subject: Re: bug#79024: 31.0.50; Multiple working trees support for VC

From: Sean Whitton <[email-masked]>
Date: Thu, 14 Aug 2025 15:03:37 +0100

Hello again Eli,

Do you know of any reason we couldn't refactor things in vc-git.el like
this?  It would reduce complexity a fair bit.

-- 
Sean Whitton
>From 5112ef83409ea181de1c61c9257d30c0e11e2e80 Mon Sep 17 00:00:00 2001
From: Sean Whitton <[email-masked]>
Date: Thu, 14 Aug 2025 15:02:02 +0100
Subject: [PATCH] Refactor binding coding-system-for-write for command
 arguments

* lisp/vc/vc-git.el (vc-git-command): Handle binding
coding-system-for-write to locale-coding-system on MS-Windows.
(vc-git-checkin, vc-git-modify-change-comment): Don't bind
coding-system-for-write solely for the sake of handling command
line arguments.  (Continue to bind it for other purposes.)
---
 lisp/vc/vc-git.el | 47 +++++++++++++++++++----------------------------
 1 file changed, 19 insertions(+), 28 deletions(-)

diff --git a/lisp/vc/vc-git.el b/lisp/vc/vc-git.el
index f01807e0113..b243f9b37f9 100644
--- a/lisp/vc/vc-git.el
+++ b/lisp/vc/vc-git.el
@@ -1149,13 +1149,6 @@ vc-git-checkin
          (default-directory (expand-file-name root))
          (only (or (cdr files)
                    (not (equal root (abbreviate-file-name file1)))))
-         (pcsw coding-system-for-write)
-         (coding-system-for-write
-          ;; On MS-Windows, we must encode command-line arguments in
-          ;; the system codepage.
-          (if (eq system-type 'windows-nt)
-              locale-coding-system
-            (or coding-system-for-write vc-git-commits-coding-system)))
          (msg-file
           ;; On MS-Windows, pass the commit log message through a
           ;; file, to work around the limitation that command-line
@@ -1226,14 +1219,13 @@ vc-git-checkin
                     (t (push file-name to-stash)))
               (setq pos (point))))))
       (unless (string-empty-p vc-git-patch-string)
-        (let (;; Temporarily countermand the let-binding at the
-              ;; beginning of this function.
-              (coding-system-for-write
+        (let ((coding-system-for-write
+               ;; On DOS/Windows, it is important for the patch file to
+               ;; have the Unix EOL format, because Git expects that,
+               ;; even on Windows.
                (coding-system-change-eol-conversion
-                ;; On DOS/Windows, it is important for the patch file
-                ;; to have the Unix EOL format, because Git expects
-                ;; that, even on Windows.
-                (or pcsw vc-git-commits-coding-system) 'unix)))
+                (or coding-system-for-write vc-git-commits-coding-system)
+                'unix)))
           (vc-git--with-apply-temp-to-staging patch
             (with-temp-file patch
               (insert vc-git-patch-string)))))
@@ -1251,7 +1243,7 @@ vc-git-checkin
                    (vc-git-command t 0 nil "stash" "show" "-p")))))))
       (when msg-file
         (let ((coding-system-for-write
-               (or pcsw vc-git-commits-coding-system)))
+               (or coding-system-for-write vc-git-commits-coding-system)))
           (write-region (car args) nil msg-file))
         (setq args (cdr args)))
       (setq args (nconc (if msg-file
@@ -2118,18 +2110,12 @@ vc-git-modify-change-comment
               (write-region message nil msg-file)))
           ;; Regardless of the state of the index and working tree, this
           ;; will always create an empty commit, thanks to --only.
-          (let ((coding-system-for-write
-                 ;; On MS-Windows, we must encode command-line arguments in
-                 ;; the system codepage.
-                 (if (eq system-type 'windows-nt)
-                     locale-coding-system
-                   coding-system-for-write)))
-            (apply #'vc-git-command nil 0 nil
-                   "commit" "--only" "--allow-empty"
-                   (nconc (if msg-file
-                              (list "-F" (file-local-name msg-file))
-                            (list "-m" message))
-                          args))))
+          (apply #'vc-git-command nil 0 nil
+                 "commit" "--only" "--allow-empty"
+                 (nconc (if msg-file
+                            (list "-F" (file-local-name msg-file))
+                          (list "-m" message))
+                        args)))
       (when (and msg-file (file-exists-p msg-file))
         (delete-file msg-file))))
   (with-environment-variables (("GIT_SEQUENCE_EDITOR" "true"))
@@ -2493,7 +2479,12 @@ vc-git-command
   (let ((coding-system-for-read
          (or coding-system-for-read vc-git-log-output-coding-system))
 	(coding-system-for-write
-         (or coding-system-for-write vc-git-commits-coding-system))
+         ;; On MS-Windows, we must encode command-line arguments in the
+         ;; system codepage.
+         (cond ((eq system-type 'windows-nt)
+                locale-coding-system)
+               (coding-system-for-write)
+               (vc-git-commits-coding-system)))
         (process-environment
          (append
           `("GIT_DIR"
-- 
2.47.2