1/* SPDX-License-Identifier: GPL-2.0 */ 2/* 3 * fs/hmdfs/hmdfs_dentryfile.h 4 * 5 * Copyright (c) 2020-2021 Huawei Device Co., Ltd. 6 */ 7 8#ifndef HMDFS_DENTRYFILE_H 9#define HMDFS_DENTRYFILE_H 10 11#include "hmdfs.h" 12#include <linux/namei.h> 13 14/* use for escape from hmdfs file system, hmdfs hide follow names */ 15#define CURRENT_DIR "." 16#define PARENT_DIR ".." 17 18/* local dentry cache data */ 19#define DENTRY_FILE_XATTR_NAME "user.hmdfs_cache" 20 21#define DENTRY_FILE_NAME_RETRY 10 22 23#define MAX_BUCKET_LEVEL 63 24#define BUCKET_BLOCKS 2 25#define MAX_DIR_BUCKETS (1 << ((MAX_BUCKET_LEVEL / 2) - 1)) 26 27#define CONFLICTING_FILE_CONST_SUFFIX "_conflict_dev" 28#define CONFLICTING_FILE_SUFFIX "_conflict_dev%u" 29#define CONFLICTING_DIR_SUFFIX "_remote_directory" 30 31#define POS_BIT_NUM 64 32#define DEV_ID_BIT_NUM 16 33#define GROUP_ID_BIT_NUM 39 34#define OFFSET_BIT_NUM 8 35#define OFFSET_BIT_MASK 0xFF 36 37#define DEFAULT_DCACHE_TIMEOUT 30 38#define DEFAULT_DCACHE_PRECISION 10 39#define DEFAULT_DCACHE_THRESHOLD 1000 40#define HMDFS_STALE_REMOTE_ISIZE ULLONG_MAX 41 42/* Seconds per-week */ 43#define MAX_DCACHE_TIMEOUT 604800 44 45struct hmdfs_iterate_callback { 46 struct dir_context ctx; 47 struct dir_context *caller; 48 int result; 49 struct rb_root *root; 50}; 51 52/* 53 * 4096 = version(1) + bitmap(10) + reserved(5) 54 * + nsl(80 * 43) + filename(80 * 8) 55 */ 56#define DENTRYGROUP_SIZE 4096 57#define DENTRY_NAME_LEN 8 58#define DENTRY_RESERVED_LENGTH 3 59#define DENTRY_PER_GROUP 80 60#define DENTRY_BITMAP_LENGTH 10 61#define DENTRY_GROUP_RESERVED 5 62#define DENTRYGROUP_HEADER 4096 63 64struct hmdfs_dentry { 65 __le32 hash; 66 __le16 i_mode; 67 __le16 namelen; 68 __le64 i_size; 69 /* modification time */ 70 __le64 i_mtime; 71 /* modification time in nano scale */ 72 __le32 i_mtime_nsec; 73 /* combination of inode number and generation */ 74 __le64 i_ino; 75 __le32 i_flag; 76 /* reserved bytes for long term extend, total 43 bytes */ 77 __u8 reserved[DENTRY_RESERVED_LENGTH]; 78} __packed; 79 80/* 4K/51 Bytes = 80 dentries for per dentrygroup */ 81struct hmdfs_dentry_group { 82 __u8 dentry_version; /* dentry version start from 1 */ 83 __u8 bitmap[DENTRY_BITMAP_LENGTH]; 84 struct hmdfs_dentry nsl[DENTRY_PER_GROUP]; 85 __u8 filename[DENTRY_PER_GROUP][DENTRY_NAME_LEN]; 86 __u8 reserved[DENTRY_GROUP_RESERVED]; 87} __packed; 88 89/** 90 * The content of 1st 4k block in dentryfile.dat. 91 * Used for check whether the dcache can be used directly or 92 * need to rebuild. 93 * 94 * Since the ctime has 10ms or less precision, if the dcache 95 * rebuild at the same time of the dentry inode ctime, maybe 96 * non-consistent in dcache. 97 * eg: create 1.jpg 2.jpg 3.jpg 98 * dcache rebuild may only has 1.jpg 2.jpg 99 * So, we need use these time to verify the dcache. 100 */ 101struct hmdfs_dcache_header { 102 /* The time of dcache rebuild */ 103 __le64 dcache_crtime; 104 __le64 dcache_crtime_nsec; 105 106 /* The directory inode ctime when dcache rebuild */ 107 __le64 dentry_ctime; 108 __le64 dentry_ctime_nsec; 109 110 /* The dentry count */ 111 __le64 num; 112 113 /* The case sensitive */ 114 __u8 case_sensitive; 115} __packed; 116 117static inline loff_t get_dentry_group_pos(unsigned int bidx) 118{ 119 return ((loff_t)bidx) * DENTRYGROUP_SIZE + DENTRYGROUP_HEADER; 120} 121 122static inline unsigned int get_dentry_group_cnt(struct inode *inode) 123{ 124 loff_t size = i_size_read(inode); 125 126 return size >= DENTRYGROUP_HEADER ? 127 (size - DENTRYGROUP_HEADER) / DENTRYGROUP_SIZE : 128 0; 129} 130 131#define DENTRY_NAME_MAX_LEN (DENTRY_PER_GROUP * DENTRY_NAME_LEN) 132#define BITS_PER_BYTE 8 133#define HMDFS_SLOT_LEN_BITS 3 134#define get_dentry_slots(x) (((x) + BITS_PER_BYTE - 1) >> HMDFS_SLOT_LEN_BITS) 135 136#define INUNUMBER_START 10000000 137 138#ifdef CONFIG_HMDFS_FS_PERMISSION 139#define DENTRY_FILE_PERM 0660 140#else 141#define DENTRY_FILE_PERM 0666 142#endif 143 144struct hmdfs_dcache_lookup_ctx { 145 struct hmdfs_sb_info *sbi; 146 const struct qstr *name; 147 struct file *filp; 148 __u32 hash; 149 150 /* for case sensitive */ 151 unsigned int bidx; 152 struct hmdfs_dentry_group *page; 153 154 /* for case insensitive */ 155 struct hmdfs_dentry *insense_de; 156 unsigned int insense_bidx; 157 struct hmdfs_dentry_group *insense_page; 158}; 159 160extern void hmdfs_init_dcache_lookup_ctx(struct hmdfs_dcache_lookup_ctx *ctx, 161 struct hmdfs_sb_info *sbi, 162 const struct qstr *qstr, 163 struct file *filp); 164 165int create_dentry(struct dentry *child_dentry, struct inode *inode, 166 struct file *file, struct hmdfs_sb_info *sbi); 167int read_dentry(struct hmdfs_sb_info *sbi, char *file_name, 168 struct dir_context *ctx); 169struct hmdfs_dentry *hmdfs_find_dentry(struct dentry *child_dentry, 170 struct hmdfs_dcache_lookup_ctx *ctx); 171void hmdfs_delete_dentry(struct dentry *d, struct file *filp); 172int hmdfs_rename_dentry(struct dentry *old_dentry, struct dentry *new_dentry, 173 struct file *old_filp, struct file *new_filp); 174int get_inonumber(void); 175struct file *create_local_dentry_file_cache(struct hmdfs_sb_info *sbi); 176int update_inode_to_dentry(struct dentry *child_dentry, struct inode *inode); 177struct file *cache_file_persistent(struct hmdfs_peer *con, struct file *filp, 178 const char *relative_path, bool server); 179 180#define HMDFS_TYPE_COMMON 0 181#define HMDFS_TYPE_DOT 1 182#define HMDFS_TYPE_DENTRY 2 183#define HMDFS_TYPE_DENTRY_CACHE 3 184int hmdfs_file_type(const char *name); 185 186loff_t hmdfs_set_pos(unsigned long dev_id, unsigned long group_id, 187 unsigned long offset); 188 189struct getdents_callback_real { 190 struct dir_context ctx; 191 struct path *parent_path; 192 loff_t num; 193 struct file *file; 194 struct hmdfs_sb_info *sbi; 195 const char *dir; 196}; 197 198struct file *hmdfs_server_rebuild_dents(struct hmdfs_sb_info *sbi, 199 struct path *path, loff_t *num, 200 const char *dir); 201 202#define DCACHE_LIFETIME 30 203 204struct clearcache_item { 205 uint64_t dev_id; 206 struct file *filp; 207 unsigned long time; 208 struct list_head list; 209 struct kref ref; 210 struct hmdfs_dentry_info *d_info; 211}; 212 213void hmdfs_add_remote_cache_list(struct hmdfs_peer *con, const char *dir_path); 214 215struct remotecache_item { 216 struct hmdfs_peer *con; 217 struct list_head list; 218 __u8 drop_flag; 219}; 220 221#define HMDFS_CFN_CID_SIZE 65 222#define HMDFS_SERVER_CID "" 223 224struct cache_file_node { 225 struct list_head list; 226 struct hmdfs_sb_info *sbi; 227 char *relative_path; 228 u8 cid[HMDFS_CFN_CID_SIZE]; 229 refcount_t ref; 230 bool server; 231 struct file *filp; 232}; 233 234struct cache_file_item { 235 struct list_head list; 236 const char *name; 237}; 238 239struct cache_file_callback { 240 struct dir_context ctx; 241 const char *dirname; 242 struct hmdfs_sb_info *sbi; 243 bool server; 244 struct list_head list; 245}; 246 247int hmdfs_drop_remote_cache_dents(struct dentry *dentry); 248void hmdfs_send_drop_push(struct hmdfs_peer *con, const char *path); 249void hmdfs_mark_drop_flag(uint64_t device_id, struct dentry *dentry); 250void hmdfs_clear_drop_flag(struct dentry *dentry); 251void delete_in_cache_file(uint64_t dev_id, struct dentry *dentry); 252void create_in_cache_file(uint64_t dev_id, struct dentry *dentry); 253struct clearcache_item *hmdfs_find_cache_item(uint64_t dev_id, 254 struct dentry *dentry); 255bool hmdfs_cache_revalidate(unsigned long conn_time, uint64_t dev_id, 256 struct dentry *dentry); 257void hmdfs_remove_cache_filp(struct hmdfs_peer *con, struct dentry *dentry); 258int hmdfs_add_cache_list(uint64_t dev_id, struct dentry *dentry, 259 struct file *filp); 260int hmdfs_clear_cache_dents(struct dentry *dentry, bool remove_cache); 261 262int hmdfs_root_unlink(uint64_t device_id, struct path *root_path, 263 const char *unlink_dir, const char *unlink_name); 264struct dentry *hmdfs_root_mkdir(uint64_t device_id, const char *local_dst_path, 265 const char *mkdir_dir, const char *mkdir_name, 266 umode_t mode); 267struct dentry *hmdfs_root_create(uint64_t device_id, const char *local_dst_path, 268 const char *create_dir, 269 const char *create_name, 270 umode_t mode, bool want_excl); 271int hmdfs_root_rmdir(uint64_t device_id, struct path *root_path, 272 const char *rmdir_dir, const char *rmdir_name); 273int hmdfs_root_rename(struct hmdfs_sb_info *sbi, uint64_t device_id, 274 const char *oldpath, const char *oldname, 275 const char *newpath, const char *newname, 276 unsigned int flags); 277 278int hmdfs_get_path_in_sb(struct super_block *sb, const char *name, 279 unsigned int flags, struct path *path); 280 281int hmdfs_wlock_file(struct file *filp, loff_t start, loff_t len); 282int hmdfs_rlock_file(struct file *filp, loff_t start, loff_t len); 283int hmdfs_unlock_file(struct file *filp, loff_t start, loff_t len); 284long cache_file_truncate(struct hmdfs_sb_info *sbi, const struct path *path, 285 loff_t length); 286ssize_t cache_file_read(struct hmdfs_sb_info *sbi, struct file *filp, void *buf, 287 size_t count, loff_t *pos); 288ssize_t cache_file_write(struct hmdfs_sb_info *sbi, struct file *filp, 289 const void *buf, size_t count, loff_t *pos); 290int hmdfs_metainfo_read_nocred(struct file *filp, 291 void *buffer, int size, int bidx); 292int hmdfs_metainfo_read(struct hmdfs_sb_info *sbi, struct file *filp, 293 void *buffer, int buffersize, int bidx); 294 295bool get_remote_dentry_file(struct dentry *dentry, struct hmdfs_peer *con); 296void get_remote_dentry_file_sync(struct dentry *dentry, struct hmdfs_peer *con); 297int get_cloud_cache_file(struct dentry *dentry, struct hmdfs_sb_info *sbi); 298 299void release_cache_item(struct kref *ref); 300void remove_cache_item(struct clearcache_item *item); 301 302void hmdfs_cfn_load(struct hmdfs_sb_info *sbi); 303void hmdfs_cfn_destroy(struct hmdfs_sb_info *sbi); 304struct cache_file_node *find_cfn(struct hmdfs_sb_info *sbi, const char *cid, 305 const char *path, bool server); 306void release_cfn(struct cache_file_node *cfn); 307void destroy_cfn(struct hmdfs_sb_info *sbi); 308void remove_cfn(struct cache_file_node *cfn); 309int delete_dentry_file(struct file *filp); 310struct file *hmdfs_server_cache_revalidate(struct hmdfs_sb_info *sbi, 311 const char *recvpath, 312 struct path *path); 313int write_header(struct file *filp, struct hmdfs_dcache_header *header); 314 315static inline struct list_head *get_list_head(struct hmdfs_sb_info *sbi, 316 bool server) 317{ 318 return ((server) ? &(sbi)->server_cache : &(sbi)->client_cache); 319} 320 321/* 322 * generate_u64_ino - generate a new 64 bit inode number 323 * 324 * @ino: origin 32 bit inode number 325 * @generation: origin 32 bit inode generation 326 * 327 * We need both remote inode number and generation to ensure the uniqueness of 328 * the local inode, thus we store inode->i_ino in lower 32 bits, and 329 * inode->i_generation in higher 32 bits. 330 */ 331static inline uint64_t generate_u64_ino(unsigned long ino, 332 unsigned int generation) 333{ 334 return (uint64_t)ino | ((uint64_t)generation << 32); 335} 336 337static inline bool cache_item_revalidate(unsigned long conn_time, 338 unsigned long item_time, 339 unsigned int timeout) 340{ 341 return time_before_eq(jiffies, item_time + timeout * HZ) && 342 time_before_eq(conn_time, item_time); 343} 344 345__u32 hmdfs_dentry_hash(const struct qstr *qstr, bool case_sense); 346__u64 get_bucketaddr(unsigned int level, __u64 buckoffset); 347__u64 get_bucket_by_level(unsigned int level); 348unsigned int get_max_depth(struct file *filp); 349#endif 350