Index: ChangeLog
===================================================================
--- ChangeLog (revision 5227)
+++ ChangeLog (working copy)
@@ -1,3 +1,15 @@
+2015-05-24 Mahyar Abbaspour
+ * src/nano.c (handle_sigwinch, regenerate_screen), src/global.c,
+ src/prompt.c (do_statusbar_input, get_prompt_string, do_yesno_prompt),
+ src/browser.c (do_browser, browser_refresh), src/help.c (do_help),
+ src/winio.c (get_key_buffer, unget_input, get_input, parse_kbinput),
+ src/text.c (do_justify, do_linter), src/nano.h, src/proto.h:
+ Handle a SIGWINCH (which signals a window-size change) not when it
+ happens but only when checking for input. Report the SIGWINCH via
+ a special key value to the calling routine, to allow not only the
+ main editor but also the help viewer and the file browser to adapt
+ their display to the new size. (Patch edited by Benno.)
+
2015-05-20 Devrim Gündüz
* doc/syntax/postgresql.nanorc: New file -- syntax highlighting for
PostgreSQL, first posted as Savannah patch #8601. Trimmed by Benno.
Index: src/global.c
===================================================================
--- src/global.c (revision 5227)
+++ src/global.c (working copy)
@@ -30,12 +30,8 @@
/* Global variables. */
#ifndef NANO_TINY
-sigjmp_buf jump_buf;
- /* Used to return to either main() or the unjustify routine in
- * do_justify() after a SIGWINCH. */
-bool jump_buf_main = FALSE;
- /* Have we set jump_buf so that we return to main() after a
- * SIGWINCH? */
+volatile sig_atomic_t sigwinch_counter = 0;
+ /* Is incremented by the handler whenever a SIGWINCH occurs. */
#endif
bool meta_key;
Index: src/nano.h
===================================================================
--- src/nano.h (revision 5227)
+++ src/nano.h (working copy)
@@ -117,7 +117,7 @@
#include
#endif
#ifndef NANO_TINY
-#include
+#include
#endif
#include
@@ -571,6 +571,9 @@
#define CONTROL_RIGHT 554
#ifndef NANO_TINY
+/* An imaginary key for when we get a SIGWINCH (window resize). */
+#define KEY_WINCH -2
+
/* Extra bits for the undo function. */
#define UNdel_del (1<<0)
#define UNdel_backspace (1<<1)
Index: src/proto.h
===================================================================
--- src/proto.h (revision 5227)
+++ src/proto.h (working copy)
@@ -28,8 +28,7 @@
/* All external variables. See global.c for their descriptions. */
#ifndef NANO_TINY
-extern sigjmp_buf jump_buf;
-extern bool jump_buf_main;
+extern volatile sig_atomic_t sigwinch_counter;
#endif
extern bool meta_key;
@@ -478,6 +477,7 @@
RETSIGTYPE do_continue(int signal);
#ifndef NANO_TINY
RETSIGTYPE handle_sigwinch(int signal);
+void regenerate_screen(void);
void allow_pending_sigwinch(bool allow);
void do_toggle(int flag);
#endif
Index: src/prompt.c
===================================================================
--- src/prompt.c (revision 5227)
+++ src/prompt.c (working copy)
@@ -66,6 +66,11 @@
/* Read in a character. */
input = get_kbinput(bottomwin);
+#ifndef NANO_TINY
+ if (input == KEY_WINCH)
+ return KEY_WINCH;
+#endif
+
#ifndef DISABLE_MOUSE
/* If we got a mouse click and it was on a shortcut, read in the
* shortcut character. */
@@ -794,6 +799,14 @@
kbinput = do_statusbar_input(&ran_func, &finished, refresh_func);
assert(statusbar_x <= strlen(answer));
+#ifndef NANO_TINY
+ if (kbinput == KEY_WINCH) {
+ refresh_func();
+ update_statusbar_line(answer, statusbar_x);
+ continue;
+ }
+#endif
+
func = func_from_key(&kbinput);
if (func == do_cancel || func == do_enter_void)
@@ -1055,6 +1068,13 @@
nostr = _("Nn");
allstr = _("Aa");
+ do {
+ int kbinput;
+ functionptrtype func;
+#ifndef DISABLE_MOUSE
+ int mouse_x, mouse_y;
+#endif
+
if (!ISSET(NO_HELP)) {
char shortstr[3];
/* Temp string for Yes, No, All. */
@@ -1098,15 +1118,14 @@
wnoutrefresh(edit);
wnoutrefresh(bottomwin);
- do {
- int kbinput;
- functionptrtype func;
-#ifndef DISABLE_MOUSE
- int mouse_x, mouse_y;
+ currmenu = MYESNO;
+ kbinput = get_kbinput(bottomwin);
+
+#ifndef NANO_TINY
+ if (kbinput == KEY_WINCH)
+ continue;
#endif
- currmenu = MYESNO;
- kbinput = get_kbinput(bottomwin);
func = func_from_key(&kbinput);
if (func == do_cancel)
Index: src/browser.c
===================================================================
--- src/browser.c (revision 5227)
+++ src/browser.c (working copy)
@@ -41,6 +41,8 @@
/* The number of columns in the longest filename in the list. */
static size_t selected = 0;
/* The currently selected filename in the list; zero-based. */
+static char *path_save = NULL;
+ /* A copy of the current path. */
/* Our main file browser function. path is the tilde-expanded path we
* start browsing from. */
@@ -75,6 +77,9 @@
path = mallocstrassn(path, get_full_path(path));
+ /* Save the current path in order to be used later. */
+ path_save = path;
+
assert(path != NULL && path[strlen(path) - 1] == '/');
/* Get the file list, and set longest and width in the process. */
@@ -118,6 +123,14 @@
kbinput = get_kbinput(edit);
+#ifndef NANO_TINY
+ if (kbinput == KEY_WINCH) {
+ kbinput = ERR;
+ curs_set(0);
+ continue;
+ }
+#endif
+
#ifndef DISABLE_MOUSE
if (kbinput == KEY_MOUSE) {
int mouse_x, mouse_y;
@@ -156,6 +169,8 @@
} else if (func == do_help_void) {
#ifndef DISABLE_HELP
do_help_void();
+ /* Perhaps the window dimensions have changed. */
+ browser_refresh();
curs_set(0);
#else
nano_disabled_msg();
@@ -547,6 +562,11 @@
char *foo;
/* The additional information that we'll display about a file. */
+ /* Perhaps window dimensions have changed; reinitialize the browser. */
+ browser_init(path_save, opendir(path_save));
+ qsort(filelist, filelist_len, sizeof(char *), diralphasort);
+
+ titlebar(path_save);
blank_edit();
wmove(edit, 0, 0);
Index: src/text.c
===================================================================
--- src/text.c (revision 5227)
+++ src/text.c (working copy)
@@ -1922,10 +1922,6 @@
if (full_justify)
openfile->current = openfile->fileage;
-#ifndef NANO_TINY
- allow_pending_sigwinch(FALSE);
-#endif
-
while (TRUE) {
size_t i;
/* Generic loop variable. */
@@ -2207,17 +2203,6 @@
edit_refresh();
-#ifndef NANO_TINY
- /* We're going to set jump_buf so that we return here after a
- * SIGWINCH instead of to main(). Indicate this. */
- jump_buf_main = FALSE;
-
- /* Return here after a SIGWINCH. */
- sigsetjmp(jump_buf, 1);
-#endif
-
- statusbar(_("Can now UnJustify!"));
-
/* If constant cursor position display is on, make sure the current
* cursor position will be properly displayed on the statusbar. */
if (ISSET(CONST_UPDATE))
@@ -2229,7 +2214,15 @@
/* Now get a keystroke and see if it's unjustify. If not, put back
* the keystroke and return. */
- kbinput = do_input(FALSE);
+#ifndef NANO_TINY
+ do {
+#endif
+ statusbar(_("Can now UnJustify!"));
+ kbinput = do_input(FALSE);
+#ifndef NANO_TINY
+ } while (kbinput == KEY_WINCH);
+#endif
+
func = func_from_key(&kbinput);
if (func == do_uncut_text) {
@@ -2295,10 +2288,6 @@
/* Display the shortcut list with UnCut. */
uncutfunc->desc = uncut_tag;
display_main_list();
-
-#ifndef NANO_TINY
- allow_pending_sigwinch(TRUE);
-#endif
}
/* Justify the current paragraph. */
@@ -3183,6 +3172,12 @@
}
kbinput = get_kbinput(bottomwin);
+
+#ifndef NANO_TINY
+ if (kbinput == KEY_WINCH)
+ continue;
+#endif
+
func = func_from_key(&kbinput);
tmplint = curlint;
Index: src/winio.c
===================================================================
--- src/winio.c (revision 5227)
+++ src/winio.c (working copy)
@@ -41,6 +41,8 @@
/* Should we temporarily disable constant cursor position
* display? */
+static sig_atomic_t sigwinch_counter_save = 0;
+
/* Control character compatibility:
*
* - NANO_BACKSPACE_KEY is Ctrl-H, which is Backspace under ASCII, ANSI,
@@ -112,10 +114,6 @@
if (key_buffer != NULL)
return;
-#ifndef NANO_TINY
- allow_pending_sigwinch(TRUE);
-#endif
-
/* Just before reading in the first character, display any pending
* screen updates. */
doupdate();
@@ -125,8 +123,17 @@
if (nodelay_mode) {
if ((input = wgetch(win)) == ERR)
return;
- } else
+ } else {
while ((input = wgetch(win)) == ERR) {
+#ifndef NANO_TINY
+ /* Did we get SIGWINCH since we were last here? */
+ if (sigwinch_counter != sigwinch_counter_save) {
+ sigwinch_counter_save = sigwinch_counter;
+ regenerate_screen();
+ input = KEY_WINCH;
+ break;
+ } else
+#endif
errcount++;
/* If we've failed to get a character MAX_BUF_SIZE times in a
@@ -137,25 +144,25 @@
if (errcount == MAX_BUF_SIZE)
handle_hupterm(0);
}
+ }
-#ifndef NANO_TINY
- allow_pending_sigwinch(FALSE);
-#endif
-
/* Increment the length of the keystroke buffer, and save the value
* of the keystroke at the end of it. */
key_buffer_len++;
key_buffer = (int *)nmalloc(sizeof(int));
key_buffer[0] = input;
+#ifndef NANO_TINY
+ /* If we got SIGWINCH, get out immediately since the win argument is
+ * no longer valid. */
+ if (input == KEY_WINCH)
+ return;
+#endif
+
/* Read in the remaining characters using non-blocking input. */
nodelay(win, TRUE);
while (TRUE) {
-#ifndef NANO_TINY
- allow_pending_sigwinch(TRUE);
-#endif
-
input = wgetch(win);
/* If there aren't any more characters, stop reading. */
@@ -168,10 +175,6 @@
key_buffer = (int *)nrealloc(key_buffer, key_buffer_len *
sizeof(int));
key_buffer[key_buffer_len - 1] = input;
-
-#ifndef NANO_TINY
- allow_pending_sigwinch(FALSE);
-#endif
}
/* Switch back to waiting mode for input. */
@@ -191,11 +194,6 @@
/* Add the keystrokes in input to the keystroke buffer. */
void unget_input(int *input, size_t input_len)
{
-#ifndef NANO_TINY
- allow_pending_sigwinch(TRUE);
- allow_pending_sigwinch(FALSE);
-#endif
-
/* If input is empty, get out. */
if (input_len == 0)
return;
@@ -249,11 +247,6 @@
{
int *input;
-#ifndef NANO_TINY
- allow_pending_sigwinch(TRUE);
- allow_pending_sigwinch(FALSE);
-#endif
-
if (key_buffer_len == 0) {
if (win != NULL) {
get_key_buffer(win);
@@ -643,6 +636,11 @@
retval = sc_seq_or(do_next_word_void, 0);
#endif
break;
+#ifndef NANO_TINY
+ case KEY_WINCH:
+ retval = KEY_WINCH;
+ break;
+#endif
}
/* If our result is an extended keypad value (i.e. a value
Index: src/help.c
===================================================================
--- src/help.c (revision 5227)
+++ src/help.c (working copy)
@@ -72,10 +72,13 @@
bottombars(MHELP);
wnoutrefresh(bottomwin);
+ while (TRUE) {
+ size_t i;
+
/* Get the last line of the help text. */
ptr = help_text;
- for (; *ptr != '\0'; last_line++) {
+ for (last_line = 0; *ptr != '\0'; last_line++) {
ptr += help_line_len(ptr);
if (*ptr == '\n')
ptr++;
@@ -83,9 +86,6 @@
if (last_line > 0)
last_line--;
- while (TRUE) {
- size_t i;
-
/* Display the help text if we don't have a key, or if the help
* text has moved. */
if (kbinput == ERR || line != old_line) {
@@ -117,6 +117,14 @@
kbinput = get_kbinput(edit);
+#ifndef NANO_TINY
+ if (kbinput == KEY_WINCH) {
+ kbinput = ERR;
+ curs_set(0);
+ continue;
+ }
+#endif
+
#ifndef DISABLE_MOUSE
if (kbinput == KEY_MOUSE) {
int mouse_x, mouse_y;
Index: src/nano.c
===================================================================
--- src/nano.c (revision 5227)
+++ src/nano.c (working copy)
@@ -25,7 +25,6 @@
#include
#include
-#include
#include
#include
#include
@@ -1245,7 +1244,6 @@
/* Trap SIGWINCH because we want to handle window resizes. */
act.sa_handler = handle_sigwinch;
sigaction(SIGWINCH, &act, NULL);
- allow_pending_sigwinch(FALSE);
#endif
/* Trap normal suspend (^Z) so we can handle it ourselves. */
@@ -1344,6 +1342,13 @@
/* Handler for SIGWINCH (window size change). */
RETSIGTYPE handle_sigwinch(int signal)
{
+ /* Let the input routine know that a SIGWINCH has occurred. */
+ sigwinch_counter++;
+}
+
+/* Reinitialize and redraw the screen completely. */
+void regenerate_screen(void)
+{
const char *tty = ttyname(0);
int fd, result = 0;
struct winsize win;
@@ -1367,10 +1372,6 @@
LINES = win.ws_row;
#endif
- /* If we've partitioned the filestruct, unpartition it now. */
- if (filepart != NULL)
- unpartition_filestruct(&filepart);
-
#ifdef USE_SLANG
/* Slang curses emulation brain damage, part 1: If we just do what
* curses does here, it'll only work properly if the resize made the
@@ -1397,14 +1398,7 @@
window_init();
/* Redraw the contents of the windows that need it. */
- blank_statusbar();
- wnoutrefresh(bottomwin);
- currmenu = MMAIN;
total_refresh();
-
- /* Jump back to either main() or the unjustify routine in
- * do_justify(). */
- siglongjmp(jump_buf, 1);
}
/* If allow is TRUE, block any SIGWINCH signals that we get, so that we
@@ -1599,6 +1593,11 @@
/* Read in a character. */
input = get_kbinput(edit);
+#ifndef NANO_TINY
+ if (input == KEY_WINCH)
+ return KEY_WINCH;
+#endif
+
#ifndef DISABLE_MOUSE
if (func_key && input == KEY_MOUSE) {
/* We received a mouse click. */
@@ -2798,17 +2797,6 @@
reset_cursor();
wnoutrefresh(edit);
-#ifndef NANO_TINY
- if (!jump_buf_main) {
- /* If we haven't already, we're going to set jump_buf so
- * that we return here after a SIGWINCH. Indicate this. */
- jump_buf_main = TRUE;
-
- /* Return here after a SIGWINCH. */
- sigsetjmp(jump_buf, 1);
- }
-#endif
-
/* Just in case we were at the statusbar prompt, make sure the
* statusbar cursor position is reset. */
do_prompt_abort();