Revision history for Perl extension Cache::FastMmap.

1.62 Sun May 17 2026
  - Fix remaining Perl-side lock leaks when user supplied
    serializer/deserializer code throws while get_and_set()
    or other locked paths are active.
  - Validate get_and_set() callback options before merging
    them into the internal locked set() call.
  - Fix expire() in write-back mode to write back the
    original Perl value, not the serialized/compressed bytes.
  - Track all live empty_on_exit caches independently instead
    of keeping only one weak reference per class.
  - Preserve silent write/delete callback failure behavior while
    keeping locks exception-safe for serializer/deserializer failures.
  - Add regression coverage for expire() with serialized values,
    multiple empty_on_exit caches, and locked exception paths.

1.61 Sat Apr 25 23:18 2026
  - Remove Cache::FastMmap::OnLeave guard object and inline
    fc_lock/fc_unlock at every call site. The per-call cost
    of building and destroying the guard closure was a
    meaningful share of CPU in cache-heavy workloads.
  - Replace the internal skip_lock/skip_unlock guard-passing
    pattern (used by get_and_set / get_and_remove) with a
    simpler _locked => 1 boolean flag.
  - Preserve the documented exception-safety contract for
    get_and_set, plus the equivalent unwritten contract for
    get (read_cb that dies), multi_get, and multi_set: the
    page lock is always released even when user code throws.
  - Add t/24.t covering the lock-release contract on every
    exception path.
  - mmc_write: check for available space before deleting an
    existing slot for the key, so a failed set() preserves
    the previous value instead of silently losing it.
  - _mmc_set_error (unix.c, win32.c): use snprintf into the
    remaining buffer space instead of strncat with the wrong
    size argument, which could overflow errbuf on long error
    messages.
  - mmc_lock: fix off-by-one allowing page == c_num_pages
    (one past the last valid page).
  - mmc_lock: replace hardcoded num_slots >= 89 sanity check
    with cache->start_slots, so caches built with custom
    start_slots values lock correctly.
  - mmc_check_fh: check fstat() return value before trusting
    statbuf.st_ino, restoring the safety net the function
    was added for.
  - mmc_iterate_next: end iteration cleanly if mmc_lock fails
    instead of walking stale page state.
  - Win32 mmc_unlock_page: split p_offset into Offset and
    OffsetHigh and add the missing return, so caches larger
    than 4GB unlock at the same offset they locked at.
  - Win32 mmc_lock_page: CloseHandle on the event handle on
    every exit path; previously every successful lock leaked
    one HANDLE.

1.60 Wed Jun 18 9:25 2025
  - Fix very broken 1.59 release that was leaving pages
    locked after initialising them.

1.59 Tue Jun 3 17:25 2025
  - Add exists() method to check if key exists in the
    cache. This avoid the decompress + deserialize cost
  - Initialise pages under lock. This avoids potential
    race conditions where multiple processes try and init
    a cache file
  - Correctly reset p_changed after storing changed details
    back to cache.

1.58 Mon May 5 16:25 2025
  - Catch a rare bug if someone closes our underlying file
    handle unexpectedly

1.57 Thu Sep 30 16:25 2021
  - Add expire($key) method to allow explicitly expiring
    a key from the cache. In write-back mode, if the key
    is dirty it will be written back, in other modes it's
    the same as remove($key)

1.56 Mon Dec 14 14:35 2020
  - Update MANIFEST to include all tests. It hasn't
    been updated in a while

1.55 Mon Dec 14 12:10 2020
  - Add ability to override internal value of 'time'
    everywhere to make tests that check expiry of items
    faster and more robust

1.54 Sat Dec 12 13:40 2020
  - Add Test::Deep as dependency to Makefile.PL

1.53 Thu Dec 10 13:40 2020
  - Handle expire_on being undef (use cache default) and
    return undef if existing value not found in cache.
    Makes get_and_set which passes on expire_on just work
    in "doesn't exist" case

1.52 Thu Dec 10 12:20 2020
  - Fix bug where a get() on a key that was expired would
     cause that key to be deleted and never written back
     even if it was dirty
  - Added new expire_on naming so that expire_time
     (relative future time) and expire_on (absolute
     unix epoch time) are now clear and distinct
  - Allow setting expire_on when doing a set() call,
     which is useful from get_and_set() to maintain
     an items absolute expiry time

1.51 Wed Nov 11 17:15 2020
  - Skip JSON/Sereal tests if modules not present
  - Updated .gitignore
    Thanks to https://github.com/szabgab/
  - GitHub Actions config file
    Thanks to https://github.com/szabgab/

1.50 Fri Nov 6 20:40 2020
  - Allow get_and_set sub to return an options
    hash passed to the internal set call

