diff lisp/info.el @ 442:abe6d1db359e r21-2-36

Import from CVS: tag r21-2-36
author cvs
date Mon, 13 Aug 2007 11:35:02 +0200
parents 8de8e3f6228a
children 576fb035e263
line wrap: on
line diff
--- a/lisp/info.el	Mon Aug 13 11:33:40 2007 +0200
+++ b/lisp/info.el	Mon Aug 13 11:35:02 2007 +0200
@@ -22,7 +22,7 @@
 ;; General Public License for more details.
 
 ;; You should have received a copy of the GNU General Public License
-;; along with XEmacs; see the file COPYING.  If not, write to the 
+;; along with XEmacs; see the file COPYING.  If not, write to the
 ;; Free Software Foundation, Inc., 59 Temple Place - Suite 330,
 ;; Boston, MA 02111-1307, USA.
 
@@ -308,7 +308,7 @@
 ;; contain none or when it has become older than info files in the same
 ;; directory.
 
-;; Modified 1998-09-23 by Didier Verna <verna@inf.enst.fr>
+;; Modified 1998-09-23 by Didier Verna <didier@xemacs.org>
 ;;
 ;; Use the new macro `with-search-caps-disable-folding'
 
@@ -402,10 +402,10 @@
 `always' auto-generate a directory listing ignoring existing
   `dir' and `localdir' files
 `if-missing', the default, auto-generates a directory listing
-  if no `dir' or `localdir' file is present.  Otherwise the 
+  if no `dir' or `localdir' file is present.  Otherwise the
   contents of any of these files is used instead.
 `if-outdated' auto-generates a directory listing if the `dir'
-  and `localdir' are either inexistent or outdated (touched 
+  and `localdir' are either inexistent or outdated (touched
   less recently than an info file in the same directory)."
   :type '(choice (const :tag "never" never)
 		 (const :tag "always" always)
@@ -413,15 +413,15 @@
 		 (const :tag "if-outdated" if-outdated))
   :group 'info)
 
-(defcustom Info-save-auto-generated-dir nil
+(defcustom Info-save-auto-generated-dir 'never
   "*Whether an auto-generated info directory listing should be saved.
 Possible values are:
-nil or `never', the default, auto-generated info directory 
+nil or `never', the default, auto-generated info directory
   information will never be saved.
 `always', auto-generated info directory information will be saved to
   a `dir' file in the same directory overwriting it if it exists
 `conservative', auto-generated info directory information will be saved
-  to a `dir' file in the same directory but the user is asked before 
+  to a `dir' file in the same directory but the user is asked before
   overwriting any existing file."
   :type '(choice (const :tag "never" never)
 		 (const :tag "always" always)
@@ -463,7 +463,7 @@
   :group 'info-faces)
 
 ;; Is this right for NT?  .zip, with -c for to stdout, right?
-(defvar Info-suffix-list '( ("" . nil) 
+(defvar Info-suffix-list '( ("" . nil)
 			    (".info" . nil)
 			    (".info.bz2" . "bzip2 -dc %s")
 			    (".info.gz" . "gzip -dc %s")
@@ -494,10 +494,12 @@
 (defvar Info-current-node nil
   "Name of node that Info is now looking at, or nil.")
 
-(defvar Info-tag-table-marker (make-marker)
+(defvar Info-tag-table-marker nil
   "Marker pointing at beginning of current Info file's tag table.
 Marker points nowhere if file has no tag table.")
 
+(defvar Info-tag-table-buffer nil)
+
 (defvar Info-current-file-completions nil
   "Cached completion list for current Info file.")
 
@@ -537,7 +539,7 @@
 looking at that node, which is (dir)Top.
 
 File: dir	Node: Top	This is the top of the INFO tree
-  This (the Directory node) gives a menu of major topics. 
+  This (the Directory node) gives a menu of major topics.
 
 * Menu: The list of major topics begins on the next line.
 
@@ -592,6 +594,7 @@
 	  (bury-buffer (find-file-noselect (car f))))
       (setq f (cdr f)))))
 
+;;;###autoload
 (defun Info-find-node (filename &optional nodename no-going-back tryfile line)
   "Go to an info node specified as separate FILENAME and NODENAME.
 Look for a plausible filename, or if not found then look for URL's and
@@ -607,7 +610,7 @@
     (Info-find-file-node nil nodename no-going-back tryfile line))
    ;; Convert filename to lower case if not found as specified.
    ;; Expand it, look harder...
-   ((let (temp temp-downcase found 
+   ((let (temp temp-downcase found
 	       (fname (substitute-in-file-name filename)))
       (let ((dirs (cond
 		   ((string-match "^\\./" fname) ; If specified name starts with `./'
@@ -628,7 +631,7 @@
 	  ;; Try downcasing, appending a suffix, or both.
 	  (setq found (Info-suffixed-file temp temp-downcase))
 	  (setq dirs (cdr dirs)))
-	(if found 
+	(if found
 	    (progn (setq filename (expand-file-name found))
 		   t))))
     (Info-find-file-node filename nodename no-going-back tryfile line))
