Commit 3f5059d8 3f5059d80eca4eace1d79a9f41c4d2ea75b8f551 by Alain Magloire

mailbox.c mailbox.h mailboxi.c mbx_imap.c mbx_mbox.c

 	mbx_mdir.c mbx_mmdf.c mbx_pop.c mbx_unix.c

introduce an implementation of mbx_unix
1 parent 1918e4dd
1 /* GNU mailutils - a suite of utilities for electronic mail 1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999 Free Software Foundation, Inc. 2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3 3
4 This program is free software; you can redistribute it and/or modify 4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Library Public License as published by 5 it under the terms of the GNU General Library Public License as published by
...@@ -31,49 +31,62 @@ ...@@ -31,49 +31,62 @@
31 31
32 /* forward prototypes */ 32 /* forward prototypes */
33 static int mbx_open (mailbox_t, int flag); 33 static int mbx_open (mailbox_t, int flag);
34 static int mbx_close (mailbox_t, int flag); 34 static int mbx_close (mailbox_t);
35 35
36 /* name */ 36 /* name */
37 static int mbx_get_name (mailbox_t, int *id, char *name, int offset, int n); 37 static int mbx_get_name (mailbox_t, int *id, char *name,
38 size_t len, size_t *n);
39 static int mbx_get_mname (mailbox_t mbox, int *id, char **name, size_t *n);
38 40
39 /* passwd */ 41 /* passwd */
40 static int mbx_get_passwd (mailbox_t, char *passwd, int offset, int len); 42 static int mbx_get_passwd (mailbox_t, char *passwd, size_t, size_t *);
41 static int mbx_get_mpasswd (mailbox_t, char **passwd, int *len); 43 static int mbx_get_mpasswd (mailbox_t, char **passwd, size_t *len);
42 static int mbx_set_passwd (mailbox_t, const char *passwd, int offset, int n); 44 static int mbx_set_passwd (mailbox_t, const char *passwd, size_t len);
43 45
44 /* deleting */ 46 /* deleting */
45 static int mbx_delete (mailbox_t, int id); 47 static int mbx_delete (mailbox_t, size_t msgno);
46 static int mbx_undelete (mailbox_t, int id); 48 static int mbx_undelete (mailbox_t, size_t msgno);
47 static int mbx_expunge (mailbox_t); 49 static int mbx_expunge (mailbox_t);
48 static int mbx_is_deleted (mailbox_t, int id); 50 static int mbx_is_deleted (mailbox_t, size_t msgno);
49 51
50 /* appending */ 52 /* appending */
51 static int mbx_new_msg (mailbox_t, int *id); 53 static int mbx_new_msg (mailbox_t, size_t *msgno);
52 static int mbx_set_header (mailbox_t, int id, const char *h, 54 static int mbx_set_header (mailbox_t, size_t msgno, const char *h,
53 int offset, int n, int replace); 55 size_t n, int replace);
54 static int mbx_set_body (mailbox_t, int id, const char *b, 56 static int mbx_set_body (mailbox_t, size_t msgno, const char *b,
55 int offset, int n, int replace); 57 size_t n, int replace);
56 static int mbx_append (mailbox_t, int id); 58 static int mbx_append (mailbox_t, size_t msgno);
57 static int mbx_destroy_msg (mailbox_t, int id); 59 static int mbx_destroy_msg (mailbox_t, size_t msgno);
58 60
59 /* reading */ 61 /* reading */
60 static int mbx_get_body (mailbox_t, int id, char *b, int offset, int n); 62 static int mbx_get_body (mailbox_t, size_t msgno, off_t off,
61 static int mbx_get_mbody (mailbox_t, int id, char **b, int *n); 63 char *b, size_t len, size_t *n);
62 static int mbx_get_header (mailbox_t, int id, char *h, int offset, int n); 64 static int mbx_get_mbody (mailbox_t, size_t msgno, off_t off,
63 static int mbx_get_mheader (mailbox_t, int id, char **h, int *n); 65 char **b, size_t *n);
66 static int mbx_get_header (mailbox_t, size_t msgno, off_t off,
67 char *h, size_t len, size_t *n);
68 static int mbx_get_mheader (mailbox_t, size_t msgno, off_t off,
69 char **h, size_t *n);
64 70
65 /* locking */ 71 /* locking */
66 static int mbx_lock (mailbox_t, int flag); 72 static int mbx_lock (mailbox_t, int flag);
67 static int mbx_unlock (mailbox_t); 73 static int mbx_unlock (mailbox_t);
68 74 //static int mbx_ilock (mailbox_t, int flag);
75 //static int mbx_iunlock (mailbox_t);
76
77 /* owner and group */
78 static int mbx_set_owner (mailbox_t, uid_t uid);
79 static int mbx_get_owner (mailbox_t, uid_t *uid);
80 static int mbx_set_group (mailbox_t, uid_t gid);
81 static int mbx_get_group (mailbox_t, uid_t *gid);
69 /* misc */ 82 /* misc */
70 static int mbx_scan (mailbox_t, int *msgs); 83 static int mbx_scan (mailbox_t, size_t *msgs);
71 static int mbx_is_updated (mailbox_t); 84 static int mbx_is_updated (mailbox_t);
72 static int mbx_get_timeout (mailbox_t, int *timeout); 85 static int mbx_get_timeout (mailbox_t, size_t *timeout);
73 static int mbx_set_timeout (mailbox_t, int timeout); 86 static int mbx_set_timeout (mailbox_t, size_t timeout);
74 static int mbx_get_refresh (mailbox_t, int *refresh); 87 static int mbx_get_refresh (mailbox_t, size_t *refresh);
75 static int mbx_set_refresh (mailbox_t, int refresh); 88 static int mbx_set_refresh (mailbox_t, size_t refresh);
76 static int mbx_get_size (mailbox_t, int id, size_t *size); 89 static int mbx_get_size (mailbox_t, size_t msgno, size_t *sh, size_t *sb);
77 static int mbx_set_notification (mailbox_t, 90 static int mbx_set_notification (mailbox_t,
78 int (*func) (mailbox_t, void *arg)); 91 int (*func) (mailbox_t, void *arg));
79 92
...@@ -101,17 +114,18 @@ static struct mailbox_builtin ...@@ -101,17 +114,18 @@ static struct mailbox_builtin
101 }; 114 };
102 115
103 int 116 int
104 malibox_add_type (struct mailbox_type *mtype) 117 mailbox_add_type (struct mailbox_type *mtype)
105 { 118 {
106 struct mailbox_builtin *current = malloc (sizeof (*current)); 119 struct mailbox_builtin *current = malloc (sizeof (*current));
107 if (current == NULL) 120 if (current == NULL)
108 return -1; 121 return ENOMEM;
109 if (mtype->utype) 122 if (mtype->utype)
110 { 123 {
111 if (url_add_type (mtype->utype) < 0) 124 int status = url_add_type (mtype->utype);
125 if (status != 0)
112 { 126 {
113 free (current); 127 free (current);
114 return -1; 128 return status;
115 } 129 }
116 mtype->id = mtype->utype->id; /* same ID as the url_type */ 130 mtype->id = mtype->utype->id; /* same ID as the url_type */
117 } 131 }
...@@ -142,37 +156,48 @@ mailbox_remove_type (struct mailbox_type *mtype) ...@@ -142,37 +156,48 @@ mailbox_remove_type (struct mailbox_type *mtype)
142 return 0;; 156 return 0;;
143 } 157 }
144 } 158 }
145 return -1; 159 return EINVAL;
146 } 160 }
147 161
148 int 162 int
149 mailbox_list_type (struct mailbox_type *list, int n) 163 mailbox_list_type (struct mailbox_type *list, size_t len, size_t *n)
150 { 164 {
151 struct mailbox_builtin *current; 165 struct mailbox_builtin *current;
152 int i; 166 size_t i;
153 for (i = 0, current = mailbox_builtin->next; current != mailbox_builtin; 167 for (i = 0, current = mailbox_builtin->next; current != mailbox_builtin;
154 current = current->next, i++) 168 current = current->next, i++)
155 { 169 {
156 if (list) 170 if (list)
157 if (i < n) 171 if (i < len)
158 list[i] = *(current->mtype); 172 list[i] = *(current->mtype);
159 } 173 }
160 return i; 174 if (n)
175 *n = i;
176 return 0;
161 } 177 }
162 178
163 int 179 int
164 mailbox_list_mtype (struct mailbox_type **mlist, int *n) 180 mailbox_list_mtype (struct mailbox_type **mlist, size_t *n)
165 { 181 {
166 struct mailbox_type *mtype; 182 struct mailbox_type *mtype;
167 int i; 183 size_t i = 0;
168 184
169 if ((i = mailbox_list_type (NULL, 0)) <= 0 185 mailbox_list_type (NULL, 0, &i);
170 || (mtype = calloc (i, sizeof (*mtype))) == NULL) 186 if (i == 0)
171 { 187 {
172 return -1; 188 if (n)
189 {
190 *n = i;
191 }
192 return 0;
193 }
194 mtype = calloc (i, sizeof (*mtype));
195 if (mtype == NULL)
196 {
197 return ENOMEM;
173 } 198 }
174 *mlist = mtype; 199 *mlist = mtype;
175 return *n = mailbox_list_type (mtype, i); 200 return *n = mailbox_list_type (mtype, i, n);
176 } 201 }
177 202
178 int 203 int
...@@ -188,14 +213,14 @@ mailbox_get_type (struct mailbox_type **mtype, int id) ...@@ -188,14 +213,14 @@ mailbox_get_type (struct mailbox_type **mtype, int id)
188 return 0;; 213 return 0;;
189 } 214 }
190 } 215 }
191 return -1; 216 return EINVAL;
192 } 217 }
193 218
194 219
195 int 220 int
196 mailbox_init (mailbox_t *mbox, const char *name, int id) 221 mailbox_init (mailbox_t *mbox, const char *name, int id)
197 { 222 {
198 int status = -1; /* -1 means error */ 223 int status = EINVAL;
199 224
200 /* 1st run: if they know what they want, shortcut */ 225 /* 1st run: if they know what they want, shortcut */
201 if (id) 226 if (id)
...@@ -262,6 +287,9 @@ mbx_check_struct (mailbox_t mbox) ...@@ -262,6 +287,9 @@ mbx_check_struct (mailbox_t mbox)
262 if (mbox->_get_name == NULL) 287 if (mbox->_get_name == NULL)
263 mbox->_get_name = mbx_get_name; 288 mbox->_get_name = mbx_get_name;
264 289
290 if (mbox->_get_mname == NULL)
291 mbox->_get_mname = mbx_get_mname;
292
265 if (mbox->_get_passwd == NULL) 293 if (mbox->_get_passwd == NULL)
266 mbox->_get_passwd = mbx_get_passwd; 294 mbox->_get_passwd = mbx_get_passwd;
267 295
...@@ -316,12 +344,30 @@ mbx_check_struct (mailbox_t mbox) ...@@ -316,12 +344,30 @@ mbx_check_struct (mailbox_t mbox)
316 if (mbox->_unlock == NULL) 344 if (mbox->_unlock == NULL)
317 mbox->_unlock = mbx_unlock; 345 mbox->_unlock = mbx_unlock;
318 346
347 if (mbox->_ilock == NULL)
348 mbox->_ilock = mbx_lock;
349
350 if (mbox->_iunlock == NULL)
351 mbox->_iunlock = mbx_unlock;
352
319 if (mbox->_scan == NULL) 353 if (mbox->_scan == NULL)
320 mbox->_scan = mbx_scan; 354 mbox->_scan = mbx_scan;
321 355
322 if (mbox->_is_updated == NULL) 356 if (mbox->_is_updated == NULL)
323 mbox->_is_updated = mbx_is_updated; 357 mbox->_is_updated = mbx_is_updated;
324 358
359 if (mbox->_set_owner == NULL)
360 mbox->_set_owner = mbx_set_owner;
361
362 if (mbox->_get_owner == NULL)
363 mbox->_get_owner = mbx_get_owner;
364
365 if (mbox->_set_group == NULL)
366 mbox->_set_group = mbx_set_group;
367
368 if (mbox->_get_group == NULL)
369 mbox->_get_group = mbx_get_group;
370
325 if (mbox->_get_timeout == NULL) 371 if (mbox->_get_timeout == NULL)
326 mbox->_get_timeout = mbx_get_timeout; 372 mbox->_get_timeout = mbx_get_timeout;
327 373
...@@ -346,233 +392,259 @@ mbx_check_struct (mailbox_t mbox) ...@@ -346,233 +392,259 @@ mbx_check_struct (mailbox_t mbox)
346 static int 392 static int
347 mbx_open (mailbox_t mbox, int flag) 393 mbx_open (mailbox_t mbox, int flag)
348 { 394 {
349 errno = ENOSYS; 395 return ENOSYS;
350 return -1;
351 } 396 }
352 397
353 static int 398 static int
354 mbx_close (mailbox_t mbox, int flag) 399 mbx_close (mailbox_t mbox)
355 { 400 {
356 errno = ENOSYS; 401 return ENOSYS;
357 return -1;
358 } 402 }
359 403
360 /* name */ 404 /* name */
361 static int 405 static int
362 mbx_get_name (mailbox_t mbox, int *id, char *name, int offset, int n) 406 mbx_get_name (mailbox_t mbox, int *id, char *name, size_t len, size_t *n)
407 {
408 return ENOSYS;
409 }
410 static int
411 mbx_get_mname (mailbox_t mbox, int *id, char **name, size_t *n)
363 { 412 {
364 errno = ENOSYS; 413 size_t i = 0;
365 return -1; 414 mbox->_get_name (mbox, id, 0, 0, &i);
415 i++;
416 *name = calloc (i, sizeof (char));
417 if (*name == NULL)
418 {
419 return ENOMEM;
420 }
421 mbox->_get_name (mbox, id, *name, i, n);
422 return 0;
366 } 423 }
367 424
368 /* passwd */ 425 /* passwd */
369 static int 426 static int
370 mbx_get_passwd (mailbox_t mbox, char *passwd, int offset, int len) 427 mbx_get_passwd (mailbox_t mbox, char *passwd, size_t len, size_t *n)
371 { 428 {
372 errno = ENOSYS; 429 return ENOSYS;
373 return -1;
374 } 430 }
375 431
376 static int 432 static int
377 mbx_get_mpasswd (mailbox_t mbox, char **passwd, int *len) 433 mbx_get_mpasswd (mailbox_t mbox, char **passwd, size_t *n)
378 { 434 {
379 int i; 435 size_t i = 0;
380 char *p; 436 mbox->_get_passwd (mbox, NULL, 0, &i);
381 if ((i = mbox->_get_passwd (mbox, NULL, 0, 0)) <= 0 437 i++;
382 || (p = calloc (i, sizeof (*p))) == NULL) 438 *passwd = calloc (i, sizeof (char));
439 if (*passwd == NULL)
383 { 440 {
384 return -1; 441 return ENOMEM;
385 } 442 }
386 *passwd = p; 443 mbox->_get_passwd (mbox, *passwd, i, n);
387 return *len = i; 444 return 0;
388 } 445 }
389 446
390 static int 447 static int
391 mbx_set_passwd (mailbox_t mbox, const char *passwd, int offset, int n) 448 mbx_set_passwd (mailbox_t mbox, const char *passwd, size_t len)
392 { 449 {
393 errno = ENOSYS; 450 return ENOSYS;
394 return -1;
395 } 451 }
396 452
397 /* deleting */ 453 /* deleting */
398 static int 454 static int
399 mbx_delete (mailbox_t mbox, int id) 455 mbx_delete (mailbox_t mbox, size_t msgno)
400 { 456 {
401 errno = ENOSYS; 457 return ENOSYS;
402 return -1;
403 } 458 }
404 459
405 static int 460 static int
406 mbx_undelete (mailbox_t mbox, int id) 461 mbx_undelete (mailbox_t mbox, size_t msgno)
407 { 462 {
408 errno = ENOSYS; 463 return ENOSYS;
409 return -1;
410 } 464 }
411 465
412 static int 466 static int
413 mbx_expunge (mailbox_t mbox) 467 mbx_expunge (mailbox_t mbox)
414 { 468 {
415 errno = ENOSYS; 469 return ENOSYS;
416 return -1;
417 } 470 }
418 471
419 static int 472 static int
420 mbx_is_deleted (mailbox_t mbox, int id) 473 mbx_is_deleted (mailbox_t mbox, size_t msgno)
421 { 474 {
422 errno = ENOSYS; 475 return ENOSYS;
423 return -1;
424 } 476 }
425 477
426 478
427 /* appending */ 479 /* appending */
428 static int 480 static int
429 mbx_new_msg (mailbox_t mbox, int *id) 481 mbx_new_msg (mailbox_t mbox, size_t *msgno)
430 { 482 {
431 errno = ENOSYS; 483 return ENOSYS;
432 return -1;
433 } 484 }
434 485
435 static int 486 static int
436 mbx_set_header (mailbox_t mbox, int id, const char *h, 487 mbx_set_header (mailbox_t mbox, size_t msgno, const char *h,
437 int offset, int n, int replace) 488 size_t len, int replace)
438 { 489 {
439 errno = ENOSYS; 490 return ENOSYS;
440 return -1;
441 } 491 }
442 492
443 static int 493 static int
444 mbx_set_body (mailbox_t mbox, int id, const char *b, 494 mbx_set_body (mailbox_t mbox, size_t msgno, const char *b,
445 int offset, int n, int replace) 495 size_t len, int replace)
446 { 496 {
447 errno = ENOSYS; 497 return ENOSYS;
448 return -1;
449 } 498 }
450 499
451 static int 500 static int
452 mbx_append (mailbox_t mbox, int id) 501 mbx_append (mailbox_t mbox, size_t msgno)
453 { 502 {
454 errno = ENOSYS; 503 return ENOSYS;
455 return -1;
456 } 504 }
457 505
458 static int 506 static int
459 mbx_destroy_msg (mailbox_t mbox, int id) 507 mbx_destroy_msg (mailbox_t mbox, size_t msgno)
460 { 508 {
461 errno = ENOSYS; 509 return ENOSYS;
462 return -1;
463 } 510 }
464 511
465 /* reading */ 512 /* reading */
466 static int 513 static int
467 mbx_get_body (mailbox_t mbox, int id, char *b, int offset, int n) 514 mbx_get_body (mailbox_t mbox, size_t msgno, off_t off,
515 char *b, size_t len, size_t *n)
468 { 516 {
469 errno = ENOSYS; 517 return ENOSYS;
470 return -1;
471 } 518 }
472 519
473 static int 520 static int
474 mbx_get_mbody (mailbox_t mbox, int id, char **body, int *len) 521 mbx_get_mbody (mailbox_t mbox, size_t msgno, off_t off,
475 { 522 char **body, size_t *n)
476 int i; 523 {
477 char *b; 524 size_t i = 0;
478 if ((i = mbox->_get_body (mbox, id, NULL, 0, 0)) <= 0 525 mbox->_get_body (mbox, msgno, off, NULL, 0, &i);
479 || (b = calloc (i, sizeof (*b))) == NULL) 526 i++;
527 *body = calloc (i, sizeof (char));
528 if (*body == NULL)
480 { 529 {
481 return -1; 530 return ENOMEM;
482 } 531 }
483 *body = b; 532 mbox->_get_body (mbox, msgno, off, *body, i, n);
484 return *len = i; 533 return 0;
485 } 534 }
486 535
487 static int 536 static int
488 mbx_get_header (mailbox_t mbox, int id, char *h, int offset, int n) 537 mbx_get_header (mailbox_t mbox, size_t msgno, off_t off,
538 char *h, size_t len, size_t *n)
489 { 539 {
490 errno = ENOSYS; 540 return ENOSYS;
491 return -1;
492 } 541 }
493 542
494 static int 543 static int
495 mbx_get_mheader (mailbox_t mbox, int id, char **header, int *len) 544 mbx_get_mheader (mailbox_t mbox, size_t msgno, off_t off,
496 { 545 char **header, size_t *n)
497 int i; 546 {
498 char *h; 547 size_t i;
499 if ((i = mbox->_get_header (mbox, id, NULL, 0, 0)) <= 0 548 i = mbox->_get_header (mbox, msgno, off, NULL, 0, &i);
500 || (h = calloc (i, sizeof (*h))) == NULL) 549 i++;
550 *header = calloc (i, sizeof (char));
551 if (*header == NULL)
501 { 552 {
502 return -1; 553 return ENOMEM;
503 } 554 }
504 *header = h; 555 mbox->_get_header (mbox, msgno, off, *header, i, n);
505 return *len = i; 556 return 0;
506 } 557 }
507 558
508 /* locking */ 559 /* locking */
509 static int 560 static int
510 mbx_lock (mailbox_t mbox, int flag) 561 mbx_lock (mailbox_t mbox, int flag)
511 { 562 {
512 errno = ENOSYS; 563 return ENOSYS;
513 return -1;
514 } 564 }
515 565
516 static int 566 static int
517 mbx_unlock (mailbox_t mbox) 567 mbx_unlock (mailbox_t mbox)
518 { 568 {
519 errno = ENOSYS; 569 return ENOSYS;
520 return -1; 570 }
571
572 /* owner and group */
573 static int
574 mbx_set_owner (mailbox_t mbox, uid_t uid)
575 {
576 mbox->owner = uid;
577 return 0;
578 }
579 static int
580 mbx_get_owner (mailbox_t mbox, uid_t *uid)
581 {
582 *uid = mbox->owner;
583 return 0;
584 }
585
586 static int
587 mbx_set_group (mailbox_t mbox, uid_t gid)
588 {
589 mbox->group = gid;
590 return 0;
591 }
592 static int
593 mbx_get_group (mailbox_t mbox, uid_t *gid)
594 {
595 *gid = mbox->group;
596 return 0;
521 } 597 }
522 598
523 /* misc */ 599 /* misc */
524 static int 600 static int
525 mbx_scan (mailbox_t mbox, int *msgs) 601 mbx_scan (mailbox_t mbox, size_t *msgs)
526 { 602 {
527 errno = ENOSYS; 603 return ENOSYS;
528 return -1;
529 } 604 }
530 605
531 static int 606 static int
532 mbx_is_updated (mailbox_t mbox) 607 mbx_is_updated (mailbox_t mbox)
533 { 608 {
534 errno = ENOSYS; 609 return ENOSYS;
535 return -1;
536 } 610 }
537 611
538 static int 612 static int
539 mbx_get_timeout (mailbox_t mbox, int *timeout) 613 mbx_get_timeout (mailbox_t mbox, size_t *timeout)
540 { 614 {
541 errno = ENOSYS; 615 *timeout = mbox->timeout;
542 return -1; 616 return 0;
543 } 617 }
544 618
545 static int 619 static int
546 mbx_set_timeout (mailbox_t mbox, int timeout) 620 mbx_set_timeout (mailbox_t mbox, size_t timeout)
547 { 621 {
548 errno = ENOSYS; 622 mbox->timeout = timeout;
549 return -1; 623 return 0;
550 } 624 }
551 625
552 static int 626 static int
553 mbx_get_refresh (mailbox_t mbox, int *refresh) 627 mbx_get_refresh (mailbox_t mbox, size_t *refresh)
554 { 628 {
555 errno = ENOSYS; 629 *refresh = mbox->refresh;
556 return -1; 630 return 0;
557 } 631 }
558 632
559 static int 633 static int
560 mbx_set_refresh (mailbox_t mbox, int refresh) 634 mbx_set_refresh (mailbox_t mbox, size_t refresh)
561 { 635 {
562 errno = ENOSYS; 636 mbox->refresh = refresh;
563 return -1; 637 return 0;
564 } 638 }
565 639
566 static int 640 static int
567 mbx_get_size (mailbox_t mbox, int id, size_t *size) 641 mbx_get_size (mailbox_t mbox, size_t msgno, size_t *sh, size_t *sb)
568 { 642 {
569 errno = ENOSYS; 643 return ENOSYS;
570 return -1;
571 } 644 }
572 645
573 static int 646 static int
574 mbx_set_notification (mailbox_t mbox, int (*func) (mailbox_t, void *arg)) 647 mbx_set_notification (mailbox_t mbox, int (*func) (mailbox_t, void *arg))
575 { 648 {
576 errno = ENOSYS; 649 return ENOSYS;
577 return -1;
578 } 650 }
......
1 /* GNU mailutils - a suite of utilities for electronic mail 1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999 Free Software Foundation, Inc. 2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3 3
4 This program is free software; you can redistribute it and/or modify 4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU Library General Public License as published by 5 it under the terms of the GNU Library General Public License as published by
...@@ -19,6 +19,8 @@ ...@@ -19,6 +19,8 @@
19 # define _MAILBOX_H 19 # define _MAILBOX_H
20 20
21 #include <url.h> 21 #include <url.h>
22 #include <sys/types.h>
23 #include <unistd.h>
22 #include <stdlib.h> 24 #include <stdlib.h>
23 25
24 #ifdef __cplusplus 26 #ifdef __cplusplus
...@@ -52,77 +54,98 @@ struct mailbox_type ...@@ -52,77 +54,98 @@ struct mailbox_type
52 struct _mailbox 54 struct _mailbox
53 { 55 {
54 /* Data */ 56 /* Data */
57
55 char *name; 58 char *name;
56 int messages; 59 uid_t owner;
57 int num_deleted; 60 gid_t group;
58 long size; 61 size_t messages;
59 int timeout; 62 size_t num_deleted;
60 int refresh; 63 off_t size;
61 mailbox_lock_t lock; 64 int lock;
62 int (*func) __P ((mailbox_t)); 65 size_t timeout;
66 size_t refresh;
67 int (*func) __P ((mailbox_t, void *arg));
68 struct mailbox_type *mtype;
63 69
70 /* back pointer to the specific mailbox */
64 void *data; 71 void *data;
65 struct mailbox_type *mtype;
66 72
67 /* Functions */ 73 /* Functions */
68 74
69 //void (*_destroy) __P ((mailbox_t *)); 75 #define MU_MB_RDONLY ((int)1)
76 #define MU_MB_WRONLY (MU_MB_RDONLY << 1)
77 #define MU_MB_RDWR (MU_MB_WRONLY << 1)
78 #define MU_MB_APPEND (MU_MB_RDWR << 1)
79 #define MU_MB_CREAT (MU_MB_APPEND << 1)
70 80
71 int (*_open) __P ((mailbox_t, int flag)); 81 int (*_open) __P ((mailbox_t, int flag));
72 int (*_close) __P ((mailbox_t, int flag)); 82 int (*_close) __P ((mailbox_t));
73 83
74 /* type */ 84 /* type */
75 int (*_get_name) __P ((mailbox_t, int *id, char *name, 85 int (*_get_name) __P ((mailbox_t, int *id, char *name,
76 int offset, int len)); 86 size_t len, size_t *n));
77 int (*_get_mname) __P ((mailbox_t, int *id, char **name, 87 int (*_get_mname) __P ((mailbox_t, int *id, char **name, size_t *n));
78 int *len));
79 88
80 /* passwd if needed */ 89 /* passwd if needed */
81 int (*_get_passwd) __P ((mailbox_t, char * passwd, int offset, int n)); 90 int (*_get_passwd) __P ((mailbox_t, char *passwd,
82 int (*_get_mpasswd) __P ((mailbox_t, char **passwd, int *n)); 91 size_t len, size_t *n));
83 int (*_set_passwd) __P ((mailbox_t, const char * passwd, 92 int (*_get_mpasswd) __P ((mailbox_t, char **passwd, size_t *n));
84 int offset, int n)); 93 int (*_set_passwd) __P ((mailbox_t, const char *passwd, size_t len));
85 /* deleting mesgs */ 94 /* deleting mesgs */
86 int (*_delete) __P ((mailbox_t, int id)); 95 int (*_is_deleted) __P ((mailbox_t, size_t msgno));
87 int (*_undelete) __P ((mailbox_t, int id)); 96 int (*_delete) __P ((mailbox_t, size_t msgno));
88 int (*_is_deleted) __P ((mailbox_t, int id)); 97 int (*_undelete) __P ((mailbox_t, size_t msgno));
89 int (*_expunge) __P ((mailbox_t)); 98 int (*_expunge) __P ((mailbox_t));
99 int (*_is_updated) __P ((mailbox_t));
100 int (*_scan) __P ((mailbox_t, size_t *msgs));
90 101
91 /* appending messages */ 102 /* appending messages */
92 int (*_new_msg) __P ((mailbox_t, int *id)); 103 int (*_new_msg) __P ((mailbox_t, size_t *msgno));
93 int (*_set_header) __P ((mailbox_t, int id, const char *h, 104 int (*_set_header) __P ((mailbox_t, size_t msgno, const char *h,
94 int offset, int n, int replace)); 105 size_t len, int replace));
95 int (*_set_body) __P ((mailbox_t, int id, const char *b, 106 int (*_set_body) __P ((mailbox_t, size_t msgno, const char *b,
96 int offset, int n, int replace)); 107 size_t len, int replace));
97 int (*_append) __P ((mailbox_t, int id)); 108 int (*_append) __P ((mailbox_t, size_t msgno));
98 int (*_destroy_msg) __P ((mailbox_t, int id)); 109 int (*_destroy_msg) __P ((mailbox_t, size_t msgno));
99 110
111 #define MU_MB_RDLOCK 0
112 #define MU_MB_WRLOCK 1
100 /* locking */ 113 /* locking */
101 int (*_lock) __P ((mailbox_t, int flag)); 114 int (*_lock) __P ((mailbox_t, int flag));
102 int (*_unlock) __P ((mailbox_t)); 115 int (*_unlock) __P ((mailbox_t));
116 int (*_ilock) __P ((mailbox_t, int flag));
117 int (*_iunlock) __P ((mailbox_t));
103 118
104 /* reading mesgs */ 119 /* reading mesgs */
105 int (*_get_body) __P ((mailbox_t, int id, char *v, 120 int (*_get_body) __P ((mailbox_t, size_t msgno, off_t off,
106 int offset, int n)); 121 char *b, size_t len, size_t *n));
107 int (*_get_mbody) __P ((mailbox_t, int id, char **v, int *n)); 122 int (*_get_mbody) __P ((mailbox_t, size_t msgno, off_t off,
108 int (*_get_header) __P ((mailbox_t, int id, char *h, 123 char **b, size_t *n));
109 int offset, int n)); 124 int (*_get_header) __P ((mailbox_t, size_t msgno, off_t off,
110 int (*_get_mheader) __P ((mailbox_t, int id, char **h, int *n)); 125 char *h, size_t len, size_t *n));
126 int (*_get_mheader) __P ((mailbox_t, size_t msgno, off_t off,
127 char **h, size_t *n));
128 int (*_get_size) __P ((mailbox_t, size_t msgno,
129 size_t *h, size_t *b));
111 130
112 /* setting flags */ 131 /* setting flags */
113 int (*_msg_is_read) __P ((mailbox_t, int id)); 132 int (*_is_read) __P ((mailbox_t, size_t msgno));
114 int (*_msg_set_read) __P ((mailbox_t, int id)); 133 int (*_set_read) __P ((mailbox_t, size_t msgno));
115 int (*_msg_is_seen) __P ((mailbox_t, int id)); 134 int (*_is_seen) __P ((mailbox_t, size_t msgno));
116 int (*_msg_set_seen) __P ((mailbox_t, int id)); 135 int (*_set_seen) __P ((mailbox_t, size_t msgno));
136
137 /* owner and group */
138 int (*_set_owner) __P ((mailbox_t, uid_t uid));
139 int (*_get_owner) __P ((mailbox_t, uid_t *uid));
140 int (*_set_group) __P ((mailbox_t, gid_t gid));
141 int (*_get_group) __P ((mailbox_t, gid_t *gid));
117 142
118 /* miscellany */ 143 /* miscellany */
119 int (*_scan) __P ((mailbox_t, int *msgs)); 144 int (*_size) __P ((mailbox_t, off_t *size));
120 int (*_is_updated) __P ((mailbox_t)); 145 int (*_get_timeout) __P ((mailbox_t, size_t *timeout));
121 int (*_get_timeout) __P ((mailbox_t, int *timeout)); 146 int (*_set_timeout) __P ((mailbox_t, size_t timeout));
122 int (*_set_timeout) __P ((mailbox_t, int timeout)); 147 int (*_get_refresh) __P ((mailbox_t, size_t *refresh));
123 int (*_get_size) __P ((mailbox_t, int id, size_t *size)); 148 int (*_set_refresh) __P ((mailbox_t, size_t refresh));
124 int (*_get_refresh) __P ((mailbox_t, int *refresh));
125 int (*_set_refresh) __P ((mailbox_t, int refresh));
126 int (*_set_notification) __P ((mailbox_t, 149 int (*_set_notification) __P ((mailbox_t,
127 int (*func) __P ((mailbox_t, void * arg)))); 150 int (*func) __P ((mailbox_t, void * arg))));
128 }; 151 };
...@@ -132,8 +155,9 @@ extern int mailbox_init __P ((mailbox_t *, const char *name, int id)); ...@@ -132,8 +155,9 @@ extern int mailbox_init __P ((mailbox_t *, const char *name, int id));
132 extern void mailbox_destroy __P ((mailbox_t *)); 155 extern void mailbox_destroy __P ((mailbox_t *));
133 156
134 /* mailbox registration */ 157 /* mailbox registration */
135 extern int mailbox_list_type __P ((struct mailbox_type mtype[], int size)); 158 extern int mailbox_list_type __P ((struct mailbox_type mtype[],
136 extern int mailbox_list_mtype __P ((struct mailbox_type *mtype[], int *size)); 159 size_t len, size_t *n));
160 extern int mailbox_list_mtype __P ((struct mailbox_type **mtype, size_t *n));
137 extern int mailbox_add_type __P ((struct mailbox_type *mtype)); 161 extern int mailbox_add_type __P ((struct mailbox_type *mtype));
138 extern int mailbox_remove_type __P ((struct mailbox_type *mtype)); 162 extern int mailbox_remove_type __P ((struct mailbox_type *mtype));
139 extern int mailbox_get_type __P ((struct mailbox_type **mtype, int id)); 163 extern int mailbox_get_type __P ((struct mailbox_type **mtype, int id));
...@@ -147,97 +171,112 @@ extern int mailbox_get_type __P ((struct mailbox_type **mtype, int id)); ...@@ -147,97 +171,112 @@ extern int mailbox_get_type __P ((struct mailbox_type **mtype, int id));
147 #endif 171 #endif
148 172
149 extern INLINE int mailbox_open __P ((mailbox_t, int flag)); 173 extern INLINE int mailbox_open __P ((mailbox_t, int flag));
150 extern INLINE int mailbox_close __P ((mailbox_t, int flag)); 174 extern INLINE int mailbox_close __P ((mailbox_t));
151 175
152 /* type */ 176 /* type */
153 extern INLINE int mailbox_get_name __P ((mailbox_t, int *id, char *name, 177 extern INLINE int mailbox_get_name __P ((mailbox_t, int *id, char *name,
154 int offset, int len)); 178 size_t len, size_t *n));
155 extern INLINE int mailbox_get_mname __P ((mailbox_t, int *id, char **name, 179 extern INLINE int mailbox_get_mname __P ((mailbox_t, int *id, char **name,
156 int *len)); 180 size_t *n));
157 181
158 /* passwd */ 182 /* passwd */
159 extern INLINE int mailbox_get_passwd __P ((mailbox_t, char *passwd, 183 extern INLINE int mailbox_get_passwd __P ((mailbox_t, char *passwd,
160 int offset, int len)); 184 size_t len, size_t *n));
161 extern INLINE int mailbox_get_mpasswd __P ((mailbox_t, char **passwd, 185 extern INLINE int mailbox_get_mpasswd __P ((mailbox_t, char **passwd,
162 int *len)); 186 size_t *n));
163 extern INLINE int mailbox_set_passwd __P ((mailbox_t, const char *passwd, 187 extern INLINE int mailbox_set_passwd __P ((mailbox_t, const char *passwd,
164 int offset, int len)); 188 size_t len));
165 189
166 /* deleting */ 190 /* deleting */
167 extern INLINE int mailbox_delete __P ((mailbox_t, int)); 191 extern INLINE int mailbox_delete __P ((mailbox_t, size_t msgno));
168 extern INLINE int mailbox_undelete __P ((mailbox_t, int)); 192 extern INLINE int mailbox_undelete __P ((mailbox_t, size_t msgno));
169 extern INLINE int mailbox_expunge __P ((mailbox_t)); 193 extern INLINE int mailbox_expunge __P ((mailbox_t));
170 extern INLINE int mailbox_is_deleted __P ((mailbox_t, int)); 194 extern INLINE int mailbox_is_deleted __P ((mailbox_t, size_t msgno));
171 195
172 /* appending */ 196 /* appending */
173 extern INLINE int mailbox_new_msg __P ((mailbox_t, int * id)); 197 extern INLINE int mailbox_new_msg __P ((mailbox_t, size_t * msgno));
174 extern INLINE int mailbox_set_header __P ((mailbox_t, int id, const char *h, 198 extern INLINE int mailbox_set_header __P ((mailbox_t, size_t msgno,
175 int offset, int n, int replace)); 199 const char *h, size_t len,
176 extern INLINE int mailbox_set_body __P ((mailbox_t, int id, const char *b, 200 int replace));
177 int offset, int n, int replace)); 201 extern INLINE int mailbox_set_body __P ((mailbox_t, size_t msgno,
178 extern INLINE int mailbox_append __P ((mailbox_t, int id)); 202 const char *b, size_t len,
179 extern INLINE int mailbox_destroy_msg __P ((mailbox_t, int id)); 203 int replace));
204 extern INLINE int mailbox_append __P ((mailbox_t, size_t msgno));
205 extern INLINE int mailbox_destroy_msg __P ((mailbox_t, size_t msgno));
180 206
181 /* reading */ 207 /* reading */
182 extern INLINE int mailbox_get_body __P ((mailbox_t, int id, char *b, 208 extern INLINE int mailbox_get_body __P ((mailbox_t, size_t msgno,
183 int offset, int n)); 209 off_t off, char *b,
184 extern INLINE int mailbox_get_mbody __P ((mailbox_t, int id, char **b, 210 size_t len, size_t *n));
185 int *n)); 211 extern INLINE int mailbox_get_mbody __P ((mailbox_t, size_t msgno, off_t off,
186 extern INLINE int mailbox_get_header __P ((mailbox_t, int id, char *h, 212 char **b, size_t *n));
187 int offset, int n)); 213 extern INLINE int mailbox_get_header __P ((mailbox_t, size_t msgno, off_t off,
188 extern INLINE int mailbox_get_mheader __P ((mailbox_t, int id, char **h, 214 char *h, size_t len, size_t *n));
189 int *n)); 215 extern INLINE int mailbox_get_mheader __P ((mailbox_t, size_t msgno, off_t off,
216 char **h, size_t *n));
190 217
191 /* locking */ 218 /* locking */
192 extern INLINE int mailbox_lock __P ((mailbox_t, int flag)); 219 extern INLINE int mailbox_lock __P ((mailbox_t, int flag));
193 extern INLINE int mailbox_unlock __P ((mailbox_t)); 220 extern INLINE int mailbox_unlock __P ((mailbox_t));
194 221
222 /* owner and group */
223 extern INLINE int mailbox_set_owner __P ((mailbox_t, uid_t uid));
224 extern INLINE int mailbox_set_group __P ((mailbox_t, gid_t gid));
225
195 /* miscellany */ 226 /* miscellany */
196 extern INLINE int mailbox_scan __P ((mailbox_t, int *msgs)); 227 extern INLINE int mailbox_scan __P ((mailbox_t, size_t *msgs));
197 extern INLINE int mailbox_is_updated __P ((mailbox_t)); 228 extern INLINE int mailbox_is_updated __P ((mailbox_t));
198 extern INLINE int mailbox_get_timeout __P ((mailbox_t, int *timeout)); 229 extern INLINE int mailbox_get_timeout __P ((mailbox_t, size_t *timeout));
199 extern INLINE int mailbox_set_timeout __P ((mailbox_t, int timeout)); 230 extern INLINE int mailbox_set_timeout __P ((mailbox_t, size_t timeout));
200 extern INLINE int mailbox_get_refresh __P ((mailbox_t, int *refresh)); 231 extern INLINE int mailbox_get_refresh __P ((mailbox_t, size_t *refresh));
201 extern INLINE int mailbox_set_refresh __P ((mailbox_t, int refresh)); 232 extern INLINE int mailbox_set_refresh __P ((mailbox_t, size_t refresh));
202 extern INLINE int mailbox_get_size __P ((mailbox_t, int id, size_t *size)); 233 extern INLINE int mailbox_get_size __P ((mailbox_t, size_t msgno,
203 extern INLINE int mailbox_set_notification __P ((mailbox_t, int 234 size_t *header, size_t *body));
204 (*func) __P ((mailbox_t)))); 235 extern INLINE int mailbox_set_notification __P ((mailbox_t,
236 int (*func)
237 __P ((mailbox_t, void *))));
205 238
206 #ifdef MU_USE_MACROS 239 #ifdef MU_USE_MACROS
207 #define mailbox_open(m, f) m->_open (m, f) 240 #define mailbox_open(m, f) m->_open (m, f)
208 #define mailbox_close(m, f) m->_close (m, f) 241 #define mailbox_close(m) m->_close (m)
209 242
210 /* type */ 243 /* type */
211 #define mailbox_get_name(m, t, d, o, n) m->_get_name (m, t, d, o, n) 244 #define mailbox_get_name(m, t, d, l, n) m->_get_name (m, t, d, l, n)
212 #define mailbox_get_mtype(m, t, d, n) m->_get_mtype (m, t, d, n) 245 #define mailbox_get_mtype(m, t, d, n) m->_get_mtype (m, t, d, n)
213 246
214 /* passwd */ 247 /* passwd */
215 #define mailbox_get_passwd(m, p, o, n) m->_get_passwd (m, p, o, n) 248 #define mailbox_get_passwd(m, p, l, n) m->_get_passwd (m, p, l, n)
216 #define mailbox_get_mpasswd(m, p, n) m->_get_mpasswd (m, p, n) 249 #define mailbox_get_mpasswd(m, p, n) m->_get_mpasswd (m, p, n)
217 #define mailbox_set_passwd(m, p, o, n) m->_set_passwd (m, p, o, n) 250 #define mailbox_set_passwd(m, p, l) m->_set_passwd (m, p, l)
218 251
219 /* deleting */ 252 /* deleting */
220 #define mailbox_delete(m, id) m->_delete (m, id) 253 #define mailbox_delete(m, mid) m->_delete (m, mid)
221 #define mailbox_undelete(m, id) m->_undelete (m, id) 254 #define mailbox_undelete(m, mid) m->_undelete (m, mid)
222 #define mailbox_is_deleted(m, id) m->_is_deleted (m, id) 255 #define mailbox_is_deleted(m, mid) m->_is_deleted (m, mid)
223 #define mailbox_expunge(m) m->_expunge (m) 256 #define mailbox_expunge(m) m->_expunge (m)
224 257
225 /* appending */ 258 /* appending */
226 #define mailbox_new_msg(m, id) m->_new_msg (m, id) 259 #define mailbox_new_msg(m, mid) m->_new_msg (m, mid)
227 #define mailbox_set_header(m, id, h, o, n, r) m->_set_header(m, id, h, o, n, r) 260 #define mailbox_set_header(m, mid, h, l, r) m->_set_header(m, mid, h, n, r)
228 #define mailbox_set_body(m, id, b, o, n, r) m->_set_body (m, id, b, o, n, r) 261 #define mailbox_set_body(m, mid, b, l r) m->_set_body (m, mid, b, l, r)
229 #define mailbox_append(m, id) m->_append (m, id) 262 #define mailbox_append(m, mid) m->_append (m, mid)
230 #define mailbox_destroy_msg(m, id) m->_destroy_msg (m, id) 263 #define mailbox_destroy_msg(m, mid) m->_destroy_msg (m, mid)
231 264
232 /* locking */ 265 /* locking */
233 #define mailbox_lock(m, f) m->_lock (m, f) 266 #define mailbox_lock(m, f) m->_lock (m, f)
234 #define mailbox_unlock(m) m->_unlock (m) 267 #define mailbox_unlock(m) m->_unlock (m)
235 268
236 /* reading */ 269 /* reading */
237 #define mailbox_get_header(m, id, h, o, n) m->_get_header (m, id, h, o, n) 270 #define mailbox_get_header(m, mid, h, l, n) m->_get_header (m, mid, h, o, n)
238 #define mailbox_get_mheader(m, id, h, n) m->_get_header (m, id, h, n) 271 #define mailbox_get_mheader(m, mid, h, l) m->_get_header (m, mid, h, l)
239 #define mailbox_get_body(m, id, b, o, n) m->_get_body (m, id, b, o, n) 272 #define mailbox_get_body(m, mid, b, l, n) m->_get_body (m, mid, b, l, n)
240 #define mailbox_get_mbody(m, id, b, n) m->_get_body (m, id, b, n) 273 #define mailbox_get_mbody(m, mid, b, n) m->_get_body (m, mid, b, n)
274
275 /* owner and group */
276 #define mailbox_set_owner(m, uid) m->_set_owner(m, uid)
277 #define mailbox_get_owner(m, uid) m->_set_owner(m, uid)
278 #define mailbox_set_group(m, gid) m->_set_group(m, gid)
279 #define mailbox_get_group(m, gid) m->_set_group(m, gid)
241 280
242 /* miscellany */ 281 /* miscellany */
243 #define mailbox_scan(m, t) m->_scan (m, t) 282 #define mailbox_scan(m, t) m->_scan (m, t)
...@@ -246,7 +285,7 @@ extern INLINE int mailbox_set_notification __P ((mailbox_t, int ...@@ -246,7 +285,7 @@ extern INLINE int mailbox_set_notification __P ((mailbox_t, int
246 #define mailbox_set_timeout(m, t) m->_set_timeout (m, t) 285 #define mailbox_set_timeout(m, t) m->_set_timeout (m, t)
247 #define mailbox_get_refresh(m, r) m->_get_refresh (m, r) 286 #define mailbox_get_refresh(m, r) m->_get_refresh (m, r)
248 #define mailbox_set_refresh(m, r) m->_set_refresh (m, r) 287 #define mailbox_set_refresh(m, r) m->_set_refresh (m, r)
249 #define mailbox_get_size(m, id, size) m->_get_size(m, id, size) 288 #define mailbox_get_size(m, mid, sh, sb) m->_get_size(m, mid, sh, sb)
250 #define mailbox_set_notification(m, func) m->_set_notification (m, func) 289 #define mailbox_set_notification(m, func) m->_set_notification (m, func)
251 #endif /* MU_USE_MACROS */ 290 #endif /* MU_USE_MACROS */
252 291
......
1 /* GNU mailutils - a suite of utilities for electronic mail 1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999 Free Software Foundation, Inc. 2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3 3
4 This program is free software; you can redistribute it and/or modify 4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU Library General Public License as published by 5 it under the terms of the GNU Library General Public License as published by
...@@ -24,57 +24,44 @@ mailbox_open (mailbox_t mbox, int flag) ...@@ -24,57 +24,44 @@ mailbox_open (mailbox_t mbox, int flag)
24 } 24 }
25 25
26 int 26 int
27 mailbox_close (mailbox_t mbox, int flag) 27 mailbox_close (mailbox_t mbox)
28 { 28 {
29 return mbox->_close (mbox, flag); 29 return mbox->_close (mbox);
30 }
31
32
33 /* type */
34 int
35 mailbox_get_type (mailbox_t mbox, int *type, char *desc, int offset, int len)
36 {
37 return mbox->_get_type (mbox, type, desc, offset, len);
38 }
39
40 int
41 mailbox_get_mtype (mailbox_t mbox, int *type, char **desc, int *len)
42 {
43 return mbox->_get_mtype (mbox, type, desc, offset, len);
44 } 30 }
45 31
46 32
47 /* passwd */ 33 /* passwd */
48 int 34 int
49 mailbox_get_passwd (mailbox_t mbox, char *passwd, int offset, int len) 35 mailbox_get_passwd (mailbox_t mbox, char *passwd, size_t len, size_t *n)
50 { 36 {
51 return mbox->_get_passwd (mbox, passwd, offset, len); 37 return mbox->_get_passwd (mbox, passwd, len, n);
52 } 38 }
53 39
54 int 40 int
55 mailbox_get_mpasswd (mailbox_t mbox, char **passwd, int *len) 41 mailbox_get_mpasswd (mailbox_t mbox, char **passwd, size_t *n)
56 { 42 {
57 return mbox->_get_mpasswd (mbox, passwd, len); 43 return mbox->_get_mpasswd (mbox, passwd, n);
58 } 44 }
59 45
60 int 46 int
61 mailbox_set_passwd (mailbox_t mbox, const char *passwd, int offset, int len) 47 mailbox_set_passwd (mailbox_t mbox, const char *passwd,
48 size_t len)
62 { 49 {
63 return mbox->_set_passwd (mbox, passwd, offset, len); 50 return mbox->_set_passwd (mbox, passwd, len);
64 } 51 }
65 52
66 53
67 /* deleting */ 54 /* deleting */
68 int 55 int
69 mailbox_delete (mailbox_t mbox, int id) 56 mailbox_delete (mailbox_t mbox, size_t msgno)
70 { 57 {
71 return mbox->_delete (mbox, id); 58 return mbox->_delete (mbox, msgno);
72 } 59 }
73 60
74 int 61 int
75 mailbox_undelete (mailbox_t mbox, int id) 62 mailbox_undelete (mailbox_t mbox, size_t msgno)
76 { 63 {
77 return mbox->_undelete (mbox, id); 64 return mbox->_undelete (mbox, msgno);
78 } 65 }
79 66
80 int 67 int
...@@ -84,69 +71,73 @@ mailbox_expunge (mailbox_t mbox) ...@@ -84,69 +71,73 @@ mailbox_expunge (mailbox_t mbox)
84 } 71 }
85 72
86 int 73 int
87 mailbox_is_deleted (mailbox_t mbox, int) 74 mailbox_is_deleted (mailbox_t mbox, size_t msgno)
88 { 75 {
89 return mbox->_is_deleted (mbox, int); 76 return mbox->_is_deleted (mbox, msgno);
90 } 77 }
91 78
92 79
93 /* appending */ 80 /* appending */
94 int 81 int
95 mailbox_new_msg (mailbox_t mbox, int * id) 82 mailbox_new_msg (mailbox_t mbox, size_t *msgno)
96 { 83 {
97 return mbox->_new_msg (mbox, id); 84 return mbox->_new_msg (mbox, msgno);
98 } 85 }
99 86
100 int 87 int
101 mailbox_set_header (mailbox_t mbox, int id, const char *h, 88 mailbox_set_header (mailbox_t mbox, size_t msgno, const char *h,
102 int offset, int n, int replace) 89 size_t len, int replace)
103 { 90 {
104 return mbox->_set_header (mbox, id, h, offset, n, replace); 91 return mbox->_set_header (mbox, msgno, h, len, replace);
105 } 92 }
106 93
107 int 94 int
108 mailbox_set_body (mailbox_t mbox, int id, const char *b, 95 mailbox_set_body (mailbox_t mbox, size_t msgno, const char *b,
109 int offset, int n, int replace) 96 size_t len, int replace)
110 { 97 {
111 return mbox->_set_body (mbox, id, b, offset, n, replace); 98 return mbox->_set_body (mbox, msgno, b, len, replace);
112 } 99 }
113 100
114 int 101 int
115 mailbox_append (mailbox_t mbox, int id) 102 mailbox_append (mailbox_t mbox, size_t msgno)
116 { 103 {
117 return mbox->_append (mbox, id); 104 return mbox->_append (mbox, msgno);
118 } 105 }
119 106
120 int 107 int
121 mailbox_destroy_msg (mailbox_t mbox, int id) 108 mailbox_destroy_msg (mailbox_t mbox, size_t msgno)
122 { 109 {
123 return mbox->_destroy_msg (mbox, id); 110 return mbox->_destroy_msg (mbox, msgno);
124 } 111 }
125 112
126 113
127 /* reading */ 114 /* reading */
128 int 115 int
129 mailbox_get_body (mailbox_t mbox, int id, char *b, int offset, int n) 116 mailbox_get_body (mailbox_t mbox, size_t msgno, off_t off, char *b,
117 size_t len, size_t *n)
130 { 118 {
131 return mbox->_get_body (mbox, id, b, offset, n); 119 return mbox->_get_body (mbox, msgno, off, b, len, n);
132 } 120 }
133 121
134 int 122 int
135 mailbox_get_mbody (mailbox_t mbox, int id, char **b, int *n) 123 mailbox_get_mbody (mailbox_t mbox, size_t msgno, off_t off,
124 char **b, size_t *n)
136 { 125 {
137 return mbox->_get_body (mbox, id, b, n); 126 return mbox->_get_mbody (mbox, msgno, off, b, n);
138 } 127 }
139 128
140 int 129 int
141 mailbox_get_header (mailbox_t mbox, int id, char *h, int offset, int n) 130 mailbox_get_header (mailbox_t mbox, size_t msgno, off_t off, char *h,
131 size_t len, size_t *n)
142 { 132 {
143 return mbox->_get_header (mbox, id, h, offset, n); 133 return mbox->_get_header (mbox, msgno, off, h, len, n);
144 } 134 }
145 135
146 int 136 int
147 mailbox_get_mheader (mailbox_t mbox, int id, char **h, int *n) 137 mailbox_get_mheader (mailbox_t mbox, size_t msgno, off_t off,
138 char **h, size_t *n)
148 { 139 {
149 return mbox->_get_header (mbox, id, h, n); 140 return mbox->_get_mheader (mbox, msgno, off, h, n);
150 } 141 }
151 142
152 143
...@@ -166,7 +157,7 @@ mailbox_unlock (mailbox_t mbox) ...@@ -166,7 +157,7 @@ mailbox_unlock (mailbox_t mbox)
166 157
167 /* misc */ 158 /* misc */
168 int 159 int
169 mailbox_scan (mailbox_t mbox, int *msgs) 160 mailbox_scan (mailbox_t mbox, size_t *msgs)
170 { 161 {
171 return mbox->_scan (mbox, msgs); 162 return mbox->_scan (mbox, msgs);
172 } 163 }
...@@ -178,31 +169,32 @@ mailbox_is_updated (mailbox_t mbox) ...@@ -178,31 +169,32 @@ mailbox_is_updated (mailbox_t mbox)
178 } 169 }
179 170
180 int 171 int
181 mailbox_get_timeout (mailbox_t mbox, int *timeout) 172 mailbox_get_timeout (mailbox_t mbox, size_t *timeout)
182 { 173 {
183 return mbox->_get_timeout (mbox, timeout); 174 return mbox->_get_timeout (mbox, timeout);
184 } 175 }
185 176
186 int 177 int
187 mailbox_set_timeout (mailbox_t mbox, int timeout) 178 mailbox_set_timeout (mailbox_t mbox, size_t timeout)
188 { 179 {
189 return mbox->_set_timeout (mbox, timeout); 180 return mbox->_set_timeout (mbox, timeout);
190 } 181 }
191 182
192 int 183 int
193 mailbox_get_refresh (mailbox_t mbox, int *refresh) 184 mailbox_get_refresh (mailbox_t mbox, size_t *refresh)
194 { 185 {
195 return mbox->_get_refresh (mbox, refresh); 186 return mbox->_get_refresh (mbox, refresh);
196 } 187 }
197 188
198 int 189 int
199 mailbox_set_refresh (mailbox_t mbox, int refresh) 190 mailbox_set_refresh (mailbox_t mbox, size_t refresh)
200 { 191 {
201 return mbox->_set_refresh (mbox, refresh); 192 return mbox->_set_refresh (mbox, refresh);
202 } 193 }
203 194
204 int 195 int
205 mailbox_set_notification (mailbox_t mbox, int (*notif) __P ((mailbox_t mbox))) 196 mailbox_set_notification (mailbox_t mbox,
197 int (*notif) __P ((mailbox_t, void *)))
206 { 198 {
207 return mbox->_set_notification (mbox, notif); 199 return mbox->_set_notification (mbox, notif);
208 } 200 }
......
1 /* GNU mailutils - a suite of utilities for electronic mail 1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999 Free Software Foundation, Inc. 2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3 3
4 This program is free software; you can redistribute it and/or modify 4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU Library General Public License as published by 5 it under the terms of the GNU Library General Public License as published by
...@@ -17,6 +17,7 @@ ...@@ -17,6 +17,7 @@
17 17
18 #include <mbx_imap.h> 18 #include <mbx_imap.h>
19 #include <url_imap.h> 19 #include <url_imap.h>
20 #include <errno.h>
20 21
21 22
22 struct mailbox_type _mailbox_imap_type = 23 struct mailbox_type _mailbox_imap_type =
...@@ -35,5 +36,5 @@ mailbox_imap_destroy (mailbox_t *mbox) ...@@ -35,5 +36,5 @@ mailbox_imap_destroy (mailbox_t *mbox)
35 int 36 int
36 mailbox_imap_init (mailbox_t *mbox, const char *name) 37 mailbox_imap_init (mailbox_t *mbox, const char *name)
37 { 38 {
38 return -1; 39 return ENOSYS;
39 } 40 }
......
1 /* GNU mailutils - a suite of utilities for electronic mail 1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999 Free Software Foundation, Inc. 2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3 3
4 This program is free software; you can redistribute it and/or modify 4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU Library General Public License as published by 5 it under the terms of the GNU Library General Public License as published by
...@@ -59,7 +59,7 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name) ...@@ -59,7 +59,7 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name)
59 */ 59 */
60 if (stat (name, &st) == -1) 60 if (stat (name, &st) == -1)
61 { 61 {
62 return -1; /* errno set by stat () */ 62 return errno; /* errno set by stat () */
63 } 63 }
64 64
65 if (S_ISREG (st.st_mode)) 65 if (S_ISREG (st.st_mode))
...@@ -77,7 +77,7 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name) ...@@ -77,7 +77,7 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name)
77 if (fd == -1) 77 if (fd == -1)
78 { 78 {
79 /* Oops !! wrong permission ? file deleted ? */ 79 /* Oops !! wrong permission ? file deleted ? */
80 return -1; /* errno set by open () */ 80 return errno; /* errno set by open () */
81 } 81 }
82 82
83 /* Read a small chunck */ 83 /* Read a small chunck */
...@@ -91,6 +91,7 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name) ...@@ -91,6 +91,7 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name)
91 */ 91 */
92 if (count == 0) /*empty file*/ 92 if (count == 0) /*empty file*/
93 { 93 {
94 close (fd);
94 return mailbox_unix_init (mbox, name); 95 return mailbox_unix_init (mbox, name);
95 } 96 }
96 97
...@@ -99,11 +100,13 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name) ...@@ -99,11 +100,13 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name)
99 if (strncmp (head, "From ", 5) == 0) 100 if (strncmp (head, "From ", 5) == 0)
100 { 101 {
101 /* This is Unix Mbox */ 102 /* This is Unix Mbox */
103 close (fd);
102 return mailbox_unix_init (mbox, name); 104 return mailbox_unix_init (mbox, name);
103 } 105 }
104 } 106 }
105 107
106 /* Try MMDF */ 108 /* Try MMDF */
109 close (fd);
107 #endif 110 #endif
108 return mailbox_unix_init (mbox, name); 111 return mailbox_unix_init (mbox, name);
109 } 112 }
...@@ -121,5 +124,5 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name) ...@@ -121,5 +124,5 @@ mailbox_mbox_init (mailbox_t *mbox, const char *name)
121 void 124 void
122 mailbox_mbox_destroy (mailbox_t *mbox) 125 mailbox_mbox_destroy (mailbox_t *mbox)
123 { 126 {
124 return (*mbox)->mtype->_destroy (mbox); 127 (*mbox)->mtype->_destroy (mbox);
125 } 128 }
......
1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Library Public License as published by
6 the Free Software Foundation; either version 2, or (at your option)
7 any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU Library General Public License for more details.
13
14 You should have received a copy of the GNU Library General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
17
1 #include <url_mdir.h> 18 #include <url_mdir.h>
2 #include <mbx_mdir.h> 19 #include <mbx_mdir.h>
20 #include <errno.h>
3 21
4 struct mailbox_type _mailbox_maildir_type = 22 struct mailbox_type _mailbox_maildir_type =
5 { 23 {
...@@ -11,7 +29,7 @@ struct mailbox_type _mailbox_maildir_type = ...@@ -11,7 +29,7 @@ struct mailbox_type _mailbox_maildir_type =
11 int 29 int
12 mailbox_maildir_init (mailbox_t *mbox, const char *name) 30 mailbox_maildir_init (mailbox_t *mbox, const char *name)
13 { 31 {
14 return -1; 32 return ENOSYS;
15 } 33 }
16 34
17 void 35 void
......
1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Library Public License as published by
6 the Free Software Foundation; either version 2, or (at your option)
7 any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU Library General Public License for more details.
13
14 You should have received a copy of the GNU Library General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
17
1 #include <url_mmdf.h> 18 #include <url_mmdf.h>
2 #include <mbx_mmdf.h> 19 #include <mbx_mmdf.h>
20 #include <errno.h>
3 21
4 struct mailbox_type _mailbox_maildir_type = 22 struct mailbox_type _mailbox_mmdf_type =
5 { 23 {
6 "MMDF", 24 "MMDF",
7 (int)&_url_mmdf_type, &_url_mmdf_type, 25 (int)&_url_mmdf_type, &_url_mmdf_type,
...@@ -11,7 +29,7 @@ struct mailbox_type _mailbox_maildir_type = ...@@ -11,7 +29,7 @@ struct mailbox_type _mailbox_maildir_type =
11 int 29 int
12 mailbox_mmdf_init (mailbox_t *mbox, const char *name) 30 mailbox_mmdf_init (mailbox_t *mbox, const char *name)
13 { 31 {
14 return -1; 32 return ENOSYS;
15 } 33 }
16 34
17 void 35 void
......
1 /* GNU mailutils - a suite of utilities for electronic mail 1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999 Free Software Foundation, Inc. 2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3 3
4 This program is free software; you can redistribute it and/or modify 4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Library Public License as published by 5 it under the terms of the GNU General Library Public License as published by
...@@ -17,6 +17,7 @@ ...@@ -17,6 +17,7 @@
17 17
18 #include <url_pop.h> 18 #include <url_pop.h>
19 #include <mbx_pop.h> 19 #include <mbx_pop.h>
20 #include <errno.h>
20 21
21 struct mailbox_type _mailbox_pop_type = 22 struct mailbox_type _mailbox_pop_type =
22 { 23 {
...@@ -34,5 +35,5 @@ mailbox_pop_destroy (mailbox_t *mbox) ...@@ -34,5 +35,5 @@ mailbox_pop_destroy (mailbox_t *mbox)
34 int 35 int
35 mailbox_pop_init (mailbox_t *mbox, const char *name) 36 mailbox_pop_init (mailbox_t *mbox, const char *name)
36 { 37 {
37 return -1; 38 return ENOSYS;
38 } 39 }
......
1 /* GNU mailutils - a suite of utilities for electronic mail
2 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Library Public License as published by
6 the Free Software Foundation; either version 2, or (at your option)
7 any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU Library General Public License for more details.
13
14 You should have received a copy of the GNU Library General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
17
1 #include <url_unix.h> 18 #include <url_unix.h>
2 #include <mbx_unix.h> 19 #include <mbx_unix.h>
3 20
21 #ifdef HAVE_CONFIG_H
22 #include "config.h"
23 #endif
24
4 #include <stdlib.h> 25 #include <stdlib.h>
5 #include <stdio.h> 26 #include <stdio.h>
6 #include <time.h> 27 #include <time.h>
7 #include <sys/stat.h> 28 #include <sys/stat.h>
29 #include <fcntl.h>
8 #include <unistd.h> 30 #include <unistd.h>
31 #include <signal.h>
32 #include <errno.h>
33 #include <pthread.h>
34 #include <string.h>
35 #include <ctype.h>
9 36
10 struct mailbox_type _mailbox_unix_type = 37 struct mailbox_type _mailbox_unix_type =
11 { 38 {
...@@ -20,146 +47,1178 @@ typedef struct _mailbox_unix_msg ...@@ -20,146 +47,1178 @@ typedef struct _mailbox_unix_msg
20 off_t body; 47 off_t body;
21 off_t end; 48 off_t end;
22 int deleted; 49 int deleted;
23 } mailbox_unix_msg_t; 50 int is_read;
51 int is_seen;
52 } *mailbox_unix_msg_t;
24 53
25 typedef struct _mailbox_unix_data 54 typedef struct _mailbox_unix_data
26 { 55 {
27 mailbox_unix_msg_t *messages; 56 mailbox_unix_msg_t messages;
28 FILE *file; 57 FILE *file;
29 mailbox_lock_t lockmode; 58 char *dirname;
30 time_t last_mode_time; 59 char *basename;
31 } mailbox_unix_data_t; 60 #ifdef HAVE_PTHREAD_H
61 pthread_mutex_t mutex;
62 #endif
63 int lock;
64 int ilock;
65 time_t mtime;
66 size_t size;
67 } *mailbox_unix_data_t;
32 68
33 69
34 /* forward prototypes */ 70 /* forward prototypes */
35 71
36 static int mailbox_unix_open (mailbox_t *mbox, const char *name); 72 static int mailbox_unix_open (mailbox_t mbox, int flag);
37 static int mailbox_unix_close (mailbox_t *mbox); 73 static int mailbox_unix_close (mailbox_t mbox);
38 74
39 static int mailbox_unix_get_name (mailbox_t, int *id, char *name, 75 static int mailbox_unix_get_name (mailbox_t, int *id, char *name,
40 int offset, int len); 76 size_t len, size_t *n);
41 static int mailbox_unix_get_mname (mailbox_t, int *id, char **name, int *len);
42 77
43 /* passwd */ 78 /* passwd */
44 static int mailbox_unix_get_passwd (mailbox_t, char *passwd, 79
45 int offset, int len); 80 /* updating/deleting */
46 static int mailbox_unix_get_mpasswd (mailbox_t, char **passwd, int *len); 81 static int mailbox_unix_is_deleted (mailbox_t, size_t msgno);
47 static int mailbox_unix_set_passwd (mailbox_t, const char *passwd, 82 static int mailbox_unix_delete (mailbox_t, size_t msgno);
48 int offset, int len); 83 static int mailbox_unix_undelete (mailbox_t, size_t msgno);
49
50 /* deleting */
51 static int mailbox_unix_delete (mailbox_t, int);
52 static int mailbox_unix_undelete (mailbox_t, int);
53 static int mailbox_unix_expunge (mailbox_t); 84 static int mailbox_unix_expunge (mailbox_t);
54 static int mailbox_unix_is_deleted (mailbox_t, int); 85 static int mailbox_unix_is_updated (mailbox_t);
86 static int mailbox_unix_scan (mailbox_t, size_t *msgs);
87
55 88
56 /* appending */ 89 /* appending */
57 static int mailbox_unix_new_msg (mailbox_t, int * id); 90 static int mailbox_unix_new_msg (mailbox_t, size_t *msgno);
58 static int mailbox_unix_set_header (mailbox_t, int id, const char *h, 91 static int mailbox_unix_set_header (mailbox_t, size_t msgno, const char *h,
59 int offset, int n, int replace); 92 size_t len, int replace);
60 static int mailbox_unix_set_body (mailbox_t, int id, const char *b, 93 static int mailbox_unix_set_body (mailbox_t, size_t msgno, const char *b,
61 int offset, int n, int replace); 94 size_t len, int replace);
62 static int mailbox_unix_append (mailbox_t, int id); 95 static int mailbox_unix_append (mailbox_t, size_t msgno);
63 static int mailbox_unix_destroy_msg (mailbox_t, int id); 96 static int mailbox_unix_destroy_msg (mailbox_t, size_t msgno);
64 97
65 /* reading */ 98 /* reading */
66 static int mailbox_unix_get_body (mailbox_t, int id, char *b, 99 static int mailbox_unix_get_body (mailbox_t, size_t msgno, off_t off,
67 int offset, int n); 100 char *b, size_t len, size_t *n);
68 static int mailbox_unix_get_mbody (mailbox_t, int id, char **b, 101 static int mailbox_unix_get_header (mailbox_t, size_t msgno, off_t off,
69 int *n); 102 char *h, size_t len, size_t *n);
70 static int mailbox_unix_get_header (mailbox_t, int id, char *h, 103 static int mailbox_unix_get_size (mailbox_t, size_t msgno, size_t *header,
71 int offset, int n); 104 size_t *body);
72 static int mailbox_unix_get_mheader (mailbox_t, int id, char **h, 105
73 int *n); 106 /* setting flags */
107 static int mailbox_unix_is_read (mailbox_t, size_t msgno);
108 static int mailbox_unix_set_read (mailbox_t, size_t msgno);
109 static int mailbox_unix_is_seen (mailbox_t, size_t msgno);
110 static int mailbox_unix_set_seen (mailbox_t, size_t msgno);
111
112 /* owner and group
113 static int mailbox_unix_set_owner (mailbox_t mbox, uid_t uid);
114 static int mailbox_unix_get_owner (mailbox_t mbox, uid_t *uid);
115 static int mailbox_unix_set_group (mailbox_t mbox, gid_t gid);
116 static int mailbox_unix_get_group (mailbox_t mbox, gid_t *gid);
117 */
74 118
75 /* locking */ 119 /* locking */
76 static int mailbox_unix_lock (mailbox_t, int flag); 120 static int mailbox_unix_lock (mailbox_t, int flag);
77 static int mailbox_unix_unlock (mailbox_t); 121 static int mailbox_unix_unlock (mailbox_t);
122 static int mailbox_unix_ilock (mailbox_t, int flag);
123 static int mailbox_unix_iunlock (mailbox_t);
78 124
79 /* miscellany */ 125 static int mailbox_unix_size (mailbox_t, off_t *size);
80 static int mailbox_unix_scan (mailbox_t, int *msgs); 126
81 static int mailbox_unix_is_updated (mailbox_t); 127 /* private stuff */
82 static int mailbox_unix_get_timeout (mailbox_t, int *timeout); 128 static int mailbox_unix_is_from (const char *);
83 static int mailbox_unix_set_timeout (mailbox_t, int timeout); 129 static int mailbox_unix_readhdr (mailbox_t mbox, char *buf, size_t len,
84 static int mailbox_unix_get_refresh (mailbox_t, int *refresh); 130 off_t *content_length);
85 static int mailbox_unix_set_refresh (mailbox_t, int refresh); 131 static int mailbox_unix_sigblock ();
86 static int mailbox_unix_get_size (mailbox_t, int id, size_t *size); 132 static int mailbox_unix_sigunblock ();
87 static int mailbox_unix_set_notification (mailbox_t, 133
88 int (*func) (mailbox_t, void *arg)); 134 /* Having a structure initialize at compiletime instead of runtime
135 may speed thing a bit, but it is a real pain to maintain with
136 the changing API */
137 static struct _mailbox unixmbox =
138 {
139 /* Data */
140
141 (char *)NULL, /* char *name ; */
142 (uid_t)-1, /* uid_t owner; */
143 (gid_t)-1, /* gid_t group; */
144 0, /* messages */
145 0, /* num_deleted */
146 (off_t)0, /* size */
147 0, /* lock */
148 0, /* timeout; */
149 0, /* refresh; */
150 (int (*)())NULL, /* (*func) __P ((mailbox_t, void *arg)) */
151
152 /* type of mailbox */
153 &_mailbox_unix_type, /*struct mailbox_type *mtype; */
154
155 /* back pointer to the specific mailbox */
156 (void *)NULL, /* void *data; */
157
158 /* Functions */
159
160 mailbox_unix_open, /* (*_open) */
161 mailbox_unix_close, /* (*_close) */
162
163 /* type */
164 mailbox_unix_get_name, /* (*_get_name) */
165 NULL, /* (*_get_mname) */
166
167 /* passwd if needed */
168 NULL, /* (*_get_passwd) */
169 NULL, /* (*_get_mpasswd) */
170 NULL, /* (*_set_passwd) */
171
172 /* updating/deleting mesgs */
173 mailbox_unix_is_deleted, /* (*_is_deleted) */
174 mailbox_unix_delete, /* (*_delete) */
175 mailbox_unix_undelete, /* (*_undelete) */
176 mailbox_unix_expunge, /* (*_expunge) */
177 mailbox_unix_is_updated, /* (*_is_updated) */
178 mailbox_unix_scan, /* (*_scan) */
179
180 /* appending messages */
181 mailbox_unix_new_msg, /* (*_new_msg) */
182 mailbox_unix_set_header, /* (*_set_header) */
183 mailbox_unix_set_body, /* (*_set_body) */
184 mailbox_unix_append, /* (*_append) */
185 mailbox_unix_destroy_msg, /* (*_destroy_msg) */
186
187 /* external locking */
188 mailbox_unix_lock, /* (*_lock) */
189 mailbox_unix_unlock, /* (*_unlock) */
190 /* internal locking */
191 mailbox_unix_ilock, /* (*_ilock) */
192 mailbox_unix_iunlock, /* (*_iunlock) */
89 193
194 /* reading mesgs */
195 mailbox_unix_get_body, /* (*_get_body) */
196 NULL, /* (*_get_mbody) */
197 mailbox_unix_get_header, /* (*_get_header) */
198 NULL, /* (*_get_mheader) */
199 mailbox_unix_get_size, /* (*_get_msg_size) */
200
201 /* setting flags */
202 mailbox_unix_is_read, /* (*_msg_is_read) */
203 mailbox_unix_set_read, /* (*_msg_set_read) */
204 mailbox_unix_is_seen, /* (*_msg_is_seen) */
205 mailbox_unix_set_seen, /* (*_msg_set_seen) */
206
207 /* owner and group */
208 NULL, /* (*_set_owner) */
209 NULL, /* (*_get_owner) */
210 NULL, /* (*_set_group) */
211 NULL, /* (*_get_group) */
212
213 mailbox_unix_size, /* (*_size) */
214 NULL, /* (*_get_timeout) */
215 NULL, /* (*_set_timeout) */
216 NULL, /* (*_get_refresh) */
217 NULL, /* (*_set_refresh) */
218 NULL, /* (*_set_notification) */
219 };
90 220
91 int 221 int
92 mailbox_unix_init (mailbox_t *pmbox, const char *name) 222 mailbox_unix_init (mailbox_t *pmbox, const char *name)
93 { 223 {
94 mailbox_t mbox; 224 mailbox_t mbox;
225 size_t len;
226 mailbox_unix_data_t mud;
227 char *sep;
95 228
96 /* 229 /* sanity check */
97 Again should we do an open() and check if indeed this is a 230 if (name == NULL || *name == '\0')
98 correct mbox ? I think not, this should be delay to _open() 231 {
99 */ 232 return EINVAL;
233 }
234
235 /* allocate memory for mbox */
100 mbox = calloc (1, sizeof (*mbox)); 236 mbox = calloc (1, sizeof (*mbox));
101 if (mbox == NULL) 237 if (mbox == NULL)
102 return -1; /* errno set by calloc() */ 238 {
239 return ENOMEM; /* errno set by calloc() */
240 }
103 241
104 /* set the type */ 242 /* binary copy of the function */
105 mbox->mtype = &_mailbox_unix_type; 243 *mbox = unixmbox;
106 244
107 mbox->_open = mailbox_unix_open; 245 /* specific unix mbox data */
108 mbox->_close = mailbox_unix_close; 246 mud = mbox->data = calloc (1, sizeof (*mud));
247 if (mbox->data == NULL)
248 {
249 mailbox_unix_destroy (&mbox);
250 return ENOMEM;
251 }
109 252
110 mbox->_get_name = mailbox_unix_get_name; 253 /* copy the name */
111 mbox->_get_mname = mailbox_unix_get_mname; 254 len = strlen (name) + 1;
255 mbox->name = calloc (len, sizeof (char));
256 if (mbox->name == NULL)
257 {
258 mailbox_unix_destroy (&mbox);
259 return ENOMEM;
260 }
261 memcpy (mbox->name, name, len);
112 262
113 /* passwd */ 263 /* save the basename and dirname */
114 mbox->_get_passwd = mailbox_unix_get_passwd; 264 sep = strrchr (name, '/');
115 mbox->_get_mpasswd = mailbox_unix_get_mpasswd; 265 if (sep)
116 mbox->_set_passwd = mailbox_unix_set_passwd; 266 {
267 size_t baseln;
268 mud->dirname = calloc (sep - name + 1, sizeof (char));
269 if (mud->dirname == NULL)
270 {
271 mailbox_unix_destroy (&mbox);
272 return ENOMEM;
273 }
274 memcpy (mud->dirname, name, sep - name);
117 275
118 /* deleting */ 276 baseln = strlen (++sep) + 1;
119 mbox->_delete = mailbox_unix_delete; 277 mud->basename = calloc (baseln, sizeof (char));
120 mbox->_undelete = mailbox_unix_undelete; 278 if (mud->basename == NULL)
121 mbox->_expunge = mailbox_unix_expunge; 279 {
122 mbox->_is_deleted = mailbox_unix_is_deleted; 280 mailbox_unix_destroy (&mbox);
281 return ENOMEM;
282 }
283 memcpy (mud->basename, sep, baseln);
284 }
285 else
286 {
287 mud->dirname = calloc (2 , sizeof (char));
288 if (mud->dirname == NULL)
289 {
290 mailbox_unix_destroy (&mbox);
291 return ENOMEM;
292 }
293 mud->dirname[0] = '.';
123 294
124 /* appending */ 295 mud->basename = calloc (len, sizeof (char));
125 mbox->_new_msg = mailbox_unix_new_msg; 296 if (mud->basename == NULL)
126 mbox->_set_header = mailbox_unix_set_header; 297 {
127 mbox->_set_body = mailbox_unix_set_body; 298 mailbox_unix_destroy (&mbox);
128 mbox->_append = mailbox_unix_append; 299 return ENOMEM;
129 mbox->_destry_msg = mailbox_unix_destroy_msg; 300 }
301 memcpy (mud->basename, name, len);
302 }
130 303
131 /* reading */ 304 /* mutex when accessing the structure fields */
132 mbox->_get_body = mailbox_unix_get_body; 305 /* FIXME: should we use rdwr locks instead ?? */
133 mbox->_get_mbody = mailbox_unix_get_mbody; 306 #ifdef HAVE_PHTREAD_H
134 mbox->_get_header = mailbox_unix_get_header; 307 pthread_mutex_init (mud->mutex, NULL);
135 mbox->_get_mheader = mailbox_unix_get_mheader; 308 #endif
136 309
137 /* locking */
138 mbox->_lock = mailbox_unix_lock;
139 mbox->_unlock = mailbox_unix_unlock;
140 310
141 /* miscellany */ 311 (*pmbox) = mbox;
142 mbox->_scan = mailbox_unix_scan;
143 mbox->_is_updated = mailbox_unix_is_updated;
144 mbox->_get_timeout = mailbox_unix_get_timeout;
145 mbox->_set_timeout = mailbox_unix_set_timeout;
146 mbox->_get_refresh = mailbox_unix_get_refresh;
147 mbox->_set_refresh = mailbox_unix_set_refresh;
148 mbox->_get_size = mailbox_unix_get_size;
149 mbox->_set_notification = mailbox_unix_set_notification;
150 312
151 return 0; 313 return 0; /* okdoke */
152 } 314 }
153 315
154 void 316 void
155 mailbox_unix_destroy (mailbox_t *mbox) 317 mailbox_unix_destroy (mailbox_t *pmbox)
156 { 318 {
157 return; 319 if (pmbox && *pmbox)
320 {
321 mailbox_t mbox = *pmbox;
322 mailbox_unix_close (mbox);
323 if (mbox->data)
324 {
325 mailbox_unix_data_t mud = mbox->data;
326 if (mud->dirname)
327 free (mud->dirname);
328 if (mud->basename)
329 free (mud->basename);
330 if (mud->messages)
331 free (mud->messages);
332 free (mbox->data);
333 }
334 if (mbox->name)
335 free (mbox->name);
336 free (*pmbox);
337 pmbox = NULL;
338 }
158 } 339 }
159 340
160 341
161 /* start of Mbox Implementation */ 342 /* start of Mbox Implementation */
162 343
163 static int mailbox_unix_open (mailbox_t mbox, int flags) 344 static int
345 mailbox_unix_open (mailbox_t mbox, int flags)
346 {
347 mailbox_unix_data_t mud = mbox->data;
348 int fd = -1;
349 int flg = 0;
350 char * mode;
351
352 /*
353 FIXME: This is another problem, should we have a special set of flags
354 MU_MB_{CREAT,APPEND,RDONLY,RDWR} or use the default open(2)
355 and if RDONLY, should we have some security checks ?
356 */
357 if (flags & MU_MB_WRONLY)
358 {
359 flg = O_WRONLY;
360 }
361 else if (flags & MU_MB_RDWR)
362 {
363 flg = O_RDWR;
364 }
365 else /* default */
366 {
367 flg = O_RDONLY;
368 }
369
370 if (flags & MU_MB_APPEND)
371 {
372 flg |= O_APPEND;
373 }
374
375 /* handle CREAT with care, not to follow symlinks */
376 if (flags & MU_MB_CREAT)
377 {
378 /* firts see if the file already exists */
379 fd = open(mbox->name, flg);
380 if (fd == -1)
381 {
382 /* oops bail out */
383 if (errno != ENOENT)
384 {
385 return errno;
386 }
387 /* Create the file */
388 fd = open(mbox->name, flg|O_CREAT|O_EXCL, 0600);
389 if (fd < 0)
390 {
391 return errno;
392 }
393 }
394 /*
395 FIXME: How about owner(uid), to whom we set it to ?
396 do We need a _set_owner(uid) to mailbox_t
397 */
398 (void)fchown (fd, mbox->owner, mbox->group);
399 /* FIXME: should we have a mode field ? */
400 (void)fchmod (fd, 0600);
401 }
402 else
403 {
404 fd = open (mbox->name, flg);
405 if (fd < 0)
406 {
407 return errno;
408 }
409 }
410
411 /* we use FILE * object */
412 if (flg & MU_MB_RDWR)
413 {
414 mode = "r+";
415 }
416 else if (flg & MU_MB_WRONLY)
417 {
418 mode = "w";
419 }
420 else if (flg & MU_MB_APPEND)
421 {
422 mode = "a";
423 }
424 else /* default readonly*/
425 {
426 mode = "r";
427 }
428
429 /* clean up */
430 mailbox_unix_close (mbox);
431
432 mailbox_unix_ilock (mbox, MU_MB_WRLOCK);
433 {
434 mud->file = fdopen (fd, mode);
435 if (mud->file == NULL)
436 {
437 /* what's up ?? */
438 mailbox_unix_iunlock (mbox);
439 return ENOMEM;
440 }
441 flockfile (mud->file);
442 {
443 char buf [BUFSIZ];
444 if (fgets (buf, sizeof (buf), mud->file) == NULL)
445 {
446 if (feof (mud->file))
447 {
448 clearerr (mud->file); /* the file maybe empty */
449 }
450 else if (ferror (mud->file))
451 {
452 mailbox_unix_iunlock (mbox);
453 return EIO;
454 }
455 }
456 else
457 {
458 if (strncmp ("From ", buf, 5) != 0)
459 {
460 /* not a Unix mbox */
461 fclose (mud->file);
462 mailbox_unix_iunlock (mbox);
463 return EIO;
464 }
465 else
466 {
467 rewind (mud->file);
468 }
469 }
470 }
471 funlockfile (mud->file);
472 }
473 mailbox_unix_iunlock (mbox);
474 return 0;
475 }
476
477 static int
478 mailbox_unix_close (mailbox_t mbox)
164 { 479 {
480 mailbox_unix_data_t mud = (mailbox_unix_data_t)mbox->data;
481
482 mailbox_unix_ilock (mbox, MU_MB_WRLOCK);
483 {
484
485 /* make sure we do not hold any lock for that file */
486
487 mailbox_unix_unlock (mbox);
488 if (mud->file)
489 {
490 fclose (mud->file);
491 }
492 mud->file = NULL;
493 }
494 mailbox_unix_iunlock (mbox);
495 return 0;
496 }
497
498 static int
499 mailbox_unix_get_name (mailbox_t mbox, int *id, char *name,
500 size_t len, size_t *n)
501 {
502 char *s = _mailbox_unix_type.name;
503 size_t i = strlen (s);
504 if (id)
505 {
506 *id = _mailbox_unix_type.id;
507 }
508 if (name && len > 0)
509 {
510 i = (len < i) ? len : i;
511 strncpy (name, s, i - 1);
512 name [i - 1] = 0;
513 }
514 if (n)
515 {
516 *n = i;
517 }
518 return 0;
519 }
520
521 /* passwd */
522 /* We don't care */
523
524 /* FIXME: a little weak, we should do full reconnaissance of the
525 the "From " header :
526 From email weekday month day time timezone year
527 */
528 static int
529 mailbox_unix_is_from (const char *from)
530 {
531 const char *sep;
532 return (strncmp (from, "From ", 5) == 0
533 && (sep = strchr (from, ':')) != NULL
534 && strchr (sep, ':') != NULL);
535 }
536
537 static int
538 mailbox_unix_readhdr (mailbox_t mbox, char *buf, size_t len,
539 off_t *content_length)
540 {
541 mailbox_unix_data_t mud = (mailbox_unix_data_t)mbox->data;
542 mailbox_unix_msg_t mum = mud->messages;
543 char *sep;
544 size_t count = mbox->messages;
545
546 /* skip over the remaining header */
547 while (fgets (buf, len, mud->file))
548 {
549 /* FIXME: The heuristic is still weak
550 we will break and consider things not to be a header if:
551 1: an empty line
552 2: can not be a header
553 */
554 if (strcmp (buf, "\n") == 0 || strcmp (buf, "\r\n") == 0
555 || (isalpha (buf[0]) && (sep = strchr (buf, ':')) == NULL))
556 {
557 break;
558 }
559 /* get the the Content lenght of the body if possible */
560 if (strncmp (buf, "Content-Length:", 15) == 0)
561 {
562 sep = strchr(buf, ':'); /* pass the ':' */
563 sep[strlen (sep) - 1] = '\0'; /* chop the newline */
564 *content_length = strtol (sep + 1, NULL, 10);
565 }
566 if (strncmp (buf, "Status:", 7) == 0)
567 {
568 sep = strchr(buf, ':'); /* pass the ':' */
569 if (strchr (sep, 'R') != NULL)
570 {
571 mum[count - 1].is_read = 1;
572 }
573 if (strchr (sep, 'O') != NULL)
574 {
575 mum[count - 1].is_seen = 1;
576 }
577 }
578 }
579 if (feof (mud->file) || ferror (mud->file))
580 {
581 return EIO;
582 }
583 return 0;
584 }
585
586 /* Updating/deleting */
587 static int
588 mailbox_unix_scan (mailbox_t mbox, size_t *msgs)
589 {
590 char buf[BUFSIZ];
591 int header = 1;
592 int body = 0;
593 off_t content_length = -1;
594 size_t count = 0;
595 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
596 mailbox_unix_msg_t mum;
597 struct stat st;
598
599 mailbox_unix_ilock (mbox, MU_MB_WRLOCK);
600 /* FIXME: I should also block signals since
601 We can affor to be intr */
602 flockfile (mud->file);
603 rewind (mud->file);
604
605 if (fstat (fileno (mud->file), &st) != 0)
606 {
607 funlockfile (mud->file);
608 mailbox_unix_iunlock (mbox);
609 return EIO;
610 }
611 mud->mtime = st.st_mtime;
612 mud->size = st.st_size;
613
614 while (fgets (buf, sizeof (buf), mud->file))
615 {
616 /* header */
617 if ((header && mailbox_unix_is_from (buf)))
618 {
619 /* FIXME: What happen if some mailer violates the rfc8222 and the
620 "From " field contains a NULL byte */
621 int over = strlen (buf);
622 count++;
623 if (count > mbox->messages)
624 {
625 mum = realloc (mud->messages, count * sizeof (*mum));
626 if (mum == NULL)
627 {
628 funlockfile (mud->file);
629 mailbox_unix_iunlock (mbox);
630 return ENOMEM;
631 }
632 mbox->messages++;
633 memset (&mum[count - 1], 0, sizeof (*mum));
634 }
635 mud->messages = mum;
636 mum[count - 1].header = ftell (mud->file);
637 mum[count - 1].header -= over;
638
639 /* skip over the remaining header */
640 if (mailbox_unix_readhdr (mbox, buf, sizeof (buf),
641 &content_length) != 0)
642 {
643 funlockfile (mud->file);
644 mailbox_unix_iunlock (mbox);
645 return EIO;
646 }
647 header = 0;
648 body = !header;
649 } /* header */
650
651 /* body */
652 if (body && content_length >= 0)
653 {
654 /* ouf ! we got the size */
655 mum[count - 1].body = ftell (mud->file) - strlen (buf);
656 fseek (mud->file, content_length, SEEK_CUR);
657 mum[count - 1].end = ftell (mud->file);
658 content_length = -1;
659 header = 1;
660 body = !header;
661 }
662 else if (body)
663 {
664 /* oops! some heuristic since we do not know the size of the body */
665 if (mum[count - 1].body == 0)
666 {
667 mum[count - 1].body = ftell (mud->file) - strlen (buf);
668 }
669
670 if (mailbox_unix_is_from (buf))
671 {
672 int over = strlen (buf);
673 mum[count - 1].end = ftell (mud->file);
674 mum[count - 1].end -= over;
675 count++;
676 if (count > mbox->messages)
677 {
678 mum = realloc (mud->messages, count * sizeof (*mum));
679 if (mum == NULL)
680 {
681 funlockfile (mud->file);
682 mailbox_unix_iunlock (mbox);
683 return ENOMEM;
684 }
685 mbox->messages++;
686 memset (&mum[count - 1], 0, sizeof (*mum));
687 }
688 mud->messages = mum;
689 mum[count - 1].header = ftell (mud->file);
690 mum[count - 1].header -= over;
691
692 /* skip over the remaining header */
693 if (mailbox_unix_readhdr (mbox, buf, sizeof (buf),
694 &content_length) != 0)
695 {
696 funlockfile (mud->file);
697 mailbox_unix_iunlock (mbox);
698 return EIO;
699 }
700
701 mum[count - 1].body = ftell (mud->file) - strlen (buf);
702 if (content_length >= 0)
703 {
704 fseek (mud->file, content_length, SEEK_CUR);
705 mum[count - 1].end = ftell (mud->file);
706 content_length = -1;
707 header = 0;
708 body = !header;
709 }
710 }
711 } /* body */
712 } /* while */
713 mum[count - 1].end = ftell (mud->file);
714 if (feof (mud->file))
715 {
716 clearerr (mud->file);
717 }
718 else if (ferror (mud->file))
719 {
720 funlockfile (mud->file);
721 mailbox_unix_iunlock (mbox);
722 return EIO;
723 }
724 rewind (mud->file);
725 funlockfile (mud->file);
726 mailbox_unix_iunlock (mbox);
727 if (msgs)
728 *msgs = count;
729 return 0;
730 }
731
732 static int
733 mailbox_unix_is_updated (mailbox_t mbox)
734 {
735 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
736 struct stat st;
737 if (mud == 0 || fstat (fileno (mud->file), &st) < 0)
738 {
739 return 0;
740 }
741 return (mud->mtime == st.st_mtime);
742 }
743
744 static int
745 mailbox_unix_is_valid (mailbox_t mbox, size_t msgno)
746 {
747 /* valid ? */
748 return (mbox->messages > 0 && msgno <= mbox->messages);
749 }
750
751 static int
752 mailbox_unix_is_deleted (mailbox_t mbox, size_t msgno)
753 {
754 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
755
756 /* Do we have a consistent view of the mbox ? */
757 if (mud == NULL || ! mailbox_unix_is_valid (mbox, msgno))
758 {
759 return 0;
760 }
761 return mud->messages[msgno].deleted;
762 }
763
764 static int
765 mailbox_unix_delete (mailbox_t mbox, size_t msgno)
766 {
767 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
768
769 /* oops out of range ? */
770 /* if already deleted, noop */
771 if (mud == NULL || ! mailbox_unix_is_valid (mbox, msgno)
772 || mailbox_unix_is_deleted (mbox, msgno))
773 {
774 return 0;
775 }
776
777 /* Mark for deletion */
778 mud->messages[msgno].deleted = 1;
779 mbox->num_deleted++;
780 return 0;
781 }
782
783 static int
784 mailbox_unix_undelete (mailbox_t mbox, size_t msgno)
785 {
786 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
787
788 /* oops out of range ? */
789 /* if already undeleted, noop */
790 if (mud == 0 || ! mailbox_unix_is_valid (mbox, msgno)
791 || ! mailbox_unix_is_deleted (mbox, msgno))
792 {
793 return 0;
794 }
795
796 /* Mark undeletion */
797 mud->messages[msgno].deleted = 0;
798 mbox->num_deleted--;
799 return 0;
800 }
801
802 static FILE *
803 mailbox_unix_tmpfile ()
804 {
805 /*FIXME: racing conidtions, to correct, .i.e don;t use tmpfile*/
806 //return tmpfile ();
807 return fopen ("/tmp/mymail", "w");
808 }
809
810 /*
811 FIXME: the use of tmpfile() on some system can lead to
812 race condition, We should use a safer approach.
813 We take a very naive approach to this, it involves unfortunately
814 two copies.
815 */
816 static int
817 mailbox_unix_expunge (mailbox_t mbox)
818 {
819 mailbox_unix_data_t mud = (mailbox_unix_data_t)mbox->data;
820 mailbox_unix_msg_t mum;
821 sigset_t sigset;
822 FILE *tmpfile;
823 size_t i;
824 off_t total = 0;
825 char buffer [BUFSIZ];
826
827 if (mud == NULL)
828 {
829 return EINVAL;
830 }
831 if (mbox->messages == 0 || mbox->num_deleted <= 0)
832 {
833 /* noop */
834 return 0;
835 }
836
837 tmpfile = mailbox_unix_tmpfile ();
838 if (tmpfile == NULL)
839 {
840 return errno;
841 }
842
843 /* Get the lock */
844 mailbox_unix_ilock (mbox, MU_MB_RDLOCK);
845 flockfile (mud->file);
846 if (mailbox_unix_lock (mbox, MU_MB_WRLOCK) < 0)
847 {
848 funlockfile (mud->file);
849 mailbox_unix_iunlock (mbox);
850 fclose (tmpfile);
851 return EINVAL;
852 }
853
854 /* Do we have a consistent view of the mbox */
855 if (! mailbox_unix_is_updated (mbox))
856 {
857 /* things change, flag an error */
858 mailbox_unix_unlock (mbox);
859 funlockfile (mud->file);
860 mailbox_unix_iunlock (mbox);
861 fclose (tmpfile);
862 return EAGAIN;
863 }
864
865
866 rewind (mud->file);
867 /* copy to temp file emails not mark deleted emails */
868 for (i = 1; i <= mbox->messages; i++)
869 {
870 mum = &mud->messages[i];
871 if ( ! mum->deleted)
872 {
873 size_t len = mum->body - mum->header;
874 size_t nread;
875 /* copy the header */
876 if (fseek (mud->file, mum->header, SEEK_SET) == -1)
877 {
878 mailbox_unix_unlock (mbox);
879 funlockfile (mud->file);
880 mailbox_unix_iunlock (mbox);
881 fclose (tmpfile);
882 return EIO;
883 }
884 while (len > 0)
885 {
886 nread = (len < sizeof (buffer)) ? len : sizeof (buffer);
887 if (fread (buffer, sizeof (*buffer), nread, mud->file) != nread
888 || fwrite(buffer, sizeof(*buffer), nread, tmpfile) != nread)
889 {
890 mailbox_unix_unlock (mbox);
891 funlockfile (mud->file);
892 mailbox_unix_iunlock (mbox);
893 fclose (tmpfile);
894 return EIO;
895 }
896 len -= nread;
897 total += nread;
898 }
899
900 /* FIXME: We should set the seen flag also here */
901
902 /* copy the body */
903 len = mum->end - mum->body;
904 if (fseek (mud->file, mum->body, SEEK_SET) < 0)
905 {
906 mailbox_unix_unlock (mbox);
907 funlockfile (mud->file);
908 mailbox_unix_iunlock (mbox);
909 fclose (tmpfile);
910 return EIO;
911 }
912 while (len > 0)
913 {
914 nread = (len < sizeof (buffer)) ? len : sizeof (buffer);
915 if (fread (buffer, sizeof (*buffer), nread, mud->file) != nread
916 || fwrite(buffer, sizeof(*buffer), nread, tmpfile) != nread)
917 {
918 mailbox_unix_unlock (mbox);
919 fclose (tmpfile);
920 mailbox_unix_iunlock (mbox);
921 funlockfile (mud->file);
922 return EIO;
923 }
924 len -= nread;
925 total += nread;
926 }
927 }
928 }
929
930 /* Critical section, we can not allowed signal here */
931 sigemptyset (&sigset);
932 sigaddset (&sigset, SIGTERM);
933 sigaddset (&sigset, SIGHUP);
934 sigaddset (&sigset, SIGTSTP);
935 sigaddset (&sigset, SIGINT);
936 sigaddset (&sigset, SIGWINCH);
937 sigprocmask (SIG_BLOCK, &sigset, 0);
938
939 /* truncate the mailbox and rewrite it */
940 rewind (mud->file);
941 rewind (tmpfile);
942 if (ftruncate (fileno(mud->file), total) < 0)
943 {
944 mailbox_unix_unlock (mbox);
945 funlockfile (mud->file);
946 mailbox_unix_iunlock (mbox);
947 fclose (tmpfile);
948 sigprocmask (SIG_UNBLOCK, &sigset, 0);
949 return EIO;
950 }
951
952 while (total > 0)
953 {
954 size_t nread = ((unsigned)total < sizeof (buffer)) ? total : sizeof (buffer);
955 if (fread (buffer, sizeof (*buffer), nread, mud->file) != nread
956 || fwrite (buffer, sizeof (*buffer), nread, tmpfile) != nread)
957 {
958 mailbox_unix_unlock (mbox);
959 funlockfile (mud->file);
960 mailbox_unix_iunlock (mbox);
961 fclose (tmpfile);
962 sigprocmask (SIG_UNBLOCK, &sigset, 0);
963 return EIO;
964 }
965 total -= nread;
966 }
967
968 fflush (mud->file);
969
970 /* Release the lock */
971 mailbox_unix_unlock (mbox);
972 funlockfile (mud->file);
973 mailbox_unix_iunlock (mbox);
974 fclose (tmpfile);
975 sigprocmask (SIG_UNBLOCK, &sigset, 0);
976 return 0;
977 }
978
979 /* appending */
980 static int
981 mailbox_unix_new_msg (mailbox_t mbox, size_t *msgno)
982 {
983 return ENOSYS;
984 }
985 static int
986 mailbox_unix_set_header (mailbox_t mbox, size_t msgno, const char *h,
987 size_t len, int replace)
988 {
989 return ENOSYS;
990 }
991 static int
992 mailbox_unix_set_body (mailbox_t mbox, size_t msgno, const char *b,
993 size_t len, int replace)
994 {
995 return ENOSYS;
996 }
997 static int
998 mailbox_unix_append (mailbox_t mbox, size_t msgno)
999 {
1000 return ENOSYS;
1001 }
1002 static int
1003 mailbox_unix_destroy_msg (mailbox_t mbox, size_t msgno)
1004 {
1005 return ENOSYS;
1006 }
1007
1008 /* reading */
1009 static int
1010 mailbox_unix_get_body (mailbox_t mbox, size_t msgno, off_t off,
1011 char *buffer, size_t len, size_t *n)
1012 {
1013 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
1014 size_t nread;
1015
1016 /* check if valid */
1017 if (len < 1 || mud == NULL || ! mailbox_unix_is_valid (mbox, msgno))
1018 {
1019 return EINVAL;
1020 }
1021
1022 mailbox_unix_ilock (mbox, MU_MB_RDLOCK);
1023 flockfile (mud->file);
1024 {
1025 mailbox_unix_msg_t mum = &(mud->messages[msgno]);
1026 off_t ln = mum->end - mum->body + off;
1027 if (ln < 0)
1028 {
1029 funlockfile (mud->file);
1030 mailbox_unix_iunlock (mbox);
1031 return EIO;
1032 }
1033 nread = (ln < len) ? ln : len;
1034 /* position the file pointer and the buffer */
1035 if (fseek (mud->file, mum->body + off, SEEK_SET) < 0)
1036 {
1037 funlockfile (mud->file);
1038 mailbox_unix_iunlock (mbox);
1039 return EIO;
1040 }
1041 if (fread (buffer, sizeof (*buffer), nread, mud->file) != nread)
1042 {
1043 funlockfile (mud->file);
1044 mailbox_unix_iunlock (mbox);
1045 return EIO;
1046 }
1047 buffer[nread - 1] = '\0';
1048 }
1049 funlockfile (mud->file);
1050 mailbox_unix_iunlock (mbox);
1051
1052 if (n)
1053 *n = nread;
1054 return 0;
1055 }
1056 static int
1057 mailbox_unix_get_header (mailbox_t mbox, size_t msgno, off_t off,
1058 char *buffer, size_t len, size_t *n)
1059 {
1060 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
1061 size_t nread = 0;
1062
1063 /* check if valid */
1064 if ( len < 1 || mud == NULL || ! mailbox_unix_is_valid (mbox, msgno))
1065 {
1066 return EINVAL;
1067 }
1068
1069 mailbox_unix_ilock (mbox, MU_MB_RDLOCK);
1070 flockfile (mud->file);
1071 {
1072 mailbox_unix_msg_t mum = &(mud->messages[msgno]);
1073 off_t ln = mum->body - mum->header + off;
1074 if (ln < 0)
1075 {
1076 funlockfile (mud->file);
1077 mailbox_unix_iunlock (mbox);
1078 return EIO;
1079 }
1080 nread = (ln < len) ? ln : len;
1081 /* position the file pointer and the buffer */
1082 if (fseek (mud->file, mum->header + off, SEEK_SET) < 0)
1083 {
1084 funlockfile (mud->file);
1085 mailbox_unix_iunlock (mbox);
1086 return EIO;
1087 }
1088 if (fread (buffer, sizeof (*buffer), nread, mud->file) != nread)
1089 {
1090 funlockfile (mud->file);
1091 mailbox_unix_iunlock (mbox);
1092 return EIO;
1093 }
1094 buffer[nread - 1] = '\0';
1095 }
1096 funlockfile (mud->file);
1097 mailbox_unix_iunlock (mbox);
1098
1099 if (n)
1100 *n = nread;
1101 return 0;
1102 }
1103
1104 /* setting flags */
1105 static int
1106 mailbox_unix_is_read (mailbox_t mbox, size_t msgno)
1107 {
1108 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
1109 if (mud == 0 || ! mailbox_unix_is_valid (mbox, msgno))
1110 {
1111 return 0;
1112 }
1113 return mud->messages[msgno].is_read;
1114 }
1115
1116 static int
1117 mailbox_unix_set_read (mailbox_t mbox, size_t msgno)
1118 {
1119 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
1120 if (mud == 0 || ! mailbox_unix_is_valid (mbox, msgno))
1121 {
1122 return EINVAL;
1123 }
1124 mud->messages[msgno].is_read = 1;;
1125 return 0;
1126 }
1127 static int
1128 mailbox_unix_is_seen (mailbox_t mbox, size_t msgno)
1129 {
1130 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
1131 if (mud == 0 || ! mailbox_unix_is_valid (mbox, msgno))
1132 {
1133 return 0;
1134 }
1135 return mud->messages[msgno].is_seen;
1136 }
1137
1138 static int
1139 mailbox_unix_set_seen (mailbox_t mbox, size_t msgno)
1140 {
1141 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
1142 if (mud == 0 || ! mailbox_unix_is_valid (mbox, msgno))
1143 {
1144 return EINVAL;
1145 }
1146 mud->messages[msgno].is_seen = 1;
1147 return 0;
1148 }
1149
1150 /* locking */
1151 static int
1152 mailbox_unix_ilock (mailbox_t mbox, int flag)
1153 {
1154 #ifdef HAVE_PTHREAD_H
1155 pthread_mutex_lock (&mutex)
1156 #endif
1157 return 0;
1158 }
1159
1160 static int
1161 mailbox_unix_iunlock (mailbox_t mbox)
1162 {
1163 #ifdef HAVE_PTHREAD_H
1164 pthread_mutex_unlock (&mutex)
1165 #endif
1166 return 0;
1167 }
1168
1169 static int
1170 mailbox_unix_lock (mailbox_t mbox, int flag)
1171 {
1172 #ifdef HAVE_MAILOCK_H
1173 #endif
1174 return 0;
1175 }
1176 static int
1177 mailbox_unix_unlock (mailbox_t mbox)
1178 {
1179 #ifdef HAVE_MAILOCK_H
1180 #endif
1181 return 0;
1182 }
1183
1184 /* miscellany */
1185 static int
1186 mailbox_unix_size (mailbox_t mbox, off_t *size)
1187 {
1188 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
1189 struct stat st;
1190 int fd;
1191
1192 if (mud == NULL || mud->file == NULL)
1193 {
1194 /* maybe was not open yet ?? */
1195 return EIO;
1196 }
1197 fd = fileno (mud->file);
1198 if (fstat (fd, &st) != 0)
1199 {
1200 /* oops !! */
1201 /* errno set by fstat () */
1202 return EIO;
1203 }
1204 *size = st.st_size;
1205 return 0;
1206 }
1207
1208 static int
1209 mailbox_unix_get_size (mailbox_t mbox, size_t msgno, size_t *h, size_t *b)
1210 {
1211 mailbox_unix_data_t mud = (mailbox_unix_data_t) mbox->data;
1212 mailbox_unix_msg_t mum;
1213
1214 if (mailbox_unix_is_valid (mbox, msgno))
1215 {
1216 return EINVAL;
1217 }
1218 mum = &(mud->messages[msgno]);
1219 if (h)
1220 *h = mum->header - mum->body;
1221 if (b)
1222 *b = mum->body - mum->header;
1223 return 0;
165 } 1224 }
......