@@ -2150,3 +2150,27 @@ int vfs_dedupe_file_range(struct file *file, struct file_dedupe_range *same)
return ret;
}
EXPORT_SYMBOL(vfs_dedupe_file_range);
+
+/**
+ * vfs_gethash - obtain a file's hash
+ * @file: file structure in question
+ * @hash_algo: the hash algorithm requested
+ * @buf: buffer to return the hash in
+ * @size: size allocated for the buffer by the caller
+ *
+ * This function allows filesystems that support securely storing the hash
+ * of a file to return it rather than forcing the kernel to recalculate it.
+ * Filesystems that cannot provide guarantees about the hash being resistant
+ * to offline attack should not implement this functionality.
+ *
+ * Returns 0 on success, -EOPNOTSUPP if the filesystem doesn't support it.
+ */
+int vfs_get_hash(struct file *file, enum hash_algo hash, uint8_t *buf,
+ size_t size)
+{
+ if (!file->f_op->get_hash)
+ return -EOPNOTSUPP;
+
+ return file->f_op->get_hash(file, hash, buf, size);
+}
+EXPORT_SYMBOL(vfs_get_hash);
@@ -40,6 +40,7 @@
#include <asm/byteorder.h>
#include <uapi/linux/fs.h>
+#include <uapi/linux/hash_info.h>
struct backing_dev_info;
struct bdi_writeback;
@@ -1819,6 +1820,8 @@ struct file_operations {
struct file *file_out, loff_t pos_out,
loff_t len, unsigned int remap_flags);
int (*fadvise)(struct file *, loff_t, loff_t, int);
+ int (*get_hash)(struct file *, enum hash_algo hash, uint8_t *buf,
+ size_t size);
} __randomize_layout;
struct inode_operations {
@@ -1895,7 +1898,8 @@ extern int vfs_dedupe_file_range(struct file *file,
extern loff_t vfs_dedupe_file_range_one(struct file *src_file, loff_t src_pos,
struct file *dst_file, loff_t dst_pos,
loff_t len, unsigned int remap_flags);
-
+extern int vfs_get_hash(struct file *file, enum hash_algo hash, uint8_t *buf,
+ size_t size);
struct super_operations {
struct inode *(*alloc_inode)(struct super_block *sb);