@@ -650,7 +653,8 @@
   ;; should be locked up where they can't do any more harm.
 
   ;; Go into info buffer.
-  (switch-to-buffer "*info*")
+  (or (eq major-mode 'Info-mode)
+      (switch-to-buffer "*info*"))
   (buffer-disable-undo (current-buffer))
   (run-hooks 'Info-startup-hook)
   (or (eq major-mode 'Info-mode)
@@ -659,7 +663,7 @@
       (equal Info-current-file filename)
       (not Info-novice)
       (string= "dir" (file-name-nondirectory Info-current-file))
-      (if (y-or-n-p-maybe-dialog-box
+      (if (y-or-n-p
 	   (format "Leave Info file `%s'? "
 		   (file-name-nondirectory Info-current-file)))
 	  (message "")
@@ -703,16 +707,20 @@
 			  (looking-at "(Indirect)\n"))
 			;; It is indirect.  Copy it to another buffer
 			;; and record that the tag table is in that buffer.
-			(save-excursion
-			  (let ((buf (current-buffer)))
-			    (set-buffer
-			     (get-buffer-create " *info tag table*"))
-			    (buffer-disable-undo (current-buffer))
-			    (setq case-fold-search t)
-			    (erase-buffer)
-			    (insert-buffer-substring buf)
-			    (set-marker Info-tag-table-marker
-					(match-end 0))))
+			  (let ((buf (current-buffer))
+				(m Info-tag-table-marker))
+			    (or
+			     Info-tag-table-buffer
+			     (setq
+			      Info-tag-table-buffer
+			      (generate-new-buffer " *info tag table*")))
+			    (save-excursion
+			      (set-buffer Info-tag-table-buffer)
+			      (buffer-disable-undo (current-buffer))
+			      (setq case-fold-search t)
+			      (erase-buffer)
+			      (insert-buffer-substring buf)
+			      (set-marker m (match-end 0))))
 		     (set-marker Info-tag-table-marker pos))))
 	      (setq Info-current-file
 		    (file-name-sans-versions buffer-file-name))))
@@ -729,18 +737,21 @@
 	    ;; Also, if this is an indirect info file,
 	    ;; read the proper subfile into this buffer.
 	    (if (marker-position Info-tag-table-marker)
-		(save-excursion
-		  (set-buffer (marker-buffer Info-tag-table-marker))
-		  (goto-char Info-tag-table-marker)
-		  (if (re-search-forward regexp nil t)
-		      (progn
-			(setq guesspos (read (current-buffer)))
-			;; If this is an indirect file,
-			;; determine which file really holds this node
-			;; and read it in.
-			(if (not (eq (current-buffer) (get-buffer "*info*")))
-			    (setq guesspos
-				  (Info-read-subfile guesspos)))))))
+		(let (foun found-mode (m Info-tag-table-marker))
+		  (save-excursion
+		    (set-buffer (marker-buffer Info-tag-table-marker))
+		    (goto-char m)
+		    (setq foun (re-search-forward regexp nil t))
+		    (if foun 
+			(setq guesspos (read (current-buffer))))
+		    (setq found-mode major-mode))
+		  (if foun 
+		      ;; If this is an indirect file,
+		      ;; determine which file really holds this node
+		      ;; and read it in.
+		      (if (not (eq major-mode found-mode))
+			  (setq guesspos
+				(Info-read-subfile guesspos))))))
 	    (goto-char (max (point-min) (- guesspos 1000)))
 	    ;; Now search from our advised position (or from beg of buffer)
 	    ;; to find the actual node.
