From 3b2949940efbe8c05263fce7ebcc390a9f178c01 Mon Sep 17 00:00:00 2001
From: Benno Schulenberg <bensberg@telfort.nl>
Date: Thu, 22 Apr 2021 19:28:34 +0200
Subject: [PATCH 13/34] editing: prevent the pointer for the top row from
 becoming dangling

When undoing several actions, it is possible for the line at the top
of the screen to be removed, leaving 'edittop' pointing to a structure
that has been freed.  Soon after, 'edittop' is referenced to determine
whether the cursor is offscreen...  Prevent this invalid reference by
stepping 'edittop' one line back in that special case.  This changes
the normal centering behavior of Undo when the cursor goes offscreen,
but... so be it.

When a single node is deleted, it is always possible to step one line
back, because a buffer contains always at least one line (even though
maybe empty), so if the current line could be deleted, there must be
one before it (when at the top of the screen).

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

Bug existed since version 2.3.3, commit 60815461,
since undoing does not always center the cursor.
---
 src/nano.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/src/nano.c b/src/nano.c
index 913329a5..2b6c416f 100644
--- a/src/nano.c
+++ b/src/nano.c
@@ -104,6 +104,9 @@ void splice_node(linestruct *afterthis, linestruct *newnode)
 /* Free the data structures in the given node. */
 void delete_node(linestruct *line)
 {
+	/* If the first line on the screen gets deleted, step one back. */
+	if (line == openfile->edittop)
+		openfile->edittop = line->prev;
 #ifdef ENABLE_WRAPPING
 	/* If the spill-over line for hard-wrapping is deleted... */
 	if (line == openfile->spillage_line)
-- 
2.29.3

