18c2ecf20Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0
28c2ecf20Sopenharmony_ci/*
38c2ecf20Sopenharmony_ci *  linux/fs/ext4/symlink.c
48c2ecf20Sopenharmony_ci *
58c2ecf20Sopenharmony_ci * Only fast symlinks left here - the rest is done by generic code. AV, 1999
68c2ecf20Sopenharmony_ci *
78c2ecf20Sopenharmony_ci * Copyright (C) 1992, 1993, 1994, 1995
88c2ecf20Sopenharmony_ci * Remy Card (card@masi.ibp.fr)
98c2ecf20Sopenharmony_ci * Laboratoire MASI - Institut Blaise Pascal
108c2ecf20Sopenharmony_ci * Universite Pierre et Marie Curie (Paris VI)
118c2ecf20Sopenharmony_ci *
128c2ecf20Sopenharmony_ci *  from
138c2ecf20Sopenharmony_ci *
148c2ecf20Sopenharmony_ci *  linux/fs/minix/symlink.c
158c2ecf20Sopenharmony_ci *
168c2ecf20Sopenharmony_ci *  Copyright (C) 1991, 1992  Linus Torvalds
178c2ecf20Sopenharmony_ci *
188c2ecf20Sopenharmony_ci *  ext4 symlink handling code
198c2ecf20Sopenharmony_ci */
208c2ecf20Sopenharmony_ci
218c2ecf20Sopenharmony_ci#include <linux/fs.h>
228c2ecf20Sopenharmony_ci#include <linux/namei.h>
238c2ecf20Sopenharmony_ci#include "ext4.h"
248c2ecf20Sopenharmony_ci#include "xattr.h"
258c2ecf20Sopenharmony_ci
268c2ecf20Sopenharmony_cistatic const char *ext4_encrypted_get_link(struct dentry *dentry,
278c2ecf20Sopenharmony_ci					   struct inode *inode,
288c2ecf20Sopenharmony_ci					   struct delayed_call *done)
298c2ecf20Sopenharmony_ci{
308c2ecf20Sopenharmony_ci	struct page *cpage = NULL;
318c2ecf20Sopenharmony_ci	const void *caddr;
328c2ecf20Sopenharmony_ci	unsigned int max_size;
338c2ecf20Sopenharmony_ci	const char *paddr;
348c2ecf20Sopenharmony_ci
358c2ecf20Sopenharmony_ci	if (!dentry)
368c2ecf20Sopenharmony_ci		return ERR_PTR(-ECHILD);
378c2ecf20Sopenharmony_ci
388c2ecf20Sopenharmony_ci	if (ext4_inode_is_fast_symlink(inode)) {
398c2ecf20Sopenharmony_ci		caddr = EXT4_I(inode)->i_data;
408c2ecf20Sopenharmony_ci		max_size = sizeof(EXT4_I(inode)->i_data);
418c2ecf20Sopenharmony_ci	} else {
428c2ecf20Sopenharmony_ci		cpage = read_mapping_page(inode->i_mapping, 0, NULL);
438c2ecf20Sopenharmony_ci		if (IS_ERR(cpage))
448c2ecf20Sopenharmony_ci			return ERR_CAST(cpage);
458c2ecf20Sopenharmony_ci		caddr = page_address(cpage);
468c2ecf20Sopenharmony_ci		max_size = inode->i_sb->s_blocksize;
478c2ecf20Sopenharmony_ci	}
488c2ecf20Sopenharmony_ci
498c2ecf20Sopenharmony_ci	paddr = fscrypt_get_symlink(inode, caddr, max_size, done);
508c2ecf20Sopenharmony_ci	if (cpage)
518c2ecf20Sopenharmony_ci		put_page(cpage);
528c2ecf20Sopenharmony_ci	return paddr;
538c2ecf20Sopenharmony_ci}
548c2ecf20Sopenharmony_ci
558c2ecf20Sopenharmony_cistatic int ext4_encrypted_symlink_getattr(const struct path *path,
568c2ecf20Sopenharmony_ci					  struct kstat *stat, u32 request_mask,
578c2ecf20Sopenharmony_ci					  unsigned int query_flags)
588c2ecf20Sopenharmony_ci{
598c2ecf20Sopenharmony_ci	ext4_getattr(path, stat, request_mask, query_flags);
608c2ecf20Sopenharmony_ci
618c2ecf20Sopenharmony_ci	return fscrypt_symlink_getattr(path, stat);
628c2ecf20Sopenharmony_ci}
638c2ecf20Sopenharmony_ci
648c2ecf20Sopenharmony_ciconst struct inode_operations ext4_encrypted_symlink_inode_operations = {
658c2ecf20Sopenharmony_ci	.get_link	= ext4_encrypted_get_link,
668c2ecf20Sopenharmony_ci	.setattr	= ext4_setattr,
678c2ecf20Sopenharmony_ci	.getattr	= ext4_encrypted_symlink_getattr,
688c2ecf20Sopenharmony_ci	.listxattr	= ext4_listxattr,
698c2ecf20Sopenharmony_ci};
708c2ecf20Sopenharmony_ci
718c2ecf20Sopenharmony_ciconst struct inode_operations ext4_symlink_inode_operations = {
728c2ecf20Sopenharmony_ci	.get_link	= page_get_link,
738c2ecf20Sopenharmony_ci	.setattr	= ext4_setattr,
748c2ecf20Sopenharmony_ci	.getattr	= ext4_getattr,
758c2ecf20Sopenharmony_ci	.listxattr	= ext4_listxattr,
768c2ecf20Sopenharmony_ci};
778c2ecf20Sopenharmony_ci
788c2ecf20Sopenharmony_ciconst struct inode_operations ext4_fast_symlink_inode_operations = {
798c2ecf20Sopenharmony_ci	.get_link	= simple_get_link,
808c2ecf20Sopenharmony_ci	.setattr	= ext4_setattr,
818c2ecf20Sopenharmony_ci	.getattr	= ext4_getattr,
828c2ecf20Sopenharmony_ci	.listxattr	= ext4_listxattr,
838c2ecf20Sopenharmony_ci};
84