mirror of
https://github.com/samba-team/samba.git
synced 2025-02-02 09:47:23 +03:00
tdb: Reimplementation of Metze's "lib/tdb: if we know pwrite and pread are thread/fork safe tdb_reopen_all() should be a noop".
This version just wraps the reopen code, so we still re-grab the lock and do the normal sanity checks. The reason we do this at all is to avoid global fd limits, see: http://forums.fedoraforum.org/showthread.php?t=210393 Note also that this whole reopen concept is fundamentally racy: if the parent goes away before the child calls tdb_reopen_all, the database can be left without an active lock and another TDB_CLEAR_IF_FIRST opener will clear it. A fork_with_tdbs() wrapper could use a pipe to solve this, but it's hardly elegant (what if there are other independent things which have similar needs?). Signed-off-by: Rusty Russell <rusty@rustcorp.com.au> Signed-off-by: Stefan Metzmacher <metze@samba.org>
This commit is contained in:
parent
fa91bc6719
commit
3b2f074bda
@ -425,6 +425,9 @@ int tdb_reopen(struct tdb_context *tdb)
|
||||
goto fail;
|
||||
}
|
||||
|
||||
/* If we have real pread & pwrite, we can skip reopen. */
|
||||
#if !defined(LIBREPLACE_PREAD_NOT_REPLACED) || \
|
||||
!defined(LIBREPLACE_PWRITE_NOT_REPLACED)
|
||||
if (tdb_munmap(tdb) != 0) {
|
||||
TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: munmap failed (%s)\n", strerror(errno)));
|
||||
goto fail;
|
||||
@ -436,11 +439,6 @@ int tdb_reopen(struct tdb_context *tdb)
|
||||
TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: open failed (%s)\n", strerror(errno)));
|
||||
goto fail;
|
||||
}
|
||||
if ((tdb->flags & TDB_CLEAR_IF_FIRST) &&
|
||||
(tdb->methods->tdb_brlock(tdb, ACTIVE_LOCK, F_RDLCK, F_SETLKW, 0, 1) == -1)) {
|
||||
TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: failed to obtain active lock\n"));
|
||||
goto fail;
|
||||
}
|
||||
if (fstat(tdb->fd, &st) != 0) {
|
||||
TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: fstat failed (%s)\n", strerror(errno)));
|
||||
goto fail;
|
||||
@ -450,6 +448,13 @@ int tdb_reopen(struct tdb_context *tdb)
|
||||
goto fail;
|
||||
}
|
||||
tdb_mmap(tdb);
|
||||
#endif /* fake pread or pwrite */
|
||||
|
||||
if ((tdb->flags & TDB_CLEAR_IF_FIRST) &&
|
||||
(tdb->methods->tdb_brlock(tdb, ACTIVE_LOCK, F_RDLCK, F_SETLKW, 0, 1) == -1)) {
|
||||
TDB_LOG((tdb, TDB_DEBUG_FATAL, "tdb_reopen: failed to obtain active lock\n"));
|
||||
goto fail;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user