commit 3eab405e7b6bbe81561a066eb4ed341cc7615780
parent 423ed031b4255657936cca30c91380a73c8e005e
Author: Benno Schulenberg <bensberg@telfort.nl>
Date: Tue, 28 May 2019 19:51:56 +0200
help: write the text directly into a new buffer, without using a tempfile
This avoids the substantial overhead of first writing and then reading a
temporary file, and in the bargain removes two possible failure points.
This fulfills https://savannah.gnu.org/bugs/?56371.
Diffstat:
M | src/help.c | | | 64 | +++++++++++++++++++++++++--------------------------------------- |
1 file changed, 25 insertions(+), 39 deletions(-)
diff --git a/src/help.c b/src/help.c
@@ -39,47 +39,47 @@ static char *end_of_intro = NULL;
static size_t location;
/* The offset (in bytes) of the topleft of the shown help text. */
-char *tempfilename = NULL;
- /* Name of the temporary file used for wrapping the help text. */
-
-/* Hard-wrap the help text, write it to the existing temporary file, and
- * read that file into a new buffer. */
+/* Hard-wrap the concatenated help text, and write it into a new buffer. */
void wrap_the_help_text(bool redisplaying)
{
size_t sum = 0;
const char *ptr = start_of_body;
- FILE *tempfile = fopen(tempfilename, "w+b");
- /* If re-opening the temporary file failed, give up. */
- if (tempfile == NULL) {
- statusline(ALERT, _("Error writing temp file: %s"), strerror(errno));
- return;
+ if (redisplaying) {
+ close_buffer();
+ switch_to_prev_buffer();
}
- /* Write the body of the help_text into the temporary file. */
+ make_new_buffer();
+
+ /* Copy the help text into the just-created new buffer. */
while (*ptr != '\0') {
int length = help_line_len(ptr);
+ char *oneline = nmalloc(length + 1);
- fwrite(ptr, sizeof(char), length, tempfile);
- ptr += length;
+ snprintf(oneline, length + 1, "%s", ptr);
+ free(openfile->current->data);
+ openfile->current->data = oneline;
- /* Hard-wrap the lines in the help text. */
+ ptr += length;
if (*ptr != '\n')
- fwrite("\n", sizeof(char), 1, tempfile);
- else while (*ptr == '\n')
- fwrite(ptr++, sizeof(char), 1, tempfile);
+ ptr--;
+
+ /* Create a new line, and then one more for each extra \n. */
+ do {
+ openfile->current->next = make_new_node(openfile->current);
+ openfile->current = openfile->current->next;
+ openfile->current->data = mallocstrcpy(NULL, "");
+ } while (*(++ptr) == '\n');
}
- fclose(tempfile);
+ openfile->filebot = openfile->current;
+ openfile->current = openfile->filetop;
- if (redisplaying) {
- close_buffer();
- switch_to_prev_buffer();
- }
-
- open_buffer(tempfilename, TRUE);
remove_magicline();
-
+#ifdef ENABLE_COLOR
+ color_update();
+#endif
prepare_for_display();
/* Move to the position in the file where we were before. */
@@ -114,20 +114,9 @@ void do_help(void)
/* A storage place for the current flag settings. */
linestruct *line;
int length;
- FILE *fp;
blank_statusbar();
- /* Get a temporary file for the help text. If it fails, give up. */
- tempfilename = safe_tempfile(&fp);
- if (tempfilename == NULL) {
- statusline(ALERT, _("Error writing temp file: %s"), strerror(errno));
- free(saved_answer);
- return;
- }
-
- fclose(fp);
-
/* Save the settings of all flags. */
memcpy(stash, flags, sizeof(flags));
@@ -277,9 +266,6 @@ void do_help(void)
free(answer);
answer = saved_answer;
- remove(tempfilename);
- free(tempfilename);
-
free(help_text);
}