Promote the pdkim variant-implementation sha routines to toplevel
[exim.git] / src / src / enq.c
CommitLineData
059ec3d9
PH
1/*************************************************
2* Exim - an Internet mail transport agent *
3*************************************************/
4
8d6d5106 5/* Copyright (c) University of Cambridge 1995 - 2015 */
059ec3d9
PH
6/* See the file NOTICE for conditions of use and distribution. */
7
8/* Functions concerned with serialization. */
9
10
11#include "exim.h"
12
13
14
15
16/*************************************************
17* Test for host or ETRN serialization *
18*************************************************/
19
20/* This function is called when a host is listed for serialization of
21connections. It is also called when ETRN is listed for serialization. We open
22the misc database and look for a record, which implies an existing connection
e8ae7214
JH
23or ETRN run. If increasing the count would take us past the given limit
24value return FALSE. If not, bump it and return TRUE. If not found, create
25one with value 1 and return TRUE.
059ec3d9
PH
26
27Arguments:
28 key string on which to serialize
e8ae7214 29 lim parallelism limit
059ec3d9
PH
30
31Returns: TRUE if OK to proceed; FALSE otherwise
32*/
33
34
35BOOL
e8ae7214 36enq_start(uschar *key, unsigned lim)
059ec3d9
PH
37{
38dbdata_serialize *serial_record;
39dbdata_serialize new_record;
40open_db dbblock;
41open_db *dbm_file;
42
43DEBUG(D_transport) debug_printf("check serialized: %s\n", key);
44
45/* Open and lock the waiting information database. The absence of O_CREAT is
46deliberate; the dbfn_open() function - which is an Exim function - always tries
47to create if it can't open a read/write file. It expects only O_RDWR or
48O_RDONLY as its argument. */
49
e8ae7214
JH
50if (!(dbm_file = dbfn_open(US"misc", O_RDWR, &dbblock, TRUE)))
51 return FALSE;
059ec3d9
PH
52
53/* See if there is a record for this host or queue run; if there is, we cannot
54proceed with the connection unless the record is very old. */
55
56serial_record = dbfn_read(dbm_file, key);
e8ae7214 57if (serial_record && time(NULL) - serial_record->time_stamp < 6*60*60)
059ec3d9 58 {
e8ae7214
JH
59 if (serial_record->count >= lim)
60 {
61 dbfn_close(dbm_file);
62 DEBUG(D_transport) debug_printf("outstanding serialization record for %s\n",
63 key);
64 return FALSE;
65 }
66 new_record.count = serial_record->count + 1;
059ec3d9 67 }
e8ae7214
JH
68else
69 new_record.count = 1;
059ec3d9 70
e8ae7214 71/* We can proceed - insert a new record or update the old one. */
059ec3d9 72
e8ae7214
JH
73DEBUG(D_transport) debug_printf("write serialization record for %s val %d\n",
74 key, new_record.count);
059ec3d9
PH
75dbfn_write(dbm_file, key, &new_record, (int)sizeof(dbdata_serialize));
76dbfn_close(dbm_file);
77return TRUE;
78}
79
80
81
82/*************************************************
83* Release serialization *
84*************************************************/
85
86/* This function is called when a serialized host's connection or serialized
87ETRN queue run ends. We open the relevant database and delete its record.
88
89Arguments:
90 key the serialization key
91
92Returns: nothing
93*/
94
95void
96enq_end(uschar *key)
97{
98open_db dbblock;
99open_db *dbm_file;
e8ae7214 100dbdata_serialize *serial_record;
059ec3d9
PH
101
102DEBUG(D_transport) debug_printf("end serialized: %s\n", key);
103
e8ae7214
JH
104if ( !(dbm_file = dbfn_open(US"misc", O_RDWR, &dbblock, TRUE))
105 || !(serial_record = dbfn_read(dbm_file, key))
106 )
107 return;
108if (--serial_record->count > 0)
109 {
110 DEBUG(D_transport) debug_printf("write serialization record for %s val %d\n",
111 key, serial_record->count);
112 dbfn_write(dbm_file, key, serial_record, (int)sizeof(dbdata_serialize));
113 }
114else
115 {
116 DEBUG(D_transport) debug_printf("remove serialization record for %s\n", key);
117 dbfn_delete(dbm_file, key);
118 }
059ec3d9
PH
119dbfn_close(dbm_file);
120}
121
122/* End of enq.c */