18c2ecf20Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0
28c2ecf20Sopenharmony_ci/*
38c2ecf20Sopenharmony_ci *  linux/fs/hpfs/inode.c
48c2ecf20Sopenharmony_ci *
58c2ecf20Sopenharmony_ci *  Mikulas Patocka (mikulas@artax.karlin.mff.cuni.cz), 1998-1999
68c2ecf20Sopenharmony_ci *
78c2ecf20Sopenharmony_ci *  inode VFS functions
88c2ecf20Sopenharmony_ci */
98c2ecf20Sopenharmony_ci
108c2ecf20Sopenharmony_ci#include <linux/slab.h>
118c2ecf20Sopenharmony_ci#include <linux/user_namespace.h>
128c2ecf20Sopenharmony_ci#include "hpfs_fn.h"
138c2ecf20Sopenharmony_ci
148c2ecf20Sopenharmony_civoid hpfs_init_inode(struct inode *i)
158c2ecf20Sopenharmony_ci{
168c2ecf20Sopenharmony_ci	struct super_block *sb = i->i_sb;
178c2ecf20Sopenharmony_ci	struct hpfs_inode_info *hpfs_inode = hpfs_i(i);
188c2ecf20Sopenharmony_ci
198c2ecf20Sopenharmony_ci	i->i_uid = hpfs_sb(sb)->sb_uid;
208c2ecf20Sopenharmony_ci	i->i_gid = hpfs_sb(sb)->sb_gid;
218c2ecf20Sopenharmony_ci	i->i_mode = hpfs_sb(sb)->sb_mode;
228c2ecf20Sopenharmony_ci	i->i_size = -1;
238c2ecf20Sopenharmony_ci	i->i_blocks = -1;
248c2ecf20Sopenharmony_ci
258c2ecf20Sopenharmony_ci	hpfs_inode->i_dno = 0;
268c2ecf20Sopenharmony_ci	hpfs_inode->i_n_secs = 0;
278c2ecf20Sopenharmony_ci	hpfs_inode->i_file_sec = 0;
288c2ecf20Sopenharmony_ci	hpfs_inode->i_disk_sec = 0;
298c2ecf20Sopenharmony_ci	hpfs_inode->i_dpos = 0;
308c2ecf20Sopenharmony_ci	hpfs_inode->i_dsubdno = 0;
318c2ecf20Sopenharmony_ci	hpfs_inode->i_ea_mode = 0;
328c2ecf20Sopenharmony_ci	hpfs_inode->i_ea_uid = 0;
338c2ecf20Sopenharmony_ci	hpfs_inode->i_ea_gid = 0;
348c2ecf20Sopenharmony_ci	hpfs_inode->i_ea_size = 0;
358c2ecf20Sopenharmony_ci
368c2ecf20Sopenharmony_ci	hpfs_inode->i_rddir_off = NULL;
378c2ecf20Sopenharmony_ci	hpfs_inode->i_dirty = 0;
388c2ecf20Sopenharmony_ci
398c2ecf20Sopenharmony_ci	i->i_ctime.tv_sec = i->i_ctime.tv_nsec = 0;
408c2ecf20Sopenharmony_ci	i->i_mtime.tv_sec = i->i_mtime.tv_nsec = 0;
418c2ecf20Sopenharmony_ci	i->i_atime.tv_sec = i->i_atime.tv_nsec = 0;
428c2ecf20Sopenharmony_ci}
438c2ecf20Sopenharmony_ci
448c2ecf20Sopenharmony_civoid hpfs_read_inode(struct inode *i)
458c2ecf20Sopenharmony_ci{
468c2ecf20Sopenharmony_ci	struct buffer_head *bh;
478c2ecf20Sopenharmony_ci	struct fnode *fnode;
488c2ecf20Sopenharmony_ci	struct super_block *sb = i->i_sb;
498c2ecf20Sopenharmony_ci	struct hpfs_inode_info *hpfs_inode = hpfs_i(i);
508c2ecf20Sopenharmony_ci	void *ea;
518c2ecf20Sopenharmony_ci	int ea_size;
528c2ecf20Sopenharmony_ci
538c2ecf20Sopenharmony_ci	if (!(fnode = hpfs_map_fnode(sb, i->i_ino, &bh))) {
548c2ecf20Sopenharmony_ci		/*i->i_mode |= S_IFREG;
558c2ecf20Sopenharmony_ci		i->i_mode &= ~0111;
568c2ecf20Sopenharmony_ci		i->i_op = &hpfs_file_iops;
578c2ecf20Sopenharmony_ci		i->i_fop = &hpfs_file_ops;
588c2ecf20Sopenharmony_ci		clear_nlink(i);*/
598c2ecf20Sopenharmony_ci		make_bad_inode(i);
608c2ecf20Sopenharmony_ci		return;
618c2ecf20Sopenharmony_ci	}
628c2ecf20Sopenharmony_ci	if (hpfs_sb(i->i_sb)->sb_eas) {
638c2ecf20Sopenharmony_ci		if ((ea = hpfs_get_ea(i->i_sb, fnode, "UID", &ea_size))) {
648c2ecf20Sopenharmony_ci			if (ea_size == 2) {
658c2ecf20Sopenharmony_ci				i_uid_write(i, le16_to_cpu(*(__le16*)ea));
668c2ecf20Sopenharmony_ci				hpfs_inode->i_ea_uid = 1;
678c2ecf20Sopenharmony_ci			}
688c2ecf20Sopenharmony_ci			kfree(ea);
698c2ecf20Sopenharmony_ci		}
708c2ecf20Sopenharmony_ci		if ((ea = hpfs_get_ea(i->i_sb, fnode, "GID", &ea_size))) {
718c2ecf20Sopenharmony_ci			if (ea_size == 2) {
728c2ecf20Sopenharmony_ci				i_gid_write(i, le16_to_cpu(*(__le16*)ea));
738c2ecf20Sopenharmony_ci				hpfs_inode->i_ea_gid = 1;
748c2ecf20Sopenharmony_ci			}
758c2ecf20Sopenharmony_ci			kfree(ea);
768c2ecf20Sopenharmony_ci		}
778c2ecf20Sopenharmony_ci		if ((ea = hpfs_get_ea(i->i_sb, fnode, "SYMLINK", &ea_size))) {
788c2ecf20Sopenharmony_ci			kfree(ea);
798c2ecf20Sopenharmony_ci			i->i_mode = S_IFLNK | 0777;
808c2ecf20Sopenharmony_ci			i->i_op = &page_symlink_inode_operations;
818c2ecf20Sopenharmony_ci			inode_nohighmem(i);
828c2ecf20Sopenharmony_ci			i->i_data.a_ops = &hpfs_symlink_aops;
838c2ecf20Sopenharmony_ci			set_nlink(i, 1);
848c2ecf20Sopenharmony_ci			i->i_size = ea_size;
858c2ecf20Sopenharmony_ci			i->i_blocks = 1;
868c2ecf20Sopenharmony_ci			brelse(bh);
878c2ecf20Sopenharmony_ci			return;
888c2ecf20Sopenharmony_ci		}
898c2ecf20Sopenharmony_ci		if ((ea = hpfs_get_ea(i->i_sb, fnode, "MODE", &ea_size))) {
908c2ecf20Sopenharmony_ci			int rdev = 0;
918c2ecf20Sopenharmony_ci			umode_t mode = hpfs_sb(sb)->sb_mode;
928c2ecf20Sopenharmony_ci			if (ea_size == 2) {
938c2ecf20Sopenharmony_ci				mode = le16_to_cpu(*(__le16*)ea);
948c2ecf20Sopenharmony_ci				hpfs_inode->i_ea_mode = 1;
958c2ecf20Sopenharmony_ci			}
968c2ecf20Sopenharmony_ci			kfree(ea);
978c2ecf20Sopenharmony_ci			i->i_mode = mode;
988c2ecf20Sopenharmony_ci			if (S_ISBLK(mode) || S_ISCHR(mode)) {
998c2ecf20Sopenharmony_ci				if ((ea = hpfs_get_ea(i->i_sb, fnode, "DEV", &ea_size))) {
1008c2ecf20Sopenharmony_ci					if (ea_size == 4)
1018c2ecf20Sopenharmony_ci						rdev = le32_to_cpu(*(__le32*)ea);
1028c2ecf20Sopenharmony_ci					kfree(ea);
1038c2ecf20Sopenharmony_ci				}
1048c2ecf20Sopenharmony_ci			}
1058c2ecf20Sopenharmony_ci			if (S_ISBLK(mode) || S_ISCHR(mode) || S_ISFIFO(mode) || S_ISSOCK(mode)) {
1068c2ecf20Sopenharmony_ci				brelse(bh);
1078c2ecf20Sopenharmony_ci				set_nlink(i, 1);
1088c2ecf20Sopenharmony_ci				i->i_size = 0;
1098c2ecf20Sopenharmony_ci				i->i_blocks = 1;
1108c2ecf20Sopenharmony_ci				init_special_inode(i, mode,
1118c2ecf20Sopenharmony_ci					new_decode_dev(rdev));
1128c2ecf20Sopenharmony_ci				return;
1138c2ecf20Sopenharmony_ci			}
1148c2ecf20Sopenharmony_ci		}
1158c2ecf20Sopenharmony_ci	}
1168c2ecf20Sopenharmony_ci	if (fnode_is_dir(fnode)) {
1178c2ecf20Sopenharmony_ci		int n_dnodes, n_subdirs;
1188c2ecf20Sopenharmony_ci		i->i_mode |= S_IFDIR;
1198c2ecf20Sopenharmony_ci		i->i_op = &hpfs_dir_iops;
1208c2ecf20Sopenharmony_ci		i->i_fop = &hpfs_dir_ops;
1218c2ecf20Sopenharmony_ci		hpfs_inode->i_parent_dir = le32_to_cpu(fnode->up);
1228c2ecf20Sopenharmony_ci		hpfs_inode->i_dno = le32_to_cpu(fnode->u.external[0].disk_secno);
1238c2ecf20Sopenharmony_ci		if (hpfs_sb(sb)->sb_chk >= 2) {
1248c2ecf20Sopenharmony_ci			struct buffer_head *bh0;
1258c2ecf20Sopenharmony_ci			if (hpfs_map_fnode(sb, hpfs_inode->i_parent_dir, &bh0)) brelse(bh0);
1268c2ecf20Sopenharmony_ci		}
1278c2ecf20Sopenharmony_ci		n_dnodes = 0; n_subdirs = 0;
1288c2ecf20Sopenharmony_ci		hpfs_count_dnodes(i->i_sb, hpfs_inode->i_dno, &n_dnodes, &n_subdirs, NULL);
1298c2ecf20Sopenharmony_ci		i->i_blocks = 4 * n_dnodes;
1308c2ecf20Sopenharmony_ci		i->i_size = 2048 * n_dnodes;
1318c2ecf20Sopenharmony_ci		set_nlink(i, 2 + n_subdirs);
1328c2ecf20Sopenharmony_ci	} else {
1338c2ecf20Sopenharmony_ci		i->i_mode |= S_IFREG;
1348c2ecf20Sopenharmony_ci		if (!hpfs_inode->i_ea_mode) i->i_mode &= ~0111;
1358c2ecf20Sopenharmony_ci		i->i_op = &hpfs_file_iops;
1368c2ecf20Sopenharmony_ci		i->i_fop = &hpfs_file_ops;
1378c2ecf20Sopenharmony_ci		set_nlink(i, 1);
1388c2ecf20Sopenharmony_ci		i->i_size = le32_to_cpu(fnode->file_size);
1398c2ecf20Sopenharmony_ci		i->i_blocks = ((i->i_size + 511) >> 9) + 1;
1408c2ecf20Sopenharmony_ci		i->i_data.a_ops = &hpfs_aops;
1418c2ecf20Sopenharmony_ci		hpfs_i(i)->mmu_private = i->i_size;
1428c2ecf20Sopenharmony_ci	}
1438c2ecf20Sopenharmony_ci	brelse(bh);
1448c2ecf20Sopenharmony_ci}
1458c2ecf20Sopenharmony_ci
1468c2ecf20Sopenharmony_cistatic void hpfs_write_inode_ea(struct inode *i, struct fnode *fnode)
1478c2ecf20Sopenharmony_ci{
1488c2ecf20Sopenharmony_ci	struct hpfs_inode_info *hpfs_inode = hpfs_i(i);
1498c2ecf20Sopenharmony_ci	/*if (le32_to_cpu(fnode->acl_size_l) || le16_to_cpu(fnode->acl_size_s)) {
1508c2ecf20Sopenharmony_ci		   Some unknown structures like ACL may be in fnode,
1518c2ecf20Sopenharmony_ci		   we'd better not overwrite them
1528c2ecf20Sopenharmony_ci		hpfs_error(i->i_sb, "fnode %08x has some unknown HPFS386 structures", i->i_ino);
1538c2ecf20Sopenharmony_ci	} else*/ if (hpfs_sb(i->i_sb)->sb_eas >= 2) {
1548c2ecf20Sopenharmony_ci		__le32 ea;
1558c2ecf20Sopenharmony_ci		if (!uid_eq(i->i_uid, hpfs_sb(i->i_sb)->sb_uid) || hpfs_inode->i_ea_uid) {
1568c2ecf20Sopenharmony_ci			ea = cpu_to_le32(i_uid_read(i));
1578c2ecf20Sopenharmony_ci			hpfs_set_ea(i, fnode, "UID", (char*)&ea, 2);
1588c2ecf20Sopenharmony_ci			hpfs_inode->i_ea_uid = 1;
1598c2ecf20Sopenharmony_ci		}
1608c2ecf20Sopenharmony_ci		if (!gid_eq(i->i_gid, hpfs_sb(i->i_sb)->sb_gid) || hpfs_inode->i_ea_gid) {
1618c2ecf20Sopenharmony_ci			ea = cpu_to_le32(i_gid_read(i));
1628c2ecf20Sopenharmony_ci			hpfs_set_ea(i, fnode, "GID", (char *)&ea, 2);
1638c2ecf20Sopenharmony_ci			hpfs_inode->i_ea_gid = 1;
1648c2ecf20Sopenharmony_ci		}
1658c2ecf20Sopenharmony_ci		if (!S_ISLNK(i->i_mode))
1668c2ecf20Sopenharmony_ci			if ((i->i_mode != ((hpfs_sb(i->i_sb)->sb_mode & ~(S_ISDIR(i->i_mode) ? 0 : 0111))
1678c2ecf20Sopenharmony_ci			  | (S_ISDIR(i->i_mode) ? S_IFDIR : S_IFREG))
1688c2ecf20Sopenharmony_ci			  && i->i_mode != ((hpfs_sb(i->i_sb)->sb_mode & ~(S_ISDIR(i->i_mode) ? 0222 : 0333))
1698c2ecf20Sopenharmony_ci			  | (S_ISDIR(i->i_mode) ? S_IFDIR : S_IFREG))) || hpfs_inode->i_ea_mode) {
1708c2ecf20Sopenharmony_ci				ea = cpu_to_le32(i->i_mode);
1718c2ecf20Sopenharmony_ci				/* sick, but legal */
1728c2ecf20Sopenharmony_ci				hpfs_set_ea(i, fnode, "MODE", (char *)&ea, 2);
1738c2ecf20Sopenharmony_ci				hpfs_inode->i_ea_mode = 1;
1748c2ecf20Sopenharmony_ci			}
1758c2ecf20Sopenharmony_ci		if (S_ISBLK(i->i_mode) || S_ISCHR(i->i_mode)) {
1768c2ecf20Sopenharmony_ci			ea = cpu_to_le32(new_encode_dev(i->i_rdev));
1778c2ecf20Sopenharmony_ci			hpfs_set_ea(i, fnode, "DEV", (char *)&ea, 4);
1788c2ecf20Sopenharmony_ci		}
1798c2ecf20Sopenharmony_ci	}
1808c2ecf20Sopenharmony_ci}
1818c2ecf20Sopenharmony_ci
1828c2ecf20Sopenharmony_civoid hpfs_write_inode(struct inode *i)
1838c2ecf20Sopenharmony_ci{
1848c2ecf20Sopenharmony_ci	struct hpfs_inode_info *hpfs_inode = hpfs_i(i);
1858c2ecf20Sopenharmony_ci	struct inode *parent;
1868c2ecf20Sopenharmony_ci	if (i->i_ino == hpfs_sb(i->i_sb)->sb_root) return;
1878c2ecf20Sopenharmony_ci	if (hpfs_inode->i_rddir_off && !atomic_read(&i->i_count)) {
1888c2ecf20Sopenharmony_ci		if (*hpfs_inode->i_rddir_off)
1898c2ecf20Sopenharmony_ci			pr_err("write_inode: some position still there\n");
1908c2ecf20Sopenharmony_ci		kfree(hpfs_inode->i_rddir_off);
1918c2ecf20Sopenharmony_ci		hpfs_inode->i_rddir_off = NULL;
1928c2ecf20Sopenharmony_ci	}
1938c2ecf20Sopenharmony_ci	if (!i->i_nlink) {
1948c2ecf20Sopenharmony_ci		return;
1958c2ecf20Sopenharmony_ci	}
1968c2ecf20Sopenharmony_ci	parent = iget_locked(i->i_sb, hpfs_inode->i_parent_dir);
1978c2ecf20Sopenharmony_ci	if (parent) {
1988c2ecf20Sopenharmony_ci		hpfs_inode->i_dirty = 0;
1998c2ecf20Sopenharmony_ci		if (parent->i_state & I_NEW) {
2008c2ecf20Sopenharmony_ci			hpfs_init_inode(parent);
2018c2ecf20Sopenharmony_ci			hpfs_read_inode(parent);
2028c2ecf20Sopenharmony_ci			unlock_new_inode(parent);
2038c2ecf20Sopenharmony_ci		}
2048c2ecf20Sopenharmony_ci		hpfs_write_inode_nolock(i);
2058c2ecf20Sopenharmony_ci		iput(parent);
2068c2ecf20Sopenharmony_ci	}
2078c2ecf20Sopenharmony_ci}
2088c2ecf20Sopenharmony_ci
2098c2ecf20Sopenharmony_civoid hpfs_write_inode_nolock(struct inode *i)
2108c2ecf20Sopenharmony_ci{
2118c2ecf20Sopenharmony_ci	struct hpfs_inode_info *hpfs_inode = hpfs_i(i);
2128c2ecf20Sopenharmony_ci	struct buffer_head *bh;
2138c2ecf20Sopenharmony_ci	struct fnode *fnode;
2148c2ecf20Sopenharmony_ci	struct quad_buffer_head qbh;
2158c2ecf20Sopenharmony_ci	struct hpfs_dirent *de;
2168c2ecf20Sopenharmony_ci	if (i->i_ino == hpfs_sb(i->i_sb)->sb_root) return;
2178c2ecf20Sopenharmony_ci	if (!(fnode = hpfs_map_fnode(i->i_sb, i->i_ino, &bh))) return;
2188c2ecf20Sopenharmony_ci	if (i->i_ino != hpfs_sb(i->i_sb)->sb_root && i->i_nlink) {
2198c2ecf20Sopenharmony_ci		if (!(de = map_fnode_dirent(i->i_sb, i->i_ino, fnode, &qbh))) {
2208c2ecf20Sopenharmony_ci			brelse(bh);
2218c2ecf20Sopenharmony_ci			return;
2228c2ecf20Sopenharmony_ci		}
2238c2ecf20Sopenharmony_ci	} else de = NULL;
2248c2ecf20Sopenharmony_ci	if (S_ISREG(i->i_mode)) {
2258c2ecf20Sopenharmony_ci		fnode->file_size = cpu_to_le32(i->i_size);
2268c2ecf20Sopenharmony_ci		if (de) de->file_size = cpu_to_le32(i->i_size);
2278c2ecf20Sopenharmony_ci	} else if (S_ISDIR(i->i_mode)) {
2288c2ecf20Sopenharmony_ci		fnode->file_size = cpu_to_le32(0);
2298c2ecf20Sopenharmony_ci		if (de) de->file_size = cpu_to_le32(0);
2308c2ecf20Sopenharmony_ci	}
2318c2ecf20Sopenharmony_ci	hpfs_write_inode_ea(i, fnode);
2328c2ecf20Sopenharmony_ci	if (de) {
2338c2ecf20Sopenharmony_ci		de->write_date = cpu_to_le32(gmt_to_local(i->i_sb, i->i_mtime.tv_sec));
2348c2ecf20Sopenharmony_ci		de->read_date = cpu_to_le32(gmt_to_local(i->i_sb, i->i_atime.tv_sec));
2358c2ecf20Sopenharmony_ci		de->creation_date = cpu_to_le32(gmt_to_local(i->i_sb, i->i_ctime.tv_sec));
2368c2ecf20Sopenharmony_ci		de->read_only = !(i->i_mode & 0222);
2378c2ecf20Sopenharmony_ci		de->ea_size = cpu_to_le32(hpfs_inode->i_ea_size);
2388c2ecf20Sopenharmony_ci		hpfs_mark_4buffers_dirty(&qbh);
2398c2ecf20Sopenharmony_ci		hpfs_brelse4(&qbh);
2408c2ecf20Sopenharmony_ci	}
2418c2ecf20Sopenharmony_ci	if (S_ISDIR(i->i_mode)) {
2428c2ecf20Sopenharmony_ci		if ((de = map_dirent(i, hpfs_inode->i_dno, "\001\001", 2, NULL, &qbh))) {
2438c2ecf20Sopenharmony_ci			de->write_date = cpu_to_le32(gmt_to_local(i->i_sb, i->i_mtime.tv_sec));
2448c2ecf20Sopenharmony_ci			de->read_date = cpu_to_le32(gmt_to_local(i->i_sb, i->i_atime.tv_sec));
2458c2ecf20Sopenharmony_ci			de->creation_date = cpu_to_le32(gmt_to_local(i->i_sb, i->i_ctime.tv_sec));
2468c2ecf20Sopenharmony_ci			de->read_only = !(i->i_mode & 0222);
2478c2ecf20Sopenharmony_ci			de->ea_size = cpu_to_le32(/*hpfs_inode->i_ea_size*/0);
2488c2ecf20Sopenharmony_ci			de->file_size = cpu_to_le32(0);
2498c2ecf20Sopenharmony_ci			hpfs_mark_4buffers_dirty(&qbh);
2508c2ecf20Sopenharmony_ci			hpfs_brelse4(&qbh);
2518c2ecf20Sopenharmony_ci		} else
2528c2ecf20Sopenharmony_ci			hpfs_error(i->i_sb,
2538c2ecf20Sopenharmony_ci				"directory %08lx doesn't have '.' entry",
2548c2ecf20Sopenharmony_ci				(unsigned long)i->i_ino);
2558c2ecf20Sopenharmony_ci	}
2568c2ecf20Sopenharmony_ci	mark_buffer_dirty(bh);
2578c2ecf20Sopenharmony_ci	brelse(bh);
2588c2ecf20Sopenharmony_ci}
2598c2ecf20Sopenharmony_ci
2608c2ecf20Sopenharmony_ciint hpfs_setattr(struct dentry *dentry, struct iattr *attr)
2618c2ecf20Sopenharmony_ci{
2628c2ecf20Sopenharmony_ci	struct inode *inode = d_inode(dentry);
2638c2ecf20Sopenharmony_ci	int error = -EINVAL;
2648c2ecf20Sopenharmony_ci
2658c2ecf20Sopenharmony_ci	hpfs_lock(inode->i_sb);
2668c2ecf20Sopenharmony_ci	if (inode->i_ino == hpfs_sb(inode->i_sb)->sb_root)
2678c2ecf20Sopenharmony_ci		goto out_unlock;
2688c2ecf20Sopenharmony_ci	if ((attr->ia_valid & ATTR_UID) &&
2698c2ecf20Sopenharmony_ci	    from_kuid(&init_user_ns, attr->ia_uid) >= 0x10000)
2708c2ecf20Sopenharmony_ci		goto out_unlock;
2718c2ecf20Sopenharmony_ci	if ((attr->ia_valid & ATTR_GID) &&
2728c2ecf20Sopenharmony_ci	    from_kgid(&init_user_ns, attr->ia_gid) >= 0x10000)
2738c2ecf20Sopenharmony_ci		goto out_unlock;
2748c2ecf20Sopenharmony_ci	if ((attr->ia_valid & ATTR_SIZE) && attr->ia_size > inode->i_size)
2758c2ecf20Sopenharmony_ci		goto out_unlock;
2768c2ecf20Sopenharmony_ci
2778c2ecf20Sopenharmony_ci	error = setattr_prepare(dentry, attr);
2788c2ecf20Sopenharmony_ci	if (error)
2798c2ecf20Sopenharmony_ci		goto out_unlock;
2808c2ecf20Sopenharmony_ci
2818c2ecf20Sopenharmony_ci	if ((attr->ia_valid & ATTR_SIZE) &&
2828c2ecf20Sopenharmony_ci	    attr->ia_size != i_size_read(inode)) {
2838c2ecf20Sopenharmony_ci		error = inode_newsize_ok(inode, attr->ia_size);
2848c2ecf20Sopenharmony_ci		if (error)
2858c2ecf20Sopenharmony_ci			goto out_unlock;
2868c2ecf20Sopenharmony_ci
2878c2ecf20Sopenharmony_ci		truncate_setsize(inode, attr->ia_size);
2888c2ecf20Sopenharmony_ci		hpfs_truncate(inode);
2898c2ecf20Sopenharmony_ci	}
2908c2ecf20Sopenharmony_ci
2918c2ecf20Sopenharmony_ci	setattr_copy(inode, attr);
2928c2ecf20Sopenharmony_ci
2938c2ecf20Sopenharmony_ci	hpfs_write_inode(inode);
2948c2ecf20Sopenharmony_ci
2958c2ecf20Sopenharmony_ci out_unlock:
2968c2ecf20Sopenharmony_ci	hpfs_unlock(inode->i_sb);
2978c2ecf20Sopenharmony_ci	return error;
2988c2ecf20Sopenharmony_ci}
2998c2ecf20Sopenharmony_ci
3008c2ecf20Sopenharmony_civoid hpfs_write_if_changed(struct inode *inode)
3018c2ecf20Sopenharmony_ci{
3028c2ecf20Sopenharmony_ci	struct hpfs_inode_info *hpfs_inode = hpfs_i(inode);
3038c2ecf20Sopenharmony_ci
3048c2ecf20Sopenharmony_ci	if (hpfs_inode->i_dirty)
3058c2ecf20Sopenharmony_ci		hpfs_write_inode(inode);
3068c2ecf20Sopenharmony_ci}
3078c2ecf20Sopenharmony_ci
3088c2ecf20Sopenharmony_civoid hpfs_evict_inode(struct inode *inode)
3098c2ecf20Sopenharmony_ci{
3108c2ecf20Sopenharmony_ci	truncate_inode_pages_final(&inode->i_data);
3118c2ecf20Sopenharmony_ci	clear_inode(inode);
3128c2ecf20Sopenharmony_ci	if (!inode->i_nlink) {
3138c2ecf20Sopenharmony_ci		hpfs_lock(inode->i_sb);
3148c2ecf20Sopenharmony_ci		hpfs_remove_fnode(inode->i_sb, inode->i_ino);
3158c2ecf20Sopenharmony_ci		hpfs_unlock(inode->i_sb);
3168c2ecf20Sopenharmony_ci	}
3178c2ecf20Sopenharmony_ci}
318