@@ -870,7 +881,7 @@
 				       (if (string-match "localdir" file)
 					   "localdir"
 					 "info dir"))))
-		      (if (not buf) 
+		      (if (not buf)
 			  (insert-file-contents file))
 		      (if (string-match "localdir" (buffer-name))
 			  (setq lbuffers (cons (current-buffer) lbuffers))
@@ -881,13 +892,13 @@
 				      Info-dir-file-attributes)))))))
 	  (or (cdr dirs) (setq Info-dir-contents-directory (car dirs)))
 	  (setq dirs (cdr dirs))))
-      
+
       ;; ensure that the localdir files are inserted last, and reverse
       ;; the list of them so that when they get pushed in, they appear
       ;; in the same order they got specified in the path, from top to
       ;; bottom.
       (nconc buffers (reverse lbuffers))
-      
+
       (or buffers
 	  (error "Can't find the Info directory node"))
       ;; Distinguish the dir file that comes with Emacs from all the
@@ -956,7 +967,7 @@
 		  (setq end (point))
 		  (setq nodes (cons (list nodename other beg end) nodes))))))
 	  (setq others (cdr others))))
-      
+
       ;; Add to the main menu a menu item for each other node.
       (re-search-forward "^\\* Menu:" nil t)
       (forward-line 1)
