#include <linux/types.h>
#include <linux/fs.h>
#include <linux/seq_file.h>
+#include <linux/mm.h>
#include <uapi/linux/lustre/lustre_user.h>
extern struct kmem_cache *pcc_inode_slab;
#define LPROCFS_WR_PCC_MAX_CMD 4096
+/* User/Group/Project ID */
+struct pcc_match_id {
+ __u32 pmi_id;
+ struct list_head pmi_linkage;
+};
+
+/* wildcard file name */
+struct pcc_match_fname {
+ char *pmf_name;
+ struct list_head pmf_linkage;
+};
+
+enum pcc_field {
+ PCC_FIELD_UID,
+ PCC_FIELD_GID,
+ PCC_FIELD_PROJID,
+ PCC_FIELD_FNAME,
+ PCC_FIELD_MAX
+};
+
+struct pcc_expression {
+ enum pcc_field pe_field;
+ struct list_head pe_cond;
+ struct list_head pe_linkage;
+};
+
+struct pcc_conjunction {
+ /* link to disjunction */
+ struct list_head pc_linkage;
+ /* list of logical conjunction */
+ struct list_head pc_expressions;
+};
+
+/**
+ * Match rule for auto PCC-cached files.
+ */
+struct pcc_match_rule {
+ char *pmr_conds_str;
+ struct list_head pmr_conds;
+};
+
+struct pcc_matcher {
+ __u32 pm_uid;
+ __u32 pm_gid;
+ __u32 pm_projid;
+ struct qstr *pm_name;
+};
+
struct pcc_dataset {
- __u32 pccd_id; /* Archive ID */
- __u32 pccd_projid; /* Project ID */
+ __u32 pccd_rwid; /* Archive ID */
+ __u32 pccd_roid; /* Readonly ID */
+ struct pcc_match_rule pccd_rule; /* Match rule */
+ __u32 pccd_rwonly:1, /* Only use as RW-PCC */
+ pccd_roonly:1; /* Only use as RO-PCC */
char pccd_pathname[PATH_MAX]; /* full path */
struct path pccd_path; /* Root path */
struct list_head pccd_linkage; /* Linked to pccs_datasets */
- atomic_t pccd_refcount; /* reference count */
+ atomic_t pccd_refcount; /* Reference count */
};
struct pcc_super {
- spinlock_t pccs_lock; /* Protect pccs_datasets */
- struct list_head pccs_datasets; /* List of datasets */
+ /* Protect pccs_datasets */
+ spinlock_t pccs_lock;
+ /* List of datasets */
+ struct list_head pccs_datasets;
+ /* creds of process who forced instantiation of super block */
+ const struct cred *pccs_cred;
};
struct pcc_inode {
+ struct ll_inode_info *pcci_lli;
/* Cache path on local file system */
- struct path pcci_path;
+ struct path pcci_path;
/*
* If reference count is 0, then the cache is not inited, if 1, then
* no one is using it.
*/
- atomic_t pcci_refcount;
+ atomic_t pcci_refcount;
/* Whether readonly or readwrite PCC */
- enum lu_pcc_type pcci_type;
- /* Whether the inode is cached locally */
- bool pcci_attr_valid;
+ enum lu_pcc_type pcci_type;
+ /* Whether the inode attr is cached locally */
+ bool pcci_attr_valid;
+ /* Layout generation */
+ __u32 pcci_layout_gen;
+ /*
+ * How many IOs are on going on this cached object. Layout can be
+ * changed only if there is no active IO.
+ */
+ atomic_t pcci_active_ios;
+ /* Waitq - wait for PCC I/O completion. */
+ wait_queue_head_t pcci_waitq;
};
struct pcc_file {
char *pccc_pathname;
union {
struct pcc_cmd_add {
- __u32 pccc_id;
- __u32 pccc_projid;
+ __u32 pccc_rwid;
+ __u32 pccc_roid;
+ struct list_head pccc_conds;
+ char *pccc_conds_str;
} pccc_add;
struct pcc_cmd_del {
__u32 pccc_pad;
} u;
};
-void pcc_super_init(struct pcc_super *super);
+int pcc_super_init(struct pcc_super *super);
void pcc_super_fini(struct pcc_super *super);
int pcc_cmd_handle(char *buffer, unsigned long count,
struct pcc_super *super);
-int
-pcc_super_dump(struct pcc_super *super, struct seq_file *m);
-int pcc_readwrite_attach(struct file *file,
- struct inode *inode, __u32 arch_id);
+int pcc_super_dump(struct pcc_super *super, struct seq_file *m);
+int pcc_readwrite_attach(struct file *file, struct inode *inode,
+ __u32 arch_id);
int pcc_readwrite_attach_fini(struct file *file, struct inode *inode,
- bool lease_broken, int rc, bool attached);
+ __u32 gen, bool lease_broken, int rc,
+ bool attached);
int pcc_ioctl_detach(struct inode *inode);
-int pcc_ioctl_state(struct inode *inode, struct lu_pcc_state *state);
+int pcc_ioctl_state(struct file *file, struct inode *inode,
+ struct lu_pcc_state *state);
void pcc_file_init(struct pcc_file *pccf);
int pcc_file_open(struct inode *inode, struct file *file);
void pcc_file_release(struct inode *inode, struct file *file);
bool *cached);
int pcc_inode_getattr(struct inode *inode, bool *cached);
int pcc_inode_setattr(struct inode *inode, struct iattr *attr, bool *cached);
-int pcc_inode_create(struct pcc_dataset *dataset, struct lu_fid *fid,
- struct dentry **pcc_dentry);
+ssize_t pcc_file_splice_read(struct file *in_file, loff_t *ppos,
+ struct pipe_inode_info *pipe, size_t count,
+ unsigned int flags, bool *cached);
+int pcc_fsync(struct file *file, loff_t start, loff_t end,
+ int datasync, bool *cached);
+int pcc_file_mmap(struct file *file, struct vm_area_struct *vma, bool *cached);
+void pcc_vm_open(struct vm_area_struct *vma);
+void pcc_vm_close(struct vm_area_struct *vma);
+int pcc_fault(struct vm_area_struct *mva, struct vm_fault *vmf, bool *cached);
+int pcc_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf,
+ bool *cached);
+int pcc_inode_create(struct super_block *sb, struct pcc_dataset *dataset,
+ struct lu_fid *fid, struct dentry **pcc_dentry);
int pcc_inode_create_fini(struct pcc_dataset *dataset, struct inode *inode,
- struct dentry *pcc_dentry);
-struct pcc_dataset *
-pcc_dataset_get(struct pcc_super *super, __u32 projid, __u32 archive_id);
+ struct dentry *pcc_dentry);
+struct pcc_dataset *pcc_dataset_match_get(struct pcc_super *super,
+ struct pcc_matcher *matcher);
void pcc_dataset_put(struct pcc_dataset *dataset);
void pcc_inode_free(struct inode *inode);
+void pcc_layout_invalidate(struct inode *inode);
+
#endif /* LLITE_PCC_H */