1.49 Tue Mar 24 10:15 2020
  - Fix windows compilation and test warnings
    Thanks to hvn@radiatorsoftware.com

1.48 Thu Apr 11 11:30 2019
  - Remove use of // so we should work on 5.8 again
  - Replace -1 with a NOPAGE constant
  - Use 64bit offsets so we support caches > 4G
  - Various valgrind code fixes
    Thanks to oschwald@gmail.com

1.47 Fri Apr 6 11:10 2018
  - Allow custom serializer or compressor options
  - Update bugtracker link to github
    Thanks to toddr@cpan.org

1.46 Fri Jul 14 19:40 2017
  - Fix tests on older perls (thanks stephanloyd9@gmail.com)
  - Use File::Spec for temp dir (thanks fraserbn@gmail.com)
  - Fix mmap_cache_internals.h include guard
  - Fix get_and_set() always returning 0 for DidStore
  - Allow setting permission when creating cache file
  - Tweak leak detection tests
  - Fix last_access/expire_time checks for impending
     1500000000 seconds since epoch

1.45 Thu Mar 14 11:10 2017
  - Deprecate raw_values and compress options, add
     new compressor and serializer options to allow
     different compressors and serializers.
     Initial compressor support: zlib, lz4, snappy
     Initial serializer support: storable, sereal, json
     Thanks to nickt@broadbean.com for initial work

1.44 Wed Jun 1 21:45 2016
  - Set FD_CLOEXEC flag on cache files when opened.
     Particularly useful in Net::Server where
     HUPing a process causes it to exec() itself.
     Unless you undef the cache references, you'll
     leak fd's after each HUP

1.43 Fri Oct 23 14:00 2015
  - Update copyright + version correctly everywhere

1.42 Fri Oct 23 13:30 2015
  - Allow get_and_set callback to return an empty list
     which means "no change". This allows atomic
     "get, and set if not present" type action, but
     without resetting the expiry time on each get.
     This is basically the same as using the read_cb

1.41 Thu Aug 29 15:30 2013
  - Actually reuse deleted slots. Meant that if
     you used ->remove() a lot, we would re-organise
     cache more than needed
  - Include typo and meta patches from dsteinbrunner

1.40 Mon Dec 5  10:30 2011
  - Work around reference holding bug in
     Compress::Zlib

1.39 Mon Jul 18 09:50 2011
  - Remove CImpl and simplify structure into just
     Cache::FastMmap module making all XS calls
     just function calls in Cache::FastMmap
     namespace

1.38 Sun Jul 17 18:30 2011
  - Fix build process that was completely broken
     after moving files around into different
     directories

1.37 Fri Jul 15 16:30 2011
  - Use a lock object with DESTROY method to avoid
     an alarm with a die leaving around a locked
     paged

1.36 Wed Sep 29 13:10 2010
  - Disable wrapping fcntl() lock call in alarm, hurts
     people that use Time::HiRes::alarm() only to try
     and catch buggy deadlock code. Enable with
     catch_deadlocks option

1.35 Fri Feb 19 12:45 2010
  - Fix for returning potential bug that returns old stored
     data. Could occur if you mix deletes
     (thanks Darrell Bishop)

1.34 Fri Jun 19 12:00 2009
  - perldoc fix (thanks Jonathan Yu)

1.33 Thu Jun 18 12:00 2009
  - Update version in META.yml

1.32 Thu Jun 18 11:55 2009
  - Better LiveCaches tracking via DESTROY

1.31 Thu Jun 18 11:40 2009
  - when in raw_values => 0 mode, the write_cb is now
    correctly called with thawed data, rather than the
    raw frozen data
  - empty_on_exit correctly called even when a global
    cache is left at interpreter exit time (required
    Scalar::Util qw(weaken) for object tracking)

1.30 Fri May 8  11:10 2009
  - Fix for Mandriva compiler (thanks Jean-Christian Hassler)