@@ -1016,7 +1027,7 @@
     (if (not (find-buffer-visiting file))
 	(if (not (file-exists-p file))
 	    (if (or (eq Info-auto-generate-directory 'always)
-		    (eq Info-auto-generate-directory 'if-missing))	      
+		    (eq Info-auto-generate-directory 'if-missing))
 		(Info-build-dir-anew (file-name-directory file)))
 	  (if (or (eq Info-auto-generate-directory 'always)
 		  (and (eq Info-auto-generate-directory 'if-outdated)
@@ -1034,7 +1045,7 @@
 	f-mod-time
 	newer)
     (setq Info-dir-newer-info-files nil)
-    (mapcar 
+    (mapcar
      #'(lambda (f)
 	 (prog2
 	     (setq f-mod-time (nth 5 (file-attributes f)))
@@ -1043,7 +1054,7 @@
 				  (> (car (cdr f-mod-time)) (car (cdr dir-mod-time))))))
 	   (if (and (file-readable-p f)
 		    newer)
-	       (setq Info-dir-newer-info-files 
+	       (setq Info-dir-newer-info-files
 		     (cons f Info-dir-newer-info-files)))))
      (directory-files (file-name-directory file)
 		      'fullname
@@ -1082,12 +1093,12 @@
 			    (match-string 1)
 			    (downcase (or (match-string 3)
 					  (match-string 1)))))
-	  (setq entry 
-		(cons (nreverse 
-		       (cdr 
-			(nreverse 
-			 (split-string 
-			  (buffer-substring 
+	  (setq entry
+		(cons (nreverse
+		       (cdr
+			(nreverse
+			 (split-string
+			  (buffer-substring
 			   (re-search-forward "[ \t]*" nil t)
 			   (or (and (re-search-forward "^[^ \t]" nil t)
 				    (goto-char (match-beginning 0)))
@@ -1108,7 +1119,7 @@
 		(if (> len description-col)
 		    (setq description-col len)))
 	    entries)
-    (setq description-col (+ 5 description-col)) 
+    (setq description-col (+ 5 description-col))
     (mapcar #'(lambda (e)
 		(setq e (cdr e))	; Drop filename
 		(insert "* " (car e) ":" (car (cdr e)))
@@ -1123,7 +1134,7 @@
 
 (defun Info-build-dir-anew (directory)
   "Build info directory information for DIRECTORY.
-The generated directory listing may be saved to a `dir' according 
+The generated directory listing may be saved to a `dir' according
 to the value of `Info-save-auto-generated-dir'"
   (save-excursion
     (let* ((dirfile (expand-file-name "dir" directory))
@@ -1131,7 +1142,7 @@
 			(eq Info-save-auto-generated-dir 'never)
 			(and (not (file-writable-p dirfile))
 			     (message "File not writable %s. Using temporary." dirfile))))
-	   (info-files 
+	   (info-files
 	    (directory-files directory
 			     'fullname
 			     ".*\\.info\\(.gz\\|.Z\\|-z\\|.zip\\)?$"
@@ -1145,13 +1156,13 @@
       (erase-buffer)
       (insert Info-dir-prologue
 	      "Info files in " directory ":\n\n")
-      (Info-dump-dir-entries 
-       (mapcar 
+      (Info-dump-dir-entries
+       (mapcar
 	#'(lambda (f)
 	    (or (Info-extract-dir-entry-from f)
 		(list 'dummy
-		      (progn 
-			(string-match "\\(.*\\)\\.info\\(.gz\\|.Z\\|-z\\|.zip\\)?$" 
+		      (progn
+			(string-match "\\(.*\\)\\.info\\(.gz\\|.Z\\|-z\\|.zip\\)?$"
 				      (file-name-nondirectory f))
 			(capitalize (match-string 1 (file-name-nondirectory f))))
 		      ":"
@@ -1167,10 +1178,10 @@
 
 (defun Info-rebuild-dir (file)
   "Build info directory information in the directory of dir FILE.
-Description of info files are merged from the info files in the 
+Description of info files are merged from the info files in the
 directory and the contents of FILE with the description in info files
-taking precedence over descriptions in FILE.  
-The generated directory listing may be saved to a `dir' according to 
+taking precedence over descriptions in FILE.
+The generated directory listing may be saved to a `dir' according to
 the value of `Info-save-auto-generated-dir' "
   (save-excursion
     (save-restriction
@@ -1179,7 +1190,7 @@
 	    file-dir-entry
 	    mark next-section
 	    not-first-section
-	    (to-temp 
+	    (to-temp
 	     (or (null Info-save-auto-generated-dir)
 		 (eq Info-save-auto-generated-dir 'never)
 		 (and (eq Info-save-auto-generated-dir 'always)
@@ -1188,8 +1199,8 @@
 		 (and (eq Info-save-auto-generated-dir 'conservative)
 		      (or (and (not (file-writable-p file))
 			       (message "File not writable %s. Using temporary." file))
-			  (not (y-or-n-p 
-				(message "%s is outdated. Overwrite ? " 
+			  (not (y-or-n-p
+				(message "%s is outdated. Overwrite ? "
 					 file))))))))
 	(set-buffer (find-file-noselect file t))
 	(setq buffer-read-only nil)
@@ -1232,12 +1243,12 @@
 		     (if file-dir-entry
 			 (setq dir-section-contents (cons file-dir-entry
 							  dir-section-contents))
-		       (setq dir-section-contents 
+		       (setq dir-section-contents
 			     (cons (list 'dummy
 					 (capitalize (file-name-sans-extension
 						      (file-name-nondirectory file)))
 					 ":"
-					 (list Info-no-description-string)) 
+					 (list Info-no-description-string))
 				   dir-section-contents))))))
 	     Info-dir-newer-info-files)
 	    (delete-region (point-min) (point-max))
@@ -1259,7 +1270,7 @@
 	  (save-buffer)
 	  (message "Rebuilding %s...done" file))))))
 
-;;;###autoload      
+;;;###autoload
 (defun Info-batch-rebuild-dir ()
   "(Re)build info `dir' files in the directories remaining on the command line.
 Use this from the command line, with `-batch';
@@ -1279,7 +1290,7 @@
 		   (car command-line-args-left))
 	(setq dir (expand-file-name "dir" (car command-line-args-left)))
 	(setq localdir (expand-file-name "localdir" (car command-line-args-left)))
-	(cond 
+	(cond
 	 ((file-exists-p dir)
 	  (Info-rebuild-dir dir))
 	 ((file-exists-p localdir)
@@ -1310,30 +1321,30 @@
     (if p (file-name-nondirectory file) file)))
 
 (defun Info-read-subfile (nodepos)
-  (set-buffer (marker-buffer Info-tag-table-marker))
-  (goto-char (point-min))
-  (search-forward "\n\^_")
   (let (lastfilepos
 	lastfilename)
-    (forward-line 2)
-    (catch 'foo
-      (while (not (looking-at "\^_"))
-	(if (not (eolp))
-	    (let ((beg (point))
-		  thisfilepos thisfilename)
-	      (search-forward ": ")
-	      (setq thisfilename  (buffer-substring beg (- (point) 2)))
-	      (setq thisfilepos (read (current-buffer)))
-	      ;; read in version 19 stops at the end of number.
-	      ;; Advance to the next line.
-	      (if (eolp)
-		  (forward-line 1))
-	      (if (> thisfilepos nodepos)
-		  (throw 'foo t))
-	      (setq lastfilename thisfilename)
-	      (setq lastfilepos thisfilepos))
-	  (throw 'foo t))))
-    (set-buffer (get-buffer "*info*"))
+    (save-excursion
+      (set-buffer (marker-buffer Info-tag-table-marker))
+      (goto-char (point-min))
+      (search-forward "\n\^_")
+      (forward-line 2)
+      (catch 'foo
+	(while (not (looking-at "\^_"))
+	  (if (not (eolp))
+	      (let ((beg (point))
+		    thisfilepos thisfilename)
+		(search-forward ": ")
+		(setq thisfilename  (buffer-substring beg (- (point) 2)))
+		(setq thisfilepos (read (current-buffer)))
+		;; read in version 19 stops at the end of number.
+		;; Advance to the next line.
+		(if (eolp)
+		    (forward-line 1))
+		(if (> thisfilepos nodepos)
+		    (throw 'foo t))
+		(setq lastfilename thisfilename)
+		(setq lastfilepos thisfilepos))
+	    (throw 'foo t)))))
     (or (equal Info-current-subfile lastfilename)
 	(let ((buffer-read-only nil))
 	  (setq buffer-file-name nil)
@@ -1567,14 +1578,15 @@
 
 (defun Info-build-node-completions ()
   (or Info-current-file-completions
-      (let ((compl (Info-build-annotation-completions)))
+      (let ((m Info-tag-table-marker)
+	    (compl (Info-build-annotation-completions)))
 	(save-excursion
 	  (save-restriction
 	    (widen)
 	    (if (marker-buffer Info-tag-table-marker)
 		(progn
 		  (set-buffer (marker-buffer Info-tag-table-marker))
-		  (goto-char Info-tag-table-marker)
+		  (goto-char m)
 		  (while (re-search-forward "\nNode: \\(.*\\)\177" nil t)
 		    (setq compl
 			  (cons (list (buffer-substring (match-beginning 1)
@@ -1587,7 +1599,7 @@
 		  (forward-line 1)
 		  (if (re-search-backward "Node: *\\([^,\n]*\\) *[,\n\t]"
 					  beg t)
-		      (setq compl 
+		      (setq compl
 			    (cons (list (buffer-substring (match-beginning 1)
 							  (match-end 1)))
 				  compl))))))))
@@ -1625,26 +1637,27 @@
       (if (not found)                   ;can only happen in subfile case -- else would have erred
           (unwind-protect
               (let ((list ()))
-                (set-buffer (marker-buffer Info-tag-table-marker))
-                (goto-char (point-min))
-                (search-forward "\n\^_\nIndirect:")
-                (save-restriction
-                  (narrow-to-region (point)
-                                    (progn (search-forward "\n\^_")
-                                           (1- (point))))
-                  (goto-char (point-min))
-                  (search-forward (concat "\n" osubfile ": "))
-                  (beginning-of-line)
-                  (while (not (eobp))
-                    (re-search-forward "\\(^.*\\): [0-9]+$")
-                    (goto-char (+ (match-end 1) 2))
-                    (setq list (cons (cons (read (current-buffer))
-                                           (buffer-substring (match-beginning 1)
-                                                             (match-end 1)))
-                                     list))
-                    (goto-char (1+ (match-end 0))))
-                  (setq list (nreverse list)
-                        list (cdr list)))
+                (save-excursion
+		  (set-buffer (marker-buffer Info-tag-table-marker))
+		  (goto-char (point-min))
+		  (search-forward "\n\^_\nIndirect:")
+		  (save-restriction
+		    (narrow-to-region (point)
+				      (progn (search-forward "\n\^_")
+					     (1- (point))))
+		    (goto-char (point-min))
+		    (search-forward (concat "\n" osubfile ": "))
+		    (beginning-of-line)
+		    (while (not (eobp))
+		      (re-search-forward "\\(^.*\\): [0-9]+$")
+		      (goto-char (+ (match-end 1) 2))
+		      (setq list (cons (cons (read (current-buffer))
+					     (buffer-substring (match-beginning 1)
+							       (match-end 1)))
+				       list))
+		      (goto-char (1+ (match-end 0))))
+		    (setq list (nreverse list)
+			  list (cdr list))))
                 (while list
                   (message "Searching subfile %s..." (cdr (car list)))
                   (Info-read-subfile (car (car list)))
@@ -1667,7 +1680,7 @@
           (Info-history-add ofile onode opoint)))))
 
 ;; Extract the value of the node-pointer named NAME.
-;; If there is none, use ERRORNAME in the error message; 
+;; If there is none, use ERRORNAME in the error message;
 ;; if ERRORNAME is nil, just return nil.
 (defun Info-extract-pointer (name &optional errorname)
   (save-excursion
@@ -1943,7 +1956,7 @@
   ;; there is a problem here in that if several menu items have the same
   ;; name you can only go to the node of the first with this command.
   (Info-goto-node (Info-extract-menu-item menu-item) nil t))
-  
+
 (defun Info-extract-menu-item (menu-item &optional noerror)
   (save-excursion
     (goto-char (point-min))
@@ -2292,7 +2305,7 @@
   "Look up an Emacs Lisp function in the Elisp manual in the Info system.
 This command is designed to be used whether you are already in Info or not."
   (interactive (let ((fn (function-at-point))
-		     (enable-recursive-minibuffers t)	     
+		     (enable-recursive-minibuffers t)
 		     val)
 		 (setq val (completing-read
 			    (format "Look up Emacs Lisp function%s: "
@@ -2813,6 +2826,9 @@
   (make-local-variable 'Info-current-subfile)
   (make-local-variable 'Info-current-node)
   (make-local-variable 'Info-tag-table-marker)
+  (setq Info-tag-table-marker (make-marker))
+  (make-local-variable 'Info-tag-table-buffer)
+  (setq Info-tag-table-buffer nil)
   (make-local-variable 'Info-current-file-completions)
   (make-local-variable 'Info-current-annotation-completions)
   (make-local-variable 'Info-index-alternatives)
@@ -2878,7 +2894,7 @@
   (interactive)
   ;; Do this first, so nothing has changed if user C-g's at query.
   (and (buffer-modified-p)
-       (y-or-n-p-maybe-dialog-box "Save the file? ")
+       (y-or-n-p "Save the file? ")
        (save-buffer))
   (use-local-map Info-mode-map)
   (setq major-mode 'Info-mode)
@@ -2999,7 +3015,7 @@
 Used to construct the menubar submenu and popup menu."
   (or event (setq event (point)))
   (let ((case-fold-search t)
-	(xref-regexp (concat "\\*" 
+	(xref-regexp (concat "\\*"
 			     (regexp-quote Info-footnote-tag)
 			     "[ \n\t]*\\([^:]*\\):"))
 	up-p prev-p next-p menu xrefs subnodes in)