Commit 0b3ced06 0b3ced0625d37c283632e93f0d49360c668cb459 by Alain Magloire

Adding more comments, and in message_destroy make sure we

destroy all the objects attached to it.
1 parent 33e314b0
...@@ -125,7 +125,7 @@ static int fill_buffer (bio_t bio, char *buffer, size_t buflen); ...@@ -125,7 +125,7 @@ static int fill_buffer (bio_t bio, char *buffer, size_t buflen);
125 filtering out the starting "." and return O(zero) when seeing the terminal 125 filtering out the starting "." and return O(zero) when seeing the terminal
126 octets ".\r\n". bio_readline () insists on having a _complete_ line .i.e 126 octets ".\r\n". bio_readline () insists on having a _complete_ line .i.e
127 a string terminated by \n, it will allocate/grow the working buffer as 127 a string terminated by \n, it will allocate/grow the working buffer as
128 needed. The '\r\n" termination is converted to '\n'. bio_destroy () 128 needed. The "\r\n" termination is converted to '\n'. bio_destroy ()
129 does not close the stream but only free () the working buffer. */ 129 does not close the stream but only free () the working buffer. */
130 struct _bio 130 struct _bio
131 { 131 {
...@@ -146,14 +146,14 @@ static int bio_read (bio_t); ...@@ -146,14 +146,14 @@ static int bio_read (bio_t);
146 static int bio_write (bio_t); 146 static int bio_write (bio_t);
147 147
148 148
149 /* This structure holds the info when for a pop_get_message() the 149 /* This structure holds the info for a pop_get_message(). The pop_message_t
150 pop_message_t type will serve as the owner of the message_t and contains 150 type, will serve as the owner of the message_t and contains the command to
151 the command to send to RETReive the specify message. The problem comes 151 send to "RETR"eive the specify message. The problem comes
152 from the header. If the POP server supports TOP, we can cleanly fetch 152 from the header. If the POP server supports TOP, we can cleanly fetch
153 the header. But otherwise we use the clumsy approach. .i.e for the header 153 the header. But otherwise we use the clumsy approach. .i.e for the header
154 we read 'til ^\n then discard the rest for the body we read after ^\n and 154 we read 'til ^\n then discard the rest, for the body we read after ^\n and
155 discard the beginning. This a waste, Pop was not conceive for this 155 discard the beginning. This a waste, Pop was not conceive for this
156 obviously. */ 156 obviously. */
157 struct _pop_message 157 struct _pop_message
158 { 158 {
159 int inbody; 159 int inbody;
...@@ -171,7 +171,7 @@ struct _pop_message ...@@ -171,7 +171,7 @@ struct _pop_message
171 struct _pop_data 171 struct _pop_data
172 { 172 {
173 void *func; /* Indicate a command is in operation, busy. */ 173 void *func; /* Indicate a command is in operation, busy. */
174 size_t id; /* Use in pop_expunge to indiate the message, if bailing out. */ 174 size_t id; /* Use in pop_expunge to hold the message num, if EAGAIN. */
175 enum pop_state state; 175 enum pop_state state;
176 pop_message_t *pmessages; 176 pop_message_t *pmessages;
177 size_t pmessages_count; 177 size_t pmessages_count;
...@@ -183,7 +183,7 @@ struct _pop_data ...@@ -183,7 +183,7 @@ struct _pop_data
183 int flags; /* Flags of for the stream_t object. */ 183 int flags; /* Flags of for the stream_t object. */
184 bio_t bio; /* Working I/O buffer. */ 184 bio_t bio; /* Working I/O buffer. */
185 int is_updated; 185 int is_updated;
186 char *user; /* Temporary holders for user and passwd. */ 186 char *user; /* Temporary holders for user and passwd. */
187 char *passwd; 187 char *passwd;
188 mailbox_t mbox; /* Back pointer. */ 188 mailbox_t mbox; /* Back pointer. */
189 } ; 189 } ;
...@@ -209,7 +209,7 @@ do \ ...@@ -209,7 +209,7 @@ do \
209 while (0) 209 while (0)
210 210
211 211
212 /* Parse the url, allocate mailbox_t etc .. */ 212 /* Parse the url, allocate mailbox_t, allocate pop internal structures. */
213 static int 213 static int
214 pop_create (mailbox_t *pmbox, const char *name) 214 pop_create (mailbox_t *pmbox, const char *name)
215 { 215 {
...@@ -293,7 +293,7 @@ pop_create (mailbox_t *pmbox, const char *name) ...@@ -293,7 +293,7 @@ pop_create (mailbox_t *pmbox, const char *name)
293 return 0; /* Okdoke. */ 293 return 0; /* Okdoke. */
294 } 294 }
295 295
296 /* Cleaning up all the ressources. */ 296 /* Cleaning up all the ressources associate with a pop mailbox. */
297 static void 297 static void
298 pop_destroy (mailbox_t *pmbox) 298 pop_destroy (mailbox_t *pmbox)
299 { 299 {
...@@ -357,6 +357,7 @@ echo_on(void) ...@@ -357,6 +357,7 @@ echo_on(void)
357 tcsetattr (0, TCSANOW, &stored_settings); 357 tcsetattr (0, TCSANOW, &stored_settings);
358 } 358 }
359 359
360 /* User/pass authentication for pop. */
360 static int 361 static int
361 pop_authenticate (auth_t auth, char **user, char **passwd) 362 pop_authenticate (auth_t auth, char **user, char **passwd)
362 { 363 {
...@@ -394,6 +395,9 @@ pop_authenticate (auth_t auth, char **user, char **passwd) ...@@ -394,6 +395,9 @@ pop_authenticate (auth_t auth, char **user, char **passwd)
394 return 0; 395 return 0;
395 } 396 }
396 397
398 /* Open the connection to the sever, ans send the authentication.
399 FIXME: Should also send the CAPA command to detect for example the suport
400 for POP, and DTRT(Do The Right Thing). */
397 static int 401 static int
398 pop_open (mailbox_t mbox, int flags) 402 pop_open (mailbox_t mbox, int flags)
399 { 403 {
...@@ -481,7 +485,7 @@ pop_open (mailbox_t mbox, int flags) ...@@ -481,7 +485,7 @@ pop_open (mailbox_t mbox, int flags)
481 return EACCES; 485 return EACCES;
482 } 486 }
483 487
484 /* Fetch the the user/passwd from them. */ 488 /* Fetch the user/passwd from them. */
485 auth_authenticate (mbox->auth, &mpd->user, &mpd->passwd); 489 auth_authenticate (mbox->auth, &mpd->user, &mpd->passwd);
486 490
487 bio->len = snprintf (bio->buffer, bio->maxlen, "USER %s\r\n", mpd->user); 491 bio->len = snprintf (bio->buffer, bio->maxlen, "USER %s\r\n", mpd->user);
...@@ -549,6 +553,7 @@ pop_open (mailbox_t mbox, int flags) ...@@ -549,6 +553,7 @@ pop_open (mailbox_t mbox, int flags)
549 return 0; 553 return 0;
550 } 554 }
551 555
556 /* Send the QUIT and close the socket. */
552 static int 557 static int
553 pop_close (mailbox_t mbox) 558 pop_close (mailbox_t mbox)
554 { 559 {
...@@ -561,6 +566,7 @@ pop_close (mailbox_t mbox) ...@@ -561,6 +566,7 @@ pop_close (mailbox_t mbox)
561 if (mpd == NULL) 566 if (mpd == NULL)
562 return EINVAL; 567 return EINVAL;
563 568
569 /* Flag busy ? */
564 if (mpd->func && mpd->func != func) 570 if (mpd->func && mpd->func != func)
565 return EBUSY; 571 return EBUSY;
566 572
...@@ -571,6 +577,7 @@ pop_close (mailbox_t mbox) ...@@ -571,6 +577,7 @@ pop_close (mailbox_t mbox)
571 switch (mpd->state) 577 switch (mpd->state)
572 { 578 {
573 case POP_NO_STATE: 579 case POP_NO_STATE:
580 /* Initiate the close. */
574 bio->len = snprintf (bio->buffer, bio->maxlen, "QUIT\r\n"); 581 bio->len = snprintf (bio->buffer, bio->maxlen, "QUIT\r\n");
575 bio->ptr = bio->buffer; 582 bio->ptr = bio->buffer;
576 mailbox_debug (mbox, MU_MAILBOX_DEBUG_PROT, bio->buffer); 583 mailbox_debug (mbox, MU_MAILBOX_DEBUG_PROT, bio->buffer);
...@@ -587,15 +594,15 @@ pop_close (mailbox_t mbox) ...@@ -587,15 +594,15 @@ pop_close (mailbox_t mbox)
587 status = bio_readline (bio); 594 status = bio_readline (bio);
588 CHECK_NON_RECOVERABLE (mpd, status); 595 CHECK_NON_RECOVERABLE (mpd, status);
589 mailbox_debug (mbox, MU_MAILBOX_DEBUG_PROT, bio->buffer); 596 mailbox_debug (mbox, MU_MAILBOX_DEBUG_PROT, bio->buffer);
590 /* Now what ! and how can we tell them about errors ? So for now 597 /* Now what ! and how can we tell them about errors ? So far now
591 lets just be verbose about the error but close the connection 598 lets just be verbose about the error but close the connection
592 anyway. */ 599 anyway. */
593 if (strncasecmp (bio->buffer, "+OK", 3) != 0) 600 if (strncasecmp (bio->buffer, "+OK", 3) != 0)
594 fprintf (stderr, "pop_close: %s\n", bio->buffer); 601 fprintf (stderr, "pop_close: %s\n", bio->buffer);
595
596 stream_close (bio->stream); 602 stream_close (bio->stream);
597 bio->stream = NULL; 603 bio->stream = NULL;
598 break; 604 break;
605
599 default: 606 default:
600 /* 607 /*
601 fprintf (stderr, "pop_close unknow state"); 608 fprintf (stderr, "pop_close unknow state");
...@@ -613,6 +620,7 @@ pop_close (mailbox_t mbox) ...@@ -613,6 +620,7 @@ pop_close (mailbox_t mbox)
613 free (mpd->pmessages[i]); 620 free (mpd->pmessages[i]);
614 } 621 }
615 } 622 }
623 /* And clear any residue. */
616 free (mpd->pmessages); 624 free (mpd->pmessages);
617 mpd->pmessages = NULL; 625 mpd->pmessages = NULL;
618 mpd->pmessages_count = 0; 626 mpd->pmessages_count = 0;
...@@ -623,6 +631,7 @@ pop_close (mailbox_t mbox) ...@@ -623,6 +631,7 @@ pop_close (mailbox_t mbox)
623 return 0; 631 return 0;
624 } 632 }
625 633
634 /* Only build/setup the message_t structure for a mesgno. */
626 static int 635 static int
627 pop_get_message (mailbox_t mbox, size_t msgno, message_t *pmsg) 636 pop_get_message (mailbox_t mbox, size_t msgno, message_t *pmsg)
628 { 637 {
...@@ -651,25 +660,28 @@ pop_get_message (mailbox_t mbox, size_t msgno, message_t *pmsg) ...@@ -651,25 +660,28 @@ pop_get_message (mailbox_t mbox, size_t msgno, message_t *pmsg)
651 mpm = calloc (1, sizeof (*mpm)); 660 mpm = calloc (1, sizeof (*mpm));
652 if (mpm == NULL) 661 if (mpm == NULL)
653 return ENOMEM; 662 return ENOMEM;
654 /* back pointer */ 663
664 /* Back pointer. */
655 mpm->mpd = mpd; 665 mpm->mpd = mpd;
656 mpm->num = msgno; 666 mpm->num = msgno;
657 667
658 /* Create the message. */ 668 /* Create the message. */
659 { 669 {
660 message_t msg = NULL; 670 message_t msg = NULL;
661 stream_t is = NULL; 671 stream_t stream = NULL;
662 if ((status = message_create (&msg, mpm)) != 0 672 if ((status = message_create (&msg, mpm)) != 0
663 || (status = stream_create (&is, MU_STREAM_READ, mpm)) != 0) 673 || (status = stream_create (&stream, MU_STREAM_READ, mpm)) != 0)
664 { 674 {
665 message_destroy (&msg, mpm); 675 message_destroy (&msg, mpm);
666 stream_destroy (&is, mpm); 676 stream_destroy (&stream, mpm);
667 free (mpm); 677 free (mpm);
668 return status; 678 return status;
669 } 679 }
670 stream_set_read (is, pop_read_message, mpm); 680 stream_set_read (stream, pop_read_message, mpm);
671 message_set_stream (msg, is, mpm); 681 stream_set_fd (stream, pop_get_fd, mpm);
672 /* The message. */ 682 stream_set_flags (stream, MU_STREAM_READ, mpm);
683 message_set_stream (msg, stream, mpm);
684 /* Save The message. */
673 mpm->message = msg; 685 mpm->message = msg;
674 } 686 }
675 687
...@@ -753,6 +765,7 @@ pop_get_message (mailbox_t mbox, size_t msgno, message_t *pmsg) ...@@ -753,6 +765,7 @@ pop_get_message (mailbox_t mbox, size_t msgno, message_t *pmsg)
753 return 0; 765 return 0;
754 } 766 }
755 767
768 /* How many messages we have. Done with STAT. */
756 static int 769 static int
757 pop_messages_count (mailbox_t mbox, size_t *pcount) 770 pop_messages_count (mailbox_t mbox, size_t *pcount)
758 { 771 {
...@@ -764,6 +777,7 @@ pop_messages_count (mailbox_t mbox, size_t *pcount) ...@@ -764,6 +777,7 @@ pop_messages_count (mailbox_t mbox, size_t *pcount)
764 if (mpd == NULL) 777 if (mpd == NULL)
765 return EINVAL; 778 return EINVAL;
766 779
780 /* Do not send a STAT if we know the answer. */
767 if (pop_is_updated (mbox)) 781 if (pop_is_updated (mbox))
768 { 782 {
769 if (pcount) 783 if (pcount)
...@@ -771,6 +785,7 @@ pop_messages_count (mailbox_t mbox, size_t *pcount) ...@@ -771,6 +785,7 @@ pop_messages_count (mailbox_t mbox, size_t *pcount)
771 return 0; 785 return 0;
772 } 786 }
773 787
788 /* Flag busy. */
774 if (mpd->func && mpd->func != func) 789 if (mpd->func && mpd->func != func)
775 return EBUSY; 790 return EBUSY;
776 791
...@@ -805,16 +820,20 @@ pop_messages_count (mailbox_t mbox, size_t *pcount) ...@@ -805,16 +820,20 @@ pop_messages_count (mailbox_t mbox, size_t *pcount)
805 break; 820 break;
806 } 821 }
807 822
823 /* Parse the answer. */
808 status = sscanf (bio->buffer, "+OK %d %d", &(mpd->messages_count), 824 status = sscanf (bio->buffer, "+OK %d %d", &(mpd->messages_count),
809 &(mpd->size)); 825 &(mpd->size));
810 826
827 /* Clear the state _after_ the scanf, since another thread could
828 start writing over bio->buffer. But We're not thread safe yet. */
811 CLEAR_STATE (mpd); 829 CLEAR_STATE (mpd);
812 830
813 mpd->is_updated = 1;
814 if (pcount)
815 *pcount = mpd->messages_count;
816 if (status == EOF || status != 2) 831 if (status == EOF || status != 2)
817 return EIO; 832 return EIO;
833
834 if (pcount)
835 *pcount = mpd->messages_count;
836 mpd->is_updated = 1;
818 return 0; 837 return 0;
819 } 838 }
820 839
...@@ -829,6 +848,9 @@ pop_is_updated (mailbox_t mbox) ...@@ -829,6 +848,9 @@ pop_is_updated (mailbox_t mbox)
829 return mpd->is_updated; 848 return mpd->is_updated;
830 } 849 }
831 850
851 /* We do not send anything to the server since, no DELE command is sent but
852 the only the attribute flag is modified.
853 DELE is sent only when expunging. */
832 static int 854 static int
833 pop_num_deleted (mailbox_t mbox, size_t *pnum) 855 pop_num_deleted (mailbox_t mbox, size_t *pnum)
834 { 856 {
...@@ -853,7 +875,8 @@ pop_num_deleted (mailbox_t mbox, size_t *pnum) ...@@ -853,7 +875,8 @@ pop_num_deleted (mailbox_t mbox, size_t *pnum)
853 return 0; 875 return 0;
854 } 876 }
855 877
856 /* We just simulated. */ 878 /* We just simulated. By sending a notification for the total msgno. */
879 /* FIXME is message is set deleted should we sent a notif ? */
857 static int 880 static int
858 pop_scan (mailbox_t mbox, size_t msgno, size_t *pcount) 881 pop_scan (mailbox_t mbox, size_t msgno, size_t *pcount)
859 { 882 {
...@@ -869,7 +892,7 @@ pop_scan (mailbox_t mbox, size_t msgno, size_t *pcount) ...@@ -869,7 +892,7 @@ pop_scan (mailbox_t mbox, size_t msgno, size_t *pcount)
869 return 0; 892 return 0;
870 } 893 }
871 894
872 /* This were we actually sending the DELE command. */ 895 /* This were we actually send the DELE command. */
873 static int 896 static int
874 pop_expunge (mailbox_t mbox) 897 pop_expunge (mailbox_t mbox)
875 { 898 {
...@@ -954,13 +977,13 @@ pop_expunge (mailbox_t mbox) ...@@ -954,13 +977,13 @@ pop_expunge (mailbox_t mbox)
954 mpd->id = 0; 977 mpd->id = 0;
955 mpd->func = NULL; 978 mpd->func = NULL;
956 mpd->state = POP_NO_STATE; 979 mpd->state = POP_NO_STATE;
957 /* Invalidate. But Really they should shutdown the challen POP protocol 980 /* Invalidate. But Really they should shutdown the channel POP protocol
958 is not meant for this like IMAP. */ 981 is not meant for this like IMAP. */
959 mpd->is_updated = 0; 982 mpd->is_updated = 0;
960 return 0; 983 return 0;
961 } 984 }
962 985
963 /* Mailbox size ? */ 986 /* Mailbox size ? It is part of the STAT command */
964 static int 987 static int
965 pop_size (mailbox_t mbox, off_t *psize) 988 pop_size (mailbox_t mbox, off_t *psize)
966 { 989 {
...@@ -999,6 +1022,10 @@ pop_body_lines (body_t body, size_t *plines) ...@@ -999,6 +1022,10 @@ pop_body_lines (body_t body, size_t *plines)
999 return 0; 1022 return 0;
1000 } 1023 }
1001 1024
1025 /* Pop does not have any command for this, We fake by reading the "Status: "
1026 header. But this is hackish some POP server(Qpopper) skip it. Also
1027 because we call header_get_value the function may return EAGAIN...
1028 uncool. */
1002 static int 1029 static int
1003 pop_get_flags (attribute_t attr, int *pflags) 1030 pop_get_flags (attribute_t attr, int *pflags)
1004 { 1031 {
...@@ -1029,6 +1056,10 @@ pop_get_fd (stream_t stream, int *pfd) ...@@ -1029,6 +1056,10 @@ pop_get_fd (stream_t stream, int *pfd)
1029 return EINVAL; 1056 return EINVAL;
1030 } 1057 }
1031 1058
1059 /* Get the UIDL. Client should be prepare since it may fail. UIDL is
1060 optionnal for many POP server.
1061 FIXME: We should check this with CAPA and fall back to md5 scheme ?
1062 Or maybe check for "X-UIDL" a la Qpopper ? */
1032 static int 1063 static int
1033 pop_uidl (message_t msg, char *buffer, size_t buflen, size_t *pnwriten) 1064 pop_uidl (message_t msg, char *buffer, size_t buflen, size_t *pnwriten)
1034 { 1065 {
...@@ -1104,6 +1135,9 @@ pop_uidl (message_t msg, char *buffer, size_t buflen, size_t *pnwriten) ...@@ -1104,6 +1135,9 @@ pop_uidl (message_t msg, char *buffer, size_t buflen, size_t *pnwriten)
1104 return status; 1135 return status;
1105 } 1136 }
1106 1137
1138 /* How we retrieve the headers. If it fails we jump to the pop_retr()
1139 code .i.e send a RETR and skip the body, ugly.
1140 NOTE: offset is meaningless. */
1107 static int 1141 static int
1108 pop_top (stream_t is, char *buffer, size_t buflen, 1142 pop_top (stream_t is, char *buffer, size_t buflen,
1109 off_t offset, size_t *pnread) 1143 off_t offset, size_t *pnread)
...@@ -1195,7 +1229,7 @@ pop_top (stream_t is, char *buffer, size_t buflen, ...@@ -1195,7 +1229,7 @@ pop_top (stream_t is, char *buffer, size_t buflen,
1195 } 1229 }
1196 break; 1230 break;
1197 default: 1231 default:
1198 /* Probabaly TOP was not supported so we fall back to RETR. */ 1232 /* Probabaly TOP was not supported so we have fall back to RETR. */
1199 mpm->skip_header = 0; 1233 mpm->skip_header = 0;
1200 mpm->skip_body = 1; 1234 mpm->skip_body = 1;
1201 return pop_retr (mpm, buffer, buflen, offset, pnread); 1235 return pop_retr (mpm, buffer, buflen, offset, pnread);
...@@ -1210,6 +1244,7 @@ pop_top (stream_t is, char *buffer, size_t buflen, ...@@ -1210,6 +1244,7 @@ pop_top (stream_t is, char *buffer, size_t buflen,
1210 return 0; 1244 return 0;
1211 } 1245 }
1212 1246
1247 /* Stub to call pop_retr (). */
1213 static int 1248 static int
1214 pop_read_header (stream_t is, char *buffer, size_t buflen, off_t offset, 1249 pop_read_header (stream_t is, char *buffer, size_t buflen, off_t offset,
1215 size_t *pnread) 1250 size_t *pnread)
...@@ -1230,6 +1265,7 @@ pop_read_header (stream_t is, char *buffer, size_t buflen, off_t offset, ...@@ -1230,6 +1265,7 @@ pop_read_header (stream_t is, char *buffer, size_t buflen, off_t offset,
1230 return pop_retr (mpm, buffer, buflen, offset, pnread); 1265 return pop_retr (mpm, buffer, buflen, offset, pnread);
1231 } 1266 }
1232 1267
1268 /* Stub to call pop_retr (). */
1233 static int 1269 static int
1234 pop_read_body (stream_t is, char *buffer, size_t buflen, off_t offset, 1270 pop_read_body (stream_t is, char *buffer, size_t buflen, off_t offset,
1235 size_t *pnread) 1271 size_t *pnread)
...@@ -1250,6 +1286,7 @@ pop_read_body (stream_t is, char *buffer, size_t buflen, off_t offset, ...@@ -1250,6 +1286,7 @@ pop_read_body (stream_t is, char *buffer, size_t buflen, off_t offset,
1250 return pop_retr (mpm, buffer, buflen, offset, pnread); 1286 return pop_retr (mpm, buffer, buflen, offset, pnread);
1251 } 1287 }
1252 1288
1289 /* Stub to call pop_retr (). */
1253 static int 1290 static int
1254 pop_read_message (stream_t is, char *buffer, size_t buflen, off_t offset, 1291 pop_read_message (stream_t is, char *buffer, size_t buflen, off_t offset,
1255 size_t *pnread) 1292 size_t *pnread)
...@@ -1270,6 +1307,7 @@ pop_read_message (stream_t is, char *buffer, size_t buflen, off_t offset, ...@@ -1270,6 +1307,7 @@ pop_read_message (stream_t is, char *buffer, size_t buflen, off_t offset,
1270 return pop_retr (mpm, buffer, buflen, offset, pnread); 1307 return pop_retr (mpm, buffer, buflen, offset, pnread);
1271 } 1308 }
1272 1309
1310 /* Little helper to fill the buffer without overflow. */
1273 static int 1311 static int
1274 fill_buffer (bio_t bio, char *buffer, size_t buflen) 1312 fill_buffer (bio_t bio, char *buffer, size_t buflen)
1275 { 1313 {
...@@ -1293,6 +1331,7 @@ fill_buffer (bio_t bio, char *buffer, size_t buflen) ...@@ -1293,6 +1331,7 @@ fill_buffer (bio_t bio, char *buffer, size_t buflen)
1293 return nread; 1331 return nread;
1294 } 1332 }
1295 1333
1334 /* The heart of most funtions. Send the RETR and skip different parts. */
1296 static int 1335 static int
1297 pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset, 1336 pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset,
1298 size_t *pnread) 1337 size_t *pnread)
...@@ -1340,7 +1379,7 @@ pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset, ...@@ -1340,7 +1379,7 @@ pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset,
1340 mpd->state = POP_RETR_RX_HDR; 1379 mpd->state = POP_RETR_RX_HDR;
1341 1380
1342 case POP_RETR_RX_HDR: 1381 case POP_RETR_RX_HDR:
1343 /* Skip the header. */ 1382 /* Skip/Take the header. */
1344 while (!mpm->inbody) 1383 while (!mpm->inbody)
1345 { 1384 {
1346 /* Do we need to fill up. */ 1385 /* Do we need to fill up. */
...@@ -1369,12 +1408,10 @@ pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset, ...@@ -1369,12 +1408,10 @@ pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset,
1369 break; 1408 break;
1370 } 1409 }
1371 } 1410 }
1372 /* Skip the newline. */
1373 //bio_readline (bio);
1374 mpd->state = POP_RETR_RX_BODY; 1411 mpd->state = POP_RETR_RX_BODY;
1375 1412
1376 case POP_RETR_RX_BODY: 1413 case POP_RETR_RX_BODY:
1377 /* Start taking the body. */ 1414 /* Start/Take the body. */
1378 { 1415 {
1379 while (mpm->inbody) 1416 while (mpm->inbody)
1380 { 1417 {
...@@ -1411,10 +1448,15 @@ pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset, ...@@ -1411,10 +1448,15 @@ pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset,
1411 } 1448 }
1412 } 1449 }
1413 mpd->state = POP_STATE_DONE; 1450 mpd->state = POP_STATE_DONE;
1451 /* Return here, because we want to return nread = 0 to notify the calle
1452 that we've finish. If we don't we will start over again by sending
1453 another RETR. hmm Is there a better way. */
1414 return 0; 1454 return 0;
1455
1415 case POP_STATE_DONE: 1456 case POP_STATE_DONE:
1416 /* A convenient break, this is here so we can return 0 read on next 1457 /* A convenient break, this is here so we can return 0 read on next
1417 call meaning we're done. */ 1458 call meaning we're done. */
1459
1418 default: 1460 default:
1419 /* fprintf (stderr, "pop_retr unknow state\n"); */ 1461 /* fprintf (stderr, "pop_retr unknow state\n"); */
1420 break; 1462 break;
...@@ -1425,6 +1467,7 @@ pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset, ...@@ -1425,6 +1467,7 @@ pop_retr (pop_message_t mpm, char *buffer, size_t buflen, off_t offset,
1425 return 0; 1467 return 0;
1426 } 1468 }
1427 1469
1470 /* Allocate buffer for I/O. */
1428 static int 1471 static int
1429 bio_create (bio_t *pbio, stream_t stream) 1472 bio_create (bio_t *pbio, stream_t stream)
1430 { 1473 {
...@@ -1439,6 +1482,7 @@ bio_create (bio_t *pbio, stream_t stream) ...@@ -1439,6 +1482,7 @@ bio_create (bio_t *pbio, stream_t stream)
1439 return 0; 1482 return 0;
1440 } 1483 }
1441 1484
1485 /* Free() buffer but do not close the stream. */
1442 static void 1486 static void
1443 bio_destroy (bio_t *pbio) 1487 bio_destroy (bio_t *pbio)
1444 { 1488 {
...@@ -1451,6 +1495,7 @@ bio_destroy (bio_t *pbio) ...@@ -1451,6 +1495,7 @@ bio_destroy (bio_t *pbio)
1451 } 1495 }
1452 } 1496 }
1453 1497
1498 /* Send as much data as possible. */
1454 static int 1499 static int
1455 bio_write (bio_t bio) 1500 bio_write (bio_t bio)
1456 { 1501 {
...@@ -1470,6 +1515,7 @@ bio_write (bio_t bio) ...@@ -1470,6 +1515,7 @@ bio_write (bio_t bio)
1470 return 0; 1515 return 0;
1471 } 1516 }
1472 1517
1518 /* Read into the buffer. */
1473 static int 1519 static int
1474 bio_read (bio_t bio) 1520 bio_read (bio_t bio)
1475 { 1521 {
......
...@@ -53,6 +53,12 @@ ...@@ -53,6 +53,12 @@
53 #define ATTRIBUTE_IS_DELETED(flag) (flag & MU_ATTRIBUTE_DELETED) 53 #define ATTRIBUTE_IS_DELETED(flag) (flag & MU_ATTRIBUTE_DELETED)
54 #define ATTRIBUTE_IS_EQUAL(flag1, flag2) (flag1 == flag2) 54 #define ATTRIBUTE_IS_EQUAL(flag1, flag2) (flag1 == flag2)
55 55
56 struct _unix_message;
57 struct _unix_data;
58
59 typedef struct _unix_data* unix_data_t;
60 typedef struct _unix_message* unix_message_t;
61
56 static int unix_create (mailbox_t *pmbox, const char *name); 62 static int unix_create (mailbox_t *pmbox, const char *name);
57 static void unix_destroy (mailbox_t *pmbox); 63 static void unix_destroy (mailbox_t *pmbox);
58 64
...@@ -64,7 +70,7 @@ struct mailbox_registrar _mailbox_unix_registrar = ...@@ -64,7 +70,7 @@ struct mailbox_registrar _mailbox_unix_registrar =
64 70
65 /* Keep the position of where the header and body starts and ends. 71 /* Keep the position of where the header and body starts and ends.
66 old_flags is the "Status:" message. */ 72 old_flags is the "Status:" message. */
67 typedef struct _unix_message 73 struct _unix_message
68 { 74 {
69 /* Offset of the parts of the messages in the mailbox. */ 75 /* Offset of the parts of the messages in the mailbox. */
70 off_t header_from; 76 off_t header_from;
...@@ -90,7 +96,7 @@ typedef struct _unix_message ...@@ -90,7 +96,7 @@ typedef struct _unix_message
90 /* A message attach to it. */ 96 /* A message attach to it. */
91 message_t message; 97 message_t message;
92 98
93 } *unix_message_t; 99 };
94 100
95 /* The umessages is an array of pointers that contains umessages_count of 101 /* The umessages is an array of pointers that contains umessages_count of
96 unix_message_t*; umessages[umessages_count]. We do it this because 102 unix_message_t*; umessages[umessages_count]. We do it this because
...@@ -98,7 +104,7 @@ typedef struct _unix_message ...@@ -98,7 +104,7 @@ typedef struct _unix_message
98 the pointers someone has on the messages. Thanks to <Dave Inglis> for 104 the pointers someone has on the messages. Thanks to <Dave Inglis> for
99 pointing this out. The messages_count is the count number of messages 105 pointing this out. The messages_count is the count number of messages
100 parsed so far. */ 106 parsed so far. */
101 typedef struct _unix_data 107 struct _unix_data
102 { 108 {
103 unix_message_t *umessages; 109 unix_message_t *umessages;
104 size_t umessages_count; 110 size_t umessages_count;
...@@ -118,8 +124,9 @@ typedef struct _unix_data ...@@ -118,8 +124,9 @@ typedef struct _unix_data
118 char *date; 124 char *date;
119 off_t off; 125 off_t off;
120 126
121 } *unix_data_t; 127 };
122 128
129 /* Mailbox implementation. */
123 static int unix_open (mailbox_t mbox, int flag); 130 static int unix_open (mailbox_t mbox, int flag);
124 static int unix_close (mailbox_t mbox); 131 static int unix_close (mailbox_t mbox);
125 static int unix_get_message (mailbox_t, size_t msgno, message_t *msg); 132 static int unix_get_message (mailbox_t, size_t msgno, message_t *msg);
...@@ -249,6 +256,7 @@ unix_create (mailbox_t *pmbox, const char *name) ...@@ -249,6 +256,7 @@ unix_create (mailbox_t *pmbox, const char *name)
249 return 0; /* okdoke */ 256 return 0; /* okdoke */
250 } 257 }
251 258
259 /* Free all ressources associated with Unix mailbox. */
252 static void 260 static void
253 unix_destroy (mailbox_t *pmbox) 261 unix_destroy (mailbox_t *pmbox)
254 { 262 {
......
...@@ -22,8 +22,7 @@ ...@@ -22,8 +22,7 @@
22 /* Parsing. 22 /* Parsing.
23 * The approach is to detect the "From " as start of a 23 * The approach is to detect the "From " as start of a
24 * new message, give the position of the header and scan 24 * new message, give the position of the header and scan
25 * until "\n" then set header_end, set body position, if we have 25 * until "\n" then set header_end, set body position,
26 * a Content-Length field jump to the point if not
27 * scan until we it another "From " and set body_end. 26 * scan until we it another "From " and set body_end.
28 * 27 *
29 ************************************ 28 ************************************
...@@ -187,7 +186,7 @@ do \ ...@@ -187,7 +186,7 @@ do \
187 (buf[4] == 'U' || buf[4] == 'u') && \ 186 (buf[4] == 'U' || buf[4] == 'u') && \
188 (buf[5] == 'S' || buf[5] == 's') && (buf[6] == ':')) 187 (buf[5] == 'S' || buf[5] == 's') && (buf[6] == ':'))
189 188
190 /* notification */ 189 /* Notification. */
191 #define MAILBOX_NOTIFICATION(mbox,which,bailing) \ 190 #define MAILBOX_NOTIFICATION(mbox,which,bailing) \
192 do \ 191 do \
193 { \ 192 { \
...@@ -201,7 +200,7 @@ do \ ...@@ -201,7 +200,7 @@ do \
201 } \ 200 } \
202 } while (0) 201 } while (0)
203 202
204 /* notifications ADD_MESG */ 203 /* Notifications ADD_MESG. */
205 #define DISPATCH_ADD_MSG(mbox,mud) \ 204 #define DISPATCH_ADD_MSG(mbox,mud) \
206 do \ 205 do \
207 { \ 206 { \
...@@ -218,17 +217,12 @@ do \ ...@@ -218,17 +217,12 @@ do \
218 unix_ilock (mbox, MU_LOCKER_WRLOCK); \ 217 unix_ilock (mbox, MU_LOCKER_WRLOCK); \
219 } while (0); 218 } while (0);
220 219
221 /* notification MBX_PROGRESS 220 /* Notification MBX_PROGRESS
222 * We do not want to fire up the progress notification 221 We do not want to fire up the progress notification every line, it will be
223 * every line, it will be too expensive, so we do it 222 too expensive, so we do it arbitrarely every 10 000 Lines.
224 * arbitrarely every 10 000 Lines. 223 FIXME: maybe this should be configurable. */
225 * FIXME: maybe this should be configurable. 224 /* This is more tricky we can not leave the mum struct incomplete. So we
226 */ 225 only tell them about the complete messages. */
227 /*
228 * This is more tricky we can not leave the mum
229 * struct incomplete. So we only tell them about
230 * the complete messages.
231 */
232 #define DISPATCH_PROGRESS(mbox,mud) \ 226 #define DISPATCH_PROGRESS(mbox,mud) \
233 do \ 227 do \
234 { \ 228 { \
...@@ -249,25 +243,7 @@ do \ ...@@ -249,25 +243,7 @@ do \
249 } \ 243 } \
250 } while (0) 244 } while (0)
251 245
252 #if 0 246 /* Allocate slots for the new messages. */
253 /* skip a function call, ?? do we gain that much */
254 #define ATTRIBUTE_CREATE(attr, m, mbox) \
255 do \
256 { \
257 attr = calloc (1, sizeof(*(attr))); \
258 attr->owner = m; \
259 if ((attr) == NULL) \
260 { \
261 unix_iunlock (mbox); \
262 unix_unlock (mbox); \
263 return ENOMEM; \
264 } \
265 } while (0)
266 #else
267 # define ATTRIBUTE_CREATE
268 #endif
269
270 /* allocate slots for the new messages */
271 /* size_t num = 2 * ((mud)->messages_count) + 10; */ 247 /* size_t num = 2 * ((mud)->messages_count) + 10; */
272 #define ALLOCATE_MSGS(mbox,mud) \ 248 #define ALLOCATE_MSGS(mbox,mud) \
273 do \ 249 do \
...@@ -303,7 +279,7 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif) ...@@ -303,7 +279,7 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif)
303 int inheader; 279 int inheader;
304 int inbody; 280 int inbody;
305 off_t total = 0; 281 off_t total = 0;
306 unix_data_t mud; 282 unix_data_t mud = mbox->data;
307 unix_message_t mum = NULL; 283 unix_message_t mum = NULL;
308 int status = 0; 284 int status = 0;
309 size_t lines; 285 size_t lines;
...@@ -313,21 +289,20 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif) ...@@ -313,21 +289,20 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif)
313 int zn, isfrom = 0; 289 int zn, isfrom = 0;
314 char *temp; 290 char *temp;
315 291
316 /* sanity */ 292 /* Sanity. */
317 if (mbox == NULL || 293 if (mud == NULL)
318 (mud = (unix_data_t)mbox->data) == NULL)
319 return EINVAL; 294 return EINVAL;
320 295
321 /* save the timestamp and size */ 296 /* Save the timestamp and size. */
322 status = stream_size (mbox->stream, &(mud->size)); 297 status = stream_size (mbox->stream, &(mud->size));
323 if (status != 0) 298 if (status != 0)
324 return status; 299 return status;
325 300
326 /* grab the locks */ 301 /* Grab the locks. */
327 unix_ilock (mbox, MU_LOCKER_WRLOCK); 302 unix_ilock (mbox, MU_LOCKER_WRLOCK);
328 unix_lock (mbox, MU_LOCKER_RDLOCK); 303 unix_lock (mbox, MU_LOCKER_RDLOCK);
329 304
330 /* seek to the starting point */ 305 /* Seek to the starting point. */
331 if (mud->umessages && msgno > 0 && mud->messages_count > 0 306 if (mud->umessages && msgno > 0 && mud->messages_count > 0
332 && msgno <= mud->messages_count) 307 && msgno <= mud->messages_count)
333 { 308 {
...@@ -352,7 +327,7 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif) ...@@ -352,7 +327,7 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif)
352 VALID(buf, temp, isfrom, zn); 327 VALID(buf, temp, isfrom, zn);
353 isfrom = (isfrom) ? 1 : 0; 328 isfrom = (isfrom) ? 1 : 0;
354 329
355 /* which part of the message are we in ? */ 330 /* Which part of the message are we in ? */
356 inheader = isfrom | ((!nl) & inheader); 331 inheader = isfrom | ((!nl) & inheader);
357 inbody = (!isfrom) & (!inheader); 332 inbody = (!isfrom) & (!inheader);
358 333
...@@ -360,10 +335,10 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif) ...@@ -360,10 +335,10 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif)
360 335
361 if (inheader) 336 if (inheader)
362 { 337 {
363 /* new message */ 338 /* New message. */
364 if (isfrom) 339 if (isfrom)
365 { 340 {
366 /* signal the end of the body */ 341 /* Signal the end of the body. */
367 if (mum && !mum->body_end) 342 if (mum && !mum->body_end)
368 { 343 {
369 mum->body_end = total - n - newline; 344 mum->body_end = total - n - newline;
...@@ -371,7 +346,7 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif) ...@@ -371,7 +346,7 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif)
371 if (do_notif) 346 if (do_notif)
372 DISPATCH_ADD_MSG(mbox, mud); 347 DISPATCH_ADD_MSG(mbox, mud);
373 } 348 }
374 /* allocate_msgs will initialize mum */ 349 /* Allocate_msgs will initialize mum. */
375 ALLOCATE_MSGS(mbox, mud); 350 ALLOCATE_MSGS(mbox, mud);
376 mud->messages_count++; 351 mud->messages_count++;
377 mum = mud->umessages[mud->messages_count - 1]; 352 mum = mud->umessages[mud->messages_count - 1];
...@@ -391,10 +366,10 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif) ...@@ -391,10 +366,10 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif)
391 } 366 }
392 } 367 }
393 368
394 /* body */ 369 /* Body. */
395 if (inbody) 370 if (inbody)
396 { 371 {
397 /* set the body position */ 372 /* Set the body position. */
398 if (mum && !mum->body) 373 if (mum && !mum->body)
399 { 374 {
400 mum->body = total - n + nl; 375 mum->body = total - n + nl;
...@@ -405,11 +380,11 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif) ...@@ -405,11 +380,11 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif)
405 380
406 newline = nl; 381 newline = nl;
407 382
408 /* every 50 mesgs update the lock, it should be every minute */ 383 /* Every 50 mesgs update the lock, it should be every minute. */
409 if ((mud->messages_count % 50) == 0) 384 if ((mud->messages_count % 50) == 0)
410 unix_touchlock (mbox); 385 unix_touchlock (mbox);
411 386
412 /* ping them every 1000 lines */ 387 /* Ping them every 1000 lines. */
413 if (do_notif) 388 if (do_notif)
414 if (((lines +1) % 1000) == 0) 389 if (((lines +1) % 1000) == 0)
415 DISPATCH_PROGRESS(mbox, mud); 390 DISPATCH_PROGRESS(mbox, mud);
...@@ -429,4 +404,3 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif) ...@@ -429,4 +404,3 @@ unix_scan0 (mailbox_t mbox, size_t msgno, size_t *pcount, int do_notif)
429 *pcount = mud->messages_count; 404 *pcount = mud->messages_count;
430 return status; 405 return status;
431 } 406 }
432
......
...@@ -27,6 +27,7 @@ ...@@ -27,6 +27,7 @@
27 #include <time.h> 27 #include <time.h>
28 #include <string.h> 28 #include <string.h>
29 29
30 /* FIXME: This should be part of the address_t object when implemented. */
30 static int extract_addr(const char *s, size_t n, char **presult, 31 static int extract_addr(const char *s, size_t n, char **presult,
31 size_t *pnwrite); 32 size_t *pnwrite);
32 static int message_read (stream_t is, char *buf, size_t buflen, 33 static int message_read (stream_t is, char *buf, size_t buflen,
...@@ -35,6 +36,7 @@ static int message_write (stream_t os, const char *buf, size_t buflen, ...@@ -35,6 +36,7 @@ static int message_write (stream_t os, const char *buf, size_t buflen,
35 off_t off, size_t *pnwrite); 36 off_t off, size_t *pnwrite);
36 static int message_get_fd (stream_t stream, int *pfd); 37 static int message_get_fd (stream_t stream, int *pfd);
37 38
39 /* Allocate ressources for the message_t. */
38 int 40 int
39 message_create (message_t *pmsg, void *owner) 41 message_create (message_t *pmsg, void *owner)
40 { 42 {
...@@ -59,31 +61,45 @@ message_destroy (message_t *pmsg, void *owner) ...@@ -59,31 +61,45 @@ message_destroy (message_t *pmsg, void *owner)
59 61
60 if (msg->owner == owner) 62 if (msg->owner == owner)
61 { 63 {
62 /* notify the listeners */ 64 /* Notify the listeners. */
65 /* FIXME: to be removed since we do not supoort this event. */
63 if (msg->event_num) 66 if (msg->event_num)
64 { 67 {
65 message_notification (msg, MU_EVT_MSG_DESTROY); 68 message_notification (msg, MU_EVT_MSG_DESTROY);
66 free (msg->event); 69 free (msg->event);
67 } 70 }
68 /* header */ 71
69 header_destroy (&(msg->header), owner); 72 /* Header. */
70 /* attribute */ 73 if (msg->header)
71 attribute_destroy (&(msg->attribute), owner); 74 header_destroy (&(msg->header), owner);
72 /* stream */ 75 if (msg->header)
73 stream_destroy (&(msg->stream), owner); 76 header_destroy (&(msg->header), msg);
74 77
75 /* if sometype of floating/temporary message */ 78 /* Attribute. */
76 body_destroy (&(msg->body), owner); 79 if (msg->attribute)
77 /* notifications are done */ 80 attribute_destroy (&(msg->attribute), owner);
78 81 if (msg->attribute)
79 /* check again for resurrection before free()ing 82 attribute_destroy (&(msg->attribute), msg);
80 * the memory maybe it was clone, if yes we can not 83
81 * free the pointer. 84 /* Stream. */
82 * 85 if (msg->stream)
83 */ 86 stream_destroy (&(msg->stream), owner);
87 if (msg->stream)
88 stream_destroy (&(msg->stream), msg);
89
90 /* Body. */
91 if (msg->body)
92 body_destroy (&(msg->body), owner);
93 if (msg->body)
94 body_destroy (&(msg->body), msg);
95
96 /* Mime. */
97 if (msg->mime)
98 mime_destroy (&(msg->mime));
99
84 free (msg); 100 free (msg);
85 } 101 }
86 /* loose the link */ 102 /* Loose the link */
87 *pmsg = NULL; 103 *pmsg = NULL;
88 } 104 }
89 } 105 }
...@@ -94,8 +110,8 @@ message_get_header (message_t msg, header_t *phdr) ...@@ -94,8 +110,8 @@ message_get_header (message_t msg, header_t *phdr)
94 if (msg == NULL || phdr == NULL) 110 if (msg == NULL || phdr == NULL)
95 return EINVAL; 111 return EINVAL;
96 112
97 /* is it a floating mesg */ 113 /* Is it a floating mesg */
98 if (msg->header == NULL && msg->owner == NULL) 114 if (msg->header == NULL)
99 { 115 {
100 header_t header; 116 header_t header;
101 int status = header_create (&header, NULL, 0, msg); 117 int status = header_create (&header, NULL, 0, msg);
...@@ -114,8 +130,9 @@ message_set_header (message_t msg, header_t hdr, void *owner) ...@@ -114,8 +130,9 @@ message_set_header (message_t msg, header_t hdr, void *owner)
114 return EINVAL; 130 return EINVAL;
115 if (msg->owner != owner) 131 if (msg->owner != owner)
116 return EACCES; 132 return EACCES;
117 /* make sure we destoy the old if it was own by the mesg */ 133 /* Make sure we destoy the old if it was own by the mesg */
118 header_destroy (&(msg->header), msg); 134 /* FIXME: I do not know if somebody has already a ref on this ? */
135 /* header_destroy (&(msg->header), msg); */
119 msg->header = hdr; 136 msg->header = hdr;
120 return 0; 137 return 0;
121 } 138 }
...@@ -126,7 +143,7 @@ message_get_body (message_t msg, body_t *pbody) ...@@ -126,7 +143,7 @@ message_get_body (message_t msg, body_t *pbody)
126 if (msg == NULL || pbody == NULL) 143 if (msg == NULL || pbody == NULL)
127 return EINVAL; 144 return EINVAL;
128 145
129 /* is it a floating mesg */ 146 /* Is it a floating mesg. */
130 if (msg->body == NULL) 147 if (msg->body == NULL)
131 { 148 {
132 body_t body; 149 body_t body;
...@@ -146,8 +163,9 @@ message_set_body (message_t msg, body_t body, void *owner) ...@@ -146,8 +163,9 @@ message_set_body (message_t msg, body_t body, void *owner)
146 return EINVAL; 163 return EINVAL;
147 if (msg->owner != owner) 164 if (msg->owner != owner)
148 return EACCES; 165 return EACCES;
149 /* make sure we destoy the old if it was own by the mesg */ 166 /* Make sure we destoy the old if it was own by the mesg. */
150 body_destroy (&(msg->body), msg); 167 /* FIXME: I do not know if somebody has already a ref on this ? */
168 /* body_destroy (&(msg->body), msg); */
151 msg->body = body; 169 msg->body = body;
152 return 0; 170 return 0;
153 } 171 }
...@@ -205,7 +223,7 @@ message_lines (message_t msg, size_t *plines) ...@@ -205,7 +223,7 @@ message_lines (message_t msg, size_t *plines)
205 size_t hlines, blines; 223 size_t hlines, blines;
206 if (msg == NULL) 224 if (msg == NULL)
207 return EINVAL; 225 return EINVAL;
208 /* Overload */ 226 /* Overload. */
209 if (msg->_lines) 227 if (msg->_lines)
210 return msg->_lines (msg, plines); 228 return msg->_lines (msg, plines);
211 if (plines) 229 if (plines)
...@@ -272,11 +290,11 @@ message_from (message_t msg, char *buf, size_t len, size_t *pnwrite) ...@@ -272,11 +290,11 @@ message_from (message_t msg, char *buf, size_t len, size_t *pnwrite)
272 if (msg == NULL) 290 if (msg == NULL)
273 return EINVAL; 291 return EINVAL;
274 292
275 /* did they provide a way to get it */ 293 /* Did they provide a way to get it ? */
276 if (msg->_from) 294 if (msg->_from)
277 return msg->_from (msg, buf, len, pnwrite); 295 return msg->_from (msg, buf, len, pnwrite);
278 296
279 /* can it be extracted from the From: */ 297 /* Can it be extracted from the From: */
280 message_get_header (msg, &header); 298 message_get_header (msg, &header);
281 status = header_get_value (header, MU_HEADER_FROM, NULL, 0, &n); 299 status = header_get_value (header, MU_HEADER_FROM, NULL, 0, &n);
282 if (status == 0 && n != 0) 300 if (status == 0 && n != 0)
...@@ -335,14 +353,14 @@ message_received (message_t msg, char *buf, size_t len, size_t *pnwrite) ...@@ -335,14 +353,14 @@ message_received (message_t msg, char *buf, size_t len, size_t *pnwrite)
335 size_t n; 353 size_t n;
336 if (msg == NULL) 354 if (msg == NULL)
337 return EINVAL; 355 return EINVAL;
338 /* is it provided */ 356 /* Is it provided ? */
339 if (msg->_received) 357 if (msg->_received)
340 return msg->_received (msg, buf, len, pnwrite); 358 return msg->_received (msg, buf, len, pnwrite);
341 359
342 /* FIXME: extract the time from "Date:" */ 360 /* FIXME: extract the time from "Date:". */
343 361
344 /* catch all */ 362 /* Catch all. */
345 /* FIXME: ctime() is not thread safe use strftime() */ 363 /* FIXME: ctime() is not thread safe use strftime(). */
346 t = time (NULL); 364 t = time (NULL);
347 n = strlen (ctime (&t)); 365 n = strlen (ctime (&t));
348 366
...@@ -406,7 +424,7 @@ message_get_uidl (message_t msg, char *buffer, size_t buflen, size_t *pwritten) ...@@ -406,7 +424,7 @@ message_get_uidl (message_t msg, char *buffer, size_t buflen, size_t *pwritten)
406 424
407 int 425 int
408 message_set_uidl (message_t msg, int (* _get_uidl) 426 message_set_uidl (message_t msg, int (* _get_uidl)
409 __P ((message_t msg, char *buffer, size_t buflen, size_t *pwritten)), void *owner) 427 __P ((message_t, char *, size_t, size_t *)), void *owner)
410 { 428 {
411 if (msg == NULL) 429 if (msg == NULL)
412 return EINVAL; 430 return EINVAL;
...@@ -527,7 +545,7 @@ message_register (message_t msg, size_t type, ...@@ -527,7 +545,7 @@ message_register (message_t msg, size_t type,
527 if (msg == NULL || action == NULL || type == 0) 545 if (msg == NULL || action == NULL || type == 0)
528 return EINVAL; 546 return EINVAL;
529 547
530 /* find a free spot */ 548 /* Find a free spot. */
531 for (i = 0; i < msg->event_num; i++) 549 for (i = 0; i < msg->event_num; i++)
532 { 550 {
533 event = &(msg->event[i]); 551 event = &(msg->event[i]);
...@@ -633,7 +651,7 @@ message_write (stream_t os, const char *buf, size_t buflen, ...@@ -633,7 +651,7 @@ message_write (stream_t os, const char *buf, size_t buflen,
633 if (os == NULL || (msg = os->owner) == NULL) 651 if (os == NULL || (msg = os->owner) == NULL)
634 return EINVAL; 652 return EINVAL;
635 653
636 /* skip the obvious */ 654 /* Skip the obvious. */
637 if (buf == NULL || *buf == '\0' || buflen == 0) 655 if (buf == NULL || *buf == '\0' || buflen == 0)
638 { 656 {
639 if (pnwrite) 657 if (pnwrite)
...@@ -649,7 +667,7 @@ message_write (stream_t os, const char *buf, size_t buflen, ...@@ -649,7 +667,7 @@ message_write (stream_t os, const char *buf, size_t buflen,
649 while (!msg->hdr_done && (nl = memchr (buf, '\n', buflen)) != NULL) 667 while (!msg->hdr_done && (nl = memchr (buf, '\n', buflen)) != NULL)
650 { 668 {
651 len = nl - buf + 1; 669 len = nl - buf + 1;
652 /* allocate more buffer to hold the header */ 670 /* Allocate more buffer to hold the header. */
653 thdr = realloc (msg->hdr_buf, msg->hdr_buflen + len); 671 thdr = realloc (msg->hdr_buf, msg->hdr_buflen + len);
654 if (thdr == NULL) 672 if (thdr == NULL)
655 { 673 {
...@@ -662,8 +680,8 @@ message_write (stream_t os, const char *buf, size_t buflen, ...@@ -662,8 +680,8 @@ message_write (stream_t os, const char *buf, size_t buflen,
662 msg->hdr_buf = thdr; 680 msg->hdr_buf = thdr;
663 memcpy (msg->hdr_buf + msg->hdr_buflen, buf, len); 681 memcpy (msg->hdr_buf + msg->hdr_buflen, buf, len);
664 msg->hdr_buflen += len; 682 msg->hdr_buflen += len;
665 /* we detect an empty line .i.e "^\n$" this signal the end 683 /* We detect an empty line .i.e "^\n$" this signal the end of the
666 * of the header */ 684 header. */
667 if (buf == nl) 685 if (buf == nl)
668 { 686 {
669 header_destroy (&(msg->header), msg); 687 header_destroy (&(msg->header), msg);
...@@ -683,7 +701,7 @@ message_write (stream_t os, const char *buf, size_t buflen, ...@@ -683,7 +701,7 @@ message_write (stream_t os, const char *buf, size_t buflen,
683 } 701 }
684 } 702 }
685 703
686 /* message header is not complete but was not a full line */ 704 /* Message header is not complete but was not a full line. */
687 if (!msg->hdr_done && buflen > 0) 705 if (!msg->hdr_done && buflen > 0)
688 { 706 {
689 char *thdr = realloc (msg->hdr_buf, msg->hdr_buflen + buflen); 707 char *thdr = realloc (msg->hdr_buf, msg->hdr_buflen + buflen);
...@@ -700,7 +718,7 @@ message_write (stream_t os, const char *buf, size_t buflen, ...@@ -700,7 +718,7 @@ message_write (stream_t os, const char *buf, size_t buflen,
700 msg->hdr_buflen += buflen; 718 msg->hdr_buflen += buflen;
701 buflen = 0; 719 buflen = 0;
702 } 720 }
703 else if (buflen > 0) /* in the body */ 721 else if (buflen > 0) /* In the body. */
704 { 722 {
705 stream_t bs; 723 stream_t bs;
706 body_t body; 724 body_t body;
...@@ -735,11 +753,12 @@ message_get_fd (stream_t stream, int *pfd) ...@@ -735,11 +753,12 @@ message_get_fd (stream_t stream, int *pfd)
735 if (stream == NULL || (msg = stream->owner) == NULL) 753 if (stream == NULL || (msg = stream->owner) == NULL)
736 return EINVAL; 754 return EINVAL;
737 755
738 /* Probably being lazy, then create a body for the stream */ 756 /* Probably being lazy, then create a body for the stream. */
739 if (msg->body == NULL) 757 if (msg->body == NULL)
740 { 758 {
741 int status = body_create (&body, msg); 759 int status = body_create (&body, msg);
742 if (status != 0 ) 760 if (status != 0 )
761
743 return status; 762 return status;
744 msg->body = body; 763 msg->body = body;
745 } 764 }
...@@ -758,7 +777,7 @@ extract_addr (const char *s, size_t n, char **presult, size_t *pnwrite) ...@@ -758,7 +777,7 @@ extract_addr (const char *s, size_t n, char **presult, size_t *pnwrite)
758 if (s == NULL || n == 0 || presult == NULL) 777 if (s == NULL || n == 0 || presult == NULL)
759 return EINVAL; 778 return EINVAL;
760 779
761 /* skip the double quotes */ 780 /* Skip the double quotes. */
762 p = memchr (s, '\"', n); 781 p = memchr (s, '\"', n);
763 if (p != NULL) 782 if (p != NULL)
764 { 783 {
...@@ -775,7 +794,7 @@ extract_addr (const char *s, size_t n, char **presult, size_t *pnwrite) ...@@ -775,7 +794,7 @@ extract_addr (const char *s, size_t n, char **presult, size_t *pnwrite)
775 } 794 }
776 } 795 }
777 796
778 /* <name@hostname> ?? */ 797 /* <name@hostname> ?? */
779 p = memchr (s, '<', n); 798 p = memchr (s, '<', n);
780 if (p != NULL) 799 if (p != NULL)
781 { 800 {
...@@ -785,7 +804,7 @@ extract_addr (const char *s, size_t n, char **presult, size_t *pnwrite) ...@@ -785,7 +804,7 @@ extract_addr (const char *s, size_t n, char **presult, size_t *pnwrite)
785 p2 = memchr (p, ' ', p1 - p); 804 p2 = memchr (p, ' ', p1 - p);
786 if (p2 == NULL) 805 if (p2 == NULL)
787 { 806 {
788 /* the NULL is already accounted for */ 807 /* The NULL is already accounted for. */
789 *presult = calloc (1, p1 - p); 808 *presult = calloc (1, p1 - p);
790 if (*presult == NULL) 809 if (*presult == NULL)
791 return ENOMEM; 810 return ENOMEM;
...@@ -796,7 +815,7 @@ extract_addr (const char *s, size_t n, char **presult, size_t *pnwrite) ...@@ -796,7 +815,7 @@ extract_addr (const char *s, size_t n, char **presult, size_t *pnwrite)
796 } 815 }
797 } 816 }
798 } 817 }
799 /* name@domain */ 818 /* name@domain */
800 p = memchr (s, '@', n); 819 p = memchr (s, '@', n);
801 if (p != NULL) 820 if (p != NULL)
802 { 821 {
......