Function: Info-find-node-2
Info-find-node-2 is a byte-compiled function defined in info.el.gz.
Signature
(Info-find-node-2 FILENAME NODENAME &optional NO-GOING-BACK STRICT-CASE)
Source Code
;; Defined in /usr/src/emacs/lisp/info.el.gz
(defun Info-find-node-2 (filename nodename &optional no-going-back strict-case)
(buffer-disable-undo (current-buffer))
(or (derived-mode-p 'Info-mode)
(Info-mode))
(widen)
(setq Info-current-node nil)
(unwind-protect
(let ((case-fold-search t)
(virtual-fun (Info-virtual-fun 'find-node
(or filename Info-current-file)
nodename))
anchorpos)
(cond
((functionp virtual-fun)
(let ((filename (or filename Info-current-file)))
(setq buffer-read-only nil)
(setq Info-current-file filename
Info-current-subfile nil
Info-current-file-completions nil
buffer-file-name nil)
(erase-buffer)
(Info-virtual-call virtual-fun filename nodename no-going-back)
(set-marker Info-tag-table-marker nil)
(setq buffer-read-only t)
(set-buffer-modified-p nil)
(setq Info-current-node-virtual t)))
((not (and
;; Reread a file when moving from a virtual node.
(not Info-current-node-virtual)
(or (null filename)
(equal Info-current-file filename))))
;; Switch files if necessary
(let ((inhibit-read-only t))
(when Info-current-node-virtual
;; When moving from a virtual node.
(setq Info-current-node-virtual nil)
(if (null filename)
(setq filename Info-current-file)))
(setq Info-current-file nil
Info-current-subfile nil
Info-current-file-completions nil
buffer-file-name nil)
(erase-buffer)
;; Erase any memory of the previous coding-system, so that
;; info-insert-file-contents sets the buffer's encoding to
;; what the Info file specifies.
(set-buffer-file-coding-system 'undecided t)
(info-insert-file-contents filename nil)
(setq default-directory (file-name-directory filename))
(set-buffer-modified-p nil)
(setq Info-file-supports-index-cookies
(Info-file-supports-index-cookies filename))
;; See whether file has a tag table. Record the location if yes.
(Info--record-tag-table nodename)
(setq Info-current-file filename)
)))
;; Use string-equal, not equal, to ignore text props.
(if (string-equal nodename "*")
(progn (setq Info-current-node nodename)
(Info-set-mode-line))
;; Possibilities:
;;
;; 1. Anchor found in tag table
;; 2. Anchor *not* in tag table
;;
;; 3. Node found in tag table
;; 4. Node *not* found in tag table, but found in file
;; 5. Node *not* in tag table, and *not* in file
;;
;; *Or* the same, but in an indirect subfile.
;; Search file for a suitable node.
(let ((guesspos (point-min))
(regexp (concat "\\(Node:\\|Ref:\\) *\\("
(if (stringp nodename)
(regexp-quote nodename)
"")
"\\) *[,\t\n\177]")))
(catch 'foo
;; First, search a tag table, if any
(when (marker-position Info-tag-table-marker)
(let* ((m Info-tag-table-marker)
(found (Info-find-in-tag-table m regexp strict-case)))
(when found
;; FOUND is (ANCHOR POS MODE).
(let ((filepos (nth 1 found))) ;File position in bytes.
;; If this is an indirect file, determine which
;; file really holds this node and read it in.
(unless (eq (nth 2 found) 'Info-mode)
;; Note that the current buffer must be the
;; *info* buffer on entry to
;; Info-read-subfile. Thus the hackery above.
(setq filepos (Info-read-subfile filepos)))
(setq guesspos
(filepos-to-bufferpos filepos 'approximate)))
;; Handle anchor
(when (nth 0 found)
(goto-char (setq anchorpos guesspos))
(throw 'foo t)))))
;; Else we may have a node, which we search for:
(goto-char (max (point-min) (- guesspos 1000)))
;; Now search from our advised position (or from beg of
;; buffer) to find the actual node. First, check
;; whether the node is right where we are, in case the
;; buffer begins with a node.
(let ((pos (Info-find-node-in-buffer regexp strict-case)))
(when pos
(goto-char pos)
(throw 'foo t)))
;; If the Texinfo source had an @ifnottex block of text
;; before the Top node, makeinfo 5.0 and 5.1 mistakenly
;; omitted that block's size from the starting position
;; of the 1st subfile, which makes GUESSPOS overshoot
;; the correct position by the length of that text. So
;; we try again with a larger slop.
(goto-char (max (point-min) (- guesspos 10000)))
(let ((pos (Info-find-node-in-buffer regexp strict-case)))
(when pos
(goto-char pos)
(throw 'foo t)))
(when (string-match "\\([^.]+\\)\\." nodename)
(let (Info-point-loc)
(Info-find-node-2
filename (match-string 1 nodename) no-going-back))
(widen)
(throw 'foo t))
;; No such anchor in tag table or node in tag table or file
(user-error "No such node or anchor: %s" nodename))
(Info-select-node)
(goto-char (point-min))
(forward-line 1) ; skip header line
;; (when (> Info-breadcrumbs-depth 0) ; skip breadcrumbs line
;; (forward-line 1))
(cond (anchorpos
(let ((new-history (list Info-current-file
(substring-no-properties nodename))))
;; Add anchors to the history too
(setq Info-history-list
(cons new-history
(remove new-history Info-history-list))))
(goto-char anchorpos))
((numberp Info-point-loc)
(forward-line (- Info-point-loc 2))
(setq Info-point-loc nil))
((stringp Info-point-loc)
(Info-find-index-name Info-point-loc)
(setq Info-point-loc nil))))))
;; If we did not finish finding the specified node,
;; go back to the previous one or to the Top node.
(unless (or Info-current-node no-going-back)
(if Info-history
(let ((hist (car Info-history)))
(setq Info-history (cdr Info-history))
(Info-find-node (nth 0 hist) (nth 1 hist) t t)
(goto-char (nth 2 hist)))
(Info-find-node Info-current-file "Top" t t)))))