nano

nano with my custom patches
git clone git://bsandro.tech/nano
Log | Files | Refs | README | LICENSE

commit d21a9c8fc3fc38b57b6f5af08fcc37d081e8995a
parent edbc1e5950efd0049570bd915d882690de396a1c
Author: Benno Schulenberg <bensberg@justemail.net>
Date:   Fri, 23 Dec 2016 22:12:48 +0100

text: discard the undo stack after formatting and after spell checking

After a call to the Formatter or the Alternate spell checker, the data
on the undo stack could refer to line positions that don't exist any
more -- the chance is small, but it is there.  So... throw the whole
undo stack away, to prevent undoing things wrongly or even crashing.

(Changes made with the internal spell checker can be undone and redone
without a problem -- nano keeps full track of those.  But the changes
made with a formatter or an external spell checker happen in another
process, so nano has no record of them.)

This fixes https://savannah.gnu.org/bugs/?49920.

Diffstat:
Msrc/text.c | 16++++++++++++----
1 file changed, 12 insertions(+), 4 deletions(-)

diff --git a/src/text.c b/src/text.c @@ -424,7 +424,6 @@ void do_indent(ssize_t cols) /* Throw away the undo stack, to prevent making mistakes when * the user tries to undo something in the reindented text. */ discard_until(NULL, openfile); - openfile->current_undo = NULL; /* Mark the file as modified. */ set_modified(); @@ -1155,6 +1154,9 @@ void discard_until(const undo *thisitem, openfilestruct *thefile) dropit = thefile->undotop; } + /* Adjust the pointer to the top of the undo stack. */ + thefile->current_undo = (undo *)thisitem; + /* Prevent a chain of editing actions from continuing. */ thefile->last_action = OTHER; } @@ -2564,7 +2566,6 @@ void do_justify(bool full_justify) /* Throw away the entire undo stack, to prevent a crash when * the user tries to undo something in the justified text. */ discard_until(NULL, openfile); - openfile->current_undo = NULL; #endif /* Blow away the unjustified text. */ free_filestruct(jusbuffer); @@ -3082,9 +3083,12 @@ const char *do_alt_speller(char *tempfile_name) /* Stat the temporary file again, and mark the buffer as modified only * if this file was changed since it was written. */ stat(tempfile_name, &spellfileinfo); - if (spellfileinfo.st_mtime != timestamp) + if (spellfileinfo.st_mtime != timestamp) { set_modified(); - + /* Flush the undo stack, to avoid making a mess when the user + * tries to undo things in spell-corrected lines. */ + discard_until(NULL, openfile); + } #ifndef NANO_TINY /* Unblock SIGWINCHes again. */ allow_sigwinch(TRUE); @@ -3557,6 +3561,10 @@ void do_formatter(void) set_modified(); + /* Flush the undo stack, to avoid a mess or crash when + * the user tries to undo things in reformatted lines. */ + discard_until(NULL, openfile); + finalstatus = _("Finished formatting"); }