5 #define DEBUG_SUBSYSTEM S_SNAP
7 #include <linux/kmod.h>
8 #include <linux/init.h>
10 #include <linux/slab.h>
11 #include <linux/string.h>
12 #include <linux/jbd.h>
13 #include <linux/ext3_fs.h>
14 #include <linux/snap.h>
15 #include <portals/list.h>
16 #include "snapfs_internal.h"
18 * XXX - Not sure for snapfs that the cache functions are even needed.
19 * Can't all lookups be done by an inode->superblock->u.generic_sbp
23 extern struct snap_table snap_tables[SNAP_MAX_TABLES];
25 /* the intent of this hash is to have collision chains of length 1 */
27 #define CACHES_SIZE (1 << CACHES_BITS)
28 #define CACHES_MASK CACHES_SIZE - 1
30 static struct list_head snap_caches[CACHES_SIZE];
33 static inline int snap_cache_hash(kdev_t dev)
35 return (CACHES_MASK) & ((0x000F & (dev)) + ((0x0F00 & (dev)) >>8));
38 inline void snap_cache_add(struct snap_cache *cache, kdev_t dev)
40 list_add(&cache->cache_chain,
41 &snap_caches[snap_cache_hash(dev)]);
42 cache->cache_dev = dev;
45 inline void snap_init_cache_hash(void)
48 for ( i = 0; i < CACHES_SIZE; i++ ) {
49 INIT_LIST_HEAD(&snap_caches[i]);
53 /* map a device to a cache */
54 struct snap_cache *snap_find_cache(kdev_t dev)
56 struct snap_cache *cache;
59 lh = &(snap_caches[snap_cache_hash(dev)]);
60 list_for_each_entry(cache, lh, cache_chain) {
61 if (cache->cache_dev == dev)
67 /* setup a cache structure when we need one */
68 struct snap_cache *snap_init_cache(void)
70 struct snap_cache *cache;
72 /* make a snap_cache structure for the hash */
73 SNAP_ALLOC(cache, sizeof(struct snap_cache));
75 memset(cache, 0, sizeof(struct snap_cache));
76 INIT_LIST_HEAD(&cache->cache_chain);
77 INIT_LIST_HEAD(&cache->cache_clone_list);
81 /*walk through the cache structure*/
82 int snap_cache_process(snap_cache_cb_t cb, void* in, unsigned long* out)
86 for (i = 0; i < CACHES_SIZE; i++) {
87 struct snap_cache *cache;
88 struct list_head *lh = &(snap_caches[i]);
89 list_for_each_entry(cache, lh, cache_chain) {
90 if (cb(cache, in, out))
99 /* free a cache structure and all of the memory it is pointing to */
100 inline void snap_free_cache(struct snap_cache *cache)
104 SNAP_FREE(cache, sizeof(struct snap_cache));