Hello Uwe,

On 09/09/2020, Uwe Brauer wrote:
> Bibtex failed.
>
> Running `BibTeX' on `main' with ``bibtex main''
> I couldn't open file name `main.aux'
>
> TeX Output exited abnormally with code 1 at Wed Sep  9 22:23:29
>

Thanks for testing! The attached patch (against 087b0300) should fix BibTeX and 
biber.

The fix involves changing `TeX-run-command` to accept an argument for an 
expected file extension in the directory (defaults to nil and passed as "aux" 
in `TeX-run-BibTeX` which leads to the correct output-directory). I am not sure 
this is the cleanest fix, but it should be backward compatible with previous 
code.

I don't use all the features of AUCTeX, so I am not even sure how to test some 
features. I would especially appreciate testing the other tex commands. I 
suspect some of them would be broken but fixing them should be straightforward 
(either by adding `%(output-dir)` to the command or by using the fix above).

Best regards,
-- Al
diff --git a/tex-buf.el b/tex-buf.el
index 510722cb..fa8f1a69 100644
--- a/tex-buf.el
+++ b/tex-buf.el
@@ -82,7 +82,7 @@ Return non-nil if document needs to be re-TeX'ed."
   (if (string-equal name "")
       (setq name (TeX-master-file)))
 
-  (TeX-check-files (concat name "." (TeX-output-extension))
+  (TeX-check-files (concat name "." (TeX-output-extension))   ;; TODO: This might need changing when TeX-output-dir is set
 		   (cons name (TeX-style-list))
 		   TeX-file-extensions))
 
@@ -826,7 +826,7 @@ omitted) and `TeX-region-file'."
 	   ;; comparison.
 	   (if (string-equal (expand-file-name name)
 			     (expand-file-name (TeX-region-file)))
-	       (TeX-check-files (concat name "." (TeX-output-extension))
+	       (TeX-check-files (concat name "." (TeX-output-extension))  ;; TODO: This might need changing when TeX-output-dir is set
 				;; Each original will be checked for all dirs
 				;; in `TeX-check-path' so this needs to be just
 				;; a filename without directory.
@@ -1093,12 +1093,12 @@ requires special treatment."
   :group 'TeX-command
   :type 'boolean)
 
-(defun TeX-run-command (name command file)
+(defun TeX-run-command (name command file &optional dir-for-extension)
   "Create a process for NAME using COMMAND to process FILE.
 Return the new process."
   (let ((default TeX-command-default)
 	(buffer (TeX-process-buffer-name file))
-	(dir (TeX-master-directory))
+	(dir (TeX-master-directory dir-for-extension))
 	(command-buff (current-buffer)))
     (TeX-process-check file)		; Check that no process is running
     (setq-default TeX-command-buffer command-buff)
@@ -1232,7 +1232,7 @@ run of `TeX-run-TeX', use
 
 (defun TeX-run-BibTeX (name command file)
   "Create a process for NAME using COMMAND to format FILE with BibTeX."
-  (let ((process (TeX-run-command name command file)))
+  (let ((process (TeX-run-command name command file "aux")))
     (setq TeX-sentinel-function #'TeX-BibTeX-sentinel)
     (if TeX-process-asynchronous
 	process
@@ -2290,7 +2290,11 @@ The compatibility argument IGNORE is ignored."
 	  (cond ((eq extension t)
 		 (concat TeX-region "." TeX-default-extension))
 		(extension
-		 (concat TeX-region "." extension))
+                 (if (and TeX-output-dir
+                          (when-let (reg (TeX--clean-extensions-regexp t))
+                            (string-match-p reg (concat "." extension))))
+                     (concat TeX-output-dir "/" TeX-region "." extension)
+		   (concat TeX-region "." extension)))
 		(t
 		 TeX-region))))
 
diff --git a/tex.el b/tex.el
index b2bbbbf7..e90035d1 100644
--- a/tex.el
+++ b/tex.el
@@ -188,7 +188,7 @@ If nil, none is specified."
 ;; `TeX-expand-list-builtin' for a description of the % escapes
 
 (defcustom TeX-command-list
-  '(("TeX" "%(PDF)%(tex) %(file-line-error) %`%(extraopts) %S%(PDFout)%(mode)%' %t"
+  '(("TeX" "%(PDF)%(tex) %(file-line-error) %`%(extraopts) %(output-dir) %S%(PDFout)%(mode)%' %t"
      TeX-run-TeX nil
      (plain-tex-mode ams-tex-mode texinfo-mode) :help "Run plain TeX")
     ("LaTeX" "%`%l%(mode)%' %T"
@@ -212,7 +212,7 @@ If nil, none is specified."
      (plain-tex-mode latex-mode doctex-mode ams-tex-mode texinfo-mode
 		     context-mode)
      :help "Run BibTeX")
-    ("Biber" "biber %s" TeX-run-Biber nil
+    ("Biber" "biber %s %(output-dir)" TeX-run-Biber nil
      (plain-tex-mode latex-mode doctex-mode ams-tex-mode texinfo-mode)
      :help "Run Biber")
     ("View" "%V" TeX-run-discard-or-function t t :help "Run Viewer")
@@ -399,7 +399,7 @@ The executable `latex' is LaTeX version 2e."
 
 (defcustom LaTeX-command-style
   ;; They have all been combined in LaTeX 2e.
-  '(("" "%(PDF)%(latex) %(file-line-error) %(extraopts) %S%(PDFout)"))
+  '(("" "%(PDF)%(latex) %(file-line-error) %(extraopts) %(output-dir) %S%(PDFout)"))
 "List of style options and LaTeX commands.
 
 If the first element (a regular expression) matches the name of one of
@@ -566,6 +566,10 @@ string."
     ("%(cntxcom)" ConTeXt-expand-command)
     ("%(execopts)" ConTeXt-expand-options)
     ("%(extraopts)" (lambda () TeX-command-extra-options))
+    ("%(output-dir)" (lambda () (if (not TeX-output-dir) ""
+                                  (unless (file-exists-p TeX-output-dir)
+                                    (make-directory TeX-output-dir))
+                                  (concat "--output-directory=\"" TeX-output-dir "\""))))
     ("%S" TeX-source-correlate-expand-options)
     ("%dS" TeX-source-specials-view-expand-options)
     ("%cS" TeX-source-specials-view-expand-client)
@@ -1237,7 +1241,7 @@ entry in `TeX-view-program-list-builtin'."
 				 (get-file-buffer (TeX-region-file t)))
 			       (current-buffer))
 	(pdf-sync-forward-search))
-    (let ((pdf (concat file "." (TeX-output-extension))))
+    (let ((pdf (TeX-active-master (TeX-output-extension))))
       (pop-to-buffer (or (find-buffer-visiting pdf)
 			 (find-file-noselect pdf))))))
 
