upas/fs: put date822 into the index, fix from and replyto handling

the date, from and replyto fields where unstable, in that the value
read depended on the state of the cache.

fixing the from and replyto fields is easy, we just handle the
substitution in parsebody().

the date field however requires us to put the date822 into the index
so it can be recovered without requiering to reparse the header
(and body, as we might have a message/rfc822 message with promoted
fields).

with these changes, the fields will be consistent and independnet
of the cache state.

a small optimization also has been added:

after parsing the body, attachments and substitution of from/replyto,
the boundary and unixfrom strings are not needed anymore and can
be freed early.
front
cinap_lenrek 2020-07-05 17:44:32 +02:00
parent e161f1c8ba
commit 43e56e26de
5 changed files with 66 additions and 58 deletions

View File

@ -57,6 +57,7 @@ cachefree(Mailbox *mb, Message *m)
}
for(s = m->part; s; s = s->next)
cachefree(mb, s);
if(m->mallocd){
free(m->start);
m->mallocd = 0;
@ -69,20 +70,28 @@ cachefree(Mailbox *mb, Message *m)
free(m->header);
m->hallocd = 0;
}
for(i = 0; i < nelem(m->references); i++){
free(m->references[i]);
m->references[i] = 0;
m->references[i] = nil;
}
free(m->unixfrom);
m->unixfrom = nil;
free(m->unixheader);
m->unixheader = nil;
free(m->boundary);
m->boundary = nil;
m->csize = 0;
m->start = 0;
m->end = 0;
m->header = 0;
m->hend = 0;
m->start = nil;
m->end = nil;
m->header = nil;
m->hend = nil;
m->hlen = -1;
m->body = 0;
m->bend = 0;
m->mheader = 0;
m->mhend = 0;
m->body = nil;
m->bend = nil;
m->mheader = nil;
m->mhend = nil;
m->decoded = 0;
m->converted = 0;
m->badchars = 0;

View File

