1#ifndef __LINUX_DCACHE_H 2#define __LINUX_DCACHE_H 3 4#ifdef __KERNEL__ 5 6#include <asm/atomic.h> 7#include <linux/mount.h> 8#include <linux/kernel.h> 9 10/* 11 * linux/include/linux/dcache.h 12 * 13 * Dirent cache data structures 14 * 15 * (C) Copyright 1997 Thomas Schoebel-Theuer, 16 * with heavy changes by Linus Torvalds 17 */ 18 19#define IS_ROOT(x) ((x) == (x)->d_parent) 20 21/* 22 * "quick string" -- eases parameter passing, but more importantly 23 * saves "metadata" about the string (ie length and the hash). 24 */ 25struct qstr { 26 const unsigned char * name; 27 unsigned int len; 28 unsigned int hash; 29}; 30 31struct dentry_stat_t { 32 int nr_dentry; 33 int nr_unused; 34 int age_limit; /* age in seconds */ 35 int want_pages; /* pages requested by system */ 36 int dummy[2]; 37}; 38extern struct dentry_stat_t dentry_stat; 39 40/* Name hashing routines. Initial hash value */ 41/* Hash courtesy of the R5 hash in reiserfs modulo sign bits */ 42#define init_name_hash() 0 43 44/* partial hash update function. Assume roughly 4 bits per character */ 45static __inline__ unsigned long partial_name_hash(unsigned long c, unsigned long prevhash) 46{ 47 return (prevhash + (c << 4) + (c >> 4)) * 11; 48} 49 50/* Finally: cut down the number of bits to a int value (and try to avoid losing bits) */ 51static __inline__ unsigned long end_name_hash(unsigned long hash) 52{ 53 return (unsigned int) hash; 54} 55 56/* Compute the hash for a name string. */ 57static __inline__ unsigned int full_name_hash(const unsigned char * name, unsigned int len) 58{ 59 unsigned long hash = init_name_hash(); 60 while (len--) 61 hash = partial_name_hash(*name++, hash); 62 return end_name_hash(hash); 63} 64 65#define DNAME_INLINE_LEN 16 66 67struct dentry { 68 atomic_t d_count; 69 unsigned int d_flags; 70 struct inode * d_inode; /* Where the name belongs to - NULL is negative */ 71 struct dentry * d_parent; /* parent directory */ 72 struct list_head d_hash; /* lookup hash list */ 73 struct list_head d_lru; /* d_count = 0 LRU list */ 74 struct list_head d_child; /* child of parent list */ 75 struct list_head d_subdirs; /* our children */ 76 struct list_head d_alias; /* inode alias list */ 77 int d_mounted; 78 struct qstr d_name; 79 unsigned long d_time; /* used by d_revalidate */ 80 struct dentry_operations *d_op; 81 struct super_block * d_sb; /* The root of the dentry tree */ 82 unsigned long d_vfs_flags; 83 void * d_fsdata; /* fs-specific data */ 84 unsigned char d_iname[DNAME_INLINE_LEN]; /* small names */ 85}; 86 87struct dentry_operations { 88 int (*d_revalidate)(struct dentry *, int); 89 int (*d_hash) (struct dentry *, struct qstr *); 90 int (*d_compare) (struct dentry *, struct qstr *, struct qstr *); 91 int (*d_delete)(struct dentry *); 92 void (*d_release)(struct dentry *); 93 void (*d_iput)(struct dentry *, struct inode *); 94}; 95 96/* the dentry parameter passed to d_hash and d_compare is the parent 97 * directory of the entries to be compared. It is used in case these 98 * functions need any directory specific information for determining 99 * equivalency classes. Using the dentry itself might not work, as it 100 * might be a negative dentry which has no information associated with 101 * it */ 102 103/* 104locking rules: 105 big lock dcache_lock may block 106d_revalidate: no no yes 107d_hash no no yes 108d_compare: no yes no 109d_delete: no yes no 110d_release: no no yes 111d_iput: no no yes 112 */ 113 114/* d_flags entries */ 115#define DCACHE_AUTOFS_PENDING 0x0001 /* autofs: "under construction" */ 116#define DCACHE_NFSFS_RENAMED 0x0002 /* this dentry has been "silly 117 * renamed" and has to be 118 * deleted on the last dput() 119 */ 120#define DCACHE_NFSD_DISCONNECTED 0x0004 /* This dentry is not currently connected to the 121 * dcache tree. Its parent will either be itself, 122 * or will have this flag as well. 123 * If this dentry points to a directory, then 124 * s_nfsd_free_path semaphore will be down 125 */ 126#define DCACHE_REFERENCED 0x0008 /* Recently used, don't discard. */ 127 128extern spinlock_t dcache_lock; 129 130/** 131 * d_drop - drop a dentry 132 * @dentry: dentry to drop 133 * 134 * d_drop() unhashes the entry from the parent 135 * dentry hashes, so that it won't be found through 136 * a VFS lookup any more. Note that this is different 137 * from deleting the dentry - d_delete will try to 138 * mark the dentry negative if possible, giving a 139 * successful _negative_ lookup, while d_drop will 140 * just make the cache lookup fail. 141 * 142 * d_drop() is used mainly for stuff that wants 143 * to invalidate a dentry for some reason (NFS 144 * timeouts or autofs deletes). 145 */ 146 147static __inline__ void d_drop(struct dentry * dentry) 148{ 149 spin_lock(&dcache_lock); 150 list_del(&dentry->d_hash); 151 INIT_LIST_HEAD(&dentry->d_hash); 152 spin_unlock(&dcache_lock); 153} 154 155static __inline__ int dname_external(struct dentry *d) 156{ 157 return d->d_name.name != d->d_iname; 158} 159 160/* 161 * These are the low-level FS interfaces to the dcache.. 162 */ 163extern void d_instantiate(struct dentry *, struct inode *); 164extern void d_delete(struct dentry *); 165 166/* allocate/de-allocate */ 167extern struct dentry * d_alloc(struct dentry *, const struct qstr *); 168extern void shrink_dcache_sb(struct super_block *); 169extern void shrink_dcache_parent(struct dentry *); 170extern int d_invalidate(struct dentry *); 171 172#define shrink_dcache() prune_dcache(0) 173struct zone_struct; 174/* dcache memory management */ 175extern int shrink_dcache_memory(int, unsigned int); 176extern void prune_dcache(int); 177 178/* icache memory management (defined in linux/fs/inode.c) */ 179extern int shrink_icache_memory(int, int); 180extern void prune_icache(int); 181 182/* quota cache memory management (defined in linux/fs/dquot.c) */ 183extern int shrink_dqcache_memory(int, unsigned int); 184 185/* only used at mount-time */ 186extern struct dentry * d_alloc_root(struct inode *); 187 188/* <clickety>-<click> the ramfs-type tree */ 189extern void d_genocide(struct dentry *); 190 191extern struct dentry *d_find_alias(struct inode *); 192extern void d_prune_aliases(struct inode *); 193 194/* test whether we have any submounts in a subdir tree */ 195extern int have_submounts(struct dentry *); 196 197/* 198 * This adds the entry to the hash queues. 199 */ 200extern void d_rehash(struct dentry *); 201 202/** 203 * d_add - add dentry to hash queues 204 * @entry: dentry to add 205 * @inode: The inode to attach to this dentry 206 * 207 * This adds the entry to the hash queues and initializes @inode. 208 * The entry was actually filled in earlier during d_alloc(). 209 */ 210 211static __inline__ void d_add(struct dentry * entry, struct inode * inode) 212{ 213 d_instantiate(entry, inode); 214 d_rehash(entry); 215} 216 217/* used for rename() and baskets */ 218extern void d_move(struct dentry *, struct dentry *); 219 220/* appendix may either be NULL or be used for transname suffixes */ 221extern struct dentry * d_lookup(struct dentry *, struct qstr *); 222 223/* validate "insecure" dentry pointer */ 224extern int d_validate(struct dentry *, struct dentry *); 225 226extern char * __d_path(struct dentry *, struct vfsmount *, struct dentry *, 227 struct vfsmount *, char *, int); 228 229/* Allocation counts.. */ 230 231/** 232 * dget, dget_locked - get a reference to a dentry 233 * @dentry: dentry to get a reference to 234 * 235 * Given a dentry or %NULL pointer increment the reference count 236 * if appropriate and return the dentry. A dentry will not be 237 * destroyed when it has references. dget() should never be 238 * called for dentries with zero reference counter. For these cases 239 * (preferably none, functions in dcache.c are sufficient for normal 240 * needs and they take necessary precautions) you should hold dcache_lock 241 * and call dget_locked() instead of dget(). 242 */ 243 244static __inline__ struct dentry * dget(struct dentry *dentry) 245{ 246 if (dentry) { 247 if (!atomic_read(&dentry->d_count)) 248 out_of_line_bug(); 249 atomic_inc(&dentry->d_count); 250 } 251 return dentry; 252} 253 254extern struct dentry * dget_locked(struct dentry *); 255 256/** 257 * d_unhashed - is dentry hashed 258 * @dentry: entry to check 259 * 260 * Returns true if the dentry passed is not currently hashed. 261 */ 262 263static __inline__ int d_unhashed(struct dentry *dentry) 264{ 265 return list_empty(&dentry->d_hash); 266} 267 268extern void dput(struct dentry *); 269 270static __inline__ int d_mountpoint(struct dentry *dentry) 271{ 272 return dentry->d_mounted; 273} 274 275extern struct vfsmount *lookup_mnt(struct vfsmount *, struct dentry *); 276#endif /* __KERNEL__ */ 277 278#endif /* __LINUX_DCACHE_H */ 279