Removed unnecessary variable from readlines, fixed bug where

EOF terminated line was skipped
master
Tibor Bizjak 2023-07-19 11:17:23 +02:00
parent a481bec3ba
commit 4efe1541d0
1 changed files with 27 additions and 27 deletions

View File

@ -1,9 +1,10 @@
#include <stdio.h> #include <stdio.h>
#include <ctype.h> #include <ctype.h>
#include <assert.h>
/* array bounds */ /* array bounds */
#define MAXLINES 100 #define MAXLINES 100
#define BUFF_SIZE (80 * 100) #define BUFF_SIZE (80 * MAXLINES)
int readlines(char *lines[], int maxlines, char *ln_buff, size_t lb_size); int readlines(char *lines[], int maxlines, char *ln_buff, size_t lb_size);
void writelines(char *lines[], int n); void writelines(char *lines[], int n);
@ -16,16 +17,15 @@ int main()
char buffer[BUFF_SIZE]; char buffer[BUFF_SIZE];
int line_count = readlines(lines, MAXLINES, buffer, BUFF_SIZE); int line_count = readlines(lines, MAXLINES, buffer, BUFF_SIZE);
if (line_count >= 0) { if (line_count < 0) {
line_count = -line_count - 1;
printf("warning: buffer overflow occured, read %d lines\n", line_count);
} else if (line_count > MAXLINES) {
line_count = MAXLINES;
printf("warning: too many lines, read %d lines\n", line_count);
}
qsort_string(lines, 0, line_count-1); qsort_string(lines, 0, line_count-1);
writelines(lines, line_count); writelines(lines, line_count);
} else if (line_count == -1) {
puts("error: lines overflow");
return 1;
} else if (line_count == -2) {
puts("error: buffer overflow");
return 2;
}
return 0; return 0;
} }
@ -39,40 +39,40 @@ void writelines(char *lines[], int n)
} }
/* readlines: reads lines from input, writing them to ln_buff /* readlines: reads lines from input, writing them to ln_buff
* and line pointers to lines. returns number of lines read, * and line pointers to lines.
* -1 on lines overflow * returns number of lines read,
* -2 on buffer overflow */ * -lines_read-1 < 0 on buffer overflow
* maxlines+1 on lines overflow */
int readlines(char *lines[], int maxlines, char *buffer, size_t buff_size) int readlines(char *lines[], int maxlines, char *buffer, size_t buff_size)
{ {
assert(maxlines > 0);
char ** const fst_line = lines; char ** const fst_line = lines;
char *ln_start = buffer;
int c, not_empty = 0; int c, not_empty = 0;
for (; (c = getchar()) != EOF && buff_size; --buff_size) { for (*lines = buffer; (c = getchar()) != EOF && buff_size; --buff_size) {
not_empty |= !isspace(c); not_empty |= !isspace(c);
if (c == '\n') { if (c == '\n') {
if (!not_empty) { /* skip empty lines */ if (!not_empty) { /* skip empty lines */
buff_size += buffer - ln_start; buff_size += buffer - *lines;
buffer = ln_start; buffer = *lines;
continue; continue;
} }
not_empty = 0;
*buffer++ = '\0'; *buffer++ = '\0';
*lines++ = ln_start;
if (!--maxlines) if (!--maxlines)
break; break;
not_empty = 0; *++lines = buffer;
ln_start = buffer;
} else } else
*buffer++ = c; *buffer++ = c;
} }
/* ignore trailing whitespace and emepty lines */ /* ignore trailing whitespace and empty lines */
while (c != EOF && isspace(c)) while (c != EOF && isspace(c))
c = getchar(); c = getchar();
if (!maxlines && c != EOF) /* lines overflow */ if (c != EOF && !buff_size) /* buffer overflow, return -lines_read-1 */
return -1; return fst_line - lines - 1;
if (!buff_size && c != EOF) /* buffer overflow */ if (c != EOF && !maxlines) /* lines overflow, return maxlines+1 */
return -2; return lines - fst_line + 2;
return lines - fst_line; return lines - fst_line + not_empty;
} }
/* ---------- string quicksort */ /* ---------- string quicksort */