1.29 Fri May 1  17:20 2009
  - Support for Windows (thanks to Ash & kmx.at.volny.cz)
    (https://rt.cpan.org/Public/Bug/Display.html?id=45210)
    (https://rt.cpan.org/Public/Bug/Display.html?id=16501)

1.28 Fri Jun 27 11:05 2008
  - get_and_set() returns new value + didstore boolean
     if called in list context

1.27  Wed Jun 18 17:15 2008
  - Fix non-ansi C code
  - Remove debug flags

1.26  Thu May 22 14:50 2008
  - Check for write failure when creating file
      thanks to Sam Vilain
  - Check for $ENV{TMP_DIR}
      thanks to Sam Vilain
  - Add compress option
  - Add basic statistics gathering

1.25  Mon Feb 04 13:20 2008
  - Fix multi_set bug and add test
    (http://rt.cpan.org/Ticket/Display.html?id=32895)
  - Test share_file is not a reference
    (http://rt.cpan.org/Ticket/Display.html?id=32252)
  - Fix C variable declaration error
    (http://rt.cpan.org/Ticket/Display.html?id=31223)
  - Fix compile warnings in FreeBSD
    (http://rt.cpan.org/Ticket/Display.html?id=31900)
  - Thanks to all the people that contributed
     to the above bugs

1.24  Mon Oct 22 13:15 2007
  - Add atomic get_and_remove() method thanks to
      Darrell Bishop

1.23  Wed Oct 17 16:00 2007
  - Fix expire time parsing

1.22  Wed Oct 17 14:05 2007
  - If third parameter to set() is not a references, treat it as
    a specify expiry time. Increases compatiability with
    Cache::Cache API. Helpful for Catalyst framework

1.21  Tue Oct 16 10:40 2007
  - if first parameter to new() is a hash ref, use it as
     the options hash. Helpful for Catalyst framework

1.20  Thu Oct 2 13:40 2007
  - add to documentation about page size and cache file locations
  - fix t/6.t test failure under new Test::More

1.19  Thu Aug 23 09:03 2007
  - bad C declaration crept in again, now in svn

1.18  Thu Aug 22 17:30 2007
  - fix use of $^O not to catch "darwin"
    (http://rt.cpan.org/Ticket/Display.html?id=28330)

1.17  Thu Aug 22 17:14 2007
  - fix declaration in C code that wasn't legal C

1.16  Thu May 8 17:12 2007
  - fix typo in Changes file (1.15 is 2007, not 2006)
  - fix get_keys(2) when undef values in cache
  - fix some leak detection tests

1.15  Thu May 8 17:12 2007
  - catch and rethrow die/exceptions in get_and_set() callbacks
  - avoid undef warnings when using cache_not_found mode
  - use unique tempfile name rather than the same every time
  - add allow_recursive option to allow calls to cache
    from within a read/write callback sub
  - add checks to die if we try and lock a cache twice,
    rather than just causing mysterious errors
  - add unlink_on_exit to automatically delete the share_file
    when the cache exits. default to true if we created
    the share_file, false if we connected to an existing one
  - make empty_on_exit only call empty if the pid of the
    process we're cleaning up in is the same as the pid we
    were created in
  - die in CLONE, making it clear threads aren't supported

1.14  Thu Oct 20 11:45 2006
  - alter calc_expunge to allow more efficient alternate
    implementation cases

1.13  Thu Oct 20 11:15 2006
  - mention UNIX/Win32 compatiability in docs
    (http://rt.cpan.org/Ticket/Display.html?id=16501)
  - detect page corruption better and croak rather than segfault
    (http://rt.cpan.org/Ticket/Display.html?id=17335)
  - when running in raw_values => 0 mode, always store
    reference to data. Storable doesn't like freeze(SCALAR)
    (http://rt.cpan.org/Ticket/Display.html?id=16762)
  - Handle edge case of slot count increase when page
    already nearly full possibly causing corruption
    (can only happen if ->purge() called at just the wrong time)

1.12  Thu Oct 19 09:50 2006
  - allow writing into a deleted slot

1.11  Web Oct 18 15:10 2006
  - allow setting default slot count via start_slots argument

1.10  Web Oct 18 14:50 2006
  - fc_lock() would segfault if no slots were available.
    Doesn't happen in normal usage, but can happen if
    cache behaviour altered by alternate code

1.09  Thu Feb  7 15:50 2005
  - add get_and_set() routine to allow atomic reading and
    writing of a cache value (thanks to Sreeji Das)
  - fix some tests

1.08  Thu Aug 26 12:18 2004
  - really remove dependency on perl 5.8

1.07  Thu Aug 19 22:18 2004
  - add extra documentation
  - add parameter to empty() method
  - add ability to test integrity of cache file
  - remove dependency on perl 5.8

1.06  Thu May 10 17:18 2004
  - add multi_set and multi_get methods

1.05  Sat Jan 31 17:24 2004
  - fix another edge case where page would get full, but never
    expunged when storing references

1.04  Sun Jan 25 00:46 2004
  - fix test file after new changes

1.03  Sun Jan 25 00:21 2004
  - fix bad sorting when removing old cache entries

1.02  Sat Jan 24 17:05 2004
  - fix edge case where page would get full, but never expunged

1.01  Sat Dec 13 18:17 2003
	- fix leak from improper munmap call

1.00  Sat Dec 13 14:19 2003
	- initial release
