Skip to content

Commit

Permalink
If you have an incredibly large log file.. kerneloops takes too long.
Browse files Browse the repository at this point in the history
Just parse the last 32Mb instead, should be plenty.
  • Loading branch information
fenrus75 committed Jun 22, 2008
1 parent 47cd292 commit 4aad027
Showing 1 changed file with 14 additions and 4 deletions.
18 changes: 14 additions & 4 deletions dmesg.c
Expand Up @@ -40,6 +40,8 @@ static char **linepointer;
static char *linelevel;
static int linecount;

#define MAX(A,B) ((A) > (B) ? (A) : (B))


/*
* This function splits the dmesg buffer data into lines
Expand Down Expand Up @@ -352,6 +354,7 @@ void scan_filename(char *filename, int issyslog)
struct stat statb;
FILE *file;
int ret;
size_t buflen;

memset(&statb, 0, sizeof(statb));

Expand All @@ -364,21 +367,28 @@ void scan_filename(char *filename, int issyslog)
* in theory there's a race here, since someone could spew
* to /var/log/messages before we read it in... we try to
* deal with it by reading at most 1023 bytes extra. If there's
* more than that.. any oops will be in dmesg anyway
* more than that.. any oops will be in dmesg anyway.
* Do not try to allocate an absurt amount of memory; ignore
* older log messages because they are unlikely to have
* sufficiently recent data to be useful. 32MB is more
* than enough; it's not worth looping through more log
* if the log is larger than that.
*/
buffer = calloc(statb.st_size+1024, 1);
buflen = MAX(statb.st_size+1024, 32*1024*1024);
buffer = calloc(buflen, 1);
assert(buffer != NULL);

file = fopen(filename, "rm");
if (!file) {
free(buffer);
return;
}
ret = fread(buffer, 1, statb.st_size+1023, file);
fseek(file, -buflen, SEEK_END);
ret = fread(buffer, 1, buflen-1, file);
fclose(file);

if (ret > 0)
extract_oops(buffer, statb.st_size+1023, issyslog);
extract_oops(buffer, buflen-1, issyslog);
free(buffer);
if (opted_in >= 2)
submit_queue();
Expand Down

0 comments on commit 4aad027

Please sign in to comment.