@ -67,6 +67,7 @@ struct Idx {
char *subject;
char *sender;
char *inreplyto;
char *date822;
char *idxaux; /* mailbox specific */
char *type; /* mime info */
@ -117,7 +118,6 @@ struct Message {
/* mail info */
char *unixheader;
char *unixfrom;
char *date822;
char *references[Nref]; /* nil terminated unless full */
/* mime info */

View File

@ -423,11 +423,12 @@ fileinfo(Mailbox *mb, Message *m, int t, char **pp)
}
break;
case Qdate:
p = m->date822;
if(p == nil){
p = buf;
len = snprint(buf, sizeof buf, "%#Δ", m->fileid);
}
if((p = m->date822) != nil)
break;
/* wet floor */
case Qunixdate:
p = buf;
len = snprint(buf, sizeof buf, "%#Δ", m->fileid);
break;
case Qfilename:
p = m->filename;
@ -442,10 +443,7 @@ fileinfo(Mailbox *mb, Message *m, int t, char **pp)
p = m->messageid;
break;
case Qfrom:
if(m->from != nil)
p = m->from;
else
p = m->unixfrom;
p = m->from;
break;
case Qffrom:
p = m->ffrom;
@ -494,7 +492,7 @@ fileinfo(Mailbox *mb, Message *m, int t, char **pp)
e = buf + sizeof buf;
s = buf;
for(i = 0; i < nelem(m->references); i++){
if(m->references[i] == 0)
if(m->references[i] == nil)
break;
s = seprint(s, e, "%s\n", m->references[i]);
}
@ -503,14 +501,7 @@ fileinfo(Mailbox *mb, Message *m, int t, char **pp)
len = s - buf;
break;
case Qreplyto:
if(m->replyto != nil)
p = m->replyto;
else if(m->from != nil)
p = m->from;
else if(m->sender != nil)
p = m->sender;
else if(m->unixfrom != nil)
p = m->unixfrom;
p = m->replyto;
break;
case Qsender:
p = m->sender;
@ -528,10 +519,6 @@ fileinfo(Mailbox *mb, Message *m, int t, char **pp)
case Qtype:
p = m->type;
break;
case Qunixdate:
p = buf;
len = snprint(buf, sizeof buf, "%#Δ", m->fileid);
break;
case Qfileid:
p = buf;
len = snprint(buf, sizeof buf, "%D", m->fileid);

View File

@ -5,10 +5,10 @@
#define idprint(...) if(iflag > 1) fprint(2, __VA_ARGS__); else {}
#define iprint(...) if(iflag) fprint(2, __VA_ARGS__); else {}
static char *magic = "idx magic v8\n";
static char *magic = "idx magic v9\n";
static char *mbmagic = "genericv1";
enum {
Idxfields = 22,
Idxfields = 23,
Idxto = 30000, /* index timeout in ms */
Idxstep = 300, /* sleep between tries */
@ -58,8 +58,9 @@ idxfree(Idx *i)
free(i->subject);
free(i->sender);
free(i->inreplyto);
free(i->idxaux);
free(i->date822);
free(i->filename);
free(i->idxaux);
}
memset(i, 0, sizeof *i);
}
@ -77,7 +78,7 @@ pridxmsg(Biobuf *b, Idx *x)
{
Bprint(b, "%#A %ux %D %lud ", x->digest, x->flags&~Frecent, x->fileid, x->lines);
Bprint(b, "%q %q %q %q %q ", (x->ffrom), (x->from), (x->to), (x->cc), (x->bcc));
Bprint(b, "%q %q %q %q %q ", (x->replyto), (x->messageid), (x->subject), (x->sender), (x->inreplyto));
Bprint(b, "%q %q %q %q %q %q ", (x->replyto), (x->messageid), (x->subject), (x->sender), (x->inreplyto), (x->date822));
Bprint(b, "%s %d %q %lud %lud ", x->type, x->disposition, (x->filename), x->size, x->rawbsize);
Bprint(b, "%lud %q %d\n", x->ibadchars, (x->idxaux), x->nparts);
return 0;
@ -402,15 +403,15 @@ dead:
m->subject = (f[11]);
m->sender = (f[12]);
m->inreplyto = (f[13]);
m->type = intern(f[14]);
m->disposition = atoi(f[15]);
m->filename = (f[16]);
m->size = strtoul(f[17], 0, 0);
m->rawbsize = strtoul(f[18], 0, 0);
m->ibadchars = strtoul(f[19], 0, 0);
m->idxaux = (f[20]);
m->nparts = strtoul(f[21], 0, 0);
m->date822 = (f[14]);
m->type = intern(f[15]);
m->disposition = atoi(f[16]);
m->filename = (f[17]);
m->size = strtoul(f[18], 0, 0);
m->rawbsize = strtoul(f[19], 0, 0);
m->ibadchars = strtoul(f[20], 0, 0);
m->idxaux = (f[21]);
m->nparts = strtoul(f[22], 0, 0);
m->cstate &= ~Cidxstale;
m->cstate |= Cidx|Cnew;
m->str = s;

View File

@ -486,6 +486,7 @@ parseunix(Message *m)
if((p = strchr(s, ' ')) == nil)
return;
*p = 0;
free(m->unixfrom);
m->unixfrom = strdup(s);
*p = ' ';
}
@ -563,9 +564,9 @@ parseheaders(Mailbox *mb, Message *m, int addfrom, int justmime)
free(m->unixheader);
m->unixheader = nil;
} else if(m->unixheader == nil){
if(m->unixfrom && strcmp(m->unixfrom, "???") != 0)
if(m->unixfrom != nil && strcmp(m->unixfrom, "???") != 0)
p = m->unixfrom;
else if(m->from)
else if(m->from != nil)
p = m->from;
else
p = "???";
@ -605,6 +606,24 @@ parsebody(Message *m, Mailbox *mb)
}
}else if(strncmp(m->type, "text/", 5) == 0)
sanemsg(m);
free(m->boundary);
m->boundary = nil;
if(m->replyto == nil){
if(m->from != nil)
m->replyto = strdup(m->from);
else if(m->sender != nil)
m->replyto = strdup(m->sender);
else if(m->unixfrom != nil)
m->replyto = strdup(m->unixfrom);
}
if(m->from == nil && m->unixfrom != nil)
m->from = strdup(m->unixfrom);
free(m->unixfrom);
m->unixfrom = nil;
m->rawbsize = m->rbend - m->rbody;
m->cstate |= Cbody;
}
@ -888,7 +907,7 @@ ref822(Message *m, Header *h, char*, char *p)
free(a[0]);
memmove(&a[0], &a[1], (Nref - 1) * sizeof(a[0]));
j--;
} if(a[j] != nil)
} else if(a[j] != nil)
continue;
a[j] = strdup(f[i]);
}
@ -1030,11 +1049,6 @@ delmessage(Mailbox *mb, Message *m)
cachefree(mb, m);
idxfree(m);
}
free(m->unixfrom);
free(m->unixheader);
free(m->date822);
free(m->boundary);
free(m);
}
@ -1527,11 +1541,8 @@ mailplumb(Mailbox *mb, Message *m)
if(subject == nil)
subject = "";
if(m->from != nil)
from = m->from;
else if(m->unixfrom != nil)
from = m->unixfrom;
else
from = m->from;
if(from == nil)
from = "";
sprint(len, "%lud", m->size);