From 31f0456e9ad9f7f2be58cf443a56d905571b6151 Mon Sep 17 00:00:00 2001 From: Benno Schulenberg Date: Tue, 22 Dec 2015 16:51:00 +0000 Subject: [PATCH] Moving two functions to the color.c file, where they belong. And making the checking for an impatient user into a separate routine. git-svn-id: svn://svn.savannah.gnu.org/nano/trunk/nano@5501 35c25a1d-7b9e-4130-9fde-d3aeb78583b8 --- ChangeLog | 5 ++ src/color.c | 144 ++++++++++++++++++++++++++++++++++++++++++++++++++++ src/nano.c | 141 -------------------------------------------------- src/proto.h | 6 +-- 4 files changed, 152 insertions(+), 144 deletions(-) diff --git a/ChangeLog b/ChangeLog index 7fd52410..91832f74 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,8 @@ +2015-12-22 Benno Schulenberg + * src/color.c (precalc_multicolorinfo, alloc_multidata_if_needed): + Move these two functions to the file where they belong. And make + the checking for an impatient user into a separate routine. + 2015-12-20 Benno Schulenberg * src/files.c (display_buffer), src/nano.c (main): Precalculate the multiline-regex cache data for each buffer, not just for the first. diff --git a/src/color.c b/src/color.c index 368ff8a4..2508a843 100644 --- a/src/color.c +++ b/src/color.c @@ -26,6 +26,7 @@ #include #include #include +#include #include #ifdef HAVE_MAGIC_H @@ -450,4 +451,147 @@ void reset_multis(filestruct *fileptr, bool force) } } +/* Allocate (for one line) the cache space for multiline color regexes. */ +void alloc_multidata_if_needed(filestruct *fileptr) +{ + int i; + + if (fileptr->multidata == NULL) { + fileptr->multidata = (short *)nmalloc(openfile->syntax->nmultis * sizeof(short)); + + for (i = 0; i < openfile->syntax->nmultis; i++) + fileptr->multidata[i] = -1; + } +} + +/* Poll the keyboard every second to see if the user starts typing. */ +bool key_was_pressed(void) +{ + static time_t last_time = 0; + + if (time(NULL) != last_time) { + last_time = time(NULL); + return (wgetch(edit) != ERR); + } else + return FALSE; +} + +/* Precalculate the multi-line start and end regex info so we can + * speed up rendering (with any hope at all...). */ +void precalc_multicolorinfo(void) +{ + const colortype *tmpcolor = openfile->colorstrings; + regmatch_t startmatch, endmatch; + filestruct *fileptr, *endptr; + + if (openfile->colorstrings == NULL || ISSET(NO_COLOR_SYNTAX)) + return; + +#ifdef DEBUG + fprintf(stderr, "Entering precalculation of multiline color info\n"); +#endif + /* Let us get keypresses to see if the user is trying to start + * editing. Later we may want to throw up a statusbar message + * before starting this if it takes too long to do this routine. + * For now silently abort if they hit a key. */ + nodelay(edit, TRUE); + + for (; tmpcolor != NULL; tmpcolor = tmpcolor->next) { + /* If this is not a multi-line regex, skip it. */ + if (tmpcolor->end == NULL) + continue; +#ifdef DEBUG + fprintf(stderr, "Starting work on color id %d\n", tmpcolor->id); +#endif + + for (fileptr = openfile->fileage; fileptr != NULL; fileptr = fileptr->next) { + int startx = 0, nostart = 0; + + if (key_was_pressed()) + goto precalc_cleanup; +#ifdef DEBUG + fprintf(stderr, "working on lineno %ld... ", (long)fileptr->lineno); +#endif + alloc_multidata_if_needed(fileptr); + + while ((nostart = regexec(tmpcolor->start, &fileptr->data[startx], + 1, &startmatch, (startx == 0) ? 0 : REG_NOTBOL)) == 0) { + /* Look for an end, and start marking how many lines are + * encompassed, which should speed up rendering later. */ + startx += startmatch.rm_eo; +#ifdef DEBUG + fprintf(stderr, "start found at pos %lu... ", (unsigned long)startx); +#endif + /* Look first on this line for an end. */ + if (regexec(tmpcolor->end, &fileptr->data[startx], 1, + &endmatch, (startx == 0) ? 0 : REG_NOTBOL) == 0) { + startx += endmatch.rm_eo; + fileptr->multidata[tmpcolor->id] = CSTARTENDHERE; +#ifdef DEBUG + fprintf(stderr, "end found on this line\n"); +#endif + continue; + } + + /* Nice, we didn't find the end regex on this line. Let's start looking for it. */ + for (endptr = fileptr->next; endptr != NULL; endptr = endptr->next) { +#ifdef DEBUG + fprintf(stderr, "\nadvancing to line %ld to find end... ", (long)endptr->lineno); +#endif + /* Check for interrupting keyboard input again. */ + if (key_was_pressed()) + goto precalc_cleanup; + + if (regexec(tmpcolor->end, endptr->data, 1, &endmatch, 0) == 0) + break; + } + + if (endptr == NULL) { +#ifdef DEBUG + fprintf(stderr, "no end found, breaking out\n"); +#endif + break; + } +#ifdef DEBUG + fprintf(stderr, "end found\n"); +#endif + /* We found it, we found it, la la la la la. Mark all + * the lines in between and the end properly. */ + fileptr->multidata[tmpcolor->id] = CENDAFTER; +#ifdef DEBUG + fprintf(stderr, "marking line %ld as CENDAFTER\n", (long)fileptr->lineno); +#endif + for (fileptr = fileptr->next; fileptr != endptr; fileptr = fileptr->next) { + alloc_multidata_if_needed(fileptr); + fileptr->multidata[tmpcolor->id] = CWHOLELINE; +#ifdef DEBUG + fprintf(stderr, "marking intermediary line %ld as CWHOLELINE\n", (long)fileptr->lineno); +#endif + } + + alloc_multidata_if_needed(endptr); + fileptr->multidata[tmpcolor->id] = CBEGINBEFORE; +#ifdef DEBUG + fprintf(stderr, "marking line %ld as CBEGINBEFORE\n", (long)fileptr->lineno); +#endif + /* Skip to the end point of the match. */ + startx = endmatch.rm_eo; +#ifdef DEBUG + fprintf(stderr, "jumping to line %ld pos %lu to continue\n", (long)fileptr->lineno, (unsigned long)startx); +#endif + } + + if (nostart && startx == 0) { +#ifdef DEBUG + fprintf(stderr, "no match\n"); +#endif + fileptr->multidata[tmpcolor->id] = CNONE; + continue; + } + } + } +precalc_cleanup: + nodelay(edit, FALSE); +} + #endif /* !DISABLE_COLOR */ diff --git a/src/nano.c b/src/nano.c index c92a89a6..1af88dc9 100644 --- a/src/nano.c +++ b/src/nano.c @@ -31,7 +31,6 @@ #include #include #include -#include #ifdef ENABLE_UTF8 #include #endif @@ -1854,146 +1853,6 @@ int do_mouse(void) } #endif /* !DISABLE_MOUSE */ -#ifndef DISABLE_COLOR -void alloc_multidata_if_needed(filestruct *fileptr) -{ - int i; - - if (fileptr->multidata == NULL) { - fileptr->multidata = (short *)nmalloc(openfile->syntax->nmultis * sizeof(short)); - - for (i = 0; i < openfile->syntax->nmultis; i++) - fileptr->multidata[i] = -1; - } -} - -/* Precalculate the multi-line start and end regex info so we can - * speed up rendering (with any hope at all...). */ -void precalc_multicolorinfo(void) -{ -#ifdef DEBUG - fprintf(stderr, "Entering precalculation of multiline color info\n"); -#endif - if (openfile->colorstrings != NULL && !ISSET(NO_COLOR_SYNTAX)) { - const colortype *tmpcolor = openfile->colorstrings; - regmatch_t startmatch, endmatch; - filestruct *fileptr, *endptr; - time_t last_check = time(NULL), cur_check = 0; - - /* Let us get keypresses to see if the user is trying to start - * editing. Later we may want to throw up a statusbar message - * before starting this if it takes too long to do this routine. - * For now silently abort if they hit a key. */ - nodelay(edit, TRUE); - - for (; tmpcolor != NULL; tmpcolor = tmpcolor->next) { - - /* If it's not a multi-line regex, amscray. */ - if (tmpcolor->end == NULL) - continue; -#ifdef DEBUG - fprintf(stderr, "Starting work on color id %d\n", tmpcolor->id); -#endif - - for (fileptr = openfile->fileage; fileptr != NULL; fileptr = fileptr->next) { - int startx = 0; - int nostart = 0; -#ifdef DEBUG - fprintf(stderr, "working on lineno %ld... ", (long)fileptr->lineno); -#endif - - alloc_multidata_if_needed(fileptr); - - if ((cur_check = time(NULL)) - last_check > 1) { - last_check = cur_check; - if (wgetch(edit) != ERR) - goto precalc_cleanup; - } - - while ((nostart = regexec(tmpcolor->start, &fileptr->data[startx], 1, &startmatch, - (startx == 0) ? 0 : REG_NOTBOL)) == 0) { - /* Look for an end, and start marking how many lines are - * encompassed, which should speed up rendering later. */ - startx += startmatch.rm_eo; -#ifdef DEBUG - fprintf(stderr, "start found at pos %lu... ", (unsigned long)startx); -#endif - - /* Look first on this line for an end. */ - if (regexec(tmpcolor->end, &fileptr->data[startx], 1, &endmatch, - (startx == 0) ? 0 : REG_NOTBOL) == 0) { - startx += endmatch.rm_eo; - fileptr->multidata[tmpcolor->id] = CSTARTENDHERE; -#ifdef DEBUG - fprintf(stderr, "end found on this line\n"); -#endif - continue; - } - - /* Nice, we didn't find the end regex on this line. Let's start looking for it. */ - for (endptr = fileptr->next; endptr != NULL; endptr = endptr->next) { -#ifdef DEBUG - fprintf(stderr, "\nadvancing to line %ld to find end... ", (long)endptr->lineno); -#endif - /* Check for keyboard input, again. */ - if ((cur_check = time(NULL)) - last_check > 1) { - last_check = cur_check; - if (wgetch(edit) != ERR) - goto precalc_cleanup; - } - if (regexec(tmpcolor->end, endptr->data, 1, &endmatch, 0) == 0) - break; - } - - if (endptr == NULL) { -#ifdef DEBUG - fprintf(stderr, "no end found, breaking out\n"); -#endif - break; - } - -#ifdef DEBUG - fprintf(stderr, "end found\n"); -#endif - /* We found it, we found it, la la la la la. Mark all - * the lines in between and the end properly. */ - fileptr->multidata[tmpcolor->id] = CENDAFTER; -#ifdef DEBUG - fprintf(stderr, "marking line %ld as CENDAFTER\n", (long)fileptr->lineno); -#endif - for (fileptr = fileptr->next; fileptr != endptr; fileptr = fileptr->next) { - alloc_multidata_if_needed(fileptr); - fileptr->multidata[tmpcolor->id] = CWHOLELINE; -#ifdef DEBUG - fprintf(stderr, "marking intermediary line %ld as CWHOLELINE\n", (long)fileptr->lineno); -#endif - } - alloc_multidata_if_needed(endptr); - fileptr->multidata[tmpcolor->id] = CBEGINBEFORE; -#ifdef DEBUG - fprintf(stderr, "marking line %ld as CBEGINBEFORE\n", (long)fileptr->lineno); -#endif - /* Skip to the end point of the match. */ - startx = endmatch.rm_eo; -#ifdef DEBUG - fprintf(stderr, "jumping to line %ld pos %lu to continue\n", (long)fileptr->lineno, (unsigned long)startx); -#endif - } - if (nostart && startx == 0) { -#ifdef DEBUG - fprintf(stderr, "no match\n"); -#endif - fileptr->multidata[tmpcolor->id] = CNONE; - continue; - } - } - } - } -precalc_cleanup: - nodelay(edit, FALSE); -} -#endif /* !DISABLE_COLOR */ - /* The user typed output_len multibyte characters. Add them to the edit * buffer, filtering out all ASCII control characters if allow_cntrls is * TRUE. */ diff --git a/src/proto.h b/src/proto.h index c5118e66..d9400b45 100644 --- a/src/proto.h +++ b/src/proto.h @@ -252,6 +252,9 @@ bool is_valid_mbstring(const char *s); void set_colorpairs(void); void color_init(void); void color_update(void); +void reset_multis(filestruct *fileptr, bool force); +void alloc_multidata_if_needed(filestruct *fileptr); +void precalc_multicolorinfo(void); #endif /* All functions in cut.c. */ @@ -506,7 +509,6 @@ int do_input(bool allow_funcs); int do_mouse(void); #endif void do_output(char *output, size_t output_len, bool allow_cntrls); -void precalc_multicolorinfo(void); /* All functions in prompt.c. */ int do_statusbar_input(bool *ran_func, bool *finished, @@ -571,8 +573,6 @@ void parse_include(char *ptr); short color_to_short(const char *colorname, bool *bright); void parse_colors(char *ptr, bool icase); bool parse_color_names(char *combostr, short *fg, short *bg, bool *bright); -void reset_multis(filestruct *fileptr, bool force); -void alloc_multidata_if_needed(filestruct *fileptr); #endif void parse_rcfile(FILE *rcstream #ifndef DISABLE_COLOR