Works, with a remaining bug in the indexing of multi-line field values.
authorFrancois Fleuret <francois@fleuret.org>
Sun, 27 Jan 2013 23:53:34 +0000 (00:53 +0100)
committerFrancois Fleuret <francois@fleuret.org>
Sun, 27 Jan 2013 23:53:34 +0000 (00:53 +0100)
mymail.c

index 877215c..6388365 100644 (file)
--- a/mymail.c
+++ b/mymail.c
@@ -47,6 +47,18 @@ char *search_pattern;
 
 int action_index;
 
+char *segment_next_field(char *current) {
+  while(*current && *current != ' ') current++;
+  *current = '\0'; current++;
+  while(*current && *current == ' ') current++;
+  return current;
+}
+
+void remove_eof(char *c) {
+  while(*c && *c != '\n' && *c != '\r') c++;
+  *c = '\0';
+}
+
 /********************************************************************/
 
 /* malloc with error checking.  */
@@ -76,9 +88,11 @@ void usage(FILE *out) {
 void search_in_db(const char *search_name, const char *search_regexp_string,
                   FILE *db_file) {
   char raw_line[BUFFER_SIZE];
-  char current_mail[BUFFER_SIZE];
+  char current_mail_filename[BUFFER_SIZE];
+  unsigned int current_position_in_mail;
   char *name, *value;
   regex_t regexp;
+  int already_written;
 
   if(regcomp(&regexp,
              search_regexp_string,
@@ -90,21 +104,42 @@ void search_in_db(const char *search_name, const char *search_regexp_string,
     exit(EXIT_FAILURE);
   }
 
+  current_position_in_mail = 0;
+  already_written = 0;
+
   while(fgets(raw_line, BUFFER_SIZE, db_file)) {
     name = raw_line;
-    value = raw_line;
-    while(*value && *value != ' ') value++;
-    *value = '\0'; value++;
-    while(*value && *value == ' ') value++;
+    value = segment_next_field(raw_line);
 
     /* printf("LINE [%s] %s", name, value); */
 
     if(strcmp("mail", name) == 0) {
-      strcpy(current_mail, value);
-      /* printf("READING [%s]\n", current_mail); */
-    } else {
+      char *position_in_file_string = value;
+      char *mail_filename = segment_next_field(value);
+      current_position_in_mail = atoi(position_in_file_string);
+      strcpy(current_mail_filename, mail_filename);
+      remove_eof(current_mail_filename);
+      /* printf("READING [%s]\n", current_mail_filename); */
+      already_written = 0;
+    } else if(!already_written) {
       if(strcmp(search_name, name) == 0 && regexec(&regexp, value, 0, 0, 0) == 0) {
-        printf("%s", current_mail);
+        FILE *mail_file;
+        /* printf("%s:%u\n", current_mail_filename, current_position_in_mail); */
+        mail_file = fopen(current_mail_filename, "r");
+        if(!mail_file) {
+          fprintf(stderr, "mymail: Can not open `%s'.\n", current_mail_filename);
+          exit(EXIT_FAILURE);
+        }
+        fseek(mail_file, current_position_in_mail, SEEK_SET);
+        if(fgets(raw_line, BUFFER_SIZE, mail_file)) {
+          printf("%s", raw_line);
+          while(fgets(raw_line, BUFFER_SIZE, mail_file) &&
+                strncmp(raw_line, "From ", 5)) {
+            printf("%s", raw_line);
+          }
+        }
+        fclose(mail_file);
+        already_written = 1;
       }
     }
   }
@@ -158,7 +193,7 @@ void read_file(const char *input_filename,
       int f;
       regmatch_t matches;
       if(new_header) {
-        fprintf(db_file, "mail %s:%d\n", input_filename, position_in_file);
+        fprintf(db_file, "mail %u %s\n", position_in_file, input_filename);
         new_header = 0;
       }
       for(f = 0; f < nb_fields_to_parse; f++) {
@@ -352,20 +387,17 @@ int main(int argc, char **argv) {
       char *search_name;
       char *search_regexp_string;
       search_name = search_pattern;
-      search_regexp_string = search_pattern;
-      while(*search_regexp_string && *search_regexp_string != ' ') search_regexp_string++;
-      *search_regexp_string = '\0'; search_regexp_string++;
-      while(*search_regexp_string && *search_regexp_string == ' ') search_regexp_string++;
+      search_regexp_string = segment_next_field(search_pattern);
       if(!*search_regexp_string) {
         fprintf(stderr,
                 "Syntax error in the search pattern.\n");
         exit(EXIT_FAILURE);
       }
 
-      printf("Starting search in %s for field \"%s\" matching \"%s\".\n",
-             db_filename,
-             search_name,
-             search_regexp_string);
+      /* printf("Starting search in %s for field \"%s\" matching \"%s\".\n", */
+             /* db_filename, */
+             /* search_name, */
+             /* search_regexp_string); */
 
       db_file = fopen(db_filename, "r");
 
@@ -376,6 +408,7 @@ int main(int argc, char **argv) {
                 strerror(errno));
         exit(EXIT_FAILURE);
       }
+
       search_in_db(search_name, search_regexp_string, db_file);
 
       fclose(db_file);