diff options
| author | Paul Eggert | 2016-05-05 23:11:11 -0700 |
|---|---|---|
| committer | Paul Eggert | 2016-05-05 23:11:11 -0700 |
| commit | 89ce83b20249dfb4e45f09dfdddf4c4b66d82968 (patch) | |
| tree | 3d75245a5514df2ad7b17ae6d56727b9629846a9 | |
| parent | d546ed13b04521308ef7ec8e7e5b68e03f1bbb38 (diff) | |
| parent | 50650cb6887d99b01eeb1e686fc1f695c2a0c64a (diff) | |
| download | emacs-89ce83b20249dfb4e45f09dfdddf4c4b66d82968.tar.gz emacs-89ce83b20249dfb4e45f09dfdddf4c4b66d82968.zip | |
Merge from origin/emacs-25
50650cb Doc fixes for fclist and grep
5e814e0 Minor doc fixes for quoting
3347a73 `nreverse' the marker pairs list
1a4127d Use save-excursion in xref-location-marker more
ab3ba91 shell-quote-argument DIR when appropriate
922c7a3 Rework xref-query-replace-in-results
3fe3510 * lisp/replace.el (query-replace-read-from): Use minibuffer-w...
0932b94 Fix todo-mode bug involving archived items (bug#23447)
e68ad1f ; * etc/NEWS: Tiny edit. (Bug#23432)
adc80b7 ; * test/automated/xref-tests.el: Add copyright and license.
4d8fd9c Handle "empty line" regexp in xref searches
f559b37 Add tests for xref-collect-matches
6428aa0 Use grep-find-ignored-directories instead of vc-directory-exc...
6f82d8e Clear buffer-undo-list when showing xrefs
c68a091 Note the quote translation in `message' in section "incompati...
52f86a7 * etc/NEWS: Mention (message "%s" (format ...)).
93703c5 (Common Keywords): Correct what missing :group means
79e5800 Improve documentation of Dired's 'A' and 'Q' commands
2ea2a2f Doc fixes for quoting
8544b98 posnp doc clarification
805204f Mention what a missing :group does
ec554d7 Fix documentation of dired-aux search/replace commands
| -rw-r--r-- | doc/emacs/dired.texi | 14 | ||||
| -rw-r--r-- | doc/emacs/frames.texi | 5 | ||||
| -rw-r--r-- | doc/emacs/text.texi | 4 | ||||
| -rw-r--r-- | doc/lispintro/emacs-lisp-intro.texi | 28 | ||||
| -rw-r--r-- | doc/lispref/control.texi | 11 | ||||
| -rw-r--r-- | doc/lispref/customize.texi | 9 | ||||
| -rw-r--r-- | doc/lispref/display.texi | 11 | ||||
| -rw-r--r-- | doc/lispref/help.texi | 4 | ||||
| -rw-r--r-- | doc/lispref/strings.texi | 10 | ||||
| -rw-r--r-- | etc/NEWS | 23 | ||||
| -rw-r--r-- | etc/PROBLEMS | 2 | ||||
| -rw-r--r-- | lisp/calendar/todo-mode.el | 39 | ||||
| -rw-r--r-- | lisp/cedet/cedet-cscope.el | 2 | ||||
| -rw-r--r-- | lisp/cedet/semantic/symref.el | 2 | ||||
| -rw-r--r-- | lisp/dired-aux.el | 19 | ||||
| -rw-r--r-- | lisp/man.el | 2 | ||||
| -rw-r--r-- | lisp/progmodes/elisp-mode.el | 5 | ||||
| -rw-r--r-- | lisp/progmodes/etags.el | 5 | ||||
| -rw-r--r-- | lisp/progmodes/project.el | 3 | ||||
| -rw-r--r-- | lisp/progmodes/xref.el | 146 | ||||
| -rw-r--r-- | lisp/replace.el | 21 | ||||
| -rw-r--r-- | lisp/subr.el | 15 | ||||
| -rw-r--r-- | src/bidi.c | 4 | ||||
| -rw-r--r-- | src/callint.c | 2 | ||||
| -rw-r--r-- | src/doprnt.c | 6 | ||||
| -rw-r--r-- | src/editfns.c | 13 | ||||
| -rw-r--r-- | test/automated/data/xref/file1.txt | 2 | ||||
| -rw-r--r-- | test/automated/data/xref/file2.txt | 2 | ||||
| -rw-r--r-- | test/automated/xref-tests.el | 91 |
29 files changed, 343 insertions, 157 deletions
diff --git a/doc/emacs/dired.texi b/doc/emacs/dired.texi index 68c6813c242..486e92a40bb 100644 --- a/doc/emacs/dired.texi +++ b/doc/emacs/dired.texi | |||
| @@ -795,6 +795,14 @@ This command is a variant of @code{xref-find-references} | |||
| 795 | where you can navigate between matches and display them as needed | 795 | where you can navigate between matches and display them as needed |
| 796 | using the commands described in @ref{Xref Commands}. | 796 | using the commands described in @ref{Xref Commands}. |
| 797 | 797 | ||
| 798 | @vindex grep-find-ignored-files @r{(Dired)} | ||
| 799 | @vindex grep-find-ignored-directories @r{(Dired)} | ||
| 800 | If any of the marked files are directories, then this command searches | ||
| 801 | all of the files in those directories, and any of their | ||
| 802 | subdirectories, recursively, except files whose names match | ||
| 803 | @code{grep-find-ignored-files} and subdirectories whose names match | ||
| 804 | @code{grep-find-ignored-directories}. | ||
| 805 | |||
| 798 | @kindex Q @r{(Dired)} | 806 | @kindex Q @r{(Dired)} |
| 799 | @findex dired-do-find-regexp-and-replace | 807 | @findex dired-do-find-regexp-and-replace |
| 800 | @cindex search and replace in multiple files (in Dired) | 808 | @cindex search and replace in multiple files (in Dired) |
| @@ -809,6 +817,12 @@ and you can use the special commands in that buffer (@pxref{Xref | |||
| 809 | Commands}). In particular, if you exit the query replace loop, you | 817 | Commands}). In particular, if you exit the query replace loop, you |
| 810 | can use @kbd{r} in that buffer to replace more matches. | 818 | can use @kbd{r} in that buffer to replace more matches. |
| 811 | @xref{Identifier Search}. | 819 | @xref{Identifier Search}. |
| 820 | |||
| 821 | Like with @code{dired-do-find-regexp}, if any of the marked files are | ||
| 822 | directories, this command performs replacements in all of the files in | ||
| 823 | those directories, and in any of their subdirectories, recursively, | ||
| 824 | except for files whose names match @code{grep-find-ignored-files} and | ||
| 825 | subdirectories whose names match @code{grep-find-ignored-directories}. | ||
| 812 | @end table | 826 | @end table |
| 813 | 827 | ||
| 814 | @node Shell Commands in Dired | 828 | @node Shell Commands in Dired |
diff --git a/doc/emacs/frames.texi b/doc/emacs/frames.texi index 23ccd6a8f41..a7e709f9221 100644 --- a/doc/emacs/frames.texi +++ b/doc/emacs/frames.texi | |||
| @@ -764,7 +764,8 @@ Fontconfig fonts, you can use the @command{fc-list} command to list | |||
| 764 | the available fixed-width fonts, like this: | 764 | the available fixed-width fonts, like this: |
| 765 | 765 | ||
| 766 | @example | 766 | @example |
| 767 | fc-list :spacing=mono fc-list :spacing=charcell | 767 | fc-list :spacing=mono |
| 768 | fc-list :spacing=charcell | ||
| 768 | @end example | 769 | @end example |
| 769 | 770 | ||
| 770 | @noindent | 771 | @noindent |
| @@ -772,7 +773,7 @@ For server-side X fonts, you can use the @command{xlsfonts} program to | |||
| 772 | list the available fixed-width fonts, like this: | 773 | list the available fixed-width fonts, like this: |
| 773 | 774 | ||
| 774 | @example | 775 | @example |
| 775 | xlsfonts -fn '*x*' | egrep "^[0-9]+x[0-9]+" | 776 | xlsfonts -fn '*x*' | grep -E '^[0-9]+x[0-9]+' |
| 776 | xlsfonts -fn '*-*-*-*-*-*-*-*-*-*-*-m*' | 777 | xlsfonts -fn '*-*-*-*-*-*-*-*-*-*-*-m*' |
| 777 | xlsfonts -fn '*-*-*-*-*-*-*-*-*-*-*-c*' | 778 | xlsfonts -fn '*-*-*-*-*-*-*-*-*-*-*-c*' |
| 778 | @end example | 779 | @end example |
diff --git a/doc/emacs/text.texi b/doc/emacs/text.texi index 66f01b495d1..579f7880cfe 100644 --- a/doc/emacs/text.texi +++ b/doc/emacs/text.texi | |||
| @@ -862,8 +862,8 @@ indenting the current line. @xref{Indentation}, for details. | |||
| 862 | 862 | ||
| 863 | Text mode turns off the features concerned with comments except when | 863 | Text mode turns off the features concerned with comments except when |
| 864 | you explicitly invoke them. It changes the syntax table so that | 864 | you explicitly invoke them. It changes the syntax table so that |
| 865 | single-quotes are considered part of words (e.g., @samp{don't} is | 865 | apostrophes are considered part of words (e.g., @samp{don't} is |
| 866 | considered one word). However, if a word starts with a single-quote, | 866 | considered one word). However, if a word starts with an apostrophe, |
| 867 | it is treated as a prefix for the purposes of capitalization | 867 | it is treated as a prefix for the purposes of capitalization |
| 868 | (e.g., @kbd{M-c} converts @samp{'hello'} into @samp{'Hello'}, as | 868 | (e.g., @kbd{M-c} converts @samp{'hello'} into @samp{'Hello'}, as |
| 869 | expected). | 869 | expected). |
diff --git a/doc/lispintro/emacs-lisp-intro.texi b/doc/lispintro/emacs-lisp-intro.texi index 78c1865703e..eea46af6b19 100644 --- a/doc/lispintro/emacs-lisp-intro.texi +++ b/doc/lispintro/emacs-lisp-intro.texi | |||
| @@ -1004,11 +1004,11 @@ the name stands for ``Lots of Isolated Silly Parentheses''. But the | |||
| 1004 | claim is unwarranted. Lisp stands for LISt Processing, and the | 1004 | claim is unwarranted. Lisp stands for LISt Processing, and the |
| 1005 | programming language handles @emph{lists} (and lists of lists) by | 1005 | programming language handles @emph{lists} (and lists of lists) by |
| 1006 | putting them between parentheses. The parentheses mark the boundaries | 1006 | putting them between parentheses. The parentheses mark the boundaries |
| 1007 | of the list. Sometimes a list is preceded by a single apostrophe or | 1007 | of the list. Sometimes a list is preceded by an apostrophe @samp{'}, |
| 1008 | quotation mark, @samp{'}@footnote{The single apostrophe or quotation | 1008 | called a @dfn{single-quote} in Lisp.@footnote{A single-quote is an |
| 1009 | mark is an abbreviation for the function @code{quote}; you need not | 1009 | abbreviation for the special form @code{quote}; you need not think |
| 1010 | think about functions now; functions are defined in @ref{Making | 1010 | about special forms now. @xref{Complications}.} Lists are the basis |
| 1011 | Errors, , Generate an Error Message}.} Lists are the basis of Lisp. | 1011 | of Lisp. |
| 1012 | 1012 | ||
| 1013 | @menu | 1013 | @menu |
| 1014 | * Lisp Lists:: What are lists? | 1014 | * Lisp Lists:: What are lists? |
| @@ -2490,14 +2490,7 @@ in the list and then at the function definition bound to that symbol. | |||
| 2490 | Then the instructions in the function definition are carried out. | 2490 | Then the instructions in the function definition are carried out. |
| 2491 | 2491 | ||
| 2492 | @item | 2492 | @item |
| 2493 | A single quotation mark, | 2493 | A single-quote @samp{'} tells the Lisp interpreter that it should |
| 2494 | @ifinfo | ||
| 2495 | ' | ||
| 2496 | @end ifinfo | ||
| 2497 | @ifnotinfo | ||
| 2498 | @code{'} | ||
| 2499 | @end ifnotinfo | ||
| 2500 | , tells the Lisp interpreter that it should | ||
| 2501 | return the following expression as written, and not evaluate it as it | 2494 | return the following expression as written, and not evaluate it as it |
| 2502 | would if the quote were not there. | 2495 | would if the quote were not there. |
| 2503 | 2496 | ||
| @@ -7610,7 +7603,8 @@ displays in which grave accent and apostrophe were often mirror images | |||
| 7610 | suitable for use as quotes. On most modern displays this is no longer | 7603 | suitable for use as quotes. On most modern displays this is no longer |
| 7611 | true, and when these two ASCII characters appear in documentation | 7604 | true, and when these two ASCII characters appear in documentation |
| 7612 | strings or diagnostic message formats, Emacs typically transliterates | 7605 | strings or diagnostic message formats, Emacs typically transliterates |
| 7613 | them to curved single quotes, so that the abovequoted symbol appears | 7606 | them to @dfn{curved quotes} (left and right single quotation marks), |
| 7607 | so that the abovequoted symbol appears | ||
| 7614 | as @t{‘case-fold-search’}. Source-code strings can also simply use | 7608 | as @t{‘case-fold-search’}. Source-code strings can also simply use |
| 7615 | curved quotes directly. | 7609 | curved quotes directly. |
| 7616 | 7610 | ||
| @@ -17117,7 +17111,7 @@ This line is a short, but complete Emacs Lisp expression. | |||
| 17117 | 17111 | ||
| 17118 | We are already familiar with @code{setq}. It sets the following variable, | 17112 | We are already familiar with @code{setq}. It sets the following variable, |
| 17119 | @code{major-mode}, to the subsequent value, which is @code{text-mode}. | 17113 | @code{major-mode}, to the subsequent value, which is @code{text-mode}. |
| 17120 | The single quote mark before @code{text-mode} tells Emacs to deal directly | 17114 | The single-quote before @code{text-mode} tells Emacs to deal directly |
| 17121 | with the @code{text-mode} symbol, not with whatever it might stand for. | 17115 | with the @code{text-mode} symbol, not with whatever it might stand for. |
| 17122 | @xref{set & setq, , Setting the Value of a Variable}, | 17116 | @xref{set & setq, , Setting the Value of a Variable}, |
| 17123 | for a reminder of how @code{setq} works. | 17117 | for a reminder of how @code{setq} works. |
| @@ -17284,11 +17278,11 @@ Rebinding Keys in Your Init File, emacs, The GNU Emacs Manual}, for | |||
| 17284 | details.) | 17278 | details.) |
| 17285 | 17279 | ||
| 17286 | The command invoked by the keys is @code{compare-windows}. Note that | 17280 | The command invoked by the keys is @code{compare-windows}. Note that |
| 17287 | @code{compare-windows} is preceded by a single quote; otherwise, Emacs | 17281 | @code{compare-windows} is preceded by a single-quote; otherwise, Emacs |
| 17288 | would first try to evaluate the symbol to determine its value. | 17282 | would first try to evaluate the symbol to determine its value. |
| 17289 | 17283 | ||
| 17290 | These three things, the double quotation marks, the backslash before | 17284 | These three things, the double quotation marks, the backslash before |
| 17291 | the @samp{C}, and the single quote mark are necessary parts of | 17285 | the @samp{C}, and the single-quote are necessary parts of |
| 17292 | keybinding that I tend to forget. Fortunately, I have come to | 17286 | keybinding that I tend to forget. Fortunately, I have come to |
| 17293 | remember that I should look at my existing @file{.emacs} file, and | 17287 | remember that I should look at my existing @file{.emacs} file, and |
| 17294 | adapt what is there. | 17288 | adapt what is there. |
diff --git a/doc/lispref/control.texi b/doc/lispref/control.texi index 3f48c458c02..0cdb03548bf 100644 --- a/doc/lispref/control.texi +++ b/doc/lispref/control.texi | |||
| @@ -1100,10 +1100,13 @@ These examples show typical uses of @code{error}: | |||
| 1100 | error symbol @code{error}, and a list containing the string returned by | 1100 | error symbol @code{error}, and a list containing the string returned by |
| 1101 | @code{format-message}. | 1101 | @code{format-message}. |
| 1102 | 1102 | ||
| 1103 | In a format string containing single quotes, curved quotes @t{‘like | 1103 | The @code{text-quoting-style} variable controls what quotes are |
| 1104 | this’} and grave quotes @t{`like this'} work better than straight | 1104 | generated; @xref{Keys in Documentation}. A call using a format like |
| 1105 | quotes @t{'like this'}, as @code{error} typically formats every | 1105 | @t{"Missing `%s'"} with grave accents and apostrophes typically |
| 1106 | straight quote as a curved closing quote. | 1106 | generates a message like @t{"Missing ‘foo’"} with matching curved |
| 1107 | quotes. In contrast, a call using a format like @t{"Missing '%s'"} | ||
| 1108 | with only apostrophes typically generates a message like @t{"Missing | ||
| 1109 | ’foo’"} with only closing curved quotes, an unusual style in English. | ||
| 1107 | 1110 | ||
| 1108 | @strong{Warning:} If you want to use your own string as an error message | 1111 | @strong{Warning:} If you want to use your own string as an error message |
| 1109 | verbatim, don't just write @code{(error @var{string})}. If @var{string} | 1112 | verbatim, don't just write @code{(error @var{string})}. If @var{string} |
diff --git a/doc/lispref/customize.texi b/doc/lispref/customize.texi index 14e6eb3ab25..4a6f7f2162b 100644 --- a/doc/lispref/customize.texi +++ b/doc/lispref/customize.texi | |||
| @@ -66,9 +66,12 @@ cause confusion.} | |||
| 66 | 66 | ||
| 67 | @kindex group@r{, customization keyword} | 67 | @kindex group@r{, customization keyword} |
| 68 | @item :group @var{group} | 68 | @item :group @var{group} |
| 69 | Put this customization item in group @var{group}. When you use | 69 | Put this customization item in group @var{group}. If this keyword is |
| 70 | @code{:group} in a @code{defgroup}, it makes the new group a subgroup of | 70 | missing from a customization item, it'll be placed in the same group |
| 71 | @var{group}. | 71 | that was last defined (in the current file). |
| 72 | |||
| 73 | When you use @code{:group} in a @code{defgroup}, it makes the new | ||
| 74 | group a subgroup of @var{group}. | ||
| 72 | 75 | ||
| 73 | If you use this keyword more than once, you can put a single item into | 76 | If you use this keyword more than once, you can put a single item into |
| 74 | more than one group. Displaying any of those groups will show this | 77 | more than one group. Displaying any of those groups will show this |
diff --git a/doc/lispref/display.texi b/doc/lispref/display.texi index 3673d114041..87126f9167a 100644 --- a/doc/lispref/display.texi +++ b/doc/lispref/display.texi | |||
| @@ -265,10 +265,13 @@ properties, it is displayed with the specified faces (@pxref{Faces}). | |||
| 265 | The string is also added to the @file{*Messages*} buffer, but without | 265 | The string is also added to the @file{*Messages*} buffer, but without |
| 266 | text properties (@pxref{Logging Messages}). | 266 | text properties (@pxref{Logging Messages}). |
| 267 | 267 | ||
| 268 | In a format string containing single quotes, curved quotes @t{‘like | 268 | The @code{text-quoting-style} variable controls what quotes are |
| 269 | this’} and grave quotes @t{`like this'} work better than straight | 269 | generated; @xref{Keys in Documentation}. A call using a format like |
| 270 | quotes @t{'like this'}, as @code{message} typically formats every | 270 | @t{"Missing `%s'"} with grave accents and apostrophes typically |
| 271 | straight quote as a curved closing quote. | 271 | generates a message like @t{"Missing ‘foo’"} with matching curved |
| 272 | quotes. In contrast, a call using a format like @t{"Missing '%s'"} | ||
| 273 | with only apostrophes typically generates a message like @t{"Missing | ||
| 274 | ’foo’"} with only closing curved quotes, an unusual style in English. | ||
| 272 | 275 | ||
| 273 | In batch mode, the message is printed to the standard error stream, | 276 | In batch mode, the message is printed to the standard error stream, |
| 274 | followed by a newline. | 277 | followed by a newline. |
diff --git a/doc/lispref/help.texi b/doc/lispref/help.texi index 58a11f29a4c..b945e438f55 100644 --- a/doc/lispref/help.texi +++ b/doc/lispref/help.texi | |||
| @@ -335,10 +335,14 @@ specifies @var{mapvar}'s value as the keymap for any following | |||
| 335 | @item ‘ | 335 | @item ‘ |
| 336 | @itemx ` | 336 | @itemx ` |
| 337 | (left single quotation mark and grave accent) both stand for a left quote. | 337 | (left single quotation mark and grave accent) both stand for a left quote. |
| 338 | This generates a left single quotation mark, an apostrophe, or a grave | ||
| 339 | accent depending on the value of @code{text-quoting-style}. | ||
| 338 | 340 | ||
| 339 | @item ’ | 341 | @item ’ |
| 340 | @itemx ' | 342 | @itemx ' |
| 341 | (right single quotation mark and apostrophe) both stand for a right quote. | 343 | (right single quotation mark and apostrophe) both stand for a right quote. |
| 344 | This generates a right single quotation mark or an apostrophe | ||
| 345 | depending on the value of @code{text-quoting-style}. | ||
| 342 | 346 | ||
| 343 | @item \= | 347 | @item \= |
| 344 | quotes the following character and is discarded; thus, @samp{\=`} puts | 348 | quotes the following character and is discarded; thus, @samp{\=`} puts |
diff --git a/doc/lispref/strings.texi b/doc/lispref/strings.texi index ce629aa8259..58ab02dbc41 100644 --- a/doc/lispref/strings.texi +++ b/doc/lispref/strings.texi | |||
| @@ -842,8 +842,14 @@ if any. | |||
| 842 | This function acts like @code{format}, except it also converts any | 842 | This function acts like @code{format}, except it also converts any |
| 843 | curved single quotes in @var{string} as per the value of | 843 | curved single quotes in @var{string} as per the value of |
| 844 | @code{text-quoting-style}, and treats grave accent (@t{`}) and | 844 | @code{text-quoting-style}, and treats grave accent (@t{`}) and |
| 845 | apostrophe (@t{'}) as if they were curved single quotes. @xref{Keys | 845 | apostrophe (@t{'}) as if they were curved single quotes. |
| 846 | in Documentation}. | 846 | |
| 847 | A format that quotes with grave accents and apostrophes @t{`like | ||
| 848 | this'} typically generates curved quotes @t{‘like this’}. In | ||
| 849 | contrast, a format that quotes with only apostrophes @t{'like this'} | ||
| 850 | typically generates two closing curved quotes @t{’like this’}, an | ||
| 851 | unusual style in English. @xref{Keys in Documentation}, for how the | ||
| 852 | @code{text-quoting-style} variable affects generated quotes. | ||
| 847 | @end defun | 853 | @end defun |
| 848 | 854 | ||
| 849 | @cindex @samp{%} in format | 855 | @cindex @samp{%} in format |
| @@ -1917,6 +1917,14 @@ display of diagnostics and help, but not of info. As the variable is | |||
| 1917 | not intended for casual use, it is not a user option. | 1917 | not intended for casual use, it is not a user option. |
| 1918 | 1918 | ||
| 1919 | +++ | 1919 | +++ |
| 1920 | ** Message-issuing functions like 'message' and 'error' now translate | ||
| 1921 | various sorts of single quotes in their format strings according to | ||
| 1922 | the value of 'text-quoting-style' (see above). This translation | ||
| 1923 | cannot be disabled. To get the old behavior, use 'format', which is | ||
| 1924 | not affected by 'text-quoting-style', e.g., (message "%s" (format | ||
| 1925 | "...." foo bar)). | ||
| 1926 | |||
| 1927 | +++ | ||
| 1920 | ** substitute-command-keys now replaces quotes. | 1928 | ** substitute-command-keys now replaces quotes. |
| 1921 | That is, it converts documentation strings' quoting style as per the | 1929 | That is, it converts documentation strings' quoting style as per the |
| 1922 | value of 'text-quoting-style'. Doc strings in source code can use | 1930 | value of 'text-quoting-style'. Doc strings in source code can use |
| @@ -1924,13 +1932,6 @@ either curved single quotes or grave accents and apostrophes. As | |||
| 1924 | before, characters preceded by \= are output as-is. | 1932 | before, characters preceded by \= are output as-is. |
| 1925 | 1933 | ||
| 1926 | +++ | 1934 | +++ |
| 1927 | ** Message-issuing functions 'error', 'message', etc. now convert quotes. | ||
| 1928 | They use the new 'format-message' function instead of plain 'format', | ||
| 1929 | so that they now follow user preference as per 'text-quoting-style' | ||
| 1930 | when processing curved single quotes, grave accents, and apostrophes | ||
| 1931 | in their format argument. | ||
| 1932 | |||
| 1933 | +++ | ||
| 1934 | ** The character classes [:alpha:] and [:alnum:] in regular expressions | 1935 | ** The character classes [:alpha:] and [:alnum:] in regular expressions |
| 1935 | now match multibyte characters using Unicode character properties. | 1936 | now match multibyte characters using Unicode character properties. |
| 1936 | If you want the old behavior where they matched any character with | 1937 | If you want the old behavior where they matched any character with |
| @@ -2148,9 +2149,11 @@ permissions set to temporary values (e.g., for creating private files). | |||
| 2148 | 2149 | ||
| 2149 | --- | 2150 | --- |
| 2150 | ** Function 'system-name' now returns an updated value if the current | 2151 | ** Function 'system-name' now returns an updated value if the current |
| 2151 | system's name has changed or if the Emacs process has changed systems, | 2152 | system's name has changed or if the Emacs process has changed systems. |
| 2152 | and to avoid long waits it no longer consults DNS to canonicalize the | 2153 | To avoid long waits it no longer consults DNS to canonicalize the name |
| 2153 | name. The variable 'system-name' is now obsolete. | 2154 | (in some cases this may affect generated message-id headers - customize |
| 2155 | 'message-user-fqdn' if this bothers you). The variable 'system-name' | ||
| 2156 | is now obsolete. | ||
| 2154 | 2157 | ||
| 2155 | +++ | 2158 | +++ |
| 2156 | ** Function 'write-region' no longer outputs "Wrote FILE" in batch mode. | 2159 | ** Function 'write-region' no longer outputs "Wrote FILE" in batch mode. |
diff --git a/etc/PROBLEMS b/etc/PROBLEMS index 4288808f407..49dada970bb 100644 --- a/etc/PROBLEMS +++ b/etc/PROBLEMS | |||
| @@ -1624,7 +1624,7 @@ which combination produces "M-x" in the echo area. You can also use | |||
| 1624 | the 'xmodmap' utility to show all the keys which produce a Meta | 1624 | the 'xmodmap' utility to show all the keys which produce a Meta |
| 1625 | modifier: | 1625 | modifier: |
| 1626 | 1626 | ||
| 1627 | xmodmap -pk | egrep -i "meta|alt" | 1627 | xmodmap -pk | grep -Ei "meta|alt" |
| 1628 | 1628 | ||
| 1629 | A more convenient way of finding out which keys produce a Meta modifier | 1629 | A more convenient way of finding out which keys produce a Meta modifier |
| 1630 | is to use the 'xkbprint' utility, if it's available on your system: | 1630 | is to use the 'xkbprint' utility, if it's available on your system: |
diff --git a/lisp/calendar/todo-mode.el b/lisp/calendar/todo-mode.el index 0529e970333..8e752586053 100644 --- a/lisp/calendar/todo-mode.el +++ b/lisp/calendar/todo-mode.el | |||
| @@ -902,17 +902,19 @@ Categories mode." | |||
| 902 | (todo-show) | 902 | (todo-show) |
| 903 | (let* ((archive (eq where 'archive)) | 903 | (let* ((archive (eq where 'archive)) |
| 904 | (cat (unless archive where)) | 904 | (cat (unless archive where)) |
| 905 | (goto-archive (and cat | ||
| 906 | todo-skip-archived-categories | ||
| 907 | (zerop (todo-get-count 'todo cat)) | ||
| 908 | (zerop (todo-get-count 'done cat)) | ||
| 909 | (not (zerop (todo-get-count 'archived cat))))) | ||
| 905 | (file0 (when cat ; We're in Todo Categories mode. | 910 | (file0 (when cat ; We're in Todo Categories mode. |
| 906 | ;; With non-nil `todo-skip-archived-categories' | 911 | (if goto-archive |
| 907 | ;; jump to archive file of a category with only | 912 | ;; If the category has only archived items and |
| 908 | ;; archived items. | 913 | ;; `todo-skip-archived-categories' is non-nil, jump to |
| 909 | (if (and todo-skip-archived-categories | 914 | ;; the archive category. |
| 910 | (zerop (todo-get-count 'todo cat)) | ||
| 911 | (zerop (todo-get-count 'done cat)) | ||
| 912 | (not (zerop (todo-get-count 'archived cat)))) | ||
| 913 | (concat (file-name-sans-extension | 915 | (concat (file-name-sans-extension |
| 914 | todo-current-todo-file) ".toda") | 916 | todo-current-todo-file) ".toda") |
| 915 | ;; Otherwise, jump to current todo file. | 917 | ;; Otherwise, jump to the category in the todo file. |
| 916 | todo-current-todo-file))) | 918 | todo-current-todo-file))) |
| 917 | (len (length todo-categories)) | 919 | (len (length todo-categories)) |
| 918 | (cat+file (unless cat | 920 | (cat+file (unless cat |
| @@ -923,18 +925,15 @@ Categories mode." | |||
| 923 | (category (or cat (car cat+file)))) | 925 | (category (or cat (car cat+file)))) |
| 924 | (unless cat (setq file0 (cdr cat+file))) | 926 | (unless cat (setq file0 (cdr cat+file))) |
| 925 | (with-current-buffer (find-file-noselect file0 'nowarn) | 927 | (with-current-buffer (find-file-noselect file0 'nowarn) |
| 926 | (setq todo-current-todo-file file0) | 928 | (when goto-archive (todo-archive-mode)) |
| 927 | ;; If called from Todo Categories mode, clean up before jumping. | 929 | (set-window-buffer (selected-window) |
| 928 | (if (string= (buffer-name) todo-categories-buffer) | 930 | (set-buffer (find-buffer-visiting file0))) |
| 929 | (kill-buffer)) | 931 | (unless todo-global-current-todo-file |
| 930 | (set-window-buffer (selected-window) | 932 | (setq todo-global-current-todo-file todo-current-todo-file)) |
| 931 | (set-buffer (find-buffer-visiting file0))) | 933 | (todo-category-number category) |
| 932 | (unless todo-global-current-todo-file | 934 | (todo-category-select) |
| 933 | (setq todo-global-current-todo-file todo-current-todo-file)) | 935 | (goto-char (point-min)) |
| 934 | (todo-category-number category) | 936 | (when add-item (todo-insert-item--basic)))))) |
| 935 | (todo-category-select) | ||
| 936 | (goto-char (point-min)) | ||
| 937 | (when add-item (todo-insert-item--basic)))))) | ||
| 938 | 937 | ||
| 939 | (defun todo-next-item (&optional count) | 938 | (defun todo-next-item (&optional count) |
| 940 | "Move point down to the beginning of the next item. | 939 | "Move point down to the beginning of the next item. |
diff --git a/lisp/cedet/cedet-cscope.el b/lisp/cedet/cedet-cscope.el index 9a54d341f56..373149c16e3 100644 --- a/lisp/cedet/cedet-cscope.el +++ b/lisp/cedet/cedet-cscope.el | |||
| @@ -52,7 +52,7 @@ SCOPE is the scope of the search, such as 'project or 'subdirs." | |||
| 52 | ;; -0 = Find C symbol | 52 | ;; -0 = Find C symbol |
| 53 | ;; -1 = Find global definition | 53 | ;; -1 = Find global definition |
| 54 | ;; -3 = Find references | 54 | ;; -3 = Find references |
| 55 | ;; -6 = Find egrep pattern | 55 | ;; -6 = Find grep -E pattern |
| 56 | ;; -7 = Find file | 56 | ;; -7 = Find file |
| 57 | (let ((idx (cond ((eq type 'file) | 57 | (let ((idx (cond ((eq type 'file) |
| 58 | "-7") | 58 | "-7") |
diff --git a/lisp/cedet/semantic/symref.el b/lisp/cedet/semantic/symref.el index 088740b2624..516a4f30414 100644 --- a/lisp/cedet/semantic/symref.el +++ b/lisp/cedet/semantic/symref.el | |||
| @@ -266,7 +266,7 @@ Returns an object of class `semantic-symref-result'." | |||
| 266 | ;;;###autoload | 266 | ;;;###autoload |
| 267 | (defun semantic-symref-find-text (text &optional scope) | 267 | (defun semantic-symref-find-text (text &optional scope) |
| 268 | "Find a list of occurrences of TEXT in the current project. | 268 | "Find a list of occurrences of TEXT in the current project. |
| 269 | TEXT is a regexp formatted for use with egrep. | 269 | TEXT is a regexp formatted for use with grep -E. |
| 270 | Optional SCOPE specifies which file set to search. Defaults to `project'. | 270 | Optional SCOPE specifies which file set to search. Defaults to `project'. |
| 271 | Refers to `semantic-symref-tool', to determine the reference tool to use | 271 | Refers to `semantic-symref-tool', to determine the reference tool to use |
| 272 | for the current buffer. | 272 | for the current buffer. |
diff --git a/lisp/dired-aux.el b/lisp/dired-aux.el index b23b04a45fa..8d6f6656a9a 100644 --- a/lisp/dired-aux.el +++ b/lisp/dired-aux.el | |||
| @@ -2747,14 +2747,21 @@ with the command \\[tags-loop-continue]." | |||
| 2747 | 2747 | ||
| 2748 | ;;;###autoload | 2748 | ;;;###autoload |
| 2749 | (defun dired-do-find-regexp (regexp) | 2749 | (defun dired-do-find-regexp (regexp) |
| 2750 | "Find all matches for REGEXP in all marked files, recursively." | 2750 | "Find all matches for REGEXP in all marked files. |
| 2751 | For any marked directory, all of its files are searched recursively. | ||
| 2752 | However, files matching `grep-find-ignored-files' and subdirectories | ||
| 2753 | matching `grep-find-ignored-directories' are skipped in the marked | ||
| 2754 | directories. | ||
| 2755 | |||
| 2756 | REGEXP should use constructs supported by your local `grep' command." | ||
| 2751 | (interactive "sSearch marked files (regexp): ") | 2757 | (interactive "sSearch marked files (regexp): ") |
| 2752 | (require 'grep) | 2758 | (require 'grep) |
| 2753 | (defvar grep-find-ignored-files) | 2759 | (defvar grep-find-ignored-files) |
| 2760 | (defvar grep-find-ignored-directories) | ||
| 2754 | (let* ((files (dired-get-marked-files)) | 2761 | (let* ((files (dired-get-marked-files)) |
| 2755 | (ignores (nconc (mapcar | 2762 | (ignores (nconc (mapcar |
| 2756 | (lambda (s) (concat s "/")) | 2763 | (lambda (s) (concat s "/")) |
| 2757 | vc-directory-exclusion-list) | 2764 | grep-find-ignored-directories) |
| 2758 | grep-find-ignored-files)) | 2765 | grep-find-ignored-files)) |
| 2759 | (xrefs (cl-mapcan | 2766 | (xrefs (cl-mapcan |
| 2760 | (lambda (file) | 2767 | (lambda (file) |
| @@ -2768,7 +2775,13 @@ with the command \\[tags-loop-continue]." | |||
| 2768 | 2775 | ||
| 2769 | ;;;###autoload | 2776 | ;;;###autoload |
| 2770 | (defun dired-do-find-regexp-and-replace (from to) | 2777 | (defun dired-do-find-regexp-and-replace (from to) |
| 2771 | "Replace matches of FROM with TO, in all marked files, recursively." | 2778 | "Replace matches of FROM with TO, in all marked files. |
| 2779 | For any marked directory, matches in all of its files are replaced, | ||
| 2780 | recursively. However, files matching `grep-find-ignored-files' | ||
| 2781 | and subdirectories matching `grep-find-ignored-directories' are skipped | ||
| 2782 | in the marked directories. | ||
| 2783 | |||
| 2784 | REGEXP should use constructs supported by your local `grep' command." | ||
| 2772 | (interactive | 2785 | (interactive |
| 2773 | (let ((common | 2786 | (let ((common |
| 2774 | (query-replace-read-args | 2787 | (query-replace-read-args |
diff --git a/lisp/man.el b/lisp/man.el index 2b2ee99a9be..5acf90baf28 100644 --- a/lisp/man.el +++ b/lisp/man.el | |||
| @@ -964,7 +964,7 @@ otherwise look like a page name. | |||
| 964 | 964 | ||
| 965 | An \"apropos\" query with -k gives a buffer of matching page | 965 | An \"apropos\" query with -k gives a buffer of matching page |
| 966 | names or descriptions. The pattern argument is usually an | 966 | names or descriptions. The pattern argument is usually an |
| 967 | \"egrep\" style regexp. | 967 | \"grep -E\" style regexp. |
| 968 | 968 | ||
| 969 | -k pattern" | 969 | -k pattern" |
| 970 | 970 | ||
diff --git a/lisp/progmodes/elisp-mode.el b/lisp/progmodes/elisp-mode.el index 1c728484ab5..2ad22ddd0ff 100644 --- a/lisp/progmodes/elisp-mode.el +++ b/lisp/progmodes/elisp-mode.el | |||
| @@ -823,8 +823,9 @@ non-nil result supercedes the xrefs produced by | |||
| 823 | (pcase-let (((cl-struct xref-elisp-location symbol type file) l)) | 823 | (pcase-let (((cl-struct xref-elisp-location symbol type file) l)) |
| 824 | (let ((buffer-point (find-function-search-for-symbol symbol type file))) | 824 | (let ((buffer-point (find-function-search-for-symbol symbol type file))) |
| 825 | (with-current-buffer (car buffer-point) | 825 | (with-current-buffer (car buffer-point) |
| 826 | (goto-char (or (cdr buffer-point) (point-min))) | 826 | (save-excursion |
| 827 | (point-marker))))) | 827 | (goto-char (or (cdr buffer-point) (point-min))) |
| 828 | (point-marker)))))) | ||
| 828 | 829 | ||
| 829 | (cl-defmethod xref-location-group ((l xref-elisp-location)) | 830 | (cl-defmethod xref-location-group ((l xref-elisp-location)) |
| 830 | (xref-elisp-location-file l)) | 831 | (xref-elisp-location-file l)) |
diff --git a/lisp/progmodes/etags.el b/lisp/progmodes/etags.el index a2a0df2d6e1..890d55294cf 100644 --- a/lisp/progmodes/etags.el +++ b/lisp/progmodes/etags.el | |||
| @@ -2146,8 +2146,9 @@ for \\[find-tag] (which see)." | |||
| 2146 | (with-slots (tag-info file) l | 2146 | (with-slots (tag-info file) l |
| 2147 | (let ((buffer (find-file-noselect file))) | 2147 | (let ((buffer (find-file-noselect file))) |
| 2148 | (with-current-buffer buffer | 2148 | (with-current-buffer buffer |
| 2149 | (etags-goto-tag-location tag-info) | 2149 | (save-excursion |
| 2150 | (point-marker))))) | 2150 | (etags-goto-tag-location tag-info) |
| 2151 | (point-marker)))))) | ||
| 2151 | 2152 | ||
| 2152 | (cl-defmethod xref-location-line ((l xref-etags-location)) | 2153 | (cl-defmethod xref-location-line ((l xref-etags-location)) |
| 2153 | (with-slots (tag-info) l | 2154 | (with-slots (tag-info) l |
diff --git a/lisp/progmodes/project.el b/lisp/progmodes/project.el index 9c8a88c80fc..a51c383b93b 100644 --- a/lisp/progmodes/project.el +++ b/lisp/progmodes/project.el | |||
| @@ -172,7 +172,8 @@ to find the list of ignores for each directory." | |||
| 172 | (let ((command | 172 | (let ((command |
| 173 | (format "%s %s %s -type f -print0" | 173 | (format "%s %s %s -type f -print0" |
| 174 | find-program | 174 | find-program |
| 175 | dir | 175 | (shell-quote-argument |
| 176 | (expand-file-name dir)) | ||
| 176 | (xref--find-ignores-arguments | 177 | (xref--find-ignores-arguments |
| 177 | (project-ignores project dir) | 178 | (project-ignores project dir) |
| 178 | (expand-file-name dir))))) | 179 | (expand-file-name dir))))) |
diff --git a/lisp/progmodes/xref.el b/lisp/progmodes/xref.el index b5632af13ab..f651dc9cd18 100644 --- a/lisp/progmodes/xref.el +++ b/lisp/progmodes/xref.el | |||
| @@ -521,58 +521,86 @@ references displayed in the current *xref* buffer." | |||
| 521 | (let ((fr (read-regexp "Xref query-replace (regexp)" ".*"))) | 521 | (let ((fr (read-regexp "Xref query-replace (regexp)" ".*"))) |
| 522 | (list fr | 522 | (list fr |
| 523 | (read-regexp (format "Xref query-replace (regexp) %s with: " fr))))) | 523 | (read-regexp (format "Xref query-replace (regexp) %s with: " fr))))) |
| 524 | (let ((reporter (make-progress-reporter (format "Saving search results...") | 524 | (let* (item xrefs iter) |
| 525 | 0 (line-number-at-pos (point-max)))) | 525 | (save-excursion |
| 526 | (counter 0) | 526 | (while (setq item (xref--search-property 'xref-item)) |
| 527 | pairs item) | 527 | (when (xref-match-length item) |
| 528 | (push item xrefs)))) | ||
| 528 | (unwind-protect | 529 | (unwind-protect |
| 529 | (progn | 530 | (progn |
| 530 | (save-excursion | 531 | (goto-char (point-min)) |
| 531 | (goto-char (point-min)) | 532 | (setq iter (xref--buf-pairs-iterator (nreverse xrefs))) |
| 532 | ;; TODO: This list should be computed on-demand instead. | 533 | (xref--query-replace-1 from to iter)) |
| 533 | ;; As long as the UI just iterates through matches one by | 534 | (funcall iter :cleanup)))) |
| 534 | ;; one, there's no need to compute them all in advance. | 535 | |
| 535 | ;; Then we can throw away the reporter. | 536 | (defun xref--buf-pairs-iterator (xrefs) |
| 536 | (while (setq item (xref--search-property 'xref-item)) | 537 | (let (chunk-done item next-pair file-buf pairs all-pairs) |
| 537 | (when (xref-match-length item) | 538 | (lambda (action) |
| 538 | (save-excursion | 539 | (pcase action |
| 539 | (let* ((loc (xref-item-location item)) | 540 | (:next |
| 540 | (beg (xref-location-marker loc)) | 541 | (when (or xrefs next-pair) |
| 541 | (end (move-marker (make-marker) | 542 | (setq chunk-done nil) |
| 542 | (+ beg (xref-match-length item)) | 543 | (when next-pair |
| 543 | (marker-buffer beg)))) | 544 | (setq file-buf (marker-buffer (car next-pair)) |
| 544 | ;; Perform sanity check first. | 545 | pairs (list next-pair) |
| 545 | (xref--goto-location loc) | 546 | next-pair nil)) |
| 546 | ;; FIXME: The check should probably be a generic | 547 | (while (and (not chunk-done) |
| 547 | ;; function, instead of the assumption that all | 548 | (setq item (pop xrefs))) |
| 548 | ;; matches contain the full line as summary. | 549 | (save-excursion |
| 549 | ;; TODO: Offer to re-scan otherwise. | 550 | (let* ((loc (xref-item-location item)) |
| 550 | (unless (equal (buffer-substring-no-properties | 551 | (beg (xref-location-marker loc)) |
| 551 | (line-beginning-position) | 552 | (end (move-marker (make-marker) |
| 552 | (line-end-position)) | 553 | (+ beg (xref-match-length item)) |
| 553 | (xref-item-summary item)) | 554 | (marker-buffer beg)))) |
| 554 | (user-error "Search results out of date")) | 555 | (let ((pair (cons beg end))) |
| 555 | (progress-reporter-update reporter (cl-incf counter)) | 556 | (push pair all-pairs) |
| 556 | (push (cons beg end) pairs))))) | 557 | ;; Perform sanity check first. |
| 557 | (setq pairs (nreverse pairs))) | 558 | (xref--goto-location loc) |
| 558 | (unless pairs (user-error "No suitable matches here")) | 559 | (if (xref--outdated-p item |
| 559 | (progress-reporter-done reporter) | 560 | (buffer-substring-no-properties |
| 560 | (xref--query-replace-1 from to pairs)) | 561 | (line-beginning-position) |
| 561 | (dolist (pair pairs) | 562 | (line-end-position))) |
| 562 | (move-marker (car pair) nil) | 563 | (message "Search result out of date, skipping") |
| 563 | (move-marker (cdr pair) nil))))) | 564 | (cond |
| 565 | ((null file-buf) | ||
| 566 | (setq file-buf (marker-buffer beg)) | ||
| 567 | (push pair pairs)) | ||
| 568 | ((equal file-buf (marker-buffer beg)) | ||
| 569 | (push pair pairs)) | ||
| 570 | (t | ||
| 571 | (setq chunk-done t | ||
| 572 | next-pair pair)))))))) | ||
| 573 | (cons file-buf (nreverse pairs)))) | ||
| 574 | (:cleanup | ||
| 575 | (dolist (pair all-pairs) | ||
| 576 | (move-marker (car pair) nil) | ||
| 577 | (move-marker (cdr pair) nil))))))) | ||
| 578 | |||
| 579 | (defun xref--outdated-p (item line-text) | ||
| 580 | ;; FIXME: The check should probably be a generic function instead of | ||
| 581 | ;; the assumption that all matches contain the full line as summary. | ||
| 582 | (let ((summary (xref-item-summary item)) | ||
| 583 | (strip (lambda (s) (if (string-match "\r\\'" s) | ||
| 584 | (substring-no-properties s 0 -1) | ||
| 585 | s)))) | ||
| 586 | (not | ||
| 587 | ;; Sometimes buffer contents include ^M, and sometimes Grep | ||
| 588 | ;; output includes it, and they don't always match. | ||
| 589 | (equal (funcall strip line-text) | ||
| 590 | (funcall strip summary))))) | ||
| 564 | 591 | ||
| 565 | ;; FIXME: Write a nicer UI. | 592 | ;; FIXME: Write a nicer UI. |
| 566 | (defun xref--query-replace-1 (from to pairs) | 593 | (defun xref--query-replace-1 (from to iter) |
| 567 | (let* ((query-replace-lazy-highlight nil) | 594 | (let* ((query-replace-lazy-highlight nil) |
| 568 | current-beg current-end current-buf | 595 | (continue t) |
| 596 | did-it-once buf-pairs pairs | ||
| 597 | current-beg current-end | ||
| 569 | ;; Counteract the "do the next match now" hack in | 598 | ;; Counteract the "do the next match now" hack in |
| 570 | ;; `perform-replace'. And still, it'll report that those | 599 | ;; `perform-replace'. And still, it'll report that those |
| 571 | ;; matches were "filtered out" at the end. | 600 | ;; matches were "filtered out" at the end. |
| 572 | (isearch-filter-predicate | 601 | (isearch-filter-predicate |
| 573 | (lambda (beg end) | 602 | (lambda (beg end) |
| 574 | (and current-beg | 603 | (and current-beg |
| 575 | (eq (current-buffer) current-buf) | ||
| 576 | (>= beg current-beg) | 604 | (>= beg current-beg) |
| 577 | (<= end current-end)))) | 605 | (<= end current-end)))) |
| 578 | (replace-re-search-function | 606 | (replace-re-search-function |
| @@ -581,19 +609,22 @@ references displayed in the current *xref* buffer." | |||
| 581 | (while (and (not found) pairs) | 609 | (while (and (not found) pairs) |
| 582 | (setq pair (pop pairs) | 610 | (setq pair (pop pairs) |
| 583 | current-beg (car pair) | 611 | current-beg (car pair) |
| 584 | current-end (cdr pair) | 612 | current-end (cdr pair)) |
| 585 | current-buf (marker-buffer current-beg)) | ||
| 586 | (xref--with-dedicated-window | ||
| 587 | (pop-to-buffer current-buf)) | ||
| 588 | (goto-char current-beg) | 613 | (goto-char current-beg) |
| 589 | (when (re-search-forward from current-end noerror) | 614 | (when (re-search-forward from current-end noerror) |
| 590 | (setq found t))) | 615 | (setq found t))) |
| 591 | found)))) | 616 | found)))) |
| 592 | ;; FIXME: Despite this being a multi-buffer replacement, `N' | 617 | (while (and continue (setq buf-pairs (funcall iter :next))) |
| 593 | ;; doesn't work, because we're not using | 618 | (if did-it-once |
| 594 | ;; `multi-query-replace-map', and it would expect the below | 619 | ;; Reuse the same window for subsequent buffers. |
| 595 | ;; function to be called once per buffer. | 620 | (switch-to-buffer (car buf-pairs)) |
| 596 | (perform-replace from to t t nil))) | 621 | (xref--with-dedicated-window |
| 622 | (pop-to-buffer (car buf-pairs))) | ||
| 623 | (setq did-it-once t)) | ||
| 624 | (setq pairs (cdr buf-pairs)) | ||
| 625 | (setq continue | ||
| 626 | (perform-replace from to t t nil nil multi-query-replace-map))) | ||
| 627 | (unless did-it-once (user-error "No suitable matches here")))) | ||
| 597 | 628 | ||
| 598 | (defvar xref--xref-buffer-mode-map | 629 | (defvar xref--xref-buffer-mode-map |
| 599 | (let ((map (make-sparse-keymap))) | 630 | (let ((map (make-sparse-keymap))) |
| @@ -687,7 +718,9 @@ Return an alist of the form ((FILENAME . (XREF ...)) ...)." | |||
| 687 | (defun xref--show-xref-buffer (xrefs alist) | 718 | (defun xref--show-xref-buffer (xrefs alist) |
| 688 | (let ((xref-alist (xref--analyze xrefs))) | 719 | (let ((xref-alist (xref--analyze xrefs))) |
| 689 | (with-current-buffer (get-buffer-create xref-buffer-name) | 720 | (with-current-buffer (get-buffer-create xref-buffer-name) |
| 690 | (let ((inhibit-read-only t)) | 721 | (setq buffer-undo-list nil) |
| 722 | (let ((inhibit-read-only t) | ||
| 723 | (buffer-undo-list t)) | ||
| 691 | (erase-buffer) | 724 | (erase-buffer) |
| 692 | (xref--insert-xrefs xref-alist) | 725 | (xref--insert-xrefs xref-alist) |
| 693 | (xref--xref-buffer-mode) | 726 | (xref--xref-buffer-mode) |
| @@ -908,6 +941,8 @@ IGNORES is a list of glob patterns." | |||
| 908 | (require 'find-dired) ; for `find-name-arg' | 941 | (require 'find-dired) ; for `find-name-arg' |
| 909 | (defvar grep-find-template) | 942 | (defvar grep-find-template) |
| 910 | (defvar find-name-arg) | 943 | (defvar find-name-arg) |
| 944 | ;; `shell-quote-argument' quotes the tilde as well. | ||
| 945 | (cl-assert (not (string-match-p "\\`~" dir))) | ||
| 911 | (grep-expand-template | 946 | (grep-expand-template |
| 912 | grep-find-template | 947 | grep-find-template |
| 913 | regexp | 948 | regexp |
| @@ -919,14 +954,13 @@ IGNORES is a list of glob patterns." | |||
| 919 | (concat " -o " find-name-arg " ")) | 954 | (concat " -o " find-name-arg " ")) |
| 920 | " " | 955 | " " |
| 921 | (shell-quote-argument ")")) | 956 | (shell-quote-argument ")")) |
| 922 | dir | 957 | (shell-quote-argument dir) |
| 923 | (xref--find-ignores-arguments ignores dir))) | 958 | (xref--find-ignores-arguments ignores dir))) |
| 924 | 959 | ||
| 925 | (defun xref--find-ignores-arguments (ignores dir) | 960 | (defun xref--find-ignores-arguments (ignores dir) |
| 926 | "Convert IGNORES and DIR to a list of arguments for 'find'. | 961 | "Convert IGNORES and DIR to a list of arguments for 'find'. |
| 927 | IGNORES is a list of glob patterns. DIR is an absolute | 962 | IGNORES is a list of glob patterns. DIR is an absolute |
| 928 | directory, used as the root of the ignore globs." | 963 | directory, used as the root of the ignore globs." |
| 929 | ;; `shell-quote-argument' quotes the tilde as well. | ||
| 930 | (cl-assert (not (string-match-p "\\`~" dir))) | 964 | (cl-assert (not (string-match-p "\\`~" dir))) |
| 931 | (when ignores | 965 | (when ignores |
| 932 | (concat | 966 | (concat |
| @@ -1014,7 +1048,11 @@ directory, used as the root of the ignore globs." | |||
| 1014 | (syntax-propertize line-end) | 1048 | (syntax-propertize line-end) |
| 1015 | ;; FIXME: This results in several lines with the same | 1049 | ;; FIXME: This results in several lines with the same |
| 1016 | ;; summary. Solve with composite pattern? | 1050 | ;; summary. Solve with composite pattern? |
| 1017 | (while (re-search-forward regexp line-end t) | 1051 | (while (and |
| 1052 | ;; REGEXP might match an empty string. Or line. | ||
| 1053 | (or (null matches) | ||
| 1054 | (> (point) line-beg)) | ||
| 1055 | (re-search-forward regexp line-end t)) | ||
| 1018 | (let* ((beg-column (- (match-beginning 0) line-beg)) | 1056 | (let* ((beg-column (- (match-beginning 0) line-beg)) |
| 1019 | (end-column (- (match-end 0) line-beg)) | 1057 | (end-column (- (match-end 0) line-beg)) |
| 1020 | (loc (xref-make-file-location file line beg-column)) | 1058 | (loc (xref-make-file-location file line beg-column)) |
diff --git a/lisp/replace.el b/lisp/replace.el index 169fc3f4701..0b25200be57 100644 --- a/lisp/replace.el +++ b/lisp/replace.el | |||
| @@ -191,18 +191,15 @@ wants to replace FROM with TO." | |||
| 191 | ;; a region in order to specify the minibuffer input. | 191 | ;; a region in order to specify the minibuffer input. |
| 192 | ;; That should not clobber the region for the query-replace itself. | 192 | ;; That should not clobber the region for the query-replace itself. |
| 193 | (save-excursion | 193 | (save-excursion |
| 194 | ;; The `with-current-buffer' ensures that the binding | 194 | (minibuffer-with-setup-hook |
| 195 | ;; for `text-property-default-nonsticky' isn't a buffer | 195 | (lambda () |
| 196 | ;; local binding in the current buffer, which | 196 | (setq-local text-property-default-nonsticky |
| 197 | ;; `read-from-minibuffer' wouldn't see. | 197 | (cons '(separator . t) text-property-default-nonsticky))) |
| 198 | (with-current-buffer (window-buffer (minibuffer-window)) | 198 | (if regexp-flag |
| 199 | (let ((text-property-default-nonsticky | 199 | (read-regexp prompt nil 'query-replace-from-to-history) |
| 200 | (cons '(separator . t) text-property-default-nonsticky))) | 200 | (read-from-minibuffer |
| 201 | (if regexp-flag | 201 | prompt nil nil nil 'query-replace-from-to-history |
| 202 | (read-regexp prompt nil 'query-replace-from-to-history) | 202 | (car (if regexp-flag regexp-search-ring search-ring)) t))))) |
| 203 | (read-from-minibuffer | ||
| 204 | prompt nil nil nil 'query-replace-from-to-history | ||
| 205 | (car (if regexp-flag regexp-search-ring search-ring)) t)))))) | ||
| 206 | (to)) | 203 | (to)) |
| 207 | (if (and (zerop (length from)) query-replace-defaults) | 204 | (if (and (zerop (length from)) query-replace-defaults) |
| 208 | (cons (caar query-replace-defaults) | 205 | (cons (caar query-replace-defaults) |
diff --git a/lisp/subr.el b/lisp/subr.el index f67f70f85c9..094710b026c 100644 --- a/lisp/subr.el +++ b/lisp/subr.el | |||
| @@ -291,21 +291,27 @@ This function accepts any number of arguments, but ignores them." | |||
| 291 | 291 | ||
| 292 | ;; Signal a compile-error if the first arg is missing. | 292 | ;; Signal a compile-error if the first arg is missing. |
| 293 | (defun error (&rest args) | 293 | (defun error (&rest args) |
| 294 | "Signal an error, making error message by passing all args to `format'. | 294 | "Signal an error, making a message by passing args to `format-message'. |
| 295 | In Emacs, the convention is that error messages start with a capital | 295 | In Emacs, the convention is that error messages start with a capital |
| 296 | letter but *do not* end with a period. Please follow this convention | 296 | letter but *do not* end with a period. Please follow this convention |
| 297 | for the sake of consistency." | 297 | for the sake of consistency. |
| 298 | |||
| 299 | Note: (error \"%s\" VALUE) makes the message VALUE without | ||
| 300 | interpreting format characters like `%', `\\=`', and `\\=''." | ||
| 298 | (declare (advertised-calling-convention (string &rest args) "23.1")) | 301 | (declare (advertised-calling-convention (string &rest args) "23.1")) |
| 299 | (signal 'error (list (apply #'format-message args)))) | 302 | (signal 'error (list (apply #'format-message args)))) |
| 300 | 303 | ||
| 301 | (defun user-error (format &rest args) | 304 | (defun user-error (format &rest args) |
| 302 | "Signal a pilot error, making error message by passing all args to `format'. | 305 | "Signal a pilot error, making a message by passing args to `format-message'. |
| 303 | In Emacs, the convention is that error messages start with a capital | 306 | In Emacs, the convention is that error messages start with a capital |
| 304 | letter but *do not* end with a period. Please follow this convention | 307 | letter but *do not* end with a period. Please follow this convention |
| 305 | for the sake of consistency. | 308 | for the sake of consistency. |
| 306 | This is just like `error' except that `user-error's are expected to be the | 309 | This is just like `error' except that `user-error's are expected to be the |
| 307 | result of an incorrect manipulation on the part of the user, rather than the | 310 | result of an incorrect manipulation on the part of the user, rather than the |
| 308 | result of an actual problem." | 311 | result of an actual problem. |
| 312 | |||
| 313 | Note: (user-error \"%s\" VALUE) makes the message VALUE without | ||
| 314 | interpreting format characters like `%', `\\=`', and `\\=''." | ||
| 309 | (signal 'user-error (list (apply #'format-message format args)))) | 315 | (signal 'user-error (list (apply #'format-message format args)))) |
| 310 | 316 | ||
| 311 | (defun define-error (name message &optional parent) | 317 | (defun define-error (name message &optional parent) |
| @@ -1123,6 +1129,7 @@ The return value is a positive integer." | |||
| 1123 | 1129 | ||
| 1124 | (defun posnp (obj) | 1130 | (defun posnp (obj) |
| 1125 | "Return non-nil if OBJ appears to be a valid `posn' object specifying a window. | 1131 | "Return non-nil if OBJ appears to be a valid `posn' object specifying a window. |
| 1132 | A `posn' object is returned from functions such as `event-start'. | ||
| 1126 | If OBJ is a valid `posn' object, but specifies a frame rather | 1133 | If OBJ is a valid `posn' object, but specifies a frame rather |
| 1127 | than a window, return nil." | 1134 | than a window, return nil." |
| 1128 | ;; FIXME: Correct the behavior of this function so that all valid | 1135 | ;; FIXME: Correct the behavior of this function so that all valid |
diff --git a/src/bidi.c b/src/bidi.c index c23ff954356..573e513469d 100644 --- a/src/bidi.c +++ b/src/bidi.c | |||
| @@ -2498,10 +2498,10 @@ typedef struct bpa_stack_entry { | |||
| 2498 | 2498 | ||
| 2499 | And finally, cross-reference these two: | 2499 | And finally, cross-reference these two: |
| 2500 | 2500 | ||
| 2501 | fgrep -w -f brackets.txt decompositions.txt | 2501 | grep -Fw -f brackets.txt decompositions.txt |
| 2502 | 2502 | ||
| 2503 | where "decompositions.txt" was produced by the 1st script, and | 2503 | where "decompositions.txt" was produced by the 1st script, and |
| 2504 | "brackets.txt" by the 2nd script. In the output of fgrep, look | 2504 | "brackets.txt" by the 2nd script. In the output of grep, look |
| 2505 | only for decompositions that don't begin with some compatibility | 2505 | only for decompositions that don't begin with some compatibility |
| 2506 | formatting tag, such as "<compat>". Only decompositions that | 2506 | formatting tag, such as "<compat>". Only decompositions that |
| 2507 | consist solely of character codepoints are relevant to bidi | 2507 | consist solely of character codepoints are relevant to bidi |
diff --git a/src/callint.c b/src/callint.c index e56f7cd1b84..053ee6cdaa5 100644 --- a/src/callint.c +++ b/src/callint.c | |||
| @@ -272,7 +272,7 @@ invoke it. If KEYS is omitted or nil, the return value of | |||
| 272 | { | 272 | { |
| 273 | /* `args' will contain the array of arguments to pass to the function. | 273 | /* `args' will contain the array of arguments to pass to the function. |
| 274 | `visargs' will contain the same list but in a nicer form, so that if we | 274 | `visargs' will contain the same list but in a nicer form, so that if we |
| 275 | pass it to `Fformat' it will be understandable to a human. */ | 275 | pass it to `Fformat_message' it will be understandable to a human. */ |
| 276 | Lisp_Object *args, *visargs; | 276 | Lisp_Object *args, *visargs; |
| 277 | Lisp_Object specs; | 277 | Lisp_Object specs; |
| 278 | Lisp_Object filter_specs; | 278 | Lisp_Object filter_specs; |
diff --git a/src/doprnt.c b/src/doprnt.c index 506bbc3df35..9d8b783565f 100644 --- a/src/doprnt.c +++ b/src/doprnt.c | |||
| @@ -46,15 +46,15 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */ | |||
| 46 | ignored %s and %c conversions. (See below for the detailed documentation of | 46 | ignored %s and %c conversions. (See below for the detailed documentation of |
| 47 | what is supported.) However, this is okay, as this function is supposed to | 47 | what is supported.) However, this is okay, as this function is supposed to |
| 48 | be called from `error' and similar functions, and thus does not need to | 48 | be called from `error' and similar functions, and thus does not need to |
| 49 | support features beyond those in `Fformat', which is used by `error' on the | 49 | support features beyond those in `Fformat_message', which is used |
| 50 | Lisp level. */ | 50 | by `error' on the Lisp level. */ |
| 51 | 51 | ||
| 52 | /* In the FORMAT argument this function supports ` and ' as directives | 52 | /* In the FORMAT argument this function supports ` and ' as directives |
| 53 | that output left and right quotes as per ‘text-quoting style’. It | 53 | that output left and right quotes as per ‘text-quoting style’. It |
| 54 | also supports the following %-sequences: | 54 | also supports the following %-sequences: |
| 55 | 55 | ||
| 56 | %s means print a string argument. | 56 | %s means print a string argument. |
| 57 | %S is silently treated as %s, for loose compatibility with `Fformat'. | 57 | %S is treated as %s, for loose compatibility with `Fformat_message'. |
| 58 | %d means print a `signed int' argument in decimal. | 58 | %d means print a `signed int' argument in decimal. |
| 59 | %o means print an `unsigned int' argument in octal. | 59 | %o means print an `unsigned int' argument in octal. |
| 60 | %x means print an `unsigned int' argument in hex. | 60 | %x means print an `unsigned int' argument in hex. |
diff --git a/src/editfns.c b/src/editfns.c index 11a82c3da73..0e1a6e3415f 100644 --- a/src/editfns.c +++ b/src/editfns.c | |||
| @@ -3716,10 +3716,11 @@ In batch mode, the message is printed to the standard error stream, | |||
| 3716 | followed by a newline. | 3716 | followed by a newline. |
| 3717 | 3717 | ||
| 3718 | The first argument is a format control string, and the rest are data | 3718 | The first argument is a format control string, and the rest are data |
| 3719 | to be formatted under control of the string. See `format' for details. | 3719 | to be formatted under control of the string. See `format-message' for |
| 3720 | details. | ||
| 3720 | 3721 | ||
| 3721 | Note: Use (message "%s" VALUE) to print the value of expressions and | 3722 | Note: (message "%s" VALUE) displays the string VALUE without |
| 3722 | variables to avoid accidentally interpreting `%' as format specifiers. | 3723 | interpreting format characters like `%', `\\=`', and `\\=''. |
| 3723 | 3724 | ||
| 3724 | If the first argument is nil or the empty string, the function clears | 3725 | If the first argument is nil or the empty string, the function clears |
| 3725 | any existing message; this lets the minibuffer contents show. See | 3726 | any existing message; this lets the minibuffer contents show. See |
| @@ -3747,7 +3748,8 @@ DEFUN ("message-box", Fmessage_box, Smessage_box, 1, MANY, 0, | |||
| 3747 | doc: /* Display a message, in a dialog box if possible. | 3748 | doc: /* Display a message, in a dialog box if possible. |
| 3748 | If a dialog box is not available, use the echo area. | 3749 | If a dialog box is not available, use the echo area. |
| 3749 | The first argument is a format control string, and the rest are data | 3750 | The first argument is a format control string, and the rest are data |
| 3750 | to be formatted under control of the string. See `format' for details. | 3751 | to be formatted under control of the string. See `format-message' for |
| 3752 | details. | ||
| 3751 | 3753 | ||
| 3752 | If the first argument is nil or the empty string, clear any existing | 3754 | If the first argument is nil or the empty string, clear any existing |
| 3753 | message; let the minibuffer contents show. | 3755 | message; let the minibuffer contents show. |
| @@ -3778,7 +3780,8 @@ If this command was invoked with the mouse, use a dialog box if | |||
| 3778 | `use-dialog-box' is non-nil. | 3780 | `use-dialog-box' is non-nil. |
| 3779 | Otherwise, use the echo area. | 3781 | Otherwise, use the echo area. |
| 3780 | The first argument is a format control string, and the rest are data | 3782 | The first argument is a format control string, and the rest are data |
| 3781 | to be formatted under control of the string. See `format' for details. | 3783 | to be formatted under control of the string. See `format-message' for |
| 3784 | details. | ||
| 3782 | 3785 | ||
| 3783 | If the first argument is nil or the empty string, clear any existing | 3786 | If the first argument is nil or the empty string, clear any existing |
| 3784 | message; let the minibuffer contents show. | 3787 | message; let the minibuffer contents show. |
diff --git a/test/automated/data/xref/file1.txt b/test/automated/data/xref/file1.txt new file mode 100644 index 00000000000..5d7cc544443 --- /dev/null +++ b/test/automated/data/xref/file1.txt | |||
| @@ -0,0 +1,2 @@ | |||
| 1 | foo foo | ||
| 2 | bar | ||
diff --git a/test/automated/data/xref/file2.txt b/test/automated/data/xref/file2.txt new file mode 100644 index 00000000000..9f075f26004 --- /dev/null +++ b/test/automated/data/xref/file2.txt | |||
| @@ -0,0 +1,2 @@ | |||
| 1 | |||
| 2 | bar | ||
diff --git a/test/automated/xref-tests.el b/test/automated/xref-tests.el new file mode 100644 index 00000000000..079b196aa8b --- /dev/null +++ b/test/automated/xref-tests.el | |||
| @@ -0,0 +1,91 @@ | |||
| 1 | ;;; xref-tests.el --- tests for xref | ||
| 2 | |||
| 3 | ;; Copyright (C) 2016 Free Software Foundation, Inc. | ||
| 4 | |||
| 5 | ;; Author: Dmitry Gutov <dgutov@yandex.ru> | ||
| 6 | |||
| 7 | ;; This file is part of GNU Emacs. | ||
| 8 | |||
| 9 | ;; GNU Emacs is free software: you can redistribute it and/or modify | ||
| 10 | ;; it under the terms of the GNU General Public License as published by | ||
| 11 | ;; the Free Software Foundation, either version 3 of the License, or | ||
| 12 | ;; (at your option) any later version. | ||
| 13 | |||
| 14 | ;; GNU Emacs is distributed in the hope that it will be useful, | ||
| 15 | ;; but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 16 | ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 17 | ;; GNU General Public License for more details. | ||
| 18 | |||
| 19 | ;; You should have received a copy of the GNU General Public License | ||
| 20 | ;; along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. | ||
| 21 | |||
| 22 | ;;; Commentary: | ||
| 23 | |||
| 24 | ;;; Code: | ||
| 25 | |||
| 26 | (require 'xref) | ||
| 27 | (require 'cl-lib) | ||
| 28 | |||
| 29 | (defvar xref-tests-data-dir | ||
| 30 | (expand-file-name "data/xref/" | ||
| 31 | (file-name-directory (or load-file-name (buffer-file-name))))) | ||
| 32 | |||
| 33 | (ert-deftest xref-collect-matches-finds-none-for-some-regexp () | ||
| 34 | (should (null (xref-collect-matches "zzz" "*" xref-tests-data-dir nil)))) | ||
| 35 | |||
| 36 | (ert-deftest xref-collect-matches-finds-some-for-bar () | ||
| 37 | (let* ((matches (xref-collect-matches "bar" "*" xref-tests-data-dir nil)) | ||
| 38 | (locs (cl-sort (mapcar #'xref-item-location matches) | ||
| 39 | #'string< | ||
| 40 | :key #'xref-location-group))) | ||
| 41 | (should (= 2 (length matches))) | ||
| 42 | (should (string-match-p "file1\\.txt\\'" (xref-location-group (nth 0 locs)))) | ||
| 43 | (should (string-match-p "file2\\.txt\\'" (xref-location-group (nth 1 locs)))))) | ||
| 44 | |||
| 45 | (ert-deftest xref-collect-matches-finds-two-matches-on-the-same-line () | ||
| 46 | (let* ((matches (xref-collect-matches "foo" "*" xref-tests-data-dir nil)) | ||
| 47 | (locs (mapcar #'xref-item-location matches))) | ||
| 48 | (should (= 2 (length matches))) | ||
| 49 | (should (string-match-p "file1\\.txt\\'" (xref-location-group (nth 0 locs)))) | ||
| 50 | (should (string-match-p "file1\\.txt\\'" (xref-location-group (nth 1 locs)))) | ||
| 51 | (should (equal 1 (xref-location-line (nth 0 locs)))) | ||
| 52 | (should (equal 1 (xref-location-line (nth 1 locs)))) | ||
| 53 | (should (equal 0 (xref-file-location-column (nth 0 locs)))) | ||
| 54 | (should (equal 4 (xref-file-location-column (nth 1 locs)))))) | ||
| 55 | |||
| 56 | (ert-deftest xref-collect-matches-finds-an-empty-line-regexp-match () | ||
| 57 | (let* ((matches (xref-collect-matches "^$" "*" xref-tests-data-dir nil)) | ||
| 58 | (locs (mapcar #'xref-item-location matches))) | ||
| 59 | (should (= 1 (length matches))) | ||
| 60 | (should (string-match-p "file2\\.txt\\'" (xref-location-group (nth 0 locs)))) | ||
| 61 | (should (equal 1 (xref-location-line (nth 0 locs)))) | ||
| 62 | (should (equal 0 (xref-file-location-column (nth 0 locs)))))) | ||
| 63 | |||
| 64 | (ert-deftest xref--buf-pairs-iterator-groups-markers-by-buffers-1 () | ||
| 65 | (let* ((xrefs (xref-collect-matches "foo" "*" xref-tests-data-dir nil)) | ||
| 66 | (iter (xref--buf-pairs-iterator xrefs)) | ||
| 67 | (cons (funcall iter :next))) | ||
| 68 | (should (null (funcall iter :next))) | ||
| 69 | (should (string-match "file1\\.txt\\'" (buffer-file-name (car cons)))) | ||
| 70 | (should (= 2 (length (cdr cons)))))) | ||
| 71 | |||
| 72 | (ert-deftest xref--buf-pairs-iterator-groups-markers-by-buffers-2 () | ||
| 73 | (let* ((xrefs (xref-collect-matches "bar" "*" xref-tests-data-dir nil)) | ||
| 74 | (iter (xref--buf-pairs-iterator xrefs)) | ||
| 75 | (cons1 (funcall iter :next)) | ||
| 76 | (cons2 (funcall iter :next))) | ||
| 77 | (should (null (funcall iter :next))) | ||
| 78 | (should-not (equal (car cons1) (car cons2))) | ||
| 79 | (should (= 1 (length (cdr cons1)))) | ||
| 80 | (should (= 1 (length (cdr cons2)))))) | ||
| 81 | |||
| 82 | (ert-deftest xref--buf-pairs-iterator-cleans-up-markers () | ||
| 83 | (let* ((xrefs (xref-collect-matches "bar" "*" xref-tests-data-dir nil)) | ||
| 84 | (iter (xref--buf-pairs-iterator xrefs)) | ||
| 85 | (cons1 (funcall iter :next)) | ||
| 86 | (cons2 (funcall iter :next))) | ||
| 87 | (funcall iter :cleanup) | ||
| 88 | (should (null (marker-position (car (nth 0 (cdr cons1)))))) | ||
| 89 | (should (null (marker-position (cdr (nth 0 (cdr cons1)))))) | ||
| 90 | (should (null (marker-position (car (nth 0 (cdr cons2)))))) | ||
| 91 | (should (null (marker-position (cdr (nth 0 (cdr cons2)))))))) | ||