{
int rc;
struct flock lock_data;
-BOOL read_only = flags & O_RDONLY;
+BOOL read_only = (flags & (O_WRONLY|O_RDWR)) == O_RDONLY;
uschar * dirname, * filename;
/* The first thing to do is to open a separate file on which to lock. This
ensures that Exim has exclusive use of the database before it even tries to
-open it. If there is a database, there should be a lock file in existence. */
+open it. If there is a database, there should be a lock file in existence;
+if no lockfile we infer there is no database and error out. We open the
+lockfile using the r/w mode requested for the DB, users lacking permission
+for the DB access mode will error out here. */
if ( asprintf(CSS &dirname, "%s/db", spool_directory) < 0
|| asprintf(CSS &filename, "%s/%s.lockfile", dirname, name) < 0)
return NULL;
-if ((dbblock->lockfd = Uopen(filename, O_RDWR|O_CREAT, 0)) < 0)
+if ((dbblock->lockfd = Uopen(filename, flags, 0)) < 0)
{
printf("** Failed to open database lock file %s: %s\n", filename,
strerror(errno));
if (b->open(b, NULL, CS name, NULL,
flags & O_CREAT ? DB_HASH : DB_UNKNOWN,
flags & O_CREAT ? DB_CREATE
- : flags & O_RDONLY ? DB_RDONLY
- : 0, /*XXX is there a writeable if exists option? */
+ : flags & (O_WRONLY|O_RDWR) ? 0 : DB_RDONLY,
mode) == 0
)
return dbp;
dbp->open(dbp, CS name, NULL,
flags & O_CREAT ? DB_HASH : DB_UNKNOWN,
flags & O_CREAT ? DB_CREATE
- : flags & O_RDONLY ? DB_RDONLY
- : 0, /*XXX*/
+ : flags & (O_WRONLY|O_RDWR) ? 0 : DB_RDONLY,
mode)
) == 0
? dbp : NULL;
dbp->lkey.dptr = NULL;
dbp->gdbm = gdbm_open(CS name, 0,
flags & O_CREAT ? GDBM_WRCREAT
- : flags & (O_RDWR|O_WRONLY) ? GDBM_WRITER
- : GDBM_READER,
+ : flags & (O_RDWR|O_WRONLY) ? GDBM_WRITER : GDBM_READER,
mode, 0);
if (dbp->gdbm) return dbp;
free(dbp);
cmdlog: '220:EHLO:250:MAIL:250:RCPT:550:QUIT:250'
locking TESTSUITE/spool/db/callout.lockfile
locked TESTSUITE/spool/db/callout.lockfile
- EXIM_DBOPEN: file <TESTSUITE/spool/db/callout> dir <TESTSUITE/spool/db> flags=O_RDWR|O_CREAT
+ EXIM_DBOPEN: file <TESTSUITE/spool/db/callout> dir <TESTSUITE/spool/db> flags=O_RDWR
returned from EXIM_DBOPEN: 0xAAAAAAAA
- opened hints database TESTSUITE/spool/db/callout: flags=O_RDWR|O_CREAT
+ opened hints database TESTSUITE/spool/db/callout: flags=O_RDWR
dbfn_write: key=remote datalen NNN
wrote callout cache domain record for remote:
result=1 postmaster=0 random=0
cmdlog: '220:EHLO:250:MAIL:250:RCPT:250:QUIT:220'
locking TESTSUITE/spool/db/callout.lockfile
locked TESTSUITE/spool/db/callout.lockfile
- EXIM_DBOPEN: file <TESTSUITE/spool/db/callout> dir <TESTSUITE/spool/db> flags=O_RDWR|O_CREAT
+ EXIM_DBOPEN: file <TESTSUITE/spool/db/callout> dir <TESTSUITE/spool/db> flags=O_RDWR
returned from EXIM_DBOPEN: 0xAAAAAAAA
- opened hints database TESTSUITE/spool/db/callout: flags=O_RDWR|O_CREAT
+ opened hints database TESTSUITE/spool/db/callout: flags=O_RDWR
dbfn_write: key=y datalen NNN
wrote callout cache domain record for y:
result=1 postmaster=0 random=0