8d138742 |
1 | /* $Id: mail.h,v 1.3 2009/06/27 17:12:00 mrsam Exp $ */ |
d9898ee8 |
2 | |
3 | #ifndef liblockmail_h |
4 | #define liblockmail_h |
5 | |
6 | /* |
7 | ** Copyright 2002 Double Precision, Inc. See COPYING for |
8 | ** distribution information. |
9 | */ |
10 | |
11 | #ifdef __cplusplus |
12 | extern "C" { |
13 | #endif |
14 | |
15 | /* |
16 | ** Functions for mbox mail locks |
17 | */ |
18 | |
19 | struct ll_mail { |
20 | char *file; /* File being locked */ |
21 | |
22 | /* c-client type lock */ |
23 | |
24 | int cclientfd; |
25 | char *cclientfile; |
26 | |
27 | |
28 | /* dotlock */ |
29 | |
30 | char *dotlock; |
31 | }; |
32 | |
33 | struct ll_mail *ll_mail_alloc(const char *filename); |
34 | |
35 | /* |
36 | ** Create a c-client type lock. NOTE: c-clients will ping you with SIGUSR2, |
37 | ** which must be ignored for this implementation. |
38 | ** Returns: 0 - ok, < 0 - error. |
39 | ** |
40 | ** An error return from ll_mail_lock carries some additional context in |
41 | ** errno: |
42 | ** |
43 | ** errno == EAGAIN: potential race condition. The current lock holder MIGHT |
44 | ** have just terminated. The caller should sleep for AT LEAST 5 seconds, then |
45 | ** try again. |
46 | ** |
47 | ** errno == EEXIST: another process on this server DEFINITELY has the lock. |
48 | ** |
49 | ** Implementations might choose to wait and try again on EEXIST as well. |
50 | */ |
51 | |
52 | int ll_mail_lock(struct ll_mail *); |
53 | |
54 | /* |
55 | ** Open the mail file, read/write (creating a dot-lock). |
56 | ** Returns: >= 0 - file descriptor, < 0 - error (if EPERM, try ll_open_ro). |
57 | ** |
58 | ** errno == EEXIST: another process appears to hold a dot-lock. |
59 | ** |
60 | ** errno == EAGAIN: We just blew away a stale dotlock, should try again |
61 | ** in at least five seconds. Should NOT get two EAGAIN's in a row. |
62 | */ |
63 | |
64 | int ll_mail_open(struct ll_mail *); |
65 | |
66 | /* |
67 | ** Open in read-only mode. |
68 | */ |
69 | |
70 | int ll_mail_open_ro(struct ll_mail *); |
71 | |
72 | /* |
73 | ** Release all locks, deallocate structure. NOTE: file descriptor from |
74 | ** ll_mail_open(_ro)? is NOT closed, it's your responsibility to do that. |
75 | */ |
76 | |
77 | void ll_mail_free(struct ll_mail *); |
78 | |
79 | /* |
80 | ** As long as we have the logic done already, here's a generic dot-locking |
81 | ** function. |
82 | ** |
83 | ** dotlock - the actual filename of a dotlock file. |
84 | ** tmpfile - the filename of a temporary file to create first. |
85 | ** timeout - optional timeout. |
86 | ** |
87 | ** Return code: 0: dotlock is created. Just unlink(dotlock) when you're done. |
88 | ** |
89 | ** -1 error. Check errno: |
90 | ** |
91 | ** EEXIST - dotlock is locked |
92 | ** |
93 | ** EAGAIN - dotlock is stale (dotlock created on this machine, and the |
94 | ** process no longer exists, or dotlock created on another |
95 | ** machine, and timeout argument was > 0, and the dotlock's |
96 | ** timestamp was older than timeout seconds. |
97 | ** |
98 | ** E????? - something's broken. |
99 | ** |
100 | */ |
101 | |
102 | int ll_dotlock(const char *dotlock, const char *tmpfile, |
103 | int timeout); |
104 | |
105 | #ifdef __cplusplus |
8d138742 |
106 | } |
d9898ee8 |
107 | #endif |
108 | |
109 | #endif |