https://bugs.openldap.org/show_bug.cgi?id=7853
--- Comment #4 from Howard Chu hyc@openldap.org --- (In reply to dw@hmmz.org from comment #0)
Full_Name: David Wilson Version: LMDB 0.9.11 OS: URL: https://raw.githubusercontent.com/dw/py-lmdb/master/misc/readers_mrb_env. patch Submission from: (NULL) (178.238.153.20)
Currently if a user (wilfully or accidentally, say, through composition of third party libs) opens the same LMDB environment twice within a process, and maintains active read transactions at the time one mdb_env_close() is called, all reader slots will be deallocated in all environments due to the logic around line 4253 that unconditionally clears reader slots based on PID.
I'd like to avoid this in py-lmdb, and seems there are a few alternatives to fix it:
- Modify lock.mdb to include MDB_env* address within the process, and update
mdb_env_close() to invalidate only readers associated with the environment being closed. I dislike using the MDB_env* as an opaque publicly visible cookie, but perhaps storing this field might be reused for other things in future.
I was looking at this approach, which initially seems harmless. But unfortunately it does nothing to address the fact the fcntl lock on the lock file will still go away on the first env_close() call. If there are no other processes with the env open, then the next process that opens the env will re-init the lock file, because it doesn't know about the existing process. At that point the existing process is hosed anyway.
So the question is, if a process has made the mistake of opening the same env twice, what is the anticipated lifetime of each env instance? If the code was written according to doc guidelines, then both env instances should only be closed after all processing is done and just before program exit. In that case it doesn't really matter what happens to the reader table or the fcntl lock. But if the two instances have drastically different lifetimes, then all bets are off.