Closed Bug 597224 Opened 14 years ago Closed 14 years ago

HTTP Cache: use directory tree to store cache files

Categories

(Core :: Networking: Cache, defect)

defect
Not set
normal

Tracking

()

RESOLVED FIXED
Tracking Status
blocking2.0 --- beta9+

People

(Reporter: jduell.mcbugs, Assigned: michal)

References

(Blocks 2 open bugs)

Details

Attachments

(1 file, 3 obsolete files)

The squid developers have told us that some filesystems start to degrade in performance once they have 256 or more files per directory, and we currently dump 1000s of cache files into just one directory. This will be alleviated somewhat by bug 593198 (which we should probably do first), but we'll still probably want to move to use multiple directories. (unless we determine that all our filesystems of interest do OK with lots of files--including mobile devices.)
I'm currently using a cache directory which is itself heavily fragmented, because there are much more files as before.
Taras has found (bug 593198 comment 20) that we're taking a 1-2 second hit at some point at startup to open (and list?) the cache directory, because it's so fragmented from having too many files in one dir. I like his proposal: "lets change the storage algorithm so a file like 3E3E27FEd01 would become Cache/3/E/3E27FEd01 with Cache/0->F/ directories preallocated on cache creation to avoid fragmentation. We can lazy allocate their subdirs." I'd love to see this in FF4, but I don't expect we can block for it. If we can get a patch in time, though, I hope we can approve it. (Is there a "wanted-2.0" flag or something I should set?).
blocking2.0: --- → ?
Assignee: nobody → michal.novotny
Attached patch fix (obsolete) (deleted) — Splinter Review
Attachment #480884 - Flags: review?(jduell.mcbugs)
Attached patch patch v2 (obsolete) (deleted) — Splinter Review
I forgot to cut the first 2 chars from the filename.
Attachment #480884 - Attachment is obsolete: true
Attachment #480901 - Flags: review?(jduell.mcbugs)
Attachment #480884 - Flags: review?(jduell.mcbugs)
Yeah, not blocking.
blocking2.0: ? → -
I think this is wanted but I don't see a flag. Why does this bug depend on 593198? They are IMO independent or maybe this bug blocks 593198.
Yes, I think we do want this if it can be done for ff4, but also don't know what flag to set/ask for "want but not block". This seems likely to be easier to do quickly than bug 593198, which has the whole "how to shrink" problem. And you're right, I don't think they depend on each other.
No longer depends on: 593198
Blocks: 572459
For consideration: offline application's nsDiskCacheDeviceSQL is already using something like that, see [1]. Maybe stay consistent? [1] http://mxr.mozilla.org/mozilla-central/source/netwerk/cache/nsDiskCacheDeviceSQL.cpp#180
Blocks: 604897
Should be blocking because bug #604897 is blocking.
blocking2.0: - → ?
Comment on attachment 480901 [details] [diff] [review] patch v2 So this patch winds up having a directory tree with 16 parent subdirectories, each of which can have 16 subdirs, for 255 directories total. I suspect we want more. I don't know that we have good statistics on the breakdown of our cache files, but many users will have a 1 GB cache, and our current _CACHE_123 files are only 30 MB or so each, so until/unless we change that, users are going to have a *lot* of separate files. (Ex: if avg size is 2K, that's 500K files, most of which won't fit in the block files, if my read of bug 604897 comment 5 is right (all three CACHE files will add up to 90 MB). Even if we fit 90% of files in the block files, that's still 50K files, which would be 196 files per directory--close to the 255 cutoff where squid has found perf degradation.) So I propose we use two hex digits for the leaf directory names, ie. have 16 parent subdirs, and 255 leaf ones, for 4080 directories total. This would add a little extra cost to reading files (another directory inode to traverse, with less likelihood of it being in the filesystem cache), but it would avoid what seem to be more serious problems with too many files per directory on some systems. I'm open to arguments that we can store enough files in the cache block files, if someone has numbers to back that up. +r with this issue sorted out. >diff --git a/netwerk/cache/nsDiskCacheMap.cpp b/netwerk/cache/nsDiskCacheMap.cpp >@@ -87,16 +88,19 @@ nsDiskCacheMap::Open(nsILocalFile * cac > // check size of map file > PRUint32 mapSize = PR_Available(mMapFD); > if (mapSize == 0) { // creating a new _CACHE_MAP_ > > // block files shouldn't exist if we're creating the _CACHE_MAP_ > if (cacheFilesExist) > goto error_exit; Do we want a "cacheSubdirsExist" variable, too? I.e. should we check for the existence of at least the 16 top-level subdirs, at the same time we check for _CACHE_MAP_ and the cache block files? I'm less concerned about the case of them preexisting when we don't expect them (this code block) as I am about the 'else' block below all this (for opening an existing cache directory) where we'd implicitly assume they're present, but if any are missing, we might behave badly. Perhaps I'm being too paranoid--I'm not sure what would delete those directories (and if it did, it could always delete them during operation, after we've checked them at startup, and still break things).
(In reply to comment #11) > (Ex: if avg size is 2K, that's 500K files, most of which won't fit in the block > files, if my read of bug 604897 comment 5 is right (all three CACHE files will > add up to 90 MB). Even if we fit 90% of files in the block files, that's still > 50K files, which would be 196 files per directory--close to the 255 cutoff > where squid has found perf degradation.) After 604897 lands we can put up to 172032 records into the block files. So there is no way to fit 90% of the entries to the block files. Also remember that the cache entry has 2 records (metadata and data). > So I propose we use two hex digits for the leaf directory names, ie. have 16 > parent subdirs, and 255 leaf ones, for 4080 directories total. This would add > a little extra cost to reading files (another directory inode to traverse, with > less likelihood of it being in the filesystem cache), but it would avoid what > seem to be more serious problems with too many files per directory on some > systems. Why not to use Cache/0/1/2/34567d01 instead of Cache/0/12/34567d01 ? > I'm open to arguments that we can store enough files in the cache block files, > if someone has numbers to back that up. I'm running locally firefox with the fix from bug #604897 for several weeks now, so my FF caches entries even if the block files are full. It occupies 614MB. I'll try to get some stats from my cache. > Do we want a "cacheSubdirsExist" variable, too? I.e. should we check for the > existence of at least the 16 top-level subdirs, at the same time we check for > _CACHE_MAP_ and the cache block files? I'm less concerned about the case of > them preexisting when we don't expect them (this code block) as I am about the > 'else' block below all this (for opening an existing cache directory) where > we'd implicitly assume they're present, but if any are missing, we might behave > badly. Perhaps I'm being too paranoid--I'm not sure what would delete those > directories (and if it did, it could always delete them during operation, after > we've checked them at startup, and still break things). We don't need to do it. Any missing subdirectory would be created.
> Why not to use Cache/0/1/2/34567d01 instead of Cache/0/12/34567d01 ? a 2-level directory tree instead of 3 level means fewer filesystem directory inodes to traverse, and it seems like 256 subdirs is still small enough to avoid perf problems. Keeping the top-level to 16 dirs makes it more likely that the inodes for the first directory is in the OS cache. I just looked at how squid does this, and they use this same scheme (16 parent, with 256 leaf dirs), so that's a good sign.
Blocking, and I think this needs to happen ASAP, to get some mileage on this before we release.
blocking2.0: ? → beta9+
Here is some statistics from my cache that occupies 639989 KB (max size is 640MB). Average count of files per subdirectory is 169. If the cache size were 1GB then this the count would be around 444. So I agree that 16*256 subdirectories should be used. There are few interesting things that I'd like to investigate later: - high number of files with zero size - there should be 43381 separate files on the disk but 2 are missing - a lot of small files are stored as separate files, although there is quite a lot of free blocks metadata data both ------------------------------------------ count 58592 58592 117184 average 668.13 9289.15 4978.64 Records grouped by block files limits: ------------------------------------------ 0 0 3091 3091 1-768 50327 16797 67124 769-3072 5641 14961 20602 3073-16384 2624 16632 19256 16385- 0 7111 7111 Records grouped by blocks usage in block files: ------------------------------------------ 1-256 351 10289 10640 257-512 39916 4376 44292 513-768 10060 2132 12192 769-1024 3454 2002 5456 1025-2048 1944 7613 9557 2049-3072 243 5346 5589 3073-4096 1575 3542 5117 4097-8192 1049 7706 8755 8193-12288 0 3487 3487 12289-16384 0 1897 1897 Number of blocks needed to fit all small files into block files: ------------------------------------------ 256 110355 25436 135791 1024 8071 33260 41331 4096 3673 37003 40676 Where are actually stored files of size 1-768: ------------------------------------------ separate file 8570 3347 11917 _CACHE_001_ 41305 13435 54740 _CACHE_002_ 299 9 308 _CACHE_003_ 153 6 159 Where are actually stored files of size 769-3072: ------------------------------------------ separate file 3167 5845 9012 _CACHE_002_ 2367 8535 10902 _CACHE_003_ 107 581 688 Where are actually stored files of size 3073-16384: ------------------------------------------ separate file 1752 13589 15341 _CACHE_003_ 872 3041 3913 Bitmap of _CACHE_000_: ------------------------------------------ free bits : 20419 free continuous blocks (1) : 46 free continuous blocks (2) : 217 free continuous blocks (3) : 34 free continuous blocks (4+) : 881 Bitmap of _CACHE_001_: ------------------------------------------ free bits : 9768 free continuous blocks (1) : 14 free continuous blocks (2) : 19 free continuous blocks (3) : 28 free continuous blocks (4+) : 387 Bitmap of _CACHE_002_: ------------------------------------------ free bits : 0 free continuous blocks (1) : 0 free continuous blocks (2) : 0 free continuous blocks (3) : 0 free continuous blocks (4+) : 0
Attached patch patch v3 - now using 16*256 subdirectories (obsolete) (deleted) — Splinter Review
Attachment #480901 - Attachment is obsolete: true
Attachment #495003 - Flags: superreview?(bzbarsky)
Attachment #480901 - Flags: review?(jduell.mcbugs)
Comment on attachment 495003 [details] [diff] [review] patch v3 - now using 16*256 subdirectories Please add some comments explaining that the shifts by 28 and 20 and the 0xFFFFF mask partition the hashnumber, just so that's clear? sr=me.
Attachment #495003 - Flags: superreview?(bzbarsky) → superreview+
Attached patch patch v4 - added comment (deleted) — Splinter Review
Attachment #495003 - Attachment is obsolete: true
Keywords: checkin-needed
Status: NEW → RESOLVED
Closed: 14 years ago
Resolution: --- → FIXED
Keywords: checkin-needed
Depends on: 648232
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: