aboutsummaryrefslogtreecommitdiffstats
path: root/lisp
diff options
context:
space:
mode:
authorVibhav Pant2017-02-05 23:08:53 +0530
committerVibhav Pant2017-02-05 23:08:53 +0530
commitad70ca1dad26da79f0a95cc0ec687902ef20fa9b (patch)
tree732e8e9ace1fdd7aaf982f0fa5ac6c8e4eb5f7c7 /lisp
parent2db473bda8be72cf3c1e4694d70ce48f60492b0e (diff)
parent148100d98319499f0ac6f57b8be08cbd14884a5c (diff)
downloademacs-ad70ca1dad26da79f0a95cc0ec687902ef20fa9b.tar.gz
emacs-ad70ca1dad26da79f0a95cc0ec687902ef20fa9b.zip
Merge remote-tracking branch 'origin/master' into feature/byte-switch
Diffstat (limited to 'lisp')
-rw-r--r--lisp/auth-source.el2
-rw-r--r--lisp/buff-menu.el19
-rw-r--r--lisp/calendar/parse-time.el12
-rw-r--r--lisp/cus-start.el1
-rw-r--r--lisp/dired.el4
-rw-r--r--lisp/doc-view.el5
-rw-r--r--lisp/emacs-lisp/edebug.el13
-rw-r--r--lisp/emacs-lisp/ert-x.el26
-rw-r--r--lisp/emacs-lisp/let-alist.el2
-rw-r--r--lisp/emacs-lisp/pcase.el3
-rw-r--r--lisp/emacs-lisp/subr-x.el41
-rw-r--r--lisp/emulation/edt-mapper.el525
-rw-r--r--lisp/emulation/edt.el8
-rw-r--r--lisp/files.el15
-rw-r--r--lisp/gnus/gnus-art.el7
-rw-r--r--lisp/ibuffer.el15
-rw-r--r--lisp/image-dired.el8
-rw-r--r--lisp/indent.el32
-rw-r--r--lisp/info.el11
-rw-r--r--lisp/mh-e/mh-compat.el10
-rw-r--r--lisp/net/tramp.el30
-rw-r--r--lisp/progmodes/cc-align.el12
-rw-r--r--lisp/progmodes/cc-engine.el101
-rw-r--r--lisp/progmodes/cc-styles.el1
-rw-r--r--lisp/progmodes/cc-vars.el2
-rw-r--r--lisp/progmodes/js.el1
-rw-r--r--lisp/progmodes/xref.el6
-rw-r--r--lisp/replace.el115
-rw-r--r--lisp/subr.el2
-rw-r--r--lisp/textmodes/css-mode.el156
-rw-r--r--lisp/vc/diff-mode.el184
31 files changed, 882 insertions, 487 deletions
diff --git a/lisp/auth-source.el b/lisp/auth-source.el
index c26935fcc97..7402ab21d74 100644
--- a/lisp/auth-source.el
+++ b/lisp/auth-source.el
@@ -2129,7 +2129,7 @@ MODE can be \"login\" or \"password\"."
2129 (if user 2129 (if user
2130 (auth-source-search 2130 (auth-source-search
2131 :host host 2131 :host host
2132 :user "yourusername" 2132 :user user
2133 :max 1 2133 :max 1
2134 :require '(:user :secret) 2134 :require '(:user :secret)
2135 :create nil) 2135 :create nil)
diff --git a/lisp/buff-menu.el b/lisp/buff-menu.el
index 77b325ff25d..9f618bcb7de 100644
--- a/lisp/buff-menu.el
+++ b/lisp/buff-menu.el
@@ -102,9 +102,6 @@ This is set by the prefix argument to `buffer-menu' and related
102commands.") 102commands.")
103(make-variable-buffer-local 'Buffer-menu-files-only) 103(make-variable-buffer-local 'Buffer-menu-files-only)
104 104
105(defvar Info-current-file) ; from info.el
106(defvar Info-current-node) ; from info.el
107
108(defvar Buffer-menu-mode-map 105(defvar Buffer-menu-mode-map
109 (let ((map (make-sparse-keymap)) 106 (let ((map (make-sparse-keymap))
110 (menu-map (make-sparse-keymap))) 107 (menu-map (make-sparse-keymap)))
@@ -702,21 +699,7 @@ means list those buffers and no others."
702(defun Buffer-menu--pretty-file-name (file) 699(defun Buffer-menu--pretty-file-name (file)
703 (cond (file 700 (cond (file
704 (abbreviate-file-name file)) 701 (abbreviate-file-name file))
705 ((and (boundp 'list-buffers-directory) 702 ((bound-and-true-p list-buffers-directory))
706 list-buffers-directory)
707 list-buffers-directory)
708 ((eq major-mode 'Info-mode)
709 (Buffer-menu-info-node-description Info-current-file))
710 (t ""))) 703 (t "")))
711 704
712(defun Buffer-menu-info-node-description (file)
713 (cond
714 ((equal file "dir") "*Info Directory*")
715 ((eq file 'apropos) "*Info Apropos*")
716 ((eq file 'history) "*Info History*")
717 ((eq file 'toc) "*Info TOC*")
718 ((not (stringp file)) "") ; Avoid errors
719 (t
720 (concat "(" (file-name-nondirectory file) ") " Info-current-node))))
721
722;;; buff-menu.el ends here 705;;; buff-menu.el ends here
diff --git a/lisp/calendar/parse-time.el b/lisp/calendar/parse-time.el
index 7651c5da1f4..b781cb0eb48 100644
--- a/lisp/calendar/parse-time.el
+++ b/lisp/calendar/parse-time.el
@@ -1,4 +1,4 @@
1;;; parse-time.el --- parsing time strings 1;;; parse-time.el --- parsing time strings -*- lexical-binding: t -*-
2 2
3;; Copyright (C) 1996, 2000-2017 Free Software Foundation, Inc. 3;; Copyright (C) 1996, 2000-2017 Free Software Foundation, Inc.
4 4
@@ -203,12 +203,9 @@ any values that are unknown are returned as nil."
203 (time-second 2digit) 203 (time-second 2digit)
204 (time-secfrac "\\(\\.[0-9]+\\)?") 204 (time-secfrac "\\(\\.[0-9]+\\)?")
205 (time-numoffset (concat "\\([-+]\\)" time-hour ":?" time-minute "?")) 205 (time-numoffset (concat "\\([-+]\\)" time-hour ":?" time-minute "?"))
206 (time-offset (concat "Z" time-numoffset))
207 (partial-time (concat time-hour colon time-minute colon time-second 206 (partial-time (concat time-hour colon time-minute colon time-second
208 time-secfrac)) 207 time-secfrac))
209 (full-date (concat date-fullyear dash date-month dash date-mday)) 208 (full-date (concat date-fullyear dash date-month dash date-mday)))
210 (full-time (concat partial-time time-offset))
211 (date-time (concat full-date "T" full-time)))
212 (list (concat "^" full-date) 209 (list (concat "^" full-date)
213 (concat "T" partial-time) 210 (concat "T" partial-time)
214 (concat "\\(Z\\|" time-numoffset "\\)"))) 211 (concat "\\(Z\\|" time-numoffset "\\)")))
@@ -225,7 +222,7 @@ If DATE-STRING cannot be parsed, it falls back to
225 (time-re (nth 1 parse-time-iso8601-regexp)) 222 (time-re (nth 1 parse-time-iso8601-regexp))
226 (tz-re (nth 2 parse-time-iso8601-regexp)) 223 (tz-re (nth 2 parse-time-iso8601-regexp))
227 re-start 224 re-start
228 time seconds minute hour fractional-seconds 225 time seconds minute hour
229 day month year day-of-week dst tz) 226 day month year day-of-week dst tz)
230 ;; We need to populate 'time' with 227 ;; We need to populate 'time' with
231 ;; (SEC MIN HOUR DAY MON YEAR DOW DST TZ) 228 ;; (SEC MIN HOUR DAY MON YEAR DOW DST TZ)
@@ -240,9 +237,6 @@ If DATE-STRING cannot be parsed, it falls back to
240 (setq hour (string-to-number (match-string 1 date-string)) 237 (setq hour (string-to-number (match-string 1 date-string))
241 minute (string-to-number (match-string 2 date-string)) 238 minute (string-to-number (match-string 2 date-string))
242 seconds (string-to-number (match-string 3 date-string)) 239 seconds (string-to-number (match-string 3 date-string))
243 fractional-seconds (string-to-number (or
244 (match-string 4 date-string)
245 "0"))
246 re-start (match-end 0)) 240 re-start (match-end 0))
247 (when (string-match tz-re date-string re-start) 241 (when (string-match tz-re date-string re-start)
248 (if (string= "Z" (match-string 1 date-string)) 242 (if (string= "Z" (match-string 1 date-string))
diff --git a/lisp/cus-start.el b/lisp/cus-start.el
index a790419b86f..51c43c7d21a 100644
--- a/lisp/cus-start.el
+++ b/lisp/cus-start.el
@@ -511,6 +511,7 @@ since it could result in memory overflow and make Emacs crash."
511 (scroll-step windows integer) 511 (scroll-step windows integer)
512 (scroll-conservatively windows integer) 512 (scroll-conservatively windows integer)
513 (scroll-margin windows integer) 513 (scroll-margin windows integer)
514 (maximum-scroll-margin windows float "26.1")
514 (hscroll-margin windows integer "22.1") 515 (hscroll-margin windows integer "22.1")
515 (hscroll-step windows number "22.1") 516 (hscroll-step windows number "22.1")
516 (truncate-partial-width-windows 517 (truncate-partial-width-windows
diff --git a/lisp/dired.el b/lisp/dired.el
index 350f6a7d2e3..2733372eb7b 100644
--- a/lisp/dired.el
+++ b/lisp/dired.el
@@ -59,6 +59,10 @@
59May contain all other options that don't contradict `-l'; 59May contain all other options that don't contradict `-l';
60may contain even `F', `b', `i' and `s'. See also the variable 60may contain even `F', `b', `i' and `s'. See also the variable
61`dired-ls-F-marks-symlinks' concerning the `F' switch. 61`dired-ls-F-marks-symlinks' concerning the `F' switch.
62Options that include embedded whitespace must be quoted
63like this: \\\"--option=value with spaces\\\"; you can use
64`combine-and-quote-strings' to produce the correct quoting of
65each option.
62On systems such as MS-DOS and MS-Windows, which use `ls' emulation in Lisp, 66On systems such as MS-DOS and MS-Windows, which use `ls' emulation in Lisp,
63some of the `ls' switches are not supported; see the doc string of 67some of the `ls' switches are not supported; see the doc string of
64`insert-directory' in `ls-lisp.el' for more details." 68`insert-directory' in `ls-lisp.el' for more details."
diff --git a/lisp/doc-view.el b/lisp/doc-view.el
index 2c11cd23a7f..172ea163c18 100644
--- a/lisp/doc-view.el
+++ b/lisp/doc-view.el
@@ -442,6 +442,9 @@ Typically \"page-%s.png\".")
442(defun doc-view-revert-buffer (&optional ignore-auto noconfirm) 442(defun doc-view-revert-buffer (&optional ignore-auto noconfirm)
443 "Like `revert-buffer', but preserves the buffer's current modes." 443 "Like `revert-buffer', but preserves the buffer's current modes."
444 (interactive (list (not current-prefix-arg))) 444 (interactive (list (not current-prefix-arg)))
445 (if (< undo-outer-limit (* 2 (buffer-size)))
446 ;; It's normal for this operation to result in a very large undo entry.
447 (setq-local undo-outer-limit (* 2 (buffer-size))))
445 (cl-labels ((revert () 448 (cl-labels ((revert ()
446 (let (revert-buffer-function) 449 (let (revert-buffer-function)
447 (revert-buffer ignore-auto noconfirm 'preserve-modes)))) 450 (revert-buffer ignore-auto noconfirm 'preserve-modes))))
@@ -1763,6 +1766,8 @@ toggle between displaying the document or editing it as text.
1763 (unless doc-view-doc-type 1766 (unless doc-view-doc-type
1764 (doc-view-set-doc-type)) 1767 (doc-view-set-doc-type))
1765 (doc-view-set-up-single-converter) 1768 (doc-view-set-up-single-converter)
1769 (unless (memq doc-view-doc-type '(ps))
1770 (setq-local require-final-newline nil))
1766 1771
1767 (doc-view-make-safe-dir doc-view-cache-directory) 1772 (doc-view-make-safe-dir doc-view-cache-directory)
1768 ;; Handle compressed files, remote files, files inside archives 1773 ;; Handle compressed files, remote files, files inside archives
diff --git a/lisp/emacs-lisp/edebug.el b/lisp/emacs-lisp/edebug.el
index db54d1eeb20..ec0f08de356 100644
--- a/lisp/emacs-lisp/edebug.el
+++ b/lisp/emacs-lisp/edebug.el
@@ -112,6 +112,18 @@ and some not, use `def-edebug-spec' to specify an `edebug-form-spec'."
112 :type 'boolean 112 :type 'boolean
113 :group 'edebug) 113 :group 'edebug)
114 114
115(defcustom edebug-max-depth 150
116 "Maximum recursion depth when instrumenting code.
117This limit is intended to stop recursion if an Edebug specification
118contains an infinite loop. When Edebug is instrumenting code
119containing very large quoted lists, it may reach this limit and give
120the error message \"Too deep - perhaps infinite loop in spec?\".
121Make this limit larger to countermand that, but you may also need to
122increase `max-lisp-eval-depth' and `max-specpdl-size'."
123 :type 'integer
124 :group 'edebug
125 :version "26.1")
126
115(defcustom edebug-save-windows t 127(defcustom edebug-save-windows t
116 "If non-nil, Edebug saves and restores the window configuration. 128 "If non-nil, Edebug saves and restores the window configuration.
117That takes some time, so if your program does not care what happens to 129That takes some time, so if your program does not care what happens to
@@ -1452,7 +1464,6 @@ expressions; a `progn' form will be returned enclosing these forms."
1452(defvar edebug-after-dotted-spec nil) 1464(defvar edebug-after-dotted-spec nil)
1453 1465
1454(defvar edebug-matching-depth 0) ;; initial value 1466(defvar edebug-matching-depth 0) ;; initial value
1455(defconst edebug-max-depth 150) ;; maximum number of matching recursions.
1456 1467
1457 1468
1458;;; Failure to match 1469;;; Failure to match
diff --git a/lisp/emacs-lisp/ert-x.el b/lisp/emacs-lisp/ert-x.el
index 7d99cb30274..4cf9d9609e9 100644
--- a/lisp/emacs-lisp/ert-x.el
+++ b/lisp/emacs-lisp/ert-x.el
@@ -97,7 +97,7 @@ To be used in ERT tests. If BODY finishes successfully, the test
97buffer is killed; if there is an error, the test buffer is kept 97buffer is killed; if there is an error, the test buffer is kept
98around on error for further inspection. Its name is derived from 98around on error for further inspection. Its name is derived from
99the name of the test and the result of NAME-FORM." 99the name of the test and the result of NAME-FORM."
100 (declare (debug ((form) body)) 100 (declare (debug ((":name" form) body))
101 (indent 1)) 101 (indent 1))
102 `(ert--call-with-test-buffer ,name-form (lambda () ,@body))) 102 `(ert--call-with-test-buffer ,name-form (lambda () ,@body)))
103 103
@@ -285,6 +285,30 @@ BUFFER defaults to current buffer. Does not modify BUFFER."
285 (kill-buffer clone))))))) 285 (kill-buffer clone)))))))
286 286
287 287
288(defmacro ert-with-message-capture (var &rest body)
289 "Execute BODY while collecting anything written with `message' in VAR.
290
291Capture all messages produced by `message' when it is called from
292Lisp, and concatenate them separated by newlines into one string.
293
294This is useful for separating the issuance of messages by the
295code under test from the behavior of the *Messages* buffer."
296 (declare (debug (symbolp body))
297 (indent 1))
298 (let ((g-advice (cl-gensym)))
299 `(let* ((,var "")
300 (,g-advice (lambda (func &rest args)
301 (if (or (null args) (equal (car args) ""))
302 (apply func args)
303 (let ((msg (apply #'format-message args)))
304 (setq ,var (concat ,var msg "\n"))
305 (funcall func "%s" msg))))))
306 (advice-add 'message :around ,g-advice)
307 (unwind-protect
308 (progn ,@body)
309 (advice-remove 'message ,g-advice)))))
310
311
288(provide 'ert-x) 312(provide 'ert-x)
289 313
290;;; ert-x.el ends here 314;;; ert-x.el ends here
diff --git a/lisp/emacs-lisp/let-alist.el b/lisp/emacs-lisp/let-alist.el
index a45fc0a05c3..cf82fe3ec63 100644
--- a/lisp/emacs-lisp/let-alist.el
+++ b/lisp/emacs-lisp/let-alist.el
@@ -4,7 +4,7 @@
4 4
5;; Author: Artur Malabarba <emacs@endlessparentheses.com> 5;; Author: Artur Malabarba <emacs@endlessparentheses.com>
6;; Package-Requires: ((emacs "24.1")) 6;; Package-Requires: ((emacs "24.1"))
7;; Version: 1.0.4 7;; Version: 1.0.5
8;; Keywords: extensions lisp 8;; Keywords: extensions lisp
9;; Prefix: let-alist 9;; Prefix: let-alist
10;; Separator: - 10;; Separator: -
diff --git a/lisp/emacs-lisp/pcase.el b/lisp/emacs-lisp/pcase.el
index 54678c5f324..46a5eedd150 100644
--- a/lisp/emacs-lisp/pcase.el
+++ b/lisp/emacs-lisp/pcase.el
@@ -89,7 +89,8 @@
89 (functionp &rest form) 89 (functionp &rest form)
90 sexp)) 90 sexp))
91 91
92(def-edebug-spec pcase-MACRO pcase--edebug-match-macro) 92;; See bug#24717
93(put 'pcase-MACRO 'edebug-form-spec 'pcase--edebug-match-macro)
93 94
94;; Only called from edebug. 95;; Only called from edebug.
95(declare-function get-edebug-spec "edebug" (symbol)) 96(declare-function get-edebug-spec "edebug" (symbol))
diff --git a/lisp/emacs-lisp/subr-x.el b/lisp/emacs-lisp/subr-x.el
index 7736225b5fa..f7a846927c0 100644
--- a/lisp/emacs-lisp/subr-x.el
+++ b/lisp/emacs-lisp/subr-x.el
@@ -115,12 +115,16 @@ threading."
115 binding)) 115 binding))
116 bindings))) 116 bindings)))
117 117
118(defmacro if-let (bindings then &rest else) 118(defmacro if-let* (bindings then &rest else)
119 "Process BINDINGS and if all values are non-nil eval THEN, else ELSE. 119 "Bind variables according to VARLIST and eval THEN or ELSE.
120Argument BINDINGS is a list of tuples whose car is a symbol to be 120Each binding is evaluated in turn with `let*', and evaluation
121bound and (optionally) used in THEN, and its cadr is a sexp to be 121stops if a binding value is nil. If all are non-nil, the value
122evalled to set symbol's value. In the special case you only want 122of THEN is returned, or the last form in ELSE is returned.
123to bind a single value, BINDINGS can just be a plain tuple." 123Each element of VARLIST is a symbol (which is bound to nil)
124or a list (SYMBOL VALUEFORM) (which binds SYMBOL to the value of VALUEFORM).
125In the special case you only want to bind a single value,
126VARLIST can just be a plain tuple.
127\n(fn VARLIST THEN ELSE...)"
124 (declare (indent 2) 128 (declare (indent 2)
125 (debug ([&or (&rest (symbolp form)) (symbolp form)] form body))) 129 (debug ([&or (&rest (symbolp form)) (symbolp form)] form body)))
126 (when (and (<= (length bindings) 2) 130 (when (and (<= (length bindings) 2)
@@ -132,15 +136,23 @@ to bind a single value, BINDINGS can just be a plain tuple."
132 ,then 136 ,then
133 ,@else))) 137 ,@else)))
134 138
135(defmacro when-let (bindings &rest body) 139(defmacro when-let* (bindings &rest body)
136 "Process BINDINGS and if all values are non-nil eval BODY. 140 "Bind variables according to VARLIST and conditionally eval BODY.
137Argument BINDINGS is a list of tuples whose car is a symbol to be 141Each binding is evaluated in turn with `let*', and evaluation
138bound and (optionally) used in BODY, and its cadr is a sexp to be 142stops if a binding value is nil. If all are non-nil, the value
139evalled to set symbol's value. In the special case you only want 143of the last form in BODY is returned.
140to bind a single value, BINDINGS can just be a plain tuple." 144Each element of VARLIST is a symbol (which is bound to nil)
145or a list (SYMBOL VALUEFORM) (which binds SYMBOL to the value of VALUEFORM).
146In the special case you only want to bind a single value,
147VARLIST can just be a plain tuple.
148\n(fn VARLIST BODY...)"
141 (declare (indent 1) (debug if-let)) 149 (declare (indent 1) (debug if-let))
142 (list 'if-let bindings (macroexp-progn body))) 150 (list 'if-let bindings (macroexp-progn body)))
143 151
152(defalias 'if-let 'if-let*)
153(defalias 'when-let 'when-let*)
154(defalias 'and-let* 'when-let*)
155
144(defsubst hash-table-empty-p (hash-table) 156(defsubst hash-table-empty-p (hash-table)
145 "Check whether HASH-TABLE is empty (has 0 elements)." 157 "Check whether HASH-TABLE is empty (has 0 elements)."
146 (zerop (hash-table-count hash-table))) 158 (zerop (hash-table-count hash-table)))
@@ -214,6 +226,11 @@ user enters `recenter', `scroll-up', or `scroll-down' responses,
214perform the requested window recentering or scrolling and ask 226perform the requested window recentering or scrolling and ask
215again. 227again.
216 228
229When `use-dialog-box' is t (the default), this function can pop
230up a dialog window to collect the user input. That functionality
231requires `display-popup-menus-p' to return t. Otherwise, a text
232dialog will be used.
233
217The return value is the matching entry from the CHOICES list. 234The return value is the matching entry from the CHOICES list.
218 235
219Usage example: 236Usage example:
diff --git a/lisp/emulation/edt-mapper.el b/lisp/emulation/edt-mapper.el
index 24a8f039fa5..457ad55dd6c 100644
--- a/lisp/emulation/edt-mapper.el
+++ b/lisp/emulation/edt-mapper.el
@@ -57,9 +57,9 @@
57;; Usage: 57;; Usage:
58 58
59;; Simply load this file into emacs (version 19 or higher) 59;; Simply load this file into emacs (version 19 or higher)
60;; using the following command. 60;; and run the function edt-mapper, using the following command.
61 61
62;; emacs -q -l edt-mapper.el 62;; emacs -q -l edt-mapper -f edt-mapper
63 63
64;; The "-q" option prevents loading of your init file (commands 64;; The "-q" option prevents loading of your init file (commands
65;; therein might confuse this program). 65;; therein might confuse this program).
@@ -96,10 +96,6 @@
96 96
97;;; Code: 97;;; Code:
98 98
99;; Otherwise it just hangs. This seems preferable.
100(if noninteractive
101 (error "edt-mapper cannot be loaded in batch mode"))
102
103;;; 99;;;
104;;; Decide Emacs Variant, GNU Emacs or XEmacs (aka Lucid Emacs). 100;;; Decide Emacs Variant, GNU Emacs or XEmacs (aka Lucid Emacs).
105;;; Determine Window System, and X Server Vendor (if appropriate). 101;;; Determine Window System, and X Server Vendor (if appropriate).
@@ -124,6 +120,8 @@
124;;; 120;;;
125;;; Key variables 121;;; Key variables
126;;; 122;;;
123
124;; FIXME some/all of these should be let-bound, not global.
127(defvar edt-key nil) 125(defvar edt-key nil)
128(defvar edt-enter nil) 126(defvar edt-enter nil)
129(defvar edt-return nil) 127(defvar edt-return nil)
@@ -137,88 +135,116 @@
137(defvar edt-save-function-key-map) 135(defvar edt-save-function-key-map)
138 136
139;;; 137;;;
140;;; Determine Terminal Type (if appropriate). 138;;; Key mapping functions
141;;;
142
143(if (and edt-window-system (not (eq edt-window-system 'tty)))
144 (setq edt-term nil)
145 (setq edt-term (getenv "TERM")))
146
147;;;
148;;; Implements a workaround for a feature that was added to simple.el.
149;;;
150;;; Many function keys have no Emacs functions assigned to them by
151;;; default. A subset of these are typically assigned functions in the
152;;; EDT emulation. This includes all the keypad keys and a some others
153;;; like Delete.
154;;;
155;;; Logic in simple.el maps some of these unassigned function keys to
156;;; ordinary typing keys. Where this is the case, a call to
157;;; read-key-sequence, below, does not return the name of the function
158;;; key pressed by the user but, instead, it returns the name of the
159;;; key to which it has been mapped. It needs to know the name of the
160;;; key pressed by the user. As a workaround, we assign a function to
161;;; each of the unassigned function keys of interest, here. These
162;;; assignments override the mapping to other keys and are only
163;;; temporary since, when edt-mapper is finished executing, it causes
164;;; Emacs to exit.
165;;;
166
167(mapc
168 (lambda (function-key)
169 (if (not (lookup-key (current-global-map) function-key))
170 (define-key (current-global-map) function-key 'forward-char)))
171 '([kp-0] [kp-1] [kp-2] [kp-3] [kp-4]
172 [kp-5] [kp-6] [kp-7] [kp-8] [kp-9]
173 [kp-space]
174 [kp-tab]
175 [kp-enter]
176 [kp-multiply]
177 [kp-add]
178 [kp-separator]
179 [kp-subtract]
180 [kp-decimal]
181 [kp-divide]
182 [kp-equal]
183 [backspace]
184 [delete]
185 [tab]
186 [linefeed]
187 [clear]))
188
189;;;
190;;; Make sure the window is big enough to display the instructions,
191;;; except where window cannot be re-sized.
192;;;
193
194(if (and edt-window-system (not (eq edt-window-system 'tty)))
195 (set-frame-size (selected-frame) 80 36))
196
197;;;
198;;; Create buffers - Directions and Keys
199;;; 139;;;
200(if (not (get-buffer "Directions")) (generate-new-buffer "Directions")) 140(defun edt-map-key (ident descrip)
201(if (not (get-buffer "Keys")) (generate-new-buffer "Keys")) 141 (interactive)
142 (if (featurep 'xemacs)
143 (progn
144 (setq edt-key-seq (read-key-sequence (format "Press %s%s: " ident descrip)))
145 (setq edt-key (concat "[" (format "%s" (event-key (aref edt-key-seq 0))) "]"))
146 (cond ((not (equal edt-key edt-return))
147 (set-buffer "Keys")
148 (insert (format " (\"%s\" . %s)\n" ident edt-key))
149 (set-buffer "Directions"))
150 ;; bogosity to get next prompt to come up, if the user hits <CR>!
151 ;; check periodically to see if this is still needed...
152 (t
153 (set-buffer "Keys")
154 (insert (format " (\"%s\" . \"\" )\n" ident))
155 (set-buffer "Directions"))))
156 (setq edt-key (read-key-sequence (format "Press %s%s: " ident descrip)))
157 (cond ((not (equal edt-key edt-return))
158 (set-buffer "Keys")
159 (insert (if (vectorp edt-key)
160 (format " (\"%s\" . %s)\n" ident edt-key)
161 (format " (\"%s\" . \"%s\")\n" ident edt-key)))
162 (set-buffer "Directions"))
163 ;; bogosity to get next prompt to come up, if the user hits <CR>!
164 ;; check periodically to see if this is still needed...
165 (t
166 (set-buffer "Keys")
167 (insert (format " (\"%s\" . \"\" )\n" ident))
168 (set-buffer "Directions"))))
169 edt-key)
202 170
203;;; 171(defun edt-mapper ()
204;;; Put header in the Keys buffer 172 (if noninteractive
205;;; 173 (user-error "edt-mapper cannot be loaded in batch mode"))
206(set-buffer "Keys") 174 ;; Determine Terminal Type (if appropriate).
207(insert "\ 175 (if (and edt-window-system (not (eq edt-window-system 'tty)))
176 (setq edt-term nil)
177 (setq edt-term (getenv "TERM")))
178 ;;
179 ;; Implements a workaround for a feature that was added to simple.el.
180 ;;
181 ;; Many function keys have no Emacs functions assigned to them by
182 ;; default. A subset of these are typically assigned functions in the
183 ;; EDT emulation. This includes all the keypad keys and a some others
184 ;; like Delete.
185 ;;
186 ;; Logic in simple.el maps some of these unassigned function keys to
187 ;; ordinary typing keys. Where this is the case, a call to
188 ;; read-key-sequence, below, does not return the name of the function
189 ;; key pressed by the user but, instead, it returns the name of the
190 ;; key to which it has been mapped. It needs to know the name of the
191 ;; key pressed by the user. As a workaround, we assign a function to
192 ;; each of the unassigned function keys of interest, here. These
193 ;; assignments override the mapping to other keys and are only
194 ;; temporary since, when edt-mapper is finished executing, it causes
195 ;; Emacs to exit.
196 ;;
197 (mapc
198 (lambda (function-key)
199 (if (not (lookup-key (current-global-map) function-key))
200 (define-key (current-global-map) function-key 'forward-char)))
201 '([kp-0] [kp-1] [kp-2] [kp-3] [kp-4]
202 [kp-5] [kp-6] [kp-7] [kp-8] [kp-9]
203 [kp-space]
204 [kp-tab]
205 [kp-enter]
206 [kp-multiply]
207 [kp-add]
208 [kp-separator]
209 [kp-subtract]
210 [kp-decimal]
211 [kp-divide]
212 [kp-equal]
213 [backspace]
214 [delete]
215 [tab]
216 [linefeed]
217 [clear]))
218 ;;
219 ;; Make sure the window is big enough to display the instructions,
220 ;; except where window cannot be re-sized.
221 ;;
222 (if (and edt-window-system (not (eq edt-window-system 'tty)))
223 (set-frame-size (selected-frame) 80 36))
224 ;;
225 ;; Create buffers - Directions and Keys
226 ;;
227 (if (not (get-buffer "Directions")) (generate-new-buffer "Directions"))
228 (if (not (get-buffer "Keys")) (generate-new-buffer "Keys"))
229 ;;
230 ;; Put header in the Keys buffer
231 ;;
232 (set-buffer "Keys")
233 (insert "\
208;; 234;;
209;; Key definitions for the EDT emulation within GNU Emacs 235;; Key definitions for the EDT emulation within GNU Emacs
210;; 236;;
211 237
212(defconst *EDT-keys* 238\(defconst *EDT-keys*
213 '( 239 '(
214") 240 ")
215 241
216;;; 242 ;;
217;;; Display directions 243 ;; Display directions
218;;; 244 ;;
219(switch-to-buffer "Directions") 245 (switch-to-buffer "Directions")
220(if (and edt-window-system (not (eq edt-window-system 'tty))) 246 (if (and edt-window-system (not (eq edt-window-system 'tty)))
221 (insert " 247 (insert "
222 EDT MAPPER 248 EDT MAPPER
223 249
224 You will be asked to press keys to create a custom mapping (under a 250 You will be asked to press keys to create a custom mapping (under a
@@ -240,7 +266,7 @@
240 just press RETURN at the prompt. 266 just press RETURN at the prompt.
241 267
242") 268")
243 (insert " 269 (insert "
244 EDT MAPPER 270 EDT MAPPER
245 271
246 You will be asked to press keys to create a custom mapping of your 272 You will be asked to press keys to create a custom mapping of your
@@ -259,39 +285,39 @@
259 285
260")) 286"))
261 287
262(delete-other-windows) 288 (delete-other-windows)
263 289
264;;; 290 ;;
265;;; Save <CR> for future reference. 291 ;; Save <CR> for future reference.
266;;; 292 ;;
267;;; For GNU Emacs, running in a Window System, first hide bindings in 293 ;; For GNU Emacs, running in a Window System, first hide bindings in
268;;; function-key-map. 294 ;; function-key-map.
269;;; 295 ;;
270(cond 296 (cond
271 ((featurep 'xemacs) 297 ((featurep 'xemacs)
272 (setq edt-return-seq (read-key-sequence "Hit carriage-return <CR> to continue ")) 298 (setq edt-return-seq (read-key-sequence "Hit carriage-return <CR> to continue "))
273 (setq edt-return (concat "[" (format "%s" (event-key (aref edt-return-seq 0))) "]"))) 299 (setq edt-return (concat "[" (format "%s" (event-key (aref edt-return-seq 0))) "]")))
274 (t 300 (t
275 (if edt-window-system 301 (if edt-window-system
276 (progn 302 (progn
277 (setq edt-save-function-key-map function-key-map) 303 (setq edt-save-function-key-map function-key-map)
278 (setq function-key-map (make-sparse-keymap)))) 304 (setq function-key-map (make-sparse-keymap))))
279 (setq edt-return (read-key-sequence "Hit carriage-return <CR> to continue ")))) 305 (setq edt-return (read-key-sequence "Hit carriage-return <CR> to continue "))))
280 306
281;;; 307 ;;
282;;; Remove prefix-key bindings to F1 and F2 in global-map so they can be 308 ;; Remove prefix-key bindings to F1 and F2 in global-map so they can be
283;;; bound in the EDT Emulation mode. 309 ;; bound in the EDT Emulation mode.
284;;; 310 ;;
285(global-unset-key [f1]) 311 (global-unset-key [f1])
286(global-unset-key [f2]) 312 (global-unset-key [f2])
287 313
288;;; 314 ;;
289;;; Display Keypad Diagram and Begin Prompting for Keys 315 ;; Display Keypad Diagram and Begin Prompting for Keys
290;;; 316 ;;
291(set-buffer "Directions") 317 (set-buffer "Directions")
292(delete-region (point-min) (point-max)) 318 (delete-region (point-min) (point-max))
293(if (and edt-window-system (not (eq edt-window-system 'tty))) 319 (if (and edt-window-system (not (eq edt-window-system 'tty)))
294 (insert " 320 (insert "
295 321
296 PRESS THE KEY SPECIFIED IN THE MINIBUFFER BELOW. 322 PRESS THE KEY SPECIFIED IN THE MINIBUFFER BELOW.
297 323
@@ -321,11 +347,11 @@
321 REMEMBER: JUST PRESS RETURN TO SKIP MAPPING A KEY. 347 REMEMBER: JUST PRESS RETURN TO SKIP MAPPING A KEY.
322 348
323") 349")
324 (progn 350 (progn
325 (insert " 351 (insert "
326 GENERATING A CUSTOM CONFIGURATION FILE FOR TERMINAL TYPE: ") 352 GENERATING A CUSTOM CONFIGURATION FILE FOR TERMINAL TYPE: ")
327 (insert (format "%s." edt-term)) 353 (insert (format "%s." edt-term))
328 (insert " 354 (insert "
329 355
330 PRESS THE KEY SPECIFIED IN THE MINIBUFFER BELOW. 356 PRESS THE KEY SPECIFIED IN THE MINIBUFFER BELOW.
331 357
@@ -347,142 +373,109 @@
347 REMEMBER: JUST PRESS RETURN TO SKIP MAPPING A KEY."))) 373 REMEMBER: JUST PRESS RETURN TO SKIP MAPPING A KEY.")))
348 374
349 375
350;;;
351;;; Key mapping functions
352;;;
353(defun edt-map-key (ident descrip)
354 (interactive)
355 (if (featurep 'xemacs)
356 (progn
357 (setq edt-key-seq (read-key-sequence (format "Press %s%s: " ident descrip)))
358 (setq edt-key (concat "[" (format "%s" (event-key (aref edt-key-seq 0))) "]"))
359 (cond ((not (equal edt-key edt-return))
360 (set-buffer "Keys")
361 (insert (format " (\"%s\" . %s)\n" ident edt-key))
362 (set-buffer "Directions"))
363 ;; bogosity to get next prompt to come up, if the user hits <CR>!
364 ;; check periodically to see if this is still needed...
365 (t
366 (set-buffer "Keys")
367 (insert (format " (\"%s\" . \"\" )\n" ident))
368 (set-buffer "Directions"))))
369 (setq edt-key (read-key-sequence (format "Press %s%s: " ident descrip)))
370 (cond ((not (equal edt-key edt-return))
371 (set-buffer "Keys")
372 (insert (if (vectorp edt-key)
373 (format " (\"%s\" . %s)\n" ident edt-key)
374 (format " (\"%s\" . \"%s\")\n" ident edt-key)))
375 (set-buffer "Directions"))
376 ;; bogosity to get next prompt to come up, if the user hits <CR>!
377 ;; check periodically to see if this is still needed...
378 (t
379 (set-buffer "Keys")
380 (insert (format " (\"%s\" . \"\" )\n" ident))
381 (set-buffer "Directions"))))
382 edt-key)
383 376
384(set-buffer "Keys") 377 (set-buffer "Keys")
385(insert " 378 (insert "
386;; 379;;
387;; Arrows 380;; Arrows
388;; 381;;
389") 382")
390(set-buffer "Directions") 383 (set-buffer "Directions")
391 384
392(edt-map-key "UP" " - The Up Arrow Key") 385 (edt-map-key "UP" " - The Up Arrow Key")
393(edt-map-key "DOWN" " - The Down Arrow Key") 386 (edt-map-key "DOWN" " - The Down Arrow Key")
394(edt-map-key "LEFT" " - The Left Arrow Key") 387 (edt-map-key "LEFT" " - The Left Arrow Key")
395(edt-map-key "RIGHT" " - The Right Arrow Key") 388 (edt-map-key "RIGHT" " - The Right Arrow Key")
396 389
397 390
398(set-buffer "Keys") 391 (set-buffer "Keys")
399(insert " 392 (insert "
400;; 393;;
401;; PF keys 394;; PF keys
402;; 395;;
403") 396")
404(set-buffer "Directions") 397 (set-buffer "Directions")
405 398
406(edt-map-key "PF1" " - The PF1 (GOLD) Key") 399 (edt-map-key "PF1" " - The PF1 (GOLD) Key")
407(edt-map-key "PF2" " - The Keypad PF2 Key") 400 (edt-map-key "PF2" " - The Keypad PF2 Key")
408(edt-map-key "PF3" " - The Keypad PF3 Key") 401 (edt-map-key "PF3" " - The Keypad PF3 Key")
409(edt-map-key "PF4" " - The Keypad PF4 Key") 402 (edt-map-key "PF4" " - The Keypad PF4 Key")
410 403
411(set-buffer "Keys") 404 (set-buffer "Keys")
412(insert " 405 (insert "
413;; 406;;
414;; KP0-9 KP- KP, KPP and KPE 407;; KP0-9 KP- KP, KPP and KPE
415;; 408;;
416") 409")
417(set-buffer "Directions") 410 (set-buffer "Directions")
418 411
419(edt-map-key "KP0" " - The Keypad 0 Key") 412 (edt-map-key "KP0" " - The Keypad 0 Key")
420(edt-map-key "KP1" " - The Keypad 1 Key") 413 (edt-map-key "KP1" " - The Keypad 1 Key")
421(edt-map-key "KP2" " - The Keypad 2 Key") 414 (edt-map-key "KP2" " - The Keypad 2 Key")
422(edt-map-key "KP3" " - The Keypad 3 Key") 415 (edt-map-key "KP3" " - The Keypad 3 Key")
423(edt-map-key "KP4" " - The Keypad 4 Key") 416 (edt-map-key "KP4" " - The Keypad 4 Key")
424(edt-map-key "KP5" " - The Keypad 5 Key") 417 (edt-map-key "KP5" " - The Keypad 5 Key")
425(edt-map-key "KP6" " - The Keypad 6 Key") 418 (edt-map-key "KP6" " - The Keypad 6 Key")
426(edt-map-key "KP7" " - The Keypad 7 Key") 419 (edt-map-key "KP7" " - The Keypad 7 Key")
427(edt-map-key "KP8" " - The Keypad 8 Key") 420 (edt-map-key "KP8" " - The Keypad 8 Key")
428(edt-map-key "KP9" " - The Keypad 9 Key") 421 (edt-map-key "KP9" " - The Keypad 9 Key")
429(edt-map-key "KP-" " - The Keypad - Key") 422 (edt-map-key "KP-" " - The Keypad - Key")
430(edt-map-key "KP," " - The Keypad , Key") 423 (edt-map-key "KP," " - The Keypad , Key")
431(edt-map-key "KPP" " - The Keypad . Key") 424 (edt-map-key "KPP" " - The Keypad . Key")
432(edt-map-key "KPE" " - The Keypad Enter Key") 425 (edt-map-key "KPE" " - The Keypad Enter Key")
433;; Save the enter key 426 ;; Save the enter key
434(setq edt-enter edt-key) 427 (setq edt-enter edt-key)
435(setq edt-enter-seq edt-key-seq) 428 (setq edt-enter-seq edt-key-seq)
436 429
437 430
438(set-buffer "Keys") 431 (set-buffer "Keys")
439(insert " 432 (insert "
440;; 433;;
441;; Editing keypad (FIND, INSERT, REMOVE) 434;; Editing keypad (FIND, INSERT, REMOVE)
442;; (SELECT, PREVIOUS, NEXT) 435;; (SELECT, PREVIOUS, NEXT)
443;; 436;;
444") 437")
445(set-buffer "Directions") 438 (set-buffer "Directions")
446 439
447(edt-map-key "FIND" " - The Find key on the editing keypad") 440 (edt-map-key "FIND" " - The Find key on the editing keypad")
448(edt-map-key "INSERT" " - The Insert key on the editing keypad") 441 (edt-map-key "INSERT" " - The Insert key on the editing keypad")
449(edt-map-key "REMOVE" " - The Remove key on the editing keypad") 442 (edt-map-key "REMOVE" " - The Remove key on the editing keypad")
450(edt-map-key "SELECT" " - The Select key on the editing keypad") 443 (edt-map-key "SELECT" " - The Select key on the editing keypad")
451(edt-map-key "PREVIOUS" " - The Prev Scr key on the editing keypad") 444 (edt-map-key "PREVIOUS" " - The Prev Scr key on the editing keypad")
452(edt-map-key "NEXT" " - The Next Scr key on the editing keypad") 445 (edt-map-key "NEXT" " - The Next Scr key on the editing keypad")
453 446
454(set-buffer "Keys") 447 (set-buffer "Keys")
455(insert " 448 (insert "
456;; 449;;
457;; F1-14 Help Do F17-F20 450;; F1-14 Help Do F17-F20
458;; 451;;
459") 452")
460(set-buffer "Directions") 453 (set-buffer "Directions")
461 454
462(edt-map-key "F1" " - F1 Function Key") 455 (edt-map-key "F1" " - F1 Function Key")
463(edt-map-key "F2" " - F2 Function Key") 456 (edt-map-key "F2" " - F2 Function Key")
464(edt-map-key "F3" " - F3 Function Key") 457 (edt-map-key "F3" " - F3 Function Key")
465(edt-map-key "F4" " - F4 Function Key") 458 (edt-map-key "F4" " - F4 Function Key")
466(edt-map-key "F5" " - F5 Function Key") 459 (edt-map-key "F5" " - F5 Function Key")
467(edt-map-key "F6" " - F6 Function Key") 460 (edt-map-key "F6" " - F6 Function Key")
468(edt-map-key "F7" " - F7 Function Key") 461 (edt-map-key "F7" " - F7 Function Key")
469(edt-map-key "F8" " - F8 Function Key") 462 (edt-map-key "F8" " - F8 Function Key")
470(edt-map-key "F9" " - F9 Function Key") 463 (edt-map-key "F9" " - F9 Function Key")
471(edt-map-key "F10" " - F10 Function Key") 464 (edt-map-key "F10" " - F10 Function Key")
472(edt-map-key "F11" " - F11 Function Key") 465 (edt-map-key "F11" " - F11 Function Key")
473(edt-map-key "F12" " - F12 Function Key") 466 (edt-map-key "F12" " - F12 Function Key")
474(edt-map-key "F13" " - F13 Function Key") 467 (edt-map-key "F13" " - F13 Function Key")
475(edt-map-key "F14" " - F14 Function Key") 468 (edt-map-key "F14" " - F14 Function Key")
476(edt-map-key "HELP" " - HELP Function Key") 469 (edt-map-key "HELP" " - HELP Function Key")
477(edt-map-key "DO" " - DO Function Key") 470 (edt-map-key "DO" " - DO Function Key")
478(edt-map-key "F17" " - F17 Function Key") 471 (edt-map-key "F17" " - F17 Function Key")
479(edt-map-key "F18" " - F18 Function Key") 472 (edt-map-key "F18" " - F18 Function Key")
480(edt-map-key "F19" " - F19 Function Key") 473 (edt-map-key "F19" " - F19 Function Key")
481(edt-map-key "F20" " - F20 Function Key") 474 (edt-map-key "F20" " - F20 Function Key")
482 475
483(set-buffer "Directions") 476 (set-buffer "Directions")
484(delete-region (point-min) (point-max)) 477 (delete-region (point-min) (point-max))
485(insert " 478 (insert "
486 ADDITIONAL FUNCTION KEYS 479 ADDITIONAL FUNCTION KEYS
487 480
488 Your keyboard may have additional function keys which do not correspond 481 Your keyboard may have additional function keys which do not correspond
@@ -501,53 +494,53 @@
501 494
502 When you are done, just press RETURN at the \"EDT Key Name:\" prompt. 495 When you are done, just press RETURN at the \"EDT Key Name:\" prompt.
503") 496")
504(switch-to-buffer "Directions") 497 (switch-to-buffer "Directions")
505;;; 498 ;;
506;;; Add support for extras keys 499 ;; Add support for extras keys
507;;; 500 ;;
508(set-buffer "Keys") 501 (set-buffer "Keys")
509(insert "\ 502 (insert "\
510;; 503;;
511;; Extra Keys 504;; Extra Keys
512;; 505;;
513") 506")
514;;; 507 ;;
515;;; Restore function-key-map. 508 ;; Restore function-key-map.
516;;; 509 ;;
517(if (and edt-window-system (not (featurep 'xemacs))) 510 (if (and edt-window-system (not (featurep 'xemacs)))
518 (setq function-key-map edt-save-function-key-map)) 511 (setq function-key-map edt-save-function-key-map))
519(setq EDT-key-name "") 512 (setq EDT-key-name "")
520(while (not 513 (while (not
521 (string-equal (setq EDT-key-name (read-string "EDT Key Name: ")) "")) 514 (string-equal (setq EDT-key-name (read-string "EDT Key Name: ")) ""))
522 (edt-map-key EDT-key-name "")) 515 (edt-map-key EDT-key-name ""))
523 516
524; 517 ;;
525; No more keys to add, so wrap up. 518 ;; No more keys to add, so wrap up.
526; 519 ;;
527(set-buffer "Keys") 520 (set-buffer "Keys")
528(insert "\ 521 (insert "\
529 ) 522 )
530 ) 523 )
531") 524")
532 525
533;;; 526 ;;
534;;; Save the key mapping program 527 ;; Save the key mapping program
535;;; 528 ;;
536;;; 529 ;;
537;;; Save the key mapping file 530 ;; Save the key mapping file
538;;; 531 ;;
539(let ((file (concat 532 (let ((file (concat
540 "~/.edt-" (if (featurep 'xemacs) "xemacs" "gnu") 533 "~/.edt-" (if (featurep 'xemacs) "xemacs" "gnu")
541 (if edt-term (concat "-" edt-term)) 534 (if edt-term (concat "-" edt-term))
542 (if edt-xserver (concat "-" edt-xserver)) 535 (if edt-xserver (concat "-" edt-xserver))
543 (if edt-window-system (concat "-" (upcase (symbol-name edt-window-system)))) 536 (if edt-window-system (concat "-" (upcase (symbol-name edt-window-system))))
544 "-keys"))) 537 "-keys")))
545 (set-visited-file-name 538 (set-visited-file-name
546 (read-file-name (format "Save key mapping to file (default %s): " file) nil file))) 539 (read-file-name (format "Save key mapping to file (default %s): " file) nil file)))
547(save-buffer) 540 (save-buffer)
548 541
549(message "That's it! Press any key to exit") 542 (message "That's it! Press any key to exit")
550(sit-for 600) 543 (sit-for 600)
551(kill-emacs t) 544 (kill-emacs t))
552 545
553;;; edt-mapper.el ends here 546;;; edt-mapper.el ends here
diff --git a/lisp/emulation/edt.el b/lisp/emulation/edt.el
index 31f555b0326..a6b2d785ac5 100644
--- a/lisp/emulation/edt.el
+++ b/lisp/emulation/edt.el
@@ -1928,6 +1928,8 @@ Optional argument NOT-YES changes the default to negative."
1928;;; INITIALIZATION COMMANDS. 1928;;; INITIALIZATION COMMANDS.
1929;;; 1929;;;
1930 1930
1931(declare-function edt-mapper "edt-mapper" ())
1932
1931;;; 1933;;;
1932;;; Function used to load LK-201 key mapping file generated by edt-mapper.el. 1934;;; Function used to load LK-201 key mapping file generated by edt-mapper.el.
1933;;; 1935;;;
@@ -1968,7 +1970,7 @@ created."
1968 You can do this by quitting Emacs and then invoking Emacs again as 1970 You can do this by quitting Emacs and then invoking Emacs again as
1969 follows: 1971 follows:
1970 1972
1971 emacs -q -l edt-mapper 1973 emacs -q -l edt-mapper -f edt-mapper
1972 1974
1973 [NOTE: If you do nothing out of the ordinary in your init file, and 1975 [NOTE: If you do nothing out of the ordinary in your init file, and
1974 the search for edt-mapper is successful, you can try running it now.] 1976 the search for edt-mapper is successful, you can try running it now.]
@@ -1983,7 +1985,9 @@ created."
1983 (insert (format 1985 (insert (format
1984 "Ah yes, there it is, in \n\n %s \n\n" path)) 1986 "Ah yes, there it is, in \n\n %s \n\n" path))
1985 (if (edt-y-or-n-p "Do you want to run it now? ") 1987 (if (edt-y-or-n-p "Do you want to run it now? ")
1986 (load-file path) 1988 (progn
1989 (load-file path)
1990 (edt-mapper))
1987 (error "EDT Emulation not configured"))) 1991 (error "EDT Emulation not configured")))
1988 (insert (substitute-command-keys 1992 (insert (substitute-command-keys
1989 "Nope, I can't seem to find it. :-(\n\n")) 1993 "Nope, I can't seem to find it. :-(\n\n"))
diff --git a/lisp/files.el b/lisp/files.el
index 25392fdcc71..b7d104853c3 100644
--- a/lisp/files.el
+++ b/lisp/files.el
@@ -5134,6 +5134,14 @@ Before and after saving the buffer, this function runs
5134 "Non-nil means `save-some-buffers' should save this buffer without asking.") 5134 "Non-nil means `save-some-buffers' should save this buffer without asking.")
5135(make-variable-buffer-local 'buffer-save-without-query) 5135(make-variable-buffer-local 'buffer-save-without-query)
5136 5136
5137(defcustom save-some-buffers-default-predicate nil
5138 "Default predicate for `save-some-buffers'.
5139This allows you to stop `save-some-buffers' from asking
5140about certain files that you'd usually rather not save."
5141 :group 'auto-save
5142 :type 'function
5143 :version "26.1")
5144
5137(defun save-some-buffers (&optional arg pred) 5145(defun save-some-buffers (&optional arg pred)
5138 "Save some modified file-visiting buffers. Asks user about each one. 5146 "Save some modified file-visiting buffers. Asks user about each one.
5139You can answer `y' to save, `n' not to save, `C-r' to look at the 5147You can answer `y' to save, `n' not to save, `C-r' to look at the
@@ -5149,10 +5157,13 @@ If PRED is nil, all the file-visiting buffers are considered.
5149If PRED is t, then certain non-file buffers will also be considered. 5157If PRED is t, then certain non-file buffers will also be considered.
5150If PRED is a zero-argument function, it indicates for each buffer whether 5158If PRED is a zero-argument function, it indicates for each buffer whether
5151to consider it or not when called with that buffer current. 5159to consider it or not when called with that buffer current.
5160PRED defaults to the value of `save-some-buffers-default-predicate'.
5152 5161
5153See `save-some-buffers-action-alist' if you want to 5162See `save-some-buffers-action-alist' if you want to
5154change the additional actions you can take on files." 5163change the additional actions you can take on files."
5155 (interactive "P") 5164 (interactive "P")
5165 (unless pred
5166 (setq pred save-some-buffers-default-predicate))
5156 (save-window-excursion 5167 (save-window-excursion
5157 (let* (queried autosaved-buffers 5168 (let* (queried autosaved-buffers
5158 files-done abbrevs-done) 5169 files-done abbrevs-done)
@@ -6572,7 +6583,7 @@ normally equivalent short `-D' option is just passed on to
6572 (unless (equal switches "") 6583 (unless (equal switches "")
6573 ;; Split the switches at any spaces so we can 6584 ;; Split the switches at any spaces so we can
6574 ;; pass separate options as separate args. 6585 ;; pass separate options as separate args.
6575 (split-string switches))) 6586 (split-string-and-unquote switches)))
6576 ;; Avoid lossage if FILE starts with `-'. 6587 ;; Avoid lossage if FILE starts with `-'.
6577 '("--") 6588 '("--")
6578 (progn 6589 (progn
@@ -6812,6 +6823,8 @@ asks whether processes should be killed.
6812Runs the members of `kill-emacs-query-functions' in turn and stops 6823Runs the members of `kill-emacs-query-functions' in turn and stops
6813if any returns nil. If `confirm-kill-emacs' is non-nil, calls it." 6824if any returns nil. If `confirm-kill-emacs' is non-nil, calls it."
6814 (interactive "P") 6825 (interactive "P")
6826 ;; Don't use save-some-buffers-default-predicate, because we want
6827 ;; to ask about all the buffers before killing Emacs.
6815 (save-some-buffers arg t) 6828 (save-some-buffers arg t)
6816 (let ((confirm confirm-kill-emacs)) 6829 (let ((confirm confirm-kill-emacs))
6817 (and 6830 (and
diff --git a/lisp/gnus/gnus-art.el b/lisp/gnus/gnus-art.el
index 43e1231914c..a4ff840f755 100644
--- a/lisp/gnus/gnus-art.el
+++ b/lisp/gnus/gnus-art.el
@@ -1713,9 +1713,10 @@ regexp."
1713 ;; (modify-syntax-entry ?- "w" table) 1713 ;; (modify-syntax-entry ?- "w" table)
1714 (modify-syntax-entry ?> ")<" table) 1714 (modify-syntax-entry ?> ")<" table)
1715 (modify-syntax-entry ?< "(>" table) 1715 (modify-syntax-entry ?< "(>" table)
1716 ;; make M-. in article buffers work for `foo' strings 1716 ;; make M-. in article buffers work for `foo' strings,
1717 (modify-syntax-entry ?' " " table) 1717 ;; and still allow C-s C-w to yank ' to the search ring
1718 (modify-syntax-entry ?` " " table) 1718 (modify-syntax-entry ?' "'" table)
1719 (modify-syntax-entry ?` "'" table)
1719 table) 1720 table)
1720 "Syntax table used in article mode buffers. 1721 "Syntax table used in article mode buffers.
1721Initialized from `text-mode-syntax-table'.") 1722Initialized from `text-mode-syntax-table'.")
diff --git a/lisp/ibuffer.el b/lisp/ibuffer.el
index c6e5e471a36..71bf1d6dcc2 100644
--- a/lisp/ibuffer.el
+++ b/lisp/ibuffer.el
@@ -1319,13 +1319,14 @@ a new window in the current frame, splitting vertically."
1319 (cl-assert (derived-mode-p 'ibuffer-mode))) 1319 (cl-assert (derived-mode-p 'ibuffer-mode)))
1320 1320
1321(defun ibuffer-buffer-file-name () 1321(defun ibuffer-buffer-file-name ()
1322 (or buffer-file-name 1322 (cond
1323 (let ((dirname (or (and (boundp 'dired-directory) 1323 ((buffer-file-name))
1324 (if (stringp dired-directory) 1324 ((bound-and-true-p list-buffers-directory))
1325 dired-directory 1325 ((let ((dirname (and (boundp 'dired-directory)
1326 (car dired-directory))) 1326 (if (stringp dired-directory)
1327 (bound-and-true-p list-buffers-directory)))) 1327 dired-directory
1328 (and dirname (expand-file-name dirname))))) 1328 (car dired-directory)))))
1329 (and dirname (expand-file-name dirname))))))
1329 1330
1330(define-ibuffer-op ibuffer-do-save () 1331(define-ibuffer-op ibuffer-do-save ()
1331 "Save marked buffers as with `save-buffer'." 1332 "Save marked buffers as with `save-buffer'."
diff --git a/lisp/image-dired.el b/lisp/image-dired.el
index 901225fa2e9..2a4064560a7 100644
--- a/lisp/image-dired.el
+++ b/lisp/image-dired.el
@@ -94,6 +94,7 @@
94;; * WARNING: The "database" format used might be changed so keep a 94;; * WARNING: The "database" format used might be changed so keep a
95;; backup of `image-dired-db-file' when testing new versions. 95;; backup of `image-dired-db-file' when testing new versions.
96;; 96;;
97;; * `image-dired-display-image-mode' does not support animation
97;; 98;;
98;; TODO 99;; TODO
99;; ==== 100;; ====
@@ -228,7 +229,7 @@ Used together with `image-dired-cmd-create-thumbnail-options'."
228 :group 'image-dired) 229 :group 'image-dired)
229 230
230(defcustom image-dired-cmd-create-thumbnail-options 231(defcustom image-dired-cmd-create-thumbnail-options
231 '("-size" "%wx%h" "%f" "-resize" "%wx%h>" "-strip" "jpeg:%t") 232 '("-size" "%wx%h" "%f[0]" "-resize" "%wx%h>" "-strip" "jpeg:%t")
232 "Options of command used to create thumbnail image. 233 "Options of command used to create thumbnail image.
233Used with `image-dired-cmd-create-thumbnail-program'. 234Used with `image-dired-cmd-create-thumbnail-program'.
234Available format specifiers are: %w which is replaced by 235Available format specifiers are: %w which is replaced by
@@ -246,7 +247,7 @@ Used together with `image-dired-cmd-create-temp-image-options'."
246 :group 'image-dired) 247 :group 'image-dired)
247 248
248(defcustom image-dired-cmd-create-temp-image-options 249(defcustom image-dired-cmd-create-temp-image-options
249 '("-size" "%wx%h" "%f" "-resize" "%wx%h>" "-strip" "jpeg:%t") 250 '("-size" "%wx%h" "%f[0]" "-resize" "%wx%h>" "-strip" "jpeg:%t")
250 "Options of command used to create temporary image for display window. 251 "Options of command used to create temporary image for display window.
251Used together with `image-dired-cmd-create-temp-image-program', 252Used together with `image-dired-cmd-create-temp-image-program',
252Available format specifiers are: %w and %h which are replaced by 253Available format specifiers are: %w and %h which are replaced by
@@ -316,7 +317,7 @@ Available format specifiers are described in
316 :group 'image-dired) 317 :group 'image-dired)
317 318
318(defcustom image-dired-cmd-create-standard-thumbnail-options 319(defcustom image-dired-cmd-create-standard-thumbnail-options
319 (append '("-size" "%wx%h" "%f") 320 (append '("-size" "%wx%h" "%f[0]")
320 (unless (or image-dired-cmd-pngcrush-program 321 (unless (or image-dired-cmd-pngcrush-program
321 image-dired-cmd-pngnq-program) 322 image-dired-cmd-pngnq-program)
322 (list 323 (list
@@ -1626,6 +1627,7 @@ Resized or in full-size."
1626 :group 'image-dired 1627 :group 'image-dired
1627 (buffer-disable-undo) 1628 (buffer-disable-undo)
1628 (image-mode-setup-winprops) 1629 (image-mode-setup-winprops)
1630 (setq cursor-type nil)
1629 (add-hook 'file-name-at-point-functions 'image-dired-file-name-at-point nil t)) 1631 (add-hook 'file-name-at-point-functions 'image-dired-file-name-at-point nil t))
1630 1632
1631(defvar image-dired-minor-mode-map 1633(defvar image-dired-minor-mode-map
diff --git a/lisp/indent.el b/lisp/indent.el
index db31f0454ce..fdd184c7998 100644
--- a/lisp/indent.el
+++ b/lisp/indent.el
@@ -487,9 +487,9 @@ line, but does not move past any whitespace that was explicitly inserted
487 (if (memq (current-justification) '(center right)) 487 (if (memq (current-justification) '(center right))
488 (skip-chars-forward " \t"))) 488 (skip-chars-forward " \t")))
489 489
490(defvar indent-region-function nil 490(defvar indent-region-function #'indent-region-line-by-line
491 "Short cut function to indent region using `indent-according-to-mode'. 491 "Short cut function to indent region using `indent-according-to-mode'.
492A value of nil means really run `indent-according-to-mode' on each line.") 492Default is to really run `indent-according-to-mode' on each line.")
493 493
494(defun indent-region (start end &optional column) 494(defun indent-region (start end &optional column)
495 "Indent each nonblank line in the region. 495 "Indent each nonblank line in the region.
@@ -541,24 +541,26 @@ column to indent to; if it is nil, use one of the three methods above."
541 (funcall indent-region-function start end)) 541 (funcall indent-region-function start end))
542 ;; Else, use a default implementation that calls indent-line-function on 542 ;; Else, use a default implementation that calls indent-line-function on
543 ;; each line. 543 ;; each line.
544 (t 544 (t (indent-region-line-by-line start end)))
545 (save-excursion
546 (setq end (copy-marker end))
547 (goto-char start)
548 (let ((pr (unless (minibufferp)
549 (make-progress-reporter "Indenting region..." (point) end))))
550 (while (< (point) end)
551 (or (and (bolp) (eolp))
552 (indent-according-to-mode))
553 (forward-line 1)
554 (and pr (progress-reporter-update pr (point))))
555 (and pr (progress-reporter-done pr))
556 (move-marker end nil)))))
557 ;; In most cases, reindenting modifies the buffer, but it may also 545 ;; In most cases, reindenting modifies the buffer, but it may also
558 ;; leave it unmodified, in which case we have to deactivate the mark 546 ;; leave it unmodified, in which case we have to deactivate the mark
559 ;; by hand. 547 ;; by hand.
560 (setq deactivate-mark t)) 548 (setq deactivate-mark t))
561 549
550(defun indent-region-line-by-line (start end)
551 (save-excursion
552 (setq end (copy-marker end))
553 (goto-char start)
554 (let ((pr (unless (minibufferp)
555 (make-progress-reporter "Indenting region..." (point) end))))
556 (while (< (point) end)
557 (or (and (bolp) (eolp))
558 (indent-according-to-mode))
559 (forward-line 1)
560 (and pr (progress-reporter-update pr (point))))
561 (and pr (progress-reporter-done pr))
562 (move-marker end nil))))
563
562(define-obsolete-function-alias 'indent-relative-maybe 564(define-obsolete-function-alias 'indent-relative-maybe
563 'indent-relative-first-indent-point "26.1") 565 'indent-relative-first-indent-point "26.1")
564 566
diff --git a/lisp/info.el b/lisp/info.el
index e32b6b35632..0cfcec32f82 100644
--- a/lisp/info.el
+++ b/lisp/info.el
@@ -1599,6 +1599,16 @@ escaped (\\\",\\\\)."
1599 parameter-alist)) 1599 parameter-alist))
1600 parameter-alist)) 1600 parameter-alist))
1601 1601
1602(defun Info-node-description (file)
1603 (cond
1604 ((equal file "dir") "*Info Directory*")
1605 ((eq file 'apropos) "*Info Apropos*")
1606 ((eq file 'history) "*Info History*")
1607 ((eq file 'toc) "*Info TOC*")
1608 ((not (stringp file)) "") ; Avoid errors
1609 (t
1610 (concat "(" (file-name-nondirectory file) ") " Info-current-node))))
1611
1602(defun Info-display-images-node () 1612(defun Info-display-images-node ()
1603 "Display images in current node." 1613 "Display images in current node."
1604 (save-excursion 1614 (save-excursion
@@ -1693,6 +1703,7 @@ escaped (\\\",\\\\)."
1693 (setq Info-history-forward nil)) 1703 (setq Info-history-forward nil))
1694 (if (not (eq Info-fontify-maximum-menu-size nil)) 1704 (if (not (eq Info-fontify-maximum-menu-size nil))
1695 (Info-fontify-node)) 1705 (Info-fontify-node))
1706 (setq list-buffers-directory (Info-node-description Info-current-file))
1696 (Info-display-images-node) 1707 (Info-display-images-node)
1697 (Info-hide-cookies-node) 1708 (Info-hide-cookies-node)
1698 (run-hooks 'Info-selection-hook))))) 1709 (run-hooks 'Info-selection-hook)))))
diff --git a/lisp/mh-e/mh-compat.el b/lisp/mh-e/mh-compat.el
index aae751e8d2d..3f3990e8695 100644
--- a/lisp/mh-e/mh-compat.el
+++ b/lisp/mh-e/mh-compat.el
@@ -283,16 +283,6 @@ DOCSTRING arguments."
283See documentation for `make-obsolete-variable' for a description 283See documentation for `make-obsolete-variable' for a description
284of the arguments OBSOLETE-NAME, CURRENT-NAME, and perhaps WHEN 284of the arguments OBSOLETE-NAME, CURRENT-NAME, and perhaps WHEN
285and ACCESS-TYPE. This macro is used by XEmacs that lacks WHEN and 285and ACCESS-TYPE. This macro is used by XEmacs that lacks WHEN and
286ACCESS-TYPE arguments."
287 (if (featurep 'xemacs)
288 `(make-obsolete-variable ,obsolete-name ,current-name)
289 `(make-obsolete-variable ,obsolete-name ,current-name ,when ,access-type)))
290
291(defmacro mh-make-obsolete-variable (obsolete-name current-name &optional when access-type)
292 "Make the byte-compiler warn that OBSOLETE-NAME is obsolete.
293See documentation for `make-obsolete-variable' for a description
294of the arguments OBSOLETE-NAME, CURRENT-NAME, and perhaps WHEN
295and ACCESS-TYPE. This macro is used by XEmacs that lacks WHEN and
296ACCESS-TYPE arguments and by Emacs versions that lack ACCESS-TYPE, 286ACCESS-TYPE arguments and by Emacs versions that lack ACCESS-TYPE,
297introduced in Emacs 24." 287introduced in Emacs 24."
298 (if (featurep 'xemacs) 288 (if (featurep 'xemacs)
diff --git a/lisp/net/tramp.el b/lisp/net/tramp.el
index fc7fdd30850..48dcd5edd11 100644
--- a/lisp/net/tramp.el
+++ b/lisp/net/tramp.el
@@ -3614,18 +3614,36 @@ connection buffer."
3614 3614
3615;;; Utility functions: 3615;;; Utility functions:
3616 3616
3617(defun tramp-accept-process-output (&optional proc timeout timeout-msecs) 3617(defun tramp-accept-process-output (proc timeout)
3618 "Like `accept-process-output' for Tramp processes. 3618 "Like `accept-process-output' for Tramp processes.
3619This is needed in order to hide `last-coding-system-used', which is set 3619This is needed in order to hide `last-coding-system-used', which is set
3620for process communication also." 3620for process communication also."
3621 ;; FIXME: There are problems, when an asynchronous process runs in
3622 ;; parallel, and also timers are active. See
3623 ;; <http://lists.gnu.org/archive/html/tramp-devel/2017-01/msg00010.html>.
3624 (when (and timer-event-last
3625 (string-prefix-p "*tramp/" (process-name proc))
3626 (let (result)
3627 (maphash
3628 (lambda (key _value)
3629 (and (processp key)
3630 (not (string-prefix-p "*tramp/" (process-name key)))
3631 (tramp-compat-process-live-p key)
3632 (setq result t)))
3633 tramp-cache-data)
3634 result))
3635 (sit-for 0.01 'nodisp))
3621 (with-current-buffer (process-buffer proc) 3636 (with-current-buffer (process-buffer proc)
3622 (let (buffer-read-only last-coding-system-used) 3637 (let (buffer-read-only last-coding-system-used)
3623 ;; Under Windows XP, accept-process-output doesn't return 3638 ;; Under Windows XP, accept-process-output doesn't return
3624 ;; sometimes. So we add an additional timeout. 3639 ;; sometimes. So we add an additional timeout. JUST-THIS-ONE
3625 (with-timeout ((or timeout 1)) 3640 ;; is set due to Bug#12145.
3626 (accept-process-output proc timeout timeout-msecs (and proc t))) 3641 (tramp-message
3627 (tramp-message proc 10 "%s %s\n%s" 3642 proc 10 "%s %s %s\n%s"
3628 proc (process-status proc) (buffer-string))))) 3643 proc (process-status proc)
3644 (with-timeout (timeout)
3645 (accept-process-output proc timeout nil t))
3646 (buffer-string)))))
3629 3647
3630(defun tramp-check-for-regexp (proc regexp) 3648(defun tramp-check-for-regexp (proc regexp)
3631 "Check, whether REGEXP is contained in process buffer of PROC. 3649 "Check, whether REGEXP is contained in process buffer of PROC.
diff --git a/lisp/progmodes/cc-align.el b/lisp/progmodes/cc-align.el
index 7cb36c4396b..0f7e4b598dc 100644
--- a/lisp/progmodes/cc-align.el
+++ b/lisp/progmodes/cc-align.el
@@ -1221,6 +1221,18 @@ Works with: arglist-cont, arglist-cont-nonempty."
1221 1221
1222 (vector (progn (goto-char alignto) (current-column))))))) 1222 (vector (progn (goto-char alignto) (current-column)))))))
1223 1223
1224(defun c-lineup-under-anchor (langelem)
1225 "Line up the current line directly under the anchor position in LANGELEM.
1226
1227This is like 0, except it supersedes any indentation already calculated for
1228previous syntactic elements in the syntactic context.
1229
1230Works with: Any syntactic symbol which has an anchor position."
1231 (save-excursion
1232 (goto-char (c-langelem-pos langelem))
1233 (vector (current-column))))
1234
1235
1224(defun c-lineup-dont-change (langelem) 1236(defun c-lineup-dont-change (langelem)
1225 "Do not change the indentation of the current line. 1237 "Do not change the indentation of the current line.
1226 1238
diff --git a/lisp/progmodes/cc-engine.el b/lisp/progmodes/cc-engine.el
index fd7aa50840f..dfd7aebd569 100644
--- a/lisp/progmodes/cc-engine.el
+++ b/lisp/progmodes/cc-engine.el
@@ -10260,13 +10260,22 @@ comment at the start of cc-engine.el for more info."
10260 (t nil))))) 10260 (t nil)))))
10261 10261
10262 (setq pos (point)) 10262 (setq pos (point))
10263 (if (and after-type-id-pos 10263 (cond
10264 (goto-char after-type-id-pos) 10264 ((and after-type-id-pos
10265 (setq res (c-back-over-member-initializers)) 10265 (goto-char after-type-id-pos)
10266 (goto-char res) 10266 (setq res (c-back-over-member-initializers))
10267 (eq (car (c-beginning-of-decl-1 lim)) 'same)) 10267 (goto-char res)
10268 (cons (point) nil) ; Return value. 10268 (eq (car (c-beginning-of-decl-1 lim)) 'same))
10269 10269 (cons (point) nil)) ; Return value.
10270
10271 ((and after-type-id-pos
10272 (progn
10273 (c-backward-syntactic-ws)
10274 (eq (char-before) ?\()))
10275 ;; Single identifier between '(' and '{'. We have a bracelist.
10276 (cons after-type-id-pos nil))
10277
10278 (t
10270 (goto-char pos) 10279 (goto-char pos)
10271 ;; Checks to do on all sexps before the brace, up to the 10280 ;; Checks to do on all sexps before the brace, up to the
10272 ;; beginning of the statement. 10281 ;; beginning of the statement.
@@ -10368,7 +10377,7 @@ comment at the start of cc-engine.el for more info."
10368 ; languages where 10377 ; languages where
10369 ; `c-opt-inexpr-brace-list-key' is 10378 ; `c-opt-inexpr-brace-list-key' is
10370 ; non-nil and we have macros. 10379 ; non-nil and we have macros.
10371 (t t))) ;; The caller can go up one level. 10380 (t t)))) ;; The caller can go up one level.
10372 ))) 10381 )))
10373 10382
10374(defun c-inside-bracelist-p (containing-sexp paren-state) 10383(defun c-inside-bracelist-p (containing-sexp paren-state)
@@ -10493,6 +10502,30 @@ comment at the start of cc-engine.el for more info."
10493 (c-at-statement-start-p)) 10502 (c-at-statement-start-p))
10494(make-obsolete 'c-looking-at-bos 'c-at-statement-start-p "22.1") 10503(make-obsolete 'c-looking-at-bos 'c-at-statement-start-p "22.1")
10495 10504
10505(defun c-looking-at-statement-block ()
10506 ;; Point is at an opening brace. If this is a statement block (i.e. the
10507 ;; elements in it are terminated by semicolons) return t. Otherwise, return
10508 ;; nil.
10509 (let ((here (point)))
10510 (prog1
10511 (if (c-go-list-forward)
10512 (let ((there (point)))
10513 (backward-char)
10514 (c-syntactic-skip-backward
10515 "^;," here t)
10516 (cond
10517 ((eq (char-before) ?\;) t)
10518 ((eq (char-before) ?,) nil)
10519 (t (goto-char here)
10520 (forward-char)
10521 (and (c-syntactic-re-search-forward "{" there t t)
10522 (progn (backward-char)
10523 (c-looking-at-statement-block))))))
10524 (forward-char)
10525 (and (c-syntactic-re-search-forward "[;,]" nil t t)
10526 (eq (char-before) ?\;)))
10527 (goto-char here))))
10528
10496(defun c-looking-at-inexpr-block (lim containing-sexp &optional check-at-end) 10529(defun c-looking-at-inexpr-block (lim containing-sexp &optional check-at-end)
10497 ;; Return non-nil if we're looking at the beginning of a block 10530 ;; Return non-nil if we're looking at the beginning of a block
10498 ;; inside an expression. The value returned is actually a cons of 10531 ;; inside an expression. The value returned is actually a cons of
@@ -10648,15 +10681,7 @@ comment at the start of cc-engine.el for more info."
10648 (and (c-major-mode-is 'c++-mode) 10681 (and (c-major-mode-is 'c++-mode)
10649 (save-excursion 10682 (save-excursion
10650 (goto-char block-follows) 10683 (goto-char block-follows)
10651 (if (c-go-list-forward) 10684 (not (c-looking-at-statement-block)))))
10652 (progn
10653 (backward-char)
10654 (c-syntactic-skip-backward
10655 "^;," block-follows t)
10656 (not (eq (char-before) ?\;)))
10657 (or (not (c-syntactic-re-search-forward
10658 "[;,]" nil t t))
10659 (not (eq (char-before) ?\;)))))))
10660 nil 10685 nil
10661 (cons 'inexpr-statement (point))))) 10686 (cons 'inexpr-statement (point)))))
10662 10687
@@ -10792,17 +10817,20 @@ comment at the start of cc-engine.el for more info."
10792 syntax-extra-args 10817 syntax-extra-args
10793 stop-at-boi-only 10818 stop-at-boi-only
10794 containing-sexp 10819 containing-sexp
10795 paren-state) 10820 paren-state
10821 &optional fixed-anchor)
10796 ;; Add the indicated SYNTAX-SYMBOL to `c-syntactic-context', extending it as 10822 ;; Add the indicated SYNTAX-SYMBOL to `c-syntactic-context', extending it as
10797 ;; needed with further syntax elements of the types `substatement', 10823 ;; needed with further syntax elements of the types `substatement',
10798 ;; `inexpr-statement', `arglist-cont-nonempty', `statement-block-intro', and 10824 ;; `inexpr-statement', `arglist-cont-nonempty', `statement-block-intro',
10799 ;; `defun-block-intro'. 10825 ;; `defun-block-intro', and `brace-list-intro'.
10800 ;; 10826 ;;
10801 ;; Do the generic processing to anchor the given syntax symbol on 10827 ;; Do the generic processing to anchor the given syntax symbol on the
10802 ;; the preceding statement: Skip over any labels and containing 10828 ;; preceding statement: First skip over any labels and containing statements
10803 ;; statements on the same line, and then search backward until we 10829 ;; on the same line. If FIXED-ANCHOR is non-nil, use this as the
10804 ;; find a statement or block start that begins at boi without a 10830 ;; anchor-point for the given syntactic symbol, and don't make syntactic
10805 ;; label or comment. 10831 ;; entries for constructs beginning on lines before that containing
10832 ;; ANCHOR-POINT. Otherwise search backward until we find a statement or
10833 ;; block start that begins at boi without a label or comment.
10806 ;; 10834 ;;
10807 ;; Point is assumed to be at the prospective anchor point for the 10835 ;; Point is assumed to be at the prospective anchor point for the
10808 ;; given SYNTAX-SYMBOL. More syntax entries are added if we need to 10836 ;; given SYNTAX-SYMBOL. More syntax entries are added if we need to
@@ -10831,6 +10859,7 @@ comment at the start of cc-engine.el for more info."
10831 10859
10832 (let ((syntax-last c-syntactic-context) 10860 (let ((syntax-last c-syntactic-context)
10833 (boi (c-point 'boi)) 10861 (boi (c-point 'boi))
10862 (anchor-boi (c-point 'boi))
10834 ;; Set when we're on a label, so that we don't stop there. 10863 ;; Set when we're on a label, so that we don't stop there.
10835 ;; FIXME: To be complete we should check if we're on a label 10864 ;; FIXME: To be complete we should check if we're on a label
10836 ;; now at the start. 10865 ;; now at the start.
@@ -10908,7 +10937,9 @@ comment at the start of cc-engine.el for more info."
10908 (c-add-syntax 'substatement nil)))) 10937 (c-add-syntax 'substatement nil))))
10909 ))) 10938 )))
10910 10939
10911 containing-sexp) 10940 containing-sexp
10941 (or (null fixed-anchor)
10942 (> containing-sexp anchor-boi)))
10912 10943
10913 ;; Now we have to go out of this block. 10944 ;; Now we have to go out of this block.
10914 (goto-char containing-sexp) 10945 (goto-char containing-sexp)
@@ -10982,6 +11013,14 @@ comment at the start of cc-engine.el for more info."
10982 (cdr (assoc (match-string 1) 11013 (cdr (assoc (match-string 1)
10983 c-other-decl-block-key-in-symbols-alist)) 11014 c-other-decl-block-key-in-symbols-alist))
10984 (max (c-point 'boi paren-pos) (point)))) 11015 (max (c-point 'boi paren-pos) (point))))
11016 ((save-excursion
11017 (goto-char paren-pos)
11018 (c-looking-at-or-maybe-in-bracelist containing-sexp))
11019 (if (save-excursion
11020 (goto-char paren-pos)
11021 (c-looking-at-statement-block))
11022 (c-add-syntax 'defun-block-intro nil)
11023 (c-add-syntax 'brace-list-intro nil)))
10985 (t (c-add-syntax 'defun-block-intro nil)))) 11024 (t (c-add-syntax 'defun-block-intro nil))))
10986 11025
10987 (c-add-syntax 'statement-block-intro nil))) 11026 (c-add-syntax 'statement-block-intro nil)))
@@ -11001,7 +11040,10 @@ comment at the start of cc-engine.el for more info."
11001 (setq q (cdr (car p))) ; e.g. (nil 28) [from (arglist-cont-nonempty nil 28)] 11040 (setq q (cdr (car p))) ; e.g. (nil 28) [from (arglist-cont-nonempty nil 28)]
11002 (while q 11041 (while q
11003 (unless (car q) 11042 (unless (car q)
11004 (setcar q (point))) 11043 (setcar q (if (or (cdr p)
11044 (null fixed-anchor))
11045 (point)
11046 fixed-anchor)))
11005 (setq q (cdr q))) 11047 (setq q (cdr q)))
11006 (setq p (cdr p)))) 11048 (setq p (cdr p))))
11007 ))) 11049 )))
@@ -12354,7 +12396,8 @@ comment at the start of cc-engine.el for more info."
12354 (c-forward-syntactic-ws (c-point 'eol)) 12396 (c-forward-syntactic-ws (c-point 'eol))
12355 (c-looking-at-special-brace-list (point))))) 12397 (c-looking-at-special-brace-list (point)))))
12356 (c-add-syntax 'brace-entry-open (point)) 12398 (c-add-syntax 'brace-entry-open (point))
12357 (c-add-syntax 'brace-list-entry (point)) 12399 (c-add-stmt-syntax 'brace-list-entry nil t containing-sexp
12400 paren-state (point))
12358 )) 12401 ))
12359 )))) 12402 ))))
12360 12403
@@ -12848,7 +12891,7 @@ Cannot combine absolute offsets %S and %S in `add' method"
12848 ;; 12891 ;;
12849 ;; Note that topmost-intro always has an anchor position at bol, for 12892 ;; Note that topmost-intro always has an anchor position at bol, for
12850 ;; historical reasons. It's often used together with other symbols 12893 ;; historical reasons. It's often used together with other symbols
12851 ;; that has more sane positions. Since we always use the first 12894 ;; that have more sane positions. Since we always use the first
12852 ;; found anchor position, we rely on that these other symbols always 12895 ;; found anchor position, we rely on that these other symbols always
12853 ;; precede topmost-intro in the LANGELEMS list. 12896 ;; precede topmost-intro in the LANGELEMS list.
12854 ;; 12897 ;;
diff --git a/lisp/progmodes/cc-styles.el b/lisp/progmodes/cc-styles.el
index d3505490505..b3848a74f97 100644
--- a/lisp/progmodes/cc-styles.el
+++ b/lisp/progmodes/cc-styles.el
@@ -67,6 +67,7 @@
67 (arglist-close . c-lineup-arglist) 67 (arglist-close . c-lineup-arglist)
68 (inline-open . 0) 68 (inline-open . 0)
69 (brace-list-open . +) 69 (brace-list-open . +)
70 (brace-list-intro . c-lineup-arglist-intro-after-paren)
70 (topmost-intro-cont 71 (topmost-intro-cont
71 . (first c-lineup-topmost-intro-cont 72 . (first c-lineup-topmost-intro-cont
72 c-lineup-gnu-DEFUN-intro-cont)))) 73 c-lineup-gnu-DEFUN-intro-cont))))
diff --git a/lisp/progmodes/cc-vars.el b/lisp/progmodes/cc-vars.el
index a6a96d15188..1114b21381d 100644
--- a/lisp/progmodes/cc-vars.el
+++ b/lisp/progmodes/cc-vars.el
@@ -1115,7 +1115,7 @@ can always override the use of `c-default-style' by making calls to
1115 ;; Anchor pos: At the brace list decl start(*). 1115 ;; Anchor pos: At the brace list decl start(*).
1116 (brace-list-intro . +) 1116 (brace-list-intro . +)
1117 ;; Anchor pos: At the brace list decl start(*). 1117 ;; Anchor pos: At the brace list decl start(*).
1118 (brace-list-entry . 0) 1118 (brace-list-entry . c-lineup-under-anchor)
1119 ;; Anchor pos: At the first non-ws char after the open paren if 1119 ;; Anchor pos: At the first non-ws char after the open paren if
1120 ;; the first token is on the same line, otherwise boi at that 1120 ;; the first token is on the same line, otherwise boi at that
1121 ;; token. 1121 ;; token.
diff --git a/lisp/progmodes/js.el b/lisp/progmodes/js.el
index 74dd4add9e2..e42e01481b6 100644
--- a/lisp/progmodes/js.el
+++ b/lisp/progmodes/js.el
@@ -3849,6 +3849,7 @@ If one hasn't been set, or if it's stale, prompt for a new one."
3849 comment-start-skip "\\(//+\\|/\\*+\\)\\s *") 3849 comment-start-skip "\\(//+\\|/\\*+\\)\\s *")
3850 (setq-local comment-line-break-function #'c-indent-new-comment-line) 3850 (setq-local comment-line-break-function #'c-indent-new-comment-line)
3851 (setq-local c-block-comment-start-regexp "/\\*") 3851 (setq-local c-block-comment-start-regexp "/\\*")
3852 (setq-local comment-multi-line t)
3852 3853
3853 (setq-local electric-indent-chars 3854 (setq-local electric-indent-chars
3854 (append "{}():;," electric-indent-chars)) ;FIXME: js2-mode adds "[]*". 3855 (append "{}():;," electric-indent-chars)) ;FIXME: js2-mode adds "[]*".
diff --git a/lisp/progmodes/xref.el b/lisp/progmodes/xref.el
index a507755d42e..a8933b0103e 100644
--- a/lisp/progmodes/xref.el
+++ b/lisp/progmodes/xref.el
@@ -918,11 +918,7 @@ IGNORES is a list of glob patterns."
918 (grep-compute-defaults) 918 (grep-compute-defaults)
919 (defvar grep-find-template) 919 (defvar grep-find-template)
920 (defvar grep-highlight-matches) 920 (defvar grep-highlight-matches)
921 ;; 'grep -E -foo' results in 'grep: oo: No such file or directory'. 921 (let* ((grep-find-template (replace-regexp-in-string "<C>" "<C> -E"
922 ;; while 'grep -e -foo' inexplicably doesn't.
923 (when (eq (aref regexp 0) ?-)
924 (setq regexp (concat "\\" regexp)))
925 (let* ((grep-find-template (replace-regexp-in-string "-e " "-E "
926 grep-find-template t t)) 922 grep-find-template t t))
927 (grep-highlight-matches nil) 923 (grep-highlight-matches nil)
928 (command (xref--rgrep-command (xref--regexp-to-extended regexp) 924 (command (xref--rgrep-command (xref--regexp-to-extended regexp)
diff --git a/lisp/replace.el b/lisp/replace.el
index ff917344453..a825040a979 100644
--- a/lisp/replace.el
+++ b/lisp/replace.el
@@ -1304,6 +1304,19 @@ If the value is nil, don't highlight the buffer names specially."
1304 :type 'face 1304 :type 'face
1305 :group 'matching) 1305 :group 'matching)
1306 1306
1307(defcustom list-matching-lines-current-line-face 'lazy-highlight
1308 "Face used by \\[list-matching-lines] to highlight the current line."
1309 :type 'face
1310 :group 'matching
1311 :version "26.1")
1312
1313(defcustom list-matching-lines-jump-to-current-line nil
1314 "If non-nil, \\[list-matching-lines] shows the current line highlighted.
1315Set the point right after such line when there are matches after it."
1316:type 'boolean
1317:group 'matching
1318:version "26.1")
1319
1307(defcustom list-matching-lines-prefix-face 'shadow 1320(defcustom list-matching-lines-prefix-face 'shadow
1308 "Face used by \\[list-matching-lines] to show the prefix column. 1321 "Face used by \\[list-matching-lines] to show the prefix column.
1309If the face doesn't differ from the default face, 1322If the face doesn't differ from the default face,
@@ -1360,7 +1373,15 @@ invoke `occur'."
1360 "*") 1373 "*")
1361 (or unique-p (not interactive-p))))) 1374 (or unique-p (not interactive-p)))))
1362 1375
1363(defun occur (regexp &optional nlines) 1376;; Region limits when `occur' applies on a region.
1377(defvar occur--region-start nil)
1378(defvar occur--region-end nil)
1379(defvar occur--matches-threshold nil)
1380(defvar occur--orig-line nil)
1381(defvar occur--orig-line-str nil)
1382(defvar occur--final-pos nil)
1383
1384(defun occur (regexp &optional nlines region)
1364 "Show all lines in the current buffer containing a match for REGEXP. 1385 "Show all lines in the current buffer containing a match for REGEXP.
1365If a match spreads across multiple lines, all those lines are shown. 1386If a match spreads across multiple lines, all those lines are shown.
1366 1387
@@ -1369,9 +1390,17 @@ before if NLINES is negative.
1369NLINES defaults to `list-matching-lines-default-context-lines'. 1390NLINES defaults to `list-matching-lines-default-context-lines'.
1370Interactively it is the prefix arg. 1391Interactively it is the prefix arg.
1371 1392
1393Optional arg REGION, if non-nil, mean restrict search to the
1394specified region. Otherwise search the entire buffer.
1395REGION must be a list of (START . END) positions as returned by
1396`region-bounds'.
1397
1372The lines are shown in a buffer named `*Occur*'. 1398The lines are shown in a buffer named `*Occur*'.
1373It serves as a menu to find any of the occurrences in this buffer. 1399It serves as a menu to find any of the occurrences in this buffer.
1374\\<occur-mode-map>\\[describe-mode] in that buffer will explain how. 1400\\<occur-mode-map>\\[describe-mode] in that buffer will explain how.
1401If `list-matching-lines-jump-to-current-line' is non-nil, then show
1402the current line highlighted with `list-matching-lines-current-line-face'
1403and set point at the first match after such line.
1375 1404
1376If REGEXP contains upper case characters (excluding those preceded by `\\') 1405If REGEXP contains upper case characters (excluding those preceded by `\\')
1377and `search-upper-case' is non-nil, the matching is case-sensitive. 1406and `search-upper-case' is non-nil, the matching is case-sensitive.
@@ -1386,8 +1415,30 @@ For example, providing \"defun\\s +\\(\\S +\\)\" for REGEXP and
1386program. When there is no parenthesized subexpressions in REGEXP 1415program. When there is no parenthesized subexpressions in REGEXP
1387the entire match is collected. In any case the searched buffer 1416the entire match is collected. In any case the searched buffer
1388is not modified." 1417is not modified."
1389 (interactive (occur-read-primary-args)) 1418 (interactive
1390 (occur-1 regexp nlines (list (current-buffer)))) 1419 (nconc (occur-read-primary-args)
1420 (and (use-region-p) (list (region-bounds)))))
1421 (let* ((start (and (caar region) (max (caar region) (point-min))))
1422 (end (and (cdar region) (min (cdar region) (point-max))))
1423 (in-region-p (or start end)))
1424 (when in-region-p
1425 (or start (setq start (point-min)))
1426 (or end (setq end (point-max))))
1427 (let ((occur--region-start start)
1428 (occur--region-end end)
1429 (occur--matches-threshold
1430 (and in-region-p
1431 (line-number-at-pos (min start end))))
1432 (occur--orig-line
1433 (line-number-at-pos (point)))
1434 (occur--orig-line-str
1435 (buffer-substring-no-properties
1436 (line-beginning-position)
1437 (line-end-position))))
1438 (save-excursion ; If no matches `occur-1' doesn't restore the point.
1439 (and in-region-p (narrow-to-region start end))
1440 (occur-1 regexp nlines (list (current-buffer)))
1441 (and in-region-p (widen))))))
1391 1442
1392(defvar ido-ignore-item-temp-list) 1443(defvar ido-ignore-item-temp-list)
1393 1444
@@ -1482,7 +1533,8 @@ See also `multi-occur'."
1482 (occur-mode)) 1533 (occur-mode))
1483 (let ((inhibit-read-only t) 1534 (let ((inhibit-read-only t)
1484 ;; Don't generate undo entries for creation of the initial contents. 1535 ;; Don't generate undo entries for creation of the initial contents.
1485 (buffer-undo-list t)) 1536 (buffer-undo-list t)
1537 (occur--final-pos nil))
1486 (erase-buffer) 1538 (erase-buffer)
1487 (let ((count 1539 (let ((count
1488 (if (stringp nlines) 1540 (if (stringp nlines)
@@ -1534,6 +1586,10 @@ See also `multi-occur'."
1534 (if (= count 0) 1586 (if (= count 0)
1535 (kill-buffer occur-buf) 1587 (kill-buffer occur-buf)
1536 (display-buffer occur-buf) 1588 (display-buffer occur-buf)
1589 (when occur--final-pos
1590 (set-window-point
1591 (get-buffer-window occur-buf 'all-frames)
1592 occur--final-pos))
1537 (setq next-error-last-buffer occur-buf) 1593 (setq next-error-last-buffer occur-buf)
1538 (setq buffer-read-only t) 1594 (setq buffer-read-only t)
1539 (set-buffer-modified-p nil) 1595 (set-buffer-modified-p nil)
@@ -1545,19 +1601,26 @@ See also `multi-occur'."
1545 (let ((global-lines 0) ;; total count of matching lines 1601 (let ((global-lines 0) ;; total count of matching lines
1546 (global-matches 0) ;; total count of matches 1602 (global-matches 0) ;; total count of matches
1547 (coding nil) 1603 (coding nil)
1548 (case-fold-search case-fold)) 1604 (case-fold-search case-fold)
1605 (in-region-p (and occur--region-start occur--region-end))
1606 (multi-occur-p (cdr buffers)))
1549 ;; Map over all the buffers 1607 ;; Map over all the buffers
1550 (dolist (buf buffers) 1608 (dolist (buf buffers)
1551 (when (buffer-live-p buf) 1609 (when (buffer-live-p buf)
1552 (let ((lines 0) ;; count of matching lines 1610 (let ((lines 0) ;; count of matching lines
1553 (matches 0) ;; count of matches 1611 (matches 0) ;; count of matches
1554 (curr-line 1) ;; line count 1612 (curr-line ;; line count
1613 (or occur--matches-threshold 1))
1614 (orig-line occur--orig-line)
1615 (orig-line-str occur--orig-line-str)
1616 (orig-line-shown-p)
1555 (prev-line nil) ;; line number of prev match endpt 1617 (prev-line nil) ;; line number of prev match endpt
1556 (prev-after-lines nil) ;; context lines of prev match 1618 (prev-after-lines nil) ;; context lines of prev match
1557 (matchbeg 0) 1619 (matchbeg 0)
1558 (origpt nil) 1620 (origpt nil)
1559 (begpt nil) 1621 (begpt nil)
1560 (endpt nil) 1622 (endpt nil)
1623 (finalpt nil)
1561 (marker nil) 1624 (marker nil)
1562 (curstring "") 1625 (curstring "")
1563 (ret nil) 1626 (ret nil)
@@ -1658,6 +1721,18 @@ See also `multi-occur'."
1658 (nth 0 ret)))) 1721 (nth 0 ret))))
1659 ;; Actually insert the match display data 1722 ;; Actually insert the match display data
1660 (with-current-buffer out-buf 1723 (with-current-buffer out-buf
1724 (when (and list-matching-lines-jump-to-current-line
1725 (not multi-occur-p)
1726 (not orig-line-shown-p)
1727 (>= curr-line orig-line))
1728 (insert
1729 (concat
1730 (propertize
1731 (format "%7d:%s" orig-line orig-line-str)
1732 'face list-matching-lines-current-line-face
1733 'mouse-face 'mode-line-highlight
1734 'help-echo "Current line") "\n"))
1735 (setq orig-line-shown-p t finalpt (point)))
1661 (insert data))) 1736 (insert data)))
1662 (goto-char endpt)) 1737 (goto-char endpt))
1663 (if endpt 1738 (if endpt
@@ -1671,6 +1746,18 @@ See also `multi-occur'."
1671 (forward-line 1)) 1746 (forward-line 1))
1672 (goto-char (point-max))) 1747 (goto-char (point-max)))
1673 (setq prev-line (1- curr-line))) 1748 (setq prev-line (1- curr-line)))
1749 ;; Insert original line if haven't done yet.
1750 (when (and list-matching-lines-jump-to-current-line
1751 (not multi-occur-p)
1752 (not orig-line-shown-p))
1753 (with-current-buffer out-buf
1754 (insert
1755 (concat
1756 (propertize
1757 (format "%7d:%s" orig-line orig-line-str)
1758 'face list-matching-lines-current-line-face
1759 'mouse-face 'mode-line-highlight
1760 'help-echo "Current line") "\n"))))
1674 ;; Flush remaining context after-lines. 1761 ;; Flush remaining context after-lines.
1675 (when prev-after-lines 1762 (when prev-after-lines
1676 (with-current-buffer out-buf 1763 (with-current-buffer out-buf
@@ -1684,7 +1771,7 @@ See also `multi-occur'."
1684 (let ((beg (point)) 1771 (let ((beg (point))
1685 end) 1772 end)
1686 (insert (propertize 1773 (insert (propertize
1687 (format "%d match%s%s%s in buffer: %s\n" 1774 (format "%d match%s%s%s in buffer: %s%s\n"
1688 matches (if (= matches 1) "" "es") 1775 matches (if (= matches 1) "" "es")
1689 ;; Don't display the same number of lines 1776 ;; Don't display the same number of lines
1690 ;; and matches in case of 1 match per line. 1777 ;; and matches in case of 1 match per line.
@@ -1694,13 +1781,21 @@ See also `multi-occur'."
1694 ;; Don't display regexp for multi-buffer. 1781 ;; Don't display regexp for multi-buffer.
1695 (if (> (length buffers) 1) 1782 (if (> (length buffers) 1)
1696 "" (occur-regexp-descr regexp)) 1783 "" (occur-regexp-descr regexp))
1697 (buffer-name buf)) 1784 (buffer-name buf)
1785 (if in-region-p
1786 (format " within region: %d-%d"
1787 occur--region-start
1788 occur--region-end)
1789 ""))
1698 'read-only t)) 1790 'read-only t))
1699 (setq end (point)) 1791 (setq end (point))
1700 (add-text-properties beg end `(occur-title ,buf)) 1792 (add-text-properties beg end `(occur-title ,buf))
1701 (when title-face 1793 (when title-face
1702 (add-face-text-property beg end title-face))) 1794 (add-face-text-property beg end title-face))
1703 (goto-char (point-min))))))) 1795 (goto-char (if finalpt
1796 (setq occur--final-pos
1797 (cl-incf finalpt (- end beg)))
1798 (point-min)))))))))
1704 ;; Display total match count and regexp for multi-buffer. 1799 ;; Display total match count and regexp for multi-buffer.
1705 (when (and (not (zerop global-lines)) (> (length buffers) 1)) 1800 (when (and (not (zerop global-lines)) (> (length buffers) 1))
1706 (goto-char (point-min)) 1801 (goto-char (point-min))
diff --git a/lisp/subr.el b/lisp/subr.el
index a6ba05c2021..a204577ddf9 100644
--- a/lisp/subr.el
+++ b/lisp/subr.el
@@ -1417,8 +1417,10 @@ be a list of the form returned by `event-start' and `event-end'."
1417;; bug#23850 1417;; bug#23850
1418(make-obsolete 'string-to-unibyte "use `encode-coding-string'." "26.1") 1418(make-obsolete 'string-to-unibyte "use `encode-coding-string'." "26.1")
1419(make-obsolete 'string-as-unibyte "use `encode-coding-string'." "26.1") 1419(make-obsolete 'string-as-unibyte "use `encode-coding-string'." "26.1")
1420(make-obsolete 'string-make-unibyte "use `encode-coding-string'." "26.1")
1420(make-obsolete 'string-to-multibyte "use `decode-coding-string'." "26.1") 1421(make-obsolete 'string-to-multibyte "use `decode-coding-string'." "26.1")
1421(make-obsolete 'string-as-multibyte "use `decode-coding-string'." "26.1") 1422(make-obsolete 'string-as-multibyte "use `decode-coding-string'." "26.1")
1423(make-obsolete 'string-make-multibyte "use `decode-coding-string'." "26.1")
1422 1424
1423(defun log10 (x) 1425(defun log10 (x)
1424 "Return (log X 10), the log base 10 of X." 1426 "Return (log X 10), the log base 10 of X."
diff --git a/lisp/textmodes/css-mode.el b/lisp/textmodes/css-mode.el
index c81c3f62e16..0c7d76f7924 100644
--- a/lisp/textmodes/css-mode.el
+++ b/lisp/textmodes/css-mode.el
@@ -32,9 +32,11 @@
32 32
33;;; Code: 33;;; Code:
34 34
35(require 'eww)
35(require 'seq) 36(require 'seq)
36(require 'sgml-mode) 37(require 'sgml-mode)
37(require 'smie) 38(require 'smie)
39(require 'subr-x)
38 40
39(defgroup css nil 41(defgroup css nil
40 "Cascading Style Sheets (CSS) editing mode." 42 "Cascading Style Sheets (CSS) editing mode."
@@ -621,6 +623,12 @@ cannot be completed sensibly: `custom-ident',
621 (modify-syntax-entry ?- "_" st) 623 (modify-syntax-entry ?- "_" st)
622 st)) 624 st))
623 625
626(defvar css-mode-map
627 (let ((map (make-sparse-keymap)))
628 (define-key map [remap info-lookup-symbol] 'css-lookup-symbol)
629 map)
630 "Keymap used in `css-mode'.")
631
624(eval-and-compile 632(eval-and-compile
625 (defconst css--uri-re 633 (defconst css--uri-re
626 (concat 634 (concat
@@ -734,7 +742,30 @@ cannot be completed sensibly: `custom-ident',
734 742
735(defconst css-smie-grammar 743(defconst css-smie-grammar
736 (smie-prec2->grammar 744 (smie-prec2->grammar
737 (smie-precs->prec2 '((assoc ";") (assoc ",") (left ":"))))) 745 (smie-precs->prec2
746 '((assoc ";")
747 ;; Colons that belong to a CSS property. These get a higher
748 ;; precedence than other colons, such as colons in selectors,
749 ;; which are represented by a plain ":" token.
750 (left ":-property")
751 (assoc ",")
752 (assoc ":")))))
753
754(defun css--colon-inside-selector-p ()
755 "Return t if point looks to be inside a CSS selector.
756This function is intended to be good enough to help SMIE during
757tokenization, but should not be regarded as a reliable function
758for determining whether point is within a selector."
759 (save-excursion
760 (re-search-forward "[{};)]" nil t)
761 (eq (char-before) ?\{)))
762
763(defun css--colon-inside-funcall ()
764 "Return t if point is inside a function call."
765 (when-let (opening-paren-pos (nth 1 (syntax-ppss)))
766 (save-excursion
767 (goto-char opening-paren-pos)
768 (eq (char-after) ?\())))
738 769
739(defun css-smie--forward-token () 770(defun css-smie--forward-token ()
740 (cond 771 (cond
@@ -748,7 +779,13 @@ cannot be completed sensibly: `custom-ident',
748 ";") 779 ";")
749 ((progn (forward-comment (point-max)) 780 ((progn (forward-comment (point-max))
750 (looking-at "[;,:]")) 781 (looking-at "[;,:]"))
751 (forward-char 1) (match-string 0)) 782 (forward-char 1)
783 (if (equal (match-string 0) ":")
784 (if (or (css--colon-inside-selector-p)
785 (css--colon-inside-funcall))
786 ":"
787 ":-property")
788 (match-string 0)))
752 (t (smie-default-forward-token)))) 789 (t (smie-default-forward-token))))
753 790
754(defun css-smie--backward-token () 791(defun css-smie--backward-token ()
@@ -759,7 +796,13 @@ cannot be completed sensibly: `custom-ident',
759 ((and (eq (char-before) ?\}) (scss-smie--not-interpolation-p) 796 ((and (eq (char-before) ?\}) (scss-smie--not-interpolation-p)
760 (> pos (point))) ";") 797 (> pos (point))) ";")
761 ((memq (char-before) '(?\; ?\, ?\:)) 798 ((memq (char-before) '(?\; ?\, ?\:))
762 (forward-char -1) (string (char-after))) 799 (forward-char -1)
800 (if (eq (char-after) ?\:)
801 (if (or (css--colon-inside-selector-p)
802 (css--colon-inside-funcall))
803 ":"
804 ":-property")
805 (string (char-after))))
763 (t (smie-default-backward-token))))) 806 (t (smie-default-backward-token)))))
764 807
765(defun css-smie-rules (kind token) 808(defun css-smie-rules (kind token)
@@ -1087,5 +1130,112 @@ pseudo-elements, pseudo-classes, at-rules, and bang-rules."
1087 (setq-local font-lock-defaults 1130 (setq-local font-lock-defaults
1088 (list (scss-font-lock-keywords) nil t))) 1131 (list (scss-font-lock-keywords) nil t)))
1089 1132
1133
1134
1135(defvar css--mdn-lookup-history nil)
1136
1137(defcustom css-lookup-url-format
1138 "https://developer.mozilla.org/en-US/docs/Web/CSS/%s?raw&macros"
1139 "Format for a URL where CSS documentation can be found.
1140The format should include a single \"%s\" substitution.
1141The name of the CSS property, @-id, pseudo-class, or pseudo-element
1142to look up will be substituted there."
1143 :version "26.1"
1144 :type 'string
1145 :group 'css)
1146
1147(defun css--mdn-after-render ()
1148 (setf header-line-format nil)
1149 (goto-char (point-min))
1150 (let ((window (get-buffer-window (current-buffer) 'visible)))
1151 (when window
1152 (when (re-search-forward "^Summary" nil 'move)
1153 (beginning-of-line)
1154 (set-window-start window (point))))))
1155
1156(defconst css--mdn-symbol-regexp
1157 (concat "\\("
1158 ;; @-ids.
1159 "\\(@" (regexp-opt css-at-ids) "\\)"
1160 "\\|"
1161 ;; ;; Known properties.
1162 (regexp-opt css-property-ids t)
1163 "\\|"
1164 ;; Pseudo-classes.
1165 "\\(:" (regexp-opt css-pseudo-class-ids) "\\)"
1166 "\\|"
1167 ;; Pseudo-elements with either one or two ":"s.
1168 "\\(::?" (regexp-opt css-pseudo-element-ids) "\\)"
1169 "\\)")
1170 "Regular expression to match the CSS symbol at point.")
1171
1172(defconst css--mdn-property-regexp
1173 (concat "\\_<" (regexp-opt css-property-ids t) "\\s-*\\(?:\\=\\|:\\)")
1174 "Regular expression to match a CSS property.")
1175
1176(defconst css--mdn-completion-list
1177 (nconc
1178 ;; @-ids.
1179 (mapcar (lambda (atrule) (concat "@" atrule)) css-at-ids)
1180 ;; Pseudo-classes.
1181 (mapcar (lambda (class) (concat ":" class)) css-pseudo-class-ids)
1182 ;; Pseudo-elements with either one or two ":"s.
1183 (mapcar (lambda (elt) (concat ":" elt)) css-pseudo-element-ids)
1184 (mapcar (lambda (elt) (concat "::" elt)) css-pseudo-element-ids)
1185 ;; Properties.
1186 css-property-ids)
1187 "List of all symbols available for lookup via MDN.")
1188
1189(defun css--mdn-find-symbol ()
1190 "A helper for `css-lookup-symbol' that finds the symbol at point.
1191Returns the symbol, a string, or nil if none found."
1192 (save-excursion
1193 ;; Skip backward over a word first.
1194 (skip-chars-backward "-[:alnum:] \t")
1195 ;; Now skip ":" or "@" to see if it's a pseudo-element or at-id.
1196 (skip-chars-backward "@:")
1197 (if (looking-at css--mdn-symbol-regexp)
1198 (match-string-no-properties 0)
1199 (let ((bound (save-excursion
1200 (beginning-of-line)
1201 (point))))
1202 (when (re-search-backward css--mdn-property-regexp bound t)
1203 (match-string-no-properties 1))))))
1204
1205;;;###autoload
1206(defun css-lookup-symbol (symbol)
1207 "Display the CSS documentation for SYMBOL, as found on MDN.
1208When this command is used interactively, it picks a default
1209symbol based on the CSS text before point -- either an @-keyword,
1210a property name, a pseudo-class, or a pseudo-element, depending
1211on what is seen near point."
1212 (interactive
1213 (list
1214 (let* ((sym (css--mdn-find-symbol))
1215 (enable-recursive-minibuffers t)
1216 (value (completing-read
1217 (if sym
1218 (format "Describe CSS symbol (default %s): " sym)
1219 "Describe CSS symbol: ")
1220 css--mdn-completion-list nil nil nil
1221 'css--mdn-lookup-history sym)))
1222 (if (equal value "") sym value))))
1223 (when symbol
1224 ;; If we see a single-colon pseudo-element like ":after", turn it
1225 ;; into "::after".
1226 (when (and (eq (aref symbol 0) ?:)
1227 (member (substring symbol 1) css-pseudo-element-ids))
1228 (setq symbol (concat ":" symbol)))
1229 (let ((url (format css-lookup-url-format symbol))
1230 (buffer (get-buffer-create "*MDN CSS*")))
1231 (save-selected-window
1232 ;; Make sure to display the buffer before calling `eww', as
1233 ;; that calls `pop-to-buffer-same-window'.
1234 (switch-to-buffer-other-window buffer)
1235 (with-current-buffer buffer
1236 (eww-mode)
1237 (add-hook 'eww-after-render-hook #'css--mdn-after-render nil t)
1238 (eww url))))))
1239
1090(provide 'css-mode) 1240(provide 'css-mode)
1091;;; css-mode.el ends here 1241;;; css-mode.el ends here
diff --git a/lisp/vc/diff-mode.el b/lisp/vc/diff-mode.el
index e609ca9f943..31c33e6a720 100644
--- a/lisp/vc/diff-mode.el
+++ b/lisp/vc/diff-mode.el
@@ -437,6 +437,9 @@ See http://lists.gnu.org/archive/html/emacs-devel/2007-11/msg01990.html")
437(defconst diff-hunk-header-re 437(defconst diff-hunk-header-re
438 (concat "^\\(?:" diff-hunk-header-re-unified ".*\\|\\*\\{15\\}.*\n\\*\\*\\* .+ \\*\\*\\*\\*\\|[0-9]+\\(,[0-9]+\\)?[acd][0-9]+\\(,[0-9]+\\)?\\)$")) 438 (concat "^\\(?:" diff-hunk-header-re-unified ".*\\|\\*\\{15\\}.*\n\\*\\*\\* .+ \\*\\*\\*\\*\\|[0-9]+\\(,[0-9]+\\)?[acd][0-9]+\\(,[0-9]+\\)?\\)$"))
439(defconst diff-file-header-re (concat "^\\(--- .+\n\\+\\+\\+ \\|\\*\\*\\* .+\n--- \\|[^-+!<>0-9@* \n]\\).+\n" (substring diff-hunk-header-re 1))) 439(defconst diff-file-header-re (concat "^\\(--- .+\n\\+\\+\\+ \\|\\*\\*\\* .+\n--- \\|[^-+!<>0-9@* \n]\\).+\n" (substring diff-hunk-header-re 1)))
440
441(defconst diff-separator-re "^--+ ?$")
442
440(defvar diff-narrowed-to nil) 443(defvar diff-narrowed-to nil)
441 444
442(defun diff-hunk-style (&optional style) 445(defun diff-hunk-style (&optional style)
@@ -647,28 +650,36 @@ If the prefix ARG is given, restrict the view to the current file instead."
647 (if arg (diff-bounds-of-file) (diff-bounds-of-hunk))) 650 (if arg (diff-bounds-of-file) (diff-bounds-of-hunk)))
648 (set (make-local-variable 'diff-narrowed-to) (if arg 'file 'hunk))) 651 (set (make-local-variable 'diff-narrowed-to) (if arg 'file 'hunk)))
649 652
653(defun diff--some-hunks-p ()
654 (save-excursion
655 (goto-char (point-min))
656 (re-search-forward diff-hunk-header-re nil t)))
657
650(defun diff-hunk-kill () 658(defun diff-hunk-kill ()
651 "Kill the hunk at point." 659 "Kill the hunk at point."
652 (interactive) 660 (interactive)
653 (let* ((hunk-bounds (diff-bounds-of-hunk)) 661 (if (not (diff--some-hunks-p))
654 (file-bounds (ignore-errors (diff-bounds-of-file))) 662 (error "No hunks")
655 ;; If the current hunk is the only one for its file, kill the 663 (diff-beginning-of-hunk t)
656 ;; file header too. 664 (let* ((hunk-bounds (diff-bounds-of-hunk))
657 (bounds (if (and file-bounds 665 (file-bounds (ignore-errors (diff-bounds-of-file)))
658 (progn (goto-char (car file-bounds)) 666 ;; If the current hunk is the only one for its file, kill the
659 (= (progn (diff-hunk-next) (point)) 667 ;; file header too.
660 (car hunk-bounds))) 668 (bounds (if (and file-bounds
661 (progn (goto-char (cadr hunk-bounds)) 669 (progn (goto-char (car file-bounds))
662 ;; bzr puts a newline after the last hunk. 670 (= (progn (diff-hunk-next) (point))
663 (while (looking-at "^\n") 671 (car hunk-bounds)))
664 (forward-char 1)) 672 (progn (goto-char (cadr hunk-bounds))
665 (= (point) (cadr file-bounds)))) 673 ;; bzr puts a newline after the last hunk.
666 file-bounds 674 (while (looking-at "^\n")
667 hunk-bounds)) 675 (forward-char 1))
668 (inhibit-read-only t)) 676 (= (point) (cadr file-bounds))))
669 (apply 'kill-region bounds) 677 file-bounds
670 (goto-char (car bounds)) 678 hunk-bounds))
671 (diff-beginning-of-hunk t))) 679 (inhibit-read-only t))
680 (apply 'kill-region bounds)
681 (goto-char (car bounds))
682 (ignore-errors (diff-beginning-of-hunk t)))))
672 683
673(defun diff-beginning-of-file-and-junk () 684(defun diff-beginning-of-file-and-junk ()
674 "Go to the beginning of file-related diff-info. 685 "Go to the beginning of file-related diff-info.
@@ -720,9 +731,12 @@ data such as \"Index: ...\" and such."
720(defun diff-file-kill () 731(defun diff-file-kill ()
721 "Kill current file's hunks." 732 "Kill current file's hunks."
722 (interactive) 733 (interactive)
723 (let ((inhibit-read-only t)) 734 (if (not (diff--some-hunks-p))
724 (apply 'kill-region (diff-bounds-of-file))) 735 (error "No hunks")
725 (diff-beginning-of-hunk t)) 736 (diff-beginning-of-hunk t)
737 (let ((inhibit-read-only t))
738 (apply 'kill-region (diff-bounds-of-file)))
739 (ignore-errors (diff-beginning-of-hunk t))))
726 740
727(defun diff-kill-junk () 741(defun diff-kill-junk ()
728 "Kill spurious empty diffs." 742 "Kill spurious empty diffs."
@@ -1537,15 +1551,20 @@ Only works for unified diffs."
1537 (pcase (char-after) 1551 (pcase (char-after)
1538 (?\s (cl-decf before) (cl-decf after) t) 1552 (?\s (cl-decf before) (cl-decf after) t)
1539 (?- 1553 (?-
1540 (if (and (looking-at diff-file-header-re) 1554 (cond
1541 (zerop before) (zerop after)) 1555 ((and (looking-at diff-separator-re)
1542 ;; No need to query: this is a case where two patches 1556 (zerop before) (zerop after))
1543 ;; are concatenated and only counting the lines will 1557 nil)
1544 ;; give the right result. Let's just add an empty 1558 ((and (looking-at diff-file-header-re)
1545 ;; line so that our code which doesn't count lines 1559 (zerop before) (zerop after))
1546 ;; will not get confused. 1560 ;; No need to query: this is a case where two patches
1547 (progn (save-excursion (insert "\n")) nil) 1561 ;; are concatenated and only counting the lines will
1548 (cl-decf before) t)) 1562 ;; give the right result. Let's just add an empty
1563 ;; line so that our code which doesn't count lines
1564 ;; will not get confused.
1565 (save-excursion (insert "\n")) nil)
1566 (t
1567 (cl-decf before) t)))
1549 (?+ (cl-decf after) t) 1568 (?+ (cl-decf after) t)
1550 (_ 1569 (_
1551 (cond 1570 (cond
@@ -2000,57 +2019,58 @@ Return new point, if it was moved."
2000 "Highlight changes of hunk at point at a finer granularity." 2019 "Highlight changes of hunk at point at a finer granularity."
2001 (interactive) 2020 (interactive)
2002 (require 'smerge-mode) 2021 (require 'smerge-mode)
2003 (save-excursion 2022 (when (diff--some-hunks-p)
2004 (diff-beginning-of-hunk t) 2023 (save-excursion
2005 (let* ((start (point)) 2024 (diff-beginning-of-hunk t)
2006 (style (diff-hunk-style)) ;Skips the hunk header as well. 2025 (let* ((start (point))
2007 (beg (point)) 2026 (style (diff-hunk-style)) ;Skips the hunk header as well.
2008 (props-c '((diff-mode . fine) (face diff-refine-changed))) 2027 (beg (point))
2009 (props-r '((diff-mode . fine) (face diff-refine-removed))) 2028 (props-c '((diff-mode . fine) (face diff-refine-changed)))
2010 (props-a '((diff-mode . fine) (face diff-refine-added))) 2029 (props-r '((diff-mode . fine) (face diff-refine-removed)))
2011 ;; Be careful to go back to `start' so diff-end-of-hunk gets 2030 (props-a '((diff-mode . fine) (face diff-refine-added)))
2012 ;; to read the hunk header's line info. 2031 ;; Be careful to go back to `start' so diff-end-of-hunk gets
2013 (end (progn (goto-char start) (diff-end-of-hunk) (point)))) 2032 ;; to read the hunk header's line info.
2014 2033 (end (progn (goto-char start) (diff-end-of-hunk) (point))))
2015 (remove-overlays beg end 'diff-mode 'fine) 2034
2016 2035 (remove-overlays beg end 'diff-mode 'fine)
2017 (goto-char beg) 2036
2018 (pcase style 2037 (goto-char beg)
2019 (`unified 2038 (pcase style
2020 (while (re-search-forward "^-" end t) 2039 (`unified
2021 (let ((beg-del (progn (beginning-of-line) (point))) 2040 (while (re-search-forward "^-" end t)
2022 beg-add end-add) 2041 (let ((beg-del (progn (beginning-of-line) (point)))
2023 (when (and (diff--forward-while-leading-char ?- end) 2042 beg-add end-add)
2024 ;; Allow for "\ No newline at end of file". 2043 (when (and (diff--forward-while-leading-char ?- end)
2025 (progn (diff--forward-while-leading-char ?\\ end) 2044 ;; Allow for "\ No newline at end of file".
2026 (setq beg-add (point))) 2045 (progn (diff--forward-while-leading-char ?\\ end)
2027 (diff--forward-while-leading-char ?+ end) 2046 (setq beg-add (point)))
2028 (progn (diff--forward-while-leading-char ?\\ end) 2047 (diff--forward-while-leading-char ?+ end)
2029 (setq end-add (point)))) 2048 (progn (diff--forward-while-leading-char ?\\ end)
2030 (smerge-refine-subst beg-del beg-add beg-add end-add 2049 (setq end-add (point))))
2031 nil 'diff-refine-preproc props-r props-a))))) 2050 (smerge-refine-subst beg-del beg-add beg-add end-add
2032 (`context 2051 nil 'diff-refine-preproc props-r props-a)))))
2033 (let* ((middle (save-excursion (re-search-forward "^---"))) 2052 (`context
2034 (other middle)) 2053 (let* ((middle (save-excursion (re-search-forward "^---")))
2035 (while (re-search-forward "^\\(?:!.*\n\\)+" middle t) 2054 (other middle))
2036 (smerge-refine-subst (match-beginning 0) (match-end 0) 2055 (while (re-search-forward "^\\(?:!.*\n\\)+" middle t)
2037 (save-excursion 2056 (smerge-refine-subst (match-beginning 0) (match-end 0)
2038 (goto-char other) 2057 (save-excursion
2039 (re-search-forward "^\\(?:!.*\n\\)+" end) 2058 (goto-char other)
2040 (setq other (match-end 0)) 2059 (re-search-forward "^\\(?:!.*\n\\)+" end)
2041 (match-beginning 0)) 2060 (setq other (match-end 0))
2042 other 2061 (match-beginning 0))
2043 (if diff-use-changed-face props-c) 2062 other
2044 'diff-refine-preproc 2063 (if diff-use-changed-face props-c)
2045 (unless diff-use-changed-face props-r) 2064 'diff-refine-preproc
2046 (unless diff-use-changed-face props-a))))) 2065 (unless diff-use-changed-face props-r)
2047 (_ ;; Normal diffs. 2066 (unless diff-use-changed-face props-a)))))
2048 (let ((beg1 (1+ (point)))) 2067 (_ ;; Normal diffs.
2049 (when (re-search-forward "^---.*\n" end t) 2068 (let ((beg1 (1+ (point))))
2050 ;; It's a combined add&remove, so there's something to do. 2069 (when (re-search-forward "^---.*\n" end t)
2051 (smerge-refine-subst beg1 (match-beginning 0) 2070 ;; It's a combined add&remove, so there's something to do.
2052 (match-end 0) end 2071 (smerge-refine-subst beg1 (match-beginning 0)
2053 nil 'diff-refine-preproc props-r props-a)))))))) 2072 (match-end 0) end
2073 nil 'diff-refine-preproc props-r props-a)))))))))
2054 2074
2055(defun diff-undo (&optional arg) 2075(defun diff-undo (&optional arg)
2056 "Perform `undo', ignoring the buffer's read-only status." 2076 "Perform `undo', ignoring the buffer's read-only status."