-
Notifications
You must be signed in to change notification settings - Fork 820
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Issue with memory mapped GeoIP DB files in Linux? #7669
Comments
Agreed, it does seem like an issue, I had not had a chance to test it with the new maxmind_acl one since we havent put it into production yet. That one will close existing opened mmdb's and reload but only on restart or on remap reload when the plugin reloading makes a new instance, so I can see corruption being an issue At least some warnings in docs should be added that if using a new mmdb/geoip file then the config should be changed and you should do some sort of swapping of names between the dbs in order to not touch one that is in use until if/when a solution can be done |
opened an issue with mmdb as well, since it just seems like good functionality to have, maxmind/libmaxminddb#256 |
@pbchou can you try your test with a method as outlined here, https://github.com/maxmind/geoipupdate/blob/main/pkg/geoipupdate/database/local_file_writer.go#L134 Its in golang but you should be able to do something similar in C, i.e. write new db to a temp file, rename it to the existing DB, and then issue a sync call to atomically write the changes? This is what is recommended from the mmdb devs and what their updater tool does |
If you change the test to not reset the length (when count == 2) and use a mv instead of a copy, things run along fine (still reading 0s). I'm not sure changing the length there is a valid state since mmap is with the original length. |
The test resets the length in case the new DB is larger than the old one, and there are pointers to the regions of the file which are larger than the old file. It turns out the look-up function in the MaxMind libraries do have a pointer vs size check so it should result in a return of "corrupted database" rather than causing a segmentation fault. I assume this mv-vs-cp method works because the mmap is anchored to the disk contents rather than the file. Is there an issue with possible over-write of the disk contents after the disk sectors are freed when the original DB is replaced (perhaps old file needs to be kept with a dummy *.old file name)? |
On unix systems, when you atomically replace a file (or use |
Before the database is opened with MMDB_open(), why not first copy the database file as possibly a hidden file and then MMDB_open() and get a file handle to the copy. Any changes to the configured database file would not affect ATS but, the plugin could notice the change to the configured filename and make another copy, use MMDB_open() to get a 2nd file handle to the new copy. When it is determined safe to do so, swap the the active file handle with the new file handle and MMDB_close the old file handle. Maybe using a smart pointer to the active file handle or a mutex in order to swap file handles. |
So some feedback from us now that we've started deploying this plugin. Yes doing a copy is an issue, but doing the Thats at least to how it relates to the ats maxmind plugin |
If this is still an issue please reopen. |
Hi. I would appreciate any second opinions on this issue. I noticed that the current MaxMind enabled plugins (geoip_acl, header_rewrite, and maxmind_acl) all use the memory mapped method to open GeoIP DB files using the MaxMind libraries. The geoip_acl and header_rewrite plugins use the old geopi-api-c that allows either loading the DB into memory (GEOIP_MEMORY_CACHE) or using a memory map (GEOIP_MMAP_CACHE). The newer maxmind_acl plugin uses the newer libmaxminddb that only allows the memory map mode (MMDB_MODE_MMAP).
The potential issue is whether over-writing the DB files on the disk is visible to the MaxMind libraries. My testing on Linux says that it is although the Linux man page says that the behavior is unspecified --
Since changes are visible -- this can interfere with any in-progress look-ups when the over-write happens. In addition, if the newer DB file is larger than the older DB file, then pointers to areas of the file extending beyond the original file size may be considered by the MaxMind libraries to be corrupted DB pointers. I think the pointer vs size checking would prevent any segmentation faults at least. So in general, you would need to close and re-open the DB files if they are over-written on disk.
So should we --
Test program I used on Linux --
The text was updated successfully, but these errors were encountered: