diff options
| author | Eli Zaretskii | 2018-03-31 10:53:56 +0300 |
|---|---|---|
| committer | Eli Zaretskii | 2018-03-31 10:53:56 +0300 |
| commit | 8f746914214f19fe7eaad15e03923aca8667b87f (patch) | |
| tree | 113c1fef7552e45ff1f116e18d48275bf646894d | |
| parent | 6a2b940cb17f22008e0868b1d0caee409a31c719 (diff) | |
| parent | 20fa40ddd3e49b73cf2127a147d3b4ee03a3b5ba (diff) | |
| download | emacs-8f746914214f19fe7eaad15e03923aca8667b87f.tar.gz emacs-8f746914214f19fe7eaad15e03923aca8667b87f.zip | |
Merge branch 'master' of git.savannah.gnu.org:/srv/git/emacs
| -rw-r--r-- | admin/make-tarball.txt | 34 | ||||
| -rwxr-xr-x | make-dist | 8 | ||||
| -rw-r--r-- | src/alloc.c | 9 | ||||
| -rw-r--r-- | src/editfns.c | 7 | ||||
| -rw-r--r-- | src/fileio.c | 2 | ||||
| -rw-r--r-- | src/insdel.c | 4 | ||||
| -rw-r--r-- | src/lisp.h | 4 | ||||
| -rw-r--r-- | src/marker.c | 13 | ||||
| -rw-r--r-- | test/src/editfns-tests.el | 51 |
9 files changed, 100 insertions, 32 deletions
diff --git a/admin/make-tarball.txt b/admin/make-tarball.txt index ac6d15d6cee..19edeb79e62 100644 --- a/admin/make-tarball.txt +++ b/admin/make-tarball.txt | |||
| @@ -123,7 +123,7 @@ General steps (for each step, check for possible errors): | |||
| 123 | 123 | ||
| 124 | 9. Decide what compression schemes to offer. | 124 | 9. Decide what compression schemes to offer. |
| 125 | For a release, at least gz and xz: | 125 | For a release, at least gz and xz: |
| 126 | gzip --best -c emacs-NEW.tar > emacs-NEW.tar.gz | 126 | gzip --best --no-name -c emacs-NEW.tar > emacs-NEW.tar.gz |
| 127 | xz -c emacs-NEW.tar > emacs-NEW.tar.xz | 127 | xz -c emacs-NEW.tar > emacs-NEW.tar.xz |
| 128 | For pretests, just xz is probably fine (saves bandwidth). | 128 | For pretests, just xz is probably fine (saves bandwidth). |
| 129 | 129 | ||
| @@ -197,7 +197,6 @@ The pages to update are: | |||
| 197 | 197 | ||
| 198 | emacs.html (for a new major release, a more thorough update is needed) | 198 | emacs.html (for a new major release, a more thorough update is needed) |
| 199 | history.html | 199 | history.html |
| 200 | add the new NEWS file as news/NEWS.xx.y | ||
| 201 | 200 | ||
| 202 | For every new release, a banner is displayed on top of the emacs.html | 201 | For every new release, a banner is displayed on top of the emacs.html |
| 203 | page. Uncomment and the release banner in emacs.html. Keep it on the | 202 | page. Uncomment and the release banner in emacs.html. Keep it on the |
| @@ -210,15 +209,32 @@ manual/html_node directory, delete any old manual pages that are no | |||
| 210 | longer present. | 209 | longer present. |
| 211 | 210 | ||
| 212 | Tar up the generated html_node/emacs/ and elisp/ directories and update | 211 | Tar up the generated html_node/emacs/ and elisp/ directories and update |
| 213 | the files manual/elisp.html_node.tar.gz and emacs.html_node.tar.gz. | 212 | the files manual/elisp.html_node.tar.gz and emacs.html_node.tar.gz. |
| 213 | Use GNU Tar as follows so that the tarballs are reproducible: | ||
| 214 | 214 | ||
| 215 | Use M-x make-manuals-dist from admin/admin.el to update the | 215 | cd manual |
| 216 | manual/texi/ tarfiles. | 216 | tar='tar --numeric-owner --owner=0 --group=0 --mode=go+u,go-w --sort=name' |
| 217 | 217 | gzip='gzip --best --no-name' | |
| 218 | Add compressed copies of the main info pages from the tarfile to manual/info/. | 218 | $tar -cf - html_node/emacs | $gzip >emacs.html_node.tar.gz |
| 219 | $tar -cf - html_node/elisp | $gzip >elisp.html_node.tar.gz | ||
| 219 | 220 | ||
| 220 | Update the refcards/pdf/ and ps/ directories, and also | 221 | Use M-x make-manuals-dist from admin/admin.el to update the |
| 221 | refcards/emacs-refcards.tar.gz (use make -C etc/refcards pdf ps dist). | 222 | manual/*.tar files. |
| 223 | |||
| 224 | Add compressed copies of the main info pages from the tarfile to manual/info/ | ||
| 225 | as follows: | ||
| 226 | |||
| 227 | cd manual | ||
| 228 | mkdir info | ||
| 229 | gzip --best --no-name <../info/eintr.info >info/eintr.info.gz | ||
| 230 | gzip --best --no-name <../info/elisp.info >info/elisp.info.gz | ||
| 231 | gzip --best --no-name <../info/emacs.info >info/emacs.info.gz | ||
| 232 | |||
| 233 | FIXME: The above instructions are not quite complete, as they do not | ||
| 234 | specify how to copy the generated files in the 'manual' directory to | ||
| 235 | the corresponding web files. Also, they are missing some files, e.g., | ||
| 236 | they generate manual/html_mono/ada-mode.html but do not generate the | ||
| 237 | top-level ada-mode.html file for the one-node-per-page version. | ||
| 222 | 238 | ||
| 223 | Browsing <https://web.cvs.savannah.gnu.org/viewvc/?root=emacs> is one | 239 | Browsing <https://web.cvs.savannah.gnu.org/viewvc/?root=emacs> is one |
| 224 | way to check for any files that still need updating. | 240 | way to check for any files that still need updating. |
| @@ -639,14 +639,14 @@ if [ "${make_tar}" = yes ]; then | |||
| 639 | case "${default_gzip}" in | 639 | case "${default_gzip}" in |
| 640 | bzip2) gzip_extension=.bz2 ;; | 640 | bzip2) gzip_extension=.bz2 ;; |
| 641 | xz) gzip_extension=.xz ;; | 641 | xz) gzip_extension=.xz ;; |
| 642 | gzip) gzip_extension=.gz ; default_gzip="gzip --best";; | 642 | gzip) gzip_extension=.gz ; default_gzip="gzip --best --no-name";; |
| 643 | *) gzip_extension= ;; | 643 | *) gzip_extension= ;; |
| 644 | esac | 644 | esac |
| 645 | echo "Creating tar file" | 645 | echo "Creating tar file" |
| 646 | taropt= | 646 | taropt='--numeric-owner --owner=0 --group=0 --mode=go+u,go-w --sort=name' |
| 647 | [ "$verbose" = "yes" ] && taropt=v | 647 | [ "$verbose" = "yes" ] && taropt="$taropt --verbose" |
| 648 | 648 | ||
| 649 | (cd ${tempparent} ; tar c${taropt}f - ${emacsname} ) \ | 649 | (cd ${tempparent} ; tar $taropt -cf - ${emacsname} ) \ |
| 650 | | ${default_gzip} \ | 650 | | ${default_gzip} \ |
| 651 | > ${emacsname}.tar${gzip_extension} | 651 | > ${emacsname}.tar${gzip_extension} |
| 652 | fi | 652 | fi |
diff --git a/src/alloc.c b/src/alloc.c index 369592d70ee..9fdcc7306a8 100644 --- a/src/alloc.c +++ b/src/alloc.c | |||
| @@ -3878,15 +3878,6 @@ build_marker (struct buffer *buf, ptrdiff_t charpos, ptrdiff_t bytepos) | |||
| 3878 | return obj; | 3878 | return obj; |
| 3879 | } | 3879 | } |
| 3880 | 3880 | ||
| 3881 | /* Put MARKER back on the free list after using it temporarily. */ | ||
| 3882 | |||
| 3883 | void | ||
| 3884 | free_marker (Lisp_Object marker) | ||
| 3885 | { | ||
| 3886 | unchain_marker (XMARKER (marker)); | ||
| 3887 | free_misc (marker); | ||
| 3888 | } | ||
| 3889 | |||
| 3890 | 3881 | ||
| 3891 | /* Return a newly created vector or string with specified arguments as | 3882 | /* Return a newly created vector or string with specified arguments as |
| 3892 | elements. If all the arguments are characters that can fit | 3883 | elements. If all the arguments are characters that can fit |
diff --git a/src/editfns.c b/src/editfns.c index 727f2d0080c..608304c09ad 100644 --- a/src/editfns.c +++ b/src/editfns.c | |||
| @@ -3899,10 +3899,9 @@ save_restriction_restore (Lisp_Object data) | |||
| 3899 | 3899 | ||
| 3900 | buf->clip_changed = 1; /* Remember that the narrowing changed. */ | 3900 | buf->clip_changed = 1; /* Remember that the narrowing changed. */ |
| 3901 | } | 3901 | } |
| 3902 | /* This isn’t needed anymore, so don’t wait for GC. | 3902 | /* Detach the markers, and free the cons instead of waiting for GC. */ |
| 3903 | Do not call free_marker on XCAR (data) or XCDR (data), | 3903 | detach_marker (XCAR (data)); |
| 3904 | though, since record_marker_adjustments may have put | 3904 | detach_marker (XCDR (data)); |
| 3905 | them on the buffer’s undo list (Bug#30931). */ | ||
| 3906 | free_cons (XCONS (data)); | 3905 | free_cons (XCONS (data)); |
| 3907 | } | 3906 | } |
| 3908 | else | 3907 | else |
diff --git a/src/fileio.c b/src/fileio.c index 52ca8b6297e..2f8358f01b5 100644 --- a/src/fileio.c +++ b/src/fileio.c | |||
| @@ -224,6 +224,7 @@ report_file_error (char const *string, Lisp_Object name) | |||
| 224 | report_file_errno (string, name, errno); | 224 | report_file_errno (string, name, errno); |
| 225 | } | 225 | } |
| 226 | 226 | ||
| 227 | #ifdef USE_FILE_NOTIFY | ||
| 227 | /* Like report_file_error, but reports a file-notify-error instead. */ | 228 | /* Like report_file_error, but reports a file-notify-error instead. */ |
| 228 | 229 | ||
| 229 | void | 230 | void |
| @@ -238,6 +239,7 @@ report_file_notify_error (const char *string, Lisp_Object name) | |||
| 238 | 239 | ||
| 239 | xsignal (Qfile_notify_error, Fcons (build_string (string), errdata)); | 240 | xsignal (Qfile_notify_error, Fcons (build_string (string), errdata)); |
| 240 | } | 241 | } |
| 242 | #endif | ||
| 241 | 243 | ||
| 242 | void | 244 | void |
| 243 | close_file_unwind (int fd) | 245 | close_file_unwind (int fd) |
diff --git a/src/insdel.c b/src/insdel.c index 02e3f41bc9f..173c2438347 100644 --- a/src/insdel.c +++ b/src/insdel.c | |||
| @@ -2149,9 +2149,9 @@ signal_before_change (ptrdiff_t start_int, ptrdiff_t end_int, | |||
| 2149 | } | 2149 | } |
| 2150 | 2150 | ||
| 2151 | if (! NILP (start_marker)) | 2151 | if (! NILP (start_marker)) |
| 2152 | free_marker (start_marker); | 2152 | detach_marker (start_marker); |
| 2153 | if (! NILP (end_marker)) | 2153 | if (! NILP (end_marker)) |
| 2154 | free_marker (end_marker); | 2154 | detach_marker (end_marker); |
| 2155 | RESTORE_VALUE; | 2155 | RESTORE_VALUE; |
| 2156 | 2156 | ||
| 2157 | unbind_to (count, Qnil); | 2157 | unbind_to (count, Qnil); |
diff --git a/src/lisp.h b/src/lisp.h index b931d23bf38..c931d9c8f05 100644 --- a/src/lisp.h +++ b/src/lisp.h | |||
| @@ -3812,7 +3812,6 @@ extern Lisp_Object make_save_funcptr_ptr_obj (void (*) (void), void *, | |||
| 3812 | extern Lisp_Object make_save_memory (Lisp_Object *, ptrdiff_t); | 3812 | extern Lisp_Object make_save_memory (Lisp_Object *, ptrdiff_t); |
| 3813 | extern void free_save_value (Lisp_Object); | 3813 | extern void free_save_value (Lisp_Object); |
| 3814 | extern Lisp_Object build_overlay (Lisp_Object, Lisp_Object, Lisp_Object); | 3814 | extern Lisp_Object build_overlay (Lisp_Object, Lisp_Object, Lisp_Object); |
| 3815 | extern void free_marker (Lisp_Object); | ||
| 3816 | extern void free_cons (struct Lisp_Cons *); | 3815 | extern void free_cons (struct Lisp_Cons *); |
| 3817 | extern void init_alloc_once (void); | 3816 | extern void init_alloc_once (void); |
| 3818 | extern void init_alloc (void); | 3817 | extern void init_alloc (void); |
| @@ -4105,7 +4104,8 @@ extern ptrdiff_t marker_byte_position (Lisp_Object); | |||
| 4105 | extern void clear_charpos_cache (struct buffer *); | 4104 | extern void clear_charpos_cache (struct buffer *); |
| 4106 | extern ptrdiff_t buf_charpos_to_bytepos (struct buffer *, ptrdiff_t); | 4105 | extern ptrdiff_t buf_charpos_to_bytepos (struct buffer *, ptrdiff_t); |
| 4107 | extern ptrdiff_t buf_bytepos_to_charpos (struct buffer *, ptrdiff_t); | 4106 | extern ptrdiff_t buf_bytepos_to_charpos (struct buffer *, ptrdiff_t); |
| 4108 | extern void unchain_marker (struct Lisp_Marker *marker); | 4107 | extern void detach_marker (Lisp_Object); |
| 4108 | extern void unchain_marker (struct Lisp_Marker *); | ||
| 4109 | extern Lisp_Object set_marker_restricted (Lisp_Object, Lisp_Object, Lisp_Object); | 4109 | extern Lisp_Object set_marker_restricted (Lisp_Object, Lisp_Object, Lisp_Object); |
| 4110 | extern Lisp_Object set_marker_both (Lisp_Object, Lisp_Object, ptrdiff_t, ptrdiff_t); | 4110 | extern Lisp_Object set_marker_both (Lisp_Object, Lisp_Object, ptrdiff_t, ptrdiff_t); |
| 4111 | extern Lisp_Object set_marker_restricted_both (Lisp_Object, Lisp_Object, | 4111 | extern Lisp_Object set_marker_restricted_both (Lisp_Object, Lisp_Object, |
diff --git a/src/marker.c b/src/marker.c index 2a45ae636ed..2d5b05cc2b8 100644 --- a/src/marker.c +++ b/src/marker.c | |||
| @@ -560,7 +560,7 @@ POSITION is nil, makes marker point nowhere so it no longer slows down | |||
| 560 | editing in any buffer. Returns MARKER. */) | 560 | editing in any buffer. Returns MARKER. */) |
| 561 | (Lisp_Object marker, Lisp_Object position, Lisp_Object buffer) | 561 | (Lisp_Object marker, Lisp_Object position, Lisp_Object buffer) |
| 562 | { | 562 | { |
| 563 | return set_marker_internal (marker, position, buffer, 0); | 563 | return set_marker_internal (marker, position, buffer, false); |
| 564 | } | 564 | } |
| 565 | 565 | ||
| 566 | /* Like the above, but won't let the position be outside the visible part. */ | 566 | /* Like the above, but won't let the position be outside the visible part. */ |
| @@ -569,7 +569,7 @@ Lisp_Object | |||
| 569 | set_marker_restricted (Lisp_Object marker, Lisp_Object position, | 569 | set_marker_restricted (Lisp_Object marker, Lisp_Object position, |
| 570 | Lisp_Object buffer) | 570 | Lisp_Object buffer) |
| 571 | { | 571 | { |
| 572 | return set_marker_internal (marker, position, buffer, 1); | 572 | return set_marker_internal (marker, position, buffer, true); |
| 573 | } | 573 | } |
| 574 | 574 | ||
| 575 | /* Set the position of MARKER, specifying both the | 575 | /* Set the position of MARKER, specifying both the |
| @@ -616,6 +616,15 @@ set_marker_restricted_both (Lisp_Object marker, Lisp_Object buffer, | |||
| 616 | return marker; | 616 | return marker; |
| 617 | } | 617 | } |
| 618 | 618 | ||
| 619 | /* Detach a marker so that it no longer points anywhere and no longer | ||
| 620 | slows down editing. Do not free the marker, though, as a change | ||
| 621 | function could have inserted it into an undo list (Bug#30931). */ | ||
| 622 | void | ||
| 623 | detach_marker (Lisp_Object marker) | ||
| 624 | { | ||
| 625 | Fset_marker (marker, Qnil, Qnil); | ||
| 626 | } | ||
| 627 | |||
| 619 | /* Remove MARKER from the chain of whatever buffer it is in, | 628 | /* Remove MARKER from the chain of whatever buffer it is in, |
| 620 | leaving it points to nowhere. This is called during garbage | 629 | leaving it points to nowhere. This is called during garbage |
| 621 | collection, so we must be careful to ignore and preserve | 630 | collection, so we must be careful to ignore and preserve |
diff --git a/test/src/editfns-tests.el b/test/src/editfns-tests.el index 442ad089375..2e20c9dd126 100644 --- a/test/src/editfns-tests.el +++ b/test/src/editfns-tests.el | |||
| @@ -288,4 +288,55 @@ | |||
| 288 | (buffer-string) | 288 | (buffer-string) |
| 289 | "foo bar baz qux")))))) | 289 | "foo bar baz qux")))))) |
| 290 | 290 | ||
| 291 | (ert-deftest delete-region-undo-markers-1 () | ||
| 292 | "Make sure we don't end up with freed markers reachable from Lisp." | ||
| 293 | ;; https://debbugs.gnu.org/cgi/bugreport.cgi?bug=30931#40 | ||
| 294 | (with-temp-buffer | ||
| 295 | (insert "1234567890") | ||
| 296 | (setq buffer-undo-list nil) | ||
| 297 | (narrow-to-region 2 5) | ||
| 298 | ;; `save-restriction' in a narrowed buffer creates two markers | ||
| 299 | ;; representing the current restriction. | ||
| 300 | (save-restriction | ||
| 301 | (widen) | ||
| 302 | ;; Any markers *within* the deleted region are put onto the undo | ||
| 303 | ;; list. | ||
| 304 | (delete-region 1 6)) | ||
| 305 | ;; (princ (format "%S" buffer-undo-list) #'external-debugging-output) | ||
| 306 | ;; `buffer-undo-list' is now | ||
| 307 | ;; (("12345" . 1) (#<temp-marker1> . -1) (#<temp-marker2> . 1)) | ||
| 308 | ;; | ||
| 309 | ;; If temp-marker1 or temp-marker2 are freed prematurely, calling | ||
| 310 | ;; `type-of' on them will cause Emacs to abort. Calling | ||
| 311 | ;; `garbage-collect' will also abort if it finds any reachable | ||
| 312 | ;; freed objects. | ||
| 313 | (should (eq (type-of (car (nth 1 buffer-undo-list))) 'marker)) | ||
| 314 | (should (eq (type-of (car (nth 2 buffer-undo-list))) 'marker)) | ||
| 315 | (garbage-collect))) | ||
| 316 | |||
| 317 | (ert-deftest delete-region-undo-markers-2 () | ||
| 318 | "Make sure we don't end up with freed markers reachable from Lisp." | ||
| 319 | ;; https://debbugs.gnu.org/cgi/bugreport.cgi?bug=30931#55 | ||
| 320 | (with-temp-buffer | ||
| 321 | (insert "1234567890") | ||
| 322 | (setq buffer-undo-list nil) | ||
| 323 | ;; signal_before_change creates markers delimiting a change | ||
| 324 | ;; region. | ||
| 325 | (let ((before-change-functions | ||
| 326 | (list (lambda (beg end) | ||
| 327 | (delete-region (1- beg) (1+ end)))))) | ||
| 328 | (delete-region 2 5)) | ||
| 329 | ;; (princ (format "%S" buffer-undo-list) #'external-debugging-output) | ||
| 330 | ;; `buffer-undo-list' is now | ||
| 331 | ;; (("678" . 1) ("12345" . 1) (#<marker in no buffer> . -1) | ||
| 332 | ;; (#<temp-marker1> . -1) (#<temp-marker2> . -4)) | ||
| 333 | ;; | ||
| 334 | ;; If temp-marker1 or temp-marker2 are freed prematurely, calling | ||
| 335 | ;; `type-of' on them will cause Emacs to abort. Calling | ||
| 336 | ;; `garbage-collect' will also abort if it finds any reachable | ||
| 337 | ;; freed objects. | ||
| 338 | (should (eq (type-of (car (nth 3 buffer-undo-list))) 'marker)) | ||
| 339 | (should (eq (type-of (car (nth 4 buffer-undo-list))) 'marker)) | ||
| 340 | (garbage-collect))) | ||
| 341 | |||
| 291 | ;;; editfns-tests.el ends here | 342 | ;;; editfns-tests.el ends here |