@@ -1261,7 +1265,7 @@ viewer."
   (require 'url-util)
   (let* ((uri (concat "file://" (url-encode-url
 				 (expand-file-name
-				  (concat file "." (TeX-output-extension))))))
+                                  (TeX-active-master (TeX-output-extension))))))
 	 (owner (dbus-call-method
 		 :session (format "org.%s.%s.Daemon" de app)
 		 (format "/org/%s/%s/Daemon" de app)
@@ -2279,25 +2283,19 @@ Used as a default in TeX, LaTeX and docTeX mode.")
 If prefix ARG is non-nil, not only remove intermediate but also
 output files."
   (interactive "P")
-  (let* ((mode-prefix (TeX-mode-prefix))
-	 (suffixes (append (symbol-value
-			    (intern (concat mode-prefix
-					    "-clean-intermediate-suffixes")))
-			   (when arg
-			     (symbol-value
-			      (intern (concat mode-prefix
-					      "-clean-output-suffixes"))))))
-	 (master (TeX-active-master))
+  (let* (;; Add output extension then remove it, to make sure we get the correct
+	 ;; directory in cases TeX-output-dir is non-nil
+	 (master (file-name-sans-extension (TeX-active-master (TeX-output-extension))))
 	 (master-dir (file-name-directory master))
 	 (regexp (concat "\\("
 			 (regexp-quote (file-name-nondirectory master)) "\\|"
 			 (regexp-quote (TeX-region-file nil t))
 			 "\\)"
 			 "\\("
-			 (mapconcat 'identity suffixes "\\|")
+			 (TeX--clean-extensions-regexp arg)
 			 "\\)\\'"
 			 "\\|" (regexp-quote (TeX-region-file t t))))
-	 (files (when regexp
+	 (files (when (and regexp (or (not master-dir) (file-exists-p master-dir)))
 		  (directory-files (or master-dir ".") nil regexp))))
     (if files
 	(when (or (not TeX-clean-confirm)
@@ -2310,6 +2308,19 @@ output files."
 	    (delete-file (concat master-dir file))))
       (message "No files to be deleted"))))
 
+(defun TeX--clean-extensions-regexp (&optional arg)
+  "Returns a regexp to match extensions that should be cleaned by TeX-clean.
+If the optional argument ARG is non-nil then output files are included"
+  (when-let ((mode-prefix (TeX-mode-prefix))
+             (suffixes (append (symbol-value
+                                (intern (concat mode-prefix
+                                                "-clean-intermediate-suffixes")))
+                               (when arg
+                                 (symbol-value
+                                  (intern (concat mode-prefix
+                                                  "-clean-output-suffixes")))))))
+    (mapconcat 'identity suffixes "\\|")))
+
 ;;; Master File
 
 (defcustom TeX-master t
@@ -2403,6 +2414,25 @@ this variable to \"<none>\"."
 						   'path))
 	     (TeX-add-local-master))))))
 
+(defun TeX-master-output-file (&optional extension)
+  "Returns an output file based on `TeX-output-dir' in the
+master-file, opening it if necessary. if the optional argument
+EXTENSION is non-nil it is appended as an extension to the output
+file. If EXTENSION is t then (TeX-output-extension) is used."
+  (interactive)
+  (if (eq extension t)
+      (setq extension (TeX-output-extension)))
+  (let ((file (TeX-master-file t)) name)
+    (with-current-buffer
+        (or (find-buffer-visiting file)
+            (find-file-noselect file))
+      (when TeX-output-dir
+        (setq name (concat TeX-output-dir "/" (TeX-master-file)))))
+    (if name
+        (if extension (concat name "." extension)
+          name)
+      (TeX-master-file extension))))
+
 (defun TeX-master-file (&optional extension nondirectory ask)
   "Set and return the name of the master file for the current document.
 
@@ -2463,7 +2493,11 @@ name of master file if it cannot be determined otherwise."
 	 ;; Ask the user (but add it as a local variable).
 	 (ask (TeX-master-file-ask)))))
 
-    (let ((name (if (stringp TeX-master)
+    (if (and TeX-output-dir
+             (when-let (reg (TeX--clean-extensions-regexp t))
+               (string-match-p reg (concat "." extension))))
+        (TeX-master-output-file extension)
+      (let ((name (if (stringp TeX-master)
 		    TeX-master
 		  my-name)))
 
@@ -2481,15 +2515,15 @@ name of master file if it cannot be determined otherwise."
 
       (if extension
 	  (concat name "." extension)
-	name))))
+	name)))))
 
-(defun TeX-master-directory ()
+(defun TeX-master-directory (&optional for-extension)
   "Directory of master file."
   (file-name-as-directory
    (abbreviate-file-name
     (substitute-in-file-name
      (expand-file-name
-      (let ((dir (file-name-directory (TeX-master-file))))
+      (let ((dir (file-name-directory (TeX-master-file for-extension))))
 	(if dir (directory-file-name dir) "."))
       (and buffer-file-name
 	   (file-name-directory buffer-file-name)))))))
@@ -2563,6 +2597,16 @@ be relative to that."
   :group 'TeX-file
   :type 'string)
 
+(defcustom TeX-output-dir nil
+  "The directory where the output files will be generated. The
+  directory cannot start with a `.'.
+
+If this variable is nil, AUCTeX will assume that the output
+directory is the same as the directory of TeX-master."
+  :group 'TeX-file
+  :type '(string :format "%v"))
+(put 'TeX-output-dir 'safe-local-variable 'stringp-or-null-p)
+
 (defcustom TeX-style-local "style"
   "*Directory containing hand generated TeX information.
 

Reply via email to