hfsplus: fix HFSPLUS_I calling convention

HFSPLUS_I doesn't return a pointer to the hfsplus-specific inode
information like all other FOO_I macros, but dereference the pointer in a way
that made it look like a direct struct derefence.  This only works as long
as the HFSPLUS_I macro is used directly and prevents us from keepig a local
hfsplus_inode_info pointer.  Fix the calling convention and introduce a local
hip variable in all functions that use it constantly.

Signed-off-by: Christoph Hellwig <hch@tuxera.com>
This commit is contained in:
Christoph Hellwig 2010-10-01 05:43:31 +02:00 committed by Christoph Hellwig
parent dd73a01a30
commit 6af502de22
8 changed files with 192 additions and 172 deletions

View File

@ -192,17 +192,18 @@ struct hfs_bnode *hfs_bmap_alloc(struct hfs_btree *tree)
while (!tree->free_nodes) { while (!tree->free_nodes) {
struct inode *inode = tree->inode; struct inode *inode = tree->inode;
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
u32 count; u32 count;
int res; int res;
res = hfsplus_file_extend(inode); res = hfsplus_file_extend(inode);
if (res) if (res)
return ERR_PTR(res); return ERR_PTR(res);
HFSPLUS_I(inode).phys_size = inode->i_size = hip->phys_size = inode->i_size =
(loff_t)HFSPLUS_I(inode).alloc_blocks << (loff_t)hip->alloc_blocks <<
HFSPLUS_SB(tree->sb)->alloc_blksz_shift; HFSPLUS_SB(tree->sb)->alloc_blksz_shift;
HFSPLUS_I(inode).fs_blocks = HFSPLUS_I(inode).alloc_blocks << hip->fs_blocks =
HFSPLUS_SB(tree->sb)->fs_shift; hip->alloc_blocks << HFSPLUS_SB(tree->sb)->fs_shift;
inode_set_bytes(inode, inode->i_size); inode_set_bytes(inode, inode->i_size);
count = inode->i_size >> tree->node_size_shift; count = inode->i_size >> tree->node_size_shift;
tree->free_nodes = count - tree->node_count; tree->free_nodes = count - tree->node_count;

View File

@ -77,8 +77,8 @@ static void hfsplus_set_perms(struct inode *inode, struct hfsplus_perm *perms)
perms->rootflags |= HFSPLUS_FLG_APPEND; perms->rootflags |= HFSPLUS_FLG_APPEND;
else else
perms->rootflags &= ~HFSPLUS_FLG_APPEND; perms->rootflags &= ~HFSPLUS_FLG_APPEND;
HFSPLUS_I(inode).rootflags = perms->rootflags; HFSPLUS_I(inode)->rootflags = perms->rootflags;
HFSPLUS_I(inode).userflags = perms->userflags; HFSPLUS_I(inode)->userflags = perms->userflags;
perms->mode = cpu_to_be16(inode->i_mode); perms->mode = cpu_to_be16(inode->i_mode);
perms->owner = cpu_to_be32(inode->i_uid); perms->owner = cpu_to_be32(inode->i_uid);
perms->group = cpu_to_be32(inode->i_gid); perms->group = cpu_to_be32(inode->i_gid);
@ -95,7 +95,7 @@ static int hfsplus_cat_build_record(hfsplus_cat_entry *entry, u32 cnid, struct i
memset(folder, 0, sizeof(*folder)); memset(folder, 0, sizeof(*folder));
folder->type = cpu_to_be16(HFSPLUS_FOLDER); folder->type = cpu_to_be16(HFSPLUS_FOLDER);
folder->id = cpu_to_be32(inode->i_ino); folder->id = cpu_to_be32(inode->i_ino);
HFSPLUS_I(inode).create_date = HFSPLUS_I(inode)->create_date =
folder->create_date = folder->create_date =
folder->content_mod_date = folder->content_mod_date =
folder->attribute_mod_date = folder->attribute_mod_date =
@ -113,7 +113,7 @@ static int hfsplus_cat_build_record(hfsplus_cat_entry *entry, u32 cnid, struct i
file->type = cpu_to_be16(HFSPLUS_FILE); file->type = cpu_to_be16(HFSPLUS_FILE);
file->flags = cpu_to_be16(HFSPLUS_FILE_THREAD_EXISTS); file->flags = cpu_to_be16(HFSPLUS_FILE_THREAD_EXISTS);
file->id = cpu_to_be32(cnid); file->id = cpu_to_be32(cnid);
HFSPLUS_I(inode).create_date = HFSPLUS_I(inode)->create_date =
file->create_date = file->create_date =
file->content_mod_date = file->content_mod_date =
file->attribute_mod_date = file->attribute_mod_date =
@ -133,8 +133,8 @@ static int hfsplus_cat_build_record(hfsplus_cat_entry *entry, u32 cnid, struct i
file->user_info.fdType = cpu_to_be32(HFSP_HARDLINK_TYPE); file->user_info.fdType = cpu_to_be32(HFSP_HARDLINK_TYPE);
file->user_info.fdCreator = cpu_to_be32(HFSP_HFSPLUS_CREATOR); file->user_info.fdCreator = cpu_to_be32(HFSP_HFSPLUS_CREATOR);
file->user_info.fdFlags = cpu_to_be16(0x100); file->user_info.fdFlags = cpu_to_be16(0x100);
file->create_date = HFSPLUS_I(sbi->hidden_dir).create_date; file->create_date = HFSPLUS_I(sbi->hidden_dir)->create_date;
file->permissions.dev = cpu_to_be32(HFSPLUS_I(inode).dev); file->permissions.dev = cpu_to_be32(HFSPLUS_I(inode)->dev);
} }
return sizeof(*file); return sizeof(*file);
} }
@ -279,7 +279,7 @@ int hfsplus_delete_cat(u32 cnid, struct inode *dir, struct qstr *str)
hfsplus_free_fork(sb, cnid, &fork, HFSPLUS_TYPE_RSRC); hfsplus_free_fork(sb, cnid, &fork, HFSPLUS_TYPE_RSRC);
} }
list_for_each(pos, &HFSPLUS_I(dir).open_dir_list) { list_for_each(pos, &HFSPLUS_I(dir)->open_dir_list) {
struct hfsplus_readdir_data *rd = struct hfsplus_readdir_data *rd =
list_entry(pos, struct hfsplus_readdir_data, list); list_entry(pos, struct hfsplus_readdir_data, list);
if (fd.tree->keycmp(fd.search_key, (void *)&rd->key) < 0) if (fd.tree->keycmp(fd.search_key, (void *)&rd->key) < 0)

View File

@ -68,8 +68,8 @@ again:
cnid = be32_to_cpu(entry.file.id); cnid = be32_to_cpu(entry.file.id);
if (entry.file.user_info.fdType == cpu_to_be32(HFSP_HARDLINK_TYPE) && if (entry.file.user_info.fdType == cpu_to_be32(HFSP_HARDLINK_TYPE) &&
entry.file.user_info.fdCreator == cpu_to_be32(HFSP_HFSPLUS_CREATOR) && entry.file.user_info.fdCreator == cpu_to_be32(HFSP_HFSPLUS_CREATOR) &&
(entry.file.create_date == HFSPLUS_I(HFSPLUS_SB(sb)->hidden_dir).create_date || (entry.file.create_date == HFSPLUS_I(HFSPLUS_SB(sb)->hidden_dir)->create_date ||
entry.file.create_date == HFSPLUS_I(sb->s_root->d_inode).create_date) && entry.file.create_date == HFSPLUS_I(sb->s_root->d_inode)->create_date) &&
HFSPLUS_SB(sb)->hidden_dir) { HFSPLUS_SB(sb)->hidden_dir) {
struct qstr str; struct qstr str;
char name[32]; char name[32];
@ -102,7 +102,7 @@ again:
if (IS_ERR(inode)) if (IS_ERR(inode))
return ERR_CAST(inode); return ERR_CAST(inode);
if (S_ISREG(inode->i_mode)) if (S_ISREG(inode->i_mode))
HFSPLUS_I(inode).dev = linkid; HFSPLUS_I(inode)->dev = linkid;
out: out:
d_add(dentry, inode); d_add(dentry, inode);
return NULL; return NULL;
@ -219,7 +219,7 @@ static int hfsplus_readdir(struct file *filp, void *dirent, filldir_t filldir)
} }
filp->private_data = rd; filp->private_data = rd;
rd->file = filp; rd->file = filp;
list_add(&rd->list, &HFSPLUS_I(inode).open_dir_list); list_add(&rd->list, &HFSPLUS_I(inode)->open_dir_list);
} }
memcpy(&rd->key, fd.key, sizeof(struct hfsplus_cat_key)); memcpy(&rd->key, fd.key, sizeof(struct hfsplus_cat_key));
out: out:
@ -287,7 +287,7 @@ static int hfsplus_link(struct dentry *src_dentry, struct inode *dst_dir,
if (res != -EEXIST) if (res != -EEXIST)
return res; return res;
} }
HFSPLUS_I(inode).dev = id; HFSPLUS_I(inode)->dev = id;
cnid = sbi->next_cnid++; cnid = sbi->next_cnid++;
src_dentry->d_fsdata = (void *)(unsigned long)cnid; src_dentry->d_fsdata = (void *)(unsigned long)cnid;
res = hfsplus_create_cat(cnid, src_dir, &src_dentry->d_name, inode); res = hfsplus_create_cat(cnid, src_dir, &src_dentry->d_name, inode);
@ -326,7 +326,7 @@ static int hfsplus_unlink(struct inode *dir, struct dentry *dentry)
cnid = (u32)(unsigned long)dentry->d_fsdata; cnid = (u32)(unsigned long)dentry->d_fsdata;
if (inode->i_ino == cnid && if (inode->i_ino == cnid &&
atomic_read(&HFSPLUS_I(inode).opencnt)) { atomic_read(&HFSPLUS_I(inode)->opencnt)) {
str.name = name; str.name = name;
str.len = sprintf(name, "temp%lu", inode->i_ino); str.len = sprintf(name, "temp%lu", inode->i_ino);
res = hfsplus_rename_cat(inode->i_ino, res = hfsplus_rename_cat(inode->i_ino,
@ -347,7 +347,7 @@ static int hfsplus_unlink(struct inode *dir, struct dentry *dentry)
if (!inode->i_nlink) { if (!inode->i_nlink) {
if (inode->i_ino != cnid) { if (inode->i_ino != cnid) {
sbi->file_count--; sbi->file_count--;
if (!atomic_read(&HFSPLUS_I(inode).opencnt)) { if (!atomic_read(&HFSPLUS_I(inode)->opencnt)) {
res = hfsplus_delete_cat(inode->i_ino, res = hfsplus_delete_cat(inode->i_ino,
sbi->hidden_dir, sbi->hidden_dir,
NULL); NULL);

View File

@ -85,27 +85,32 @@ static u32 hfsplus_ext_lastblock(struct hfsplus_extent *ext)
static void __hfsplus_ext_write_extent(struct inode *inode, struct hfs_find_data *fd) static void __hfsplus_ext_write_extent(struct inode *inode, struct hfs_find_data *fd)
{ {
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
int res; int res;
hfsplus_ext_build_key(fd->search_key, inode->i_ino, HFSPLUS_I(inode).cached_start, hfsplus_ext_build_key(fd->search_key, inode->i_ino, hip->cached_start,
HFSPLUS_IS_RSRC(inode) ? HFSPLUS_TYPE_RSRC : HFSPLUS_TYPE_DATA); HFSPLUS_IS_RSRC(inode) ?
HFSPLUS_TYPE_RSRC : HFSPLUS_TYPE_DATA);
res = hfs_brec_find(fd); res = hfs_brec_find(fd);
if (HFSPLUS_I(inode).flags & HFSPLUS_FLG_EXT_NEW) { if (hip->flags & HFSPLUS_FLG_EXT_NEW) {
if (res != -ENOENT) if (res != -ENOENT)
return; return;
hfs_brec_insert(fd, HFSPLUS_I(inode).cached_extents, sizeof(hfsplus_extent_rec)); hfs_brec_insert(fd, hip->cached_extents,
HFSPLUS_I(inode).flags &= ~(HFSPLUS_FLG_EXT_DIRTY | HFSPLUS_FLG_EXT_NEW); sizeof(hfsplus_extent_rec));
hip->flags &= ~(HFSPLUS_FLG_EXT_DIRTY | HFSPLUS_FLG_EXT_NEW);
} else { } else {
if (res) if (res)
return; return;
hfs_bnode_write(fd->bnode, HFSPLUS_I(inode).cached_extents, fd->entryoffset, fd->entrylength); hfs_bnode_write(fd->bnode, hip->cached_extents,
HFSPLUS_I(inode).flags &= ~HFSPLUS_FLG_EXT_DIRTY; fd->entryoffset, fd->entrylength);
hip->flags &= ~HFSPLUS_FLG_EXT_DIRTY;
} }
} }
void hfsplus_ext_write_extent(struct inode *inode) void hfsplus_ext_write_extent(struct inode *inode)
{ {
if (HFSPLUS_I(inode).flags & HFSPLUS_FLG_EXT_DIRTY) { if (HFSPLUS_I(inode)->flags & HFSPLUS_FLG_EXT_DIRTY) {
struct hfs_find_data fd; struct hfs_find_data fd;
hfs_find_init(HFSPLUS_SB(inode->i_sb)->ext_tree, &fd); hfs_find_init(HFSPLUS_SB(inode->i_sb)->ext_tree, &fd);
@ -136,30 +141,34 @@ static inline int __hfsplus_ext_read_extent(struct hfs_find_data *fd,
static inline int __hfsplus_ext_cache_extent(struct hfs_find_data *fd, struct inode *inode, u32 block) static inline int __hfsplus_ext_cache_extent(struct hfs_find_data *fd, struct inode *inode, u32 block)
{ {
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
int res; int res;
if (HFSPLUS_I(inode).flags & HFSPLUS_FLG_EXT_DIRTY) if (hip->flags & HFSPLUS_FLG_EXT_DIRTY)
__hfsplus_ext_write_extent(inode, fd); __hfsplus_ext_write_extent(inode, fd);
res = __hfsplus_ext_read_extent(fd, HFSPLUS_I(inode).cached_extents, inode->i_ino, res = __hfsplus_ext_read_extent(fd, hip->cached_extents, inode->i_ino,
block, HFSPLUS_IS_RSRC(inode) ? HFSPLUS_TYPE_RSRC : HFSPLUS_TYPE_DATA); block, HFSPLUS_IS_RSRC(inode) ?
HFSPLUS_TYPE_RSRC :
HFSPLUS_TYPE_DATA);
if (!res) { if (!res) {
HFSPLUS_I(inode).cached_start = be32_to_cpu(fd->key->ext.start_block); hip->cached_start = be32_to_cpu(fd->key->ext.start_block);
HFSPLUS_I(inode).cached_blocks = hfsplus_ext_block_count(HFSPLUS_I(inode).cached_extents); hip->cached_blocks = hfsplus_ext_block_count(hip->cached_extents);
} else { } else {
HFSPLUS_I(inode).cached_start = HFSPLUS_I(inode).cached_blocks = 0; hip->cached_start = hip->cached_blocks = 0;
HFSPLUS_I(inode).flags &= ~(HFSPLUS_FLG_EXT_DIRTY | HFSPLUS_FLG_EXT_NEW); hip->flags &= ~(HFSPLUS_FLG_EXT_DIRTY | HFSPLUS_FLG_EXT_NEW);
} }
return res; return res;
} }
static int hfsplus_ext_read_extent(struct inode *inode, u32 block) static int hfsplus_ext_read_extent(struct inode *inode, u32 block)
{ {
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
struct hfs_find_data fd; struct hfs_find_data fd;
int res; int res;
if (block >= HFSPLUS_I(inode).cached_start && if (block >= hip->cached_start &&
block < HFSPLUS_I(inode).cached_start + HFSPLUS_I(inode).cached_blocks) block < hip->cached_start + hip->cached_blocks)
return 0; return 0;
hfs_find_init(HFSPLUS_SB(inode->i_sb)->ext_tree, &fd); hfs_find_init(HFSPLUS_SB(inode->i_sb)->ext_tree, &fd);
@ -174,6 +183,7 @@ int hfsplus_get_block(struct inode *inode, sector_t iblock,
{ {
struct super_block *sb = inode->i_sb; struct super_block *sb = inode->i_sb;
struct hfsplus_sb_info *sbi = HFSPLUS_SB(sb); struct hfsplus_sb_info *sbi = HFSPLUS_SB(sb);
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
int res = -EIO; int res = -EIO;
u32 ablock, dblock, mask; u32 ablock, dblock, mask;
int shift; int shift;
@ -182,10 +192,10 @@ int hfsplus_get_block(struct inode *inode, sector_t iblock,
shift = sbi->alloc_blksz_shift - sb->s_blocksize_bits; shift = sbi->alloc_blksz_shift - sb->s_blocksize_bits;
ablock = iblock >> sbi->fs_shift; ablock = iblock >> sbi->fs_shift;
if (iblock >= HFSPLUS_I(inode).fs_blocks) { if (iblock >= hip->fs_blocks) {
if (iblock > HFSPLUS_I(inode).fs_blocks || !create) if (iblock > hip->fs_blocks || !create)
return -EIO; return -EIO;
if (ablock >= HFSPLUS_I(inode).alloc_blocks) { if (ablock >= hip->alloc_blocks) {
res = hfsplus_file_extend(inode); res = hfsplus_file_extend(inode);
if (res) if (res)
return res; return res;
@ -193,24 +203,24 @@ int hfsplus_get_block(struct inode *inode, sector_t iblock,
} else } else
create = 0; create = 0;
if (ablock < HFSPLUS_I(inode).first_blocks) { if (ablock < hip->first_blocks) {
dblock = hfsplus_ext_find_block(HFSPLUS_I(inode).first_extents, ablock); dblock = hfsplus_ext_find_block(hip->first_extents, ablock);
goto done; goto done;
} }
if (inode->i_ino == HFSPLUS_EXT_CNID) if (inode->i_ino == HFSPLUS_EXT_CNID)
return -EIO; return -EIO;
mutex_lock(&HFSPLUS_I(inode).extents_lock); mutex_lock(&hip->extents_lock);
res = hfsplus_ext_read_extent(inode, ablock); res = hfsplus_ext_read_extent(inode, ablock);
if (!res) { if (!res) {
dblock = hfsplus_ext_find_block(HFSPLUS_I(inode).cached_extents, ablock - dblock = hfsplus_ext_find_block(hip->cached_extents,
HFSPLUS_I(inode).cached_start); ablock - hip->cached_start);
} else { } else {
mutex_unlock(&HFSPLUS_I(inode).extents_lock); mutex_unlock(&hip->extents_lock);
return -EIO; return -EIO;
} }
mutex_unlock(&HFSPLUS_I(inode).extents_lock); mutex_unlock(&hip->extents_lock);
done: done:
dprint(DBG_EXTENT, "get_block(%lu): %llu - %u\n", inode->i_ino, (long long)iblock, dblock); dprint(DBG_EXTENT, "get_block(%lu): %llu - %u\n", inode->i_ino, (long long)iblock, dblock);
@ -218,8 +228,8 @@ done:
map_bh(bh_result, sb, (dblock << sbi->fs_shift) + sbi->blockoffset + (iblock & mask)); map_bh(bh_result, sb, (dblock << sbi->fs_shift) + sbi->blockoffset + (iblock & mask));
if (create) { if (create) {
set_buffer_new(bh_result); set_buffer_new(bh_result);
HFSPLUS_I(inode).phys_size += sb->s_blocksize; hip->phys_size += sb->s_blocksize;
HFSPLUS_I(inode).fs_blocks++; hip->fs_blocks++;
inode_add_bytes(inode, sb->s_blocksize); inode_add_bytes(inode, sb->s_blocksize);
mark_inode_dirty(inode); mark_inode_dirty(inode);
} }
@ -348,6 +358,7 @@ int hfsplus_file_extend(struct inode *inode)
{ {
struct super_block *sb = inode->i_sb; struct super_block *sb = inode->i_sb;
struct hfsplus_sb_info *sbi = HFSPLUS_SB(sb); struct hfsplus_sb_info *sbi = HFSPLUS_SB(sb);
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
u32 start, len, goal; u32 start, len, goal;
int res; int res;
@ -360,17 +371,17 @@ int hfsplus_file_extend(struct inode *inode)
return -ENOSPC; return -ENOSPC;
} }
mutex_lock(&HFSPLUS_I(inode).extents_lock); mutex_lock(&hip->extents_lock);
if (HFSPLUS_I(inode).alloc_blocks == HFSPLUS_I(inode).first_blocks) if (hip->alloc_blocks == hip->first_blocks)
goal = hfsplus_ext_lastblock(HFSPLUS_I(inode).first_extents); goal = hfsplus_ext_lastblock(hip->first_extents);
else { else {
res = hfsplus_ext_read_extent(inode, HFSPLUS_I(inode).alloc_blocks); res = hfsplus_ext_read_extent(inode, hip->alloc_blocks);
if (res) if (res)
goto out; goto out;
goal = hfsplus_ext_lastblock(HFSPLUS_I(inode).cached_extents); goal = hfsplus_ext_lastblock(hip->cached_extents);
} }
len = HFSPLUS_I(inode).clump_blocks; len = hip->clump_blocks;
start = hfsplus_block_allocate(sb, sbi->total_blocks, goal, &len); start = hfsplus_block_allocate(sb, sbi->total_blocks, goal, &len);
if (start >= sbi->total_blocks) { if (start >= sbi->total_blocks) {
start = hfsplus_block_allocate(sb, goal, 0, &len); start = hfsplus_block_allocate(sb, goal, 0, &len);
@ -381,41 +392,41 @@ int hfsplus_file_extend(struct inode *inode)
} }
dprint(DBG_EXTENT, "extend %lu: %u,%u\n", inode->i_ino, start, len); dprint(DBG_EXTENT, "extend %lu: %u,%u\n", inode->i_ino, start, len);
if (HFSPLUS_I(inode).alloc_blocks <= HFSPLUS_I(inode).first_blocks) {
if (!HFSPLUS_I(inode).first_blocks) { if (hip->alloc_blocks <= hip->first_blocks) {
if (!hip->first_blocks) {
dprint(DBG_EXTENT, "first extents\n"); dprint(DBG_EXTENT, "first extents\n");
/* no extents yet */ /* no extents yet */
HFSPLUS_I(inode).first_extents[0].start_block = cpu_to_be32(start); hip->first_extents[0].start_block = cpu_to_be32(start);
HFSPLUS_I(inode).first_extents[0].block_count = cpu_to_be32(len); hip->first_extents[0].block_count = cpu_to_be32(len);
res = 0; res = 0;
} else { } else {
/* try to append to extents in inode */ /* try to append to extents in inode */
res = hfsplus_add_extent(HFSPLUS_I(inode).first_extents, res = hfsplus_add_extent(hip->first_extents,
HFSPLUS_I(inode).alloc_blocks, hip->alloc_blocks,
start, len); start, len);
if (res == -ENOSPC) if (res == -ENOSPC)
goto insert_extent; goto insert_extent;
} }
if (!res) { if (!res) {
hfsplus_dump_extent(HFSPLUS_I(inode).first_extents); hfsplus_dump_extent(hip->first_extents);
HFSPLUS_I(inode).first_blocks += len; hip->first_blocks += len;
} }
} else { } else {
res = hfsplus_add_extent(HFSPLUS_I(inode).cached_extents, res = hfsplus_add_extent(hip->cached_extents,
HFSPLUS_I(inode).alloc_blocks - hip->alloc_blocks - hip->cached_start,
HFSPLUS_I(inode).cached_start,
start, len); start, len);
if (!res) { if (!res) {
hfsplus_dump_extent(HFSPLUS_I(inode).cached_extents); hfsplus_dump_extent(hip->cached_extents);
HFSPLUS_I(inode).flags |= HFSPLUS_FLG_EXT_DIRTY; hip->flags |= HFSPLUS_FLG_EXT_DIRTY;
HFSPLUS_I(inode).cached_blocks += len; hip->cached_blocks += len;
} else if (res == -ENOSPC) } else if (res == -ENOSPC)
goto insert_extent; goto insert_extent;
} }
out: out:
mutex_unlock(&HFSPLUS_I(inode).extents_lock); mutex_unlock(&hip->extents_lock);
if (!res) { if (!res) {
HFSPLUS_I(inode).alloc_blocks += len; hip->alloc_blocks += len;
mark_inode_dirty(inode); mark_inode_dirty(inode);
} }
return res; return res;
@ -424,13 +435,13 @@ insert_extent:
dprint(DBG_EXTENT, "insert new extent\n"); dprint(DBG_EXTENT, "insert new extent\n");
hfsplus_ext_write_extent(inode); hfsplus_ext_write_extent(inode);
memset(HFSPLUS_I(inode).cached_extents, 0, sizeof(hfsplus_extent_rec)); memset(hip->cached_extents, 0, sizeof(hfsplus_extent_rec));
HFSPLUS_I(inode).cached_extents[0].start_block = cpu_to_be32(start); hip->cached_extents[0].start_block = cpu_to_be32(start);
HFSPLUS_I(inode).cached_extents[0].block_count = cpu_to_be32(len); hip->cached_extents[0].block_count = cpu_to_be32(len);
hfsplus_dump_extent(HFSPLUS_I(inode).cached_extents); hfsplus_dump_extent(hip->cached_extents);
HFSPLUS_I(inode).flags |= HFSPLUS_FLG_EXT_DIRTY | HFSPLUS_FLG_EXT_NEW; hip->flags |= HFSPLUS_FLG_EXT_DIRTY | HFSPLUS_FLG_EXT_NEW;
HFSPLUS_I(inode).cached_start = HFSPLUS_I(inode).alloc_blocks; hip->cached_start = hip->alloc_blocks;
HFSPLUS_I(inode).cached_blocks = len; hip->cached_blocks = len;
res = 0; res = 0;
goto out; goto out;
@ -439,13 +450,15 @@ insert_extent:
void hfsplus_file_truncate(struct inode *inode) void hfsplus_file_truncate(struct inode *inode)
{ {
struct super_block *sb = inode->i_sb; struct super_block *sb = inode->i_sb;
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
struct hfs_find_data fd; struct hfs_find_data fd;
u32 alloc_cnt, blk_cnt, start; u32 alloc_cnt, blk_cnt, start;
int res; int res;
dprint(DBG_INODE, "truncate: %lu, %Lu -> %Lu\n", inode->i_ino, dprint(DBG_INODE, "truncate: %lu, %Lu -> %Lu\n",
(long long)HFSPLUS_I(inode).phys_size, inode->i_size); inode->i_ino, (long long)hip->phys_size, inode->i_size);
if (inode->i_size > HFSPLUS_I(inode).phys_size) {
if (inode->i_size > hip->phys_size) {
struct address_space *mapping = inode->i_mapping; struct address_space *mapping = inode->i_mapping;
struct page *page; struct page *page;
void *fsdata; void *fsdata;
@ -462,48 +475,48 @@ void hfsplus_file_truncate(struct inode *inode)
return; return;
mark_inode_dirty(inode); mark_inode_dirty(inode);
return; return;
} else if (inode->i_size == HFSPLUS_I(inode).phys_size) } else if (inode->i_size == hip->phys_size)
return; return;
blk_cnt = (inode->i_size + HFSPLUS_SB(sb)->alloc_blksz - 1) >> blk_cnt = (inode->i_size + HFSPLUS_SB(sb)->alloc_blksz - 1) >>
HFSPLUS_SB(sb)->alloc_blksz_shift; HFSPLUS_SB(sb)->alloc_blksz_shift;
alloc_cnt = HFSPLUS_I(inode).alloc_blocks; alloc_cnt = hip->alloc_blocks;
if (blk_cnt == alloc_cnt) if (blk_cnt == alloc_cnt)
goto out; goto out;
mutex_lock(&HFSPLUS_I(inode).extents_lock); mutex_lock(&hip->extents_lock);
hfs_find_init(HFSPLUS_SB(sb)->ext_tree, &fd); hfs_find_init(HFSPLUS_SB(sb)->ext_tree, &fd);
while (1) { while (1) {
if (alloc_cnt == HFSPLUS_I(inode).first_blocks) { if (alloc_cnt == hip->first_blocks) {
hfsplus_free_extents(sb, HFSPLUS_I(inode).first_extents, hfsplus_free_extents(sb, hip->first_extents,
alloc_cnt, alloc_cnt - blk_cnt); alloc_cnt, alloc_cnt - blk_cnt);
hfsplus_dump_extent(HFSPLUS_I(inode).first_extents); hfsplus_dump_extent(hip->first_extents);
HFSPLUS_I(inode).first_blocks = blk_cnt; hip->first_blocks = blk_cnt;
break; break;
} }
res = __hfsplus_ext_cache_extent(&fd, inode, alloc_cnt); res = __hfsplus_ext_cache_extent(&fd, inode, alloc_cnt);
if (res) if (res)
break; break;
start = HFSPLUS_I(inode).cached_start; start = hip->cached_start;
hfsplus_free_extents(sb, HFSPLUS_I(inode).cached_extents, hfsplus_free_extents(sb, hip->cached_extents,
alloc_cnt - start, alloc_cnt - blk_cnt); alloc_cnt - start, alloc_cnt - blk_cnt);
hfsplus_dump_extent(HFSPLUS_I(inode).cached_extents); hfsplus_dump_extent(hip->cached_extents);
if (blk_cnt > start) { if (blk_cnt > start) {
HFSPLUS_I(inode).flags |= HFSPLUS_FLG_EXT_DIRTY; hip->flags |= HFSPLUS_FLG_EXT_DIRTY;
break; break;
} }
alloc_cnt = start; alloc_cnt = start;
HFSPLUS_I(inode).cached_start = HFSPLUS_I(inode).cached_blocks = 0; hip->cached_start = hip->cached_blocks = 0;
HFSPLUS_I(inode).flags &= ~(HFSPLUS_FLG_EXT_DIRTY | HFSPLUS_FLG_EXT_NEW); hip->flags &= ~(HFSPLUS_FLG_EXT_DIRTY | HFSPLUS_FLG_EXT_NEW);
hfs_brec_remove(&fd); hfs_brec_remove(&fd);
} }
hfs_find_exit(&fd); hfs_find_exit(&fd);
mutex_unlock(&HFSPLUS_I(inode).extents_lock); mutex_unlock(&hip->extents_lock);
HFSPLUS_I(inode).alloc_blocks = blk_cnt; hip->alloc_blocks = blk_cnt;
out: out:
HFSPLUS_I(inode).phys_size = inode->i_size; hip->phys_size = inode->i_size;
HFSPLUS_I(inode).fs_blocks = (inode->i_size + sb->s_blocksize - 1) >> sb->s_blocksize_bits; hip->fs_blocks = (inode->i_size + sb->s_blocksize - 1) >> sb->s_blocksize_bits;
inode_set_bytes(inode, HFSPLUS_I(inode).fs_blocks << sb->s_blocksize_bits); inode_set_bytes(inode, hip->fs_blocks << sb->s_blocksize_bits);
mark_inode_dirty(inode); mark_inode_dirty(inode);
} }

View File

@ -187,8 +187,8 @@ struct hfsplus_inode_info {
#define HFSPLUS_FLG_EXT_DIRTY 0x0002 #define HFSPLUS_FLG_EXT_DIRTY 0x0002
#define HFSPLUS_FLG_EXT_NEW 0x0004 #define HFSPLUS_FLG_EXT_NEW 0x0004
#define HFSPLUS_IS_DATA(inode) (!(HFSPLUS_I(inode).flags & HFSPLUS_FLG_RSRC)) #define HFSPLUS_IS_DATA(inode) (!(HFSPLUS_I(inode)->flags & HFSPLUS_FLG_RSRC))
#define HFSPLUS_IS_RSRC(inode) (HFSPLUS_I(inode).flags & HFSPLUS_FLG_RSRC) #define HFSPLUS_IS_RSRC(inode) (HFSPLUS_I(inode)->flags & HFSPLUS_FLG_RSRC)
struct hfs_find_data { struct hfs_find_data {
/* filled by caller */ /* filled by caller */
@ -379,13 +379,11 @@ static inline struct hfsplus_sb_info *HFSPLUS_SB(struct super_block *sb)
{ {
return sb->s_fs_info; return sb->s_fs_info;
} }
/*
static inline struct hfsplus_inode_info *HFSPLUS_I(struct inode *inode) static inline struct hfsplus_inode_info *HFSPLUS_I(struct inode *inode)
{ {
return list_entry(inode, struct hfsplus_inode_info, vfs_inode); return list_entry(inode, struct hfsplus_inode_info, vfs_inode);
} }
*/
#define HFSPLUS_I(inode) (*list_entry(inode, struct hfsplus_inode_info, vfs_inode))
#if 1 #if 1
#define hfsplus_kmap(p) ({ struct page *__p = (p); kmap(__p); }) #define hfsplus_kmap(p) ({ struct page *__p = (p); kmap(__p); })

View File

@ -36,7 +36,7 @@ static int hfsplus_write_begin(struct file *file, struct address_space *mapping,
*pagep = NULL; *pagep = NULL;
ret = cont_write_begin(file, mapping, pos, len, flags, pagep, fsdata, ret = cont_write_begin(file, mapping, pos, len, flags, pagep, fsdata,
hfsplus_get_block, hfsplus_get_block,
&HFSPLUS_I(mapping->host).phys_size); &HFSPLUS_I(mapping->host)->phys_size);
if (unlikely(ret)) { if (unlikely(ret)) {
loff_t isize = mapping->host->i_size; loff_t isize = mapping->host->i_size;
if (pos + len > isize) if (pos + len > isize)
@ -172,12 +172,13 @@ static struct dentry *hfsplus_file_lookup(struct inode *dir, struct dentry *dent
struct hfs_find_data fd; struct hfs_find_data fd;
struct super_block *sb = dir->i_sb; struct super_block *sb = dir->i_sb;
struct inode *inode = NULL; struct inode *inode = NULL;
struct hfsplus_inode_info *hip;
int err; int err;
if (HFSPLUS_IS_RSRC(dir) || strcmp(dentry->d_name.name, "rsrc")) if (HFSPLUS_IS_RSRC(dir) || strcmp(dentry->d_name.name, "rsrc"))
goto out; goto out;
inode = HFSPLUS_I(dir).rsrc_inode; inode = HFSPLUS_I(dir)->rsrc_inode;
if (inode) if (inode)
goto out; goto out;
@ -185,10 +186,11 @@ static struct dentry *hfsplus_file_lookup(struct inode *dir, struct dentry *dent
if (!inode) if (!inode)
return ERR_PTR(-ENOMEM); return ERR_PTR(-ENOMEM);
hip = HFSPLUS_I(inode);
inode->i_ino = dir->i_ino; inode->i_ino = dir->i_ino;
INIT_LIST_HEAD(&HFSPLUS_I(inode).open_dir_list); INIT_LIST_HEAD(&hip->open_dir_list);
mutex_init(&HFSPLUS_I(inode).extents_lock); mutex_init(&hip->extents_lock);
HFSPLUS_I(inode).flags = HFSPLUS_FLG_RSRC; hip->flags = HFSPLUS_FLG_RSRC;
hfs_find_init(HFSPLUS_SB(sb)->cat_tree, &fd); hfs_find_init(HFSPLUS_SB(sb)->cat_tree, &fd);
err = hfsplus_find_cat(sb, dir->i_ino, &fd); err = hfsplus_find_cat(sb, dir->i_ino, &fd);
@ -199,8 +201,8 @@ static struct dentry *hfsplus_file_lookup(struct inode *dir, struct dentry *dent
iput(inode); iput(inode);
return ERR_PTR(err); return ERR_PTR(err);
} }
HFSPLUS_I(inode).rsrc_inode = dir; hip->rsrc_inode = dir;
HFSPLUS_I(dir).rsrc_inode = inode; HFSPLUS_I(dir)->rsrc_inode = inode;
igrab(dir); igrab(dir);
hlist_add_head(&inode->i_hash, &HFSPLUS_SB(sb)->rsrc_inodes); hlist_add_head(&inode->i_hash, &HFSPLUS_SB(sb)->rsrc_inodes);
mark_inode_dirty(inode); mark_inode_dirty(inode);
@ -231,8 +233,8 @@ static void hfsplus_get_perms(struct inode *inode, struct hfsplus_perm *perms, i
mode = S_IFREG | ((S_IRUGO|S_IWUGO) & ~(sbi->umask)); mode = S_IFREG | ((S_IRUGO|S_IWUGO) & ~(sbi->umask));
inode->i_mode = mode; inode->i_mode = mode;
HFSPLUS_I(inode).rootflags = perms->rootflags; HFSPLUS_I(inode)->rootflags = perms->rootflags;
HFSPLUS_I(inode).userflags = perms->userflags; HFSPLUS_I(inode)->userflags = perms->userflags;
if (perms->rootflags & HFSPLUS_FLG_IMMUTABLE) if (perms->rootflags & HFSPLUS_FLG_IMMUTABLE)
inode->i_flags |= S_IMMUTABLE; inode->i_flags |= S_IMMUTABLE;
else else
@ -253,20 +255,20 @@ static void hfsplus_set_perms(struct inode *inode, struct hfsplus_perm *perms)
perms->rootflags |= HFSPLUS_FLG_APPEND; perms->rootflags |= HFSPLUS_FLG_APPEND;
else else
perms->rootflags &= ~HFSPLUS_FLG_APPEND; perms->rootflags &= ~HFSPLUS_FLG_APPEND;
perms->userflags = HFSPLUS_I(inode).userflags; perms->userflags = HFSPLUS_I(inode)->userflags;
perms->mode = cpu_to_be16(inode->i_mode); perms->mode = cpu_to_be16(inode->i_mode);
perms->owner = cpu_to_be32(inode->i_uid); perms->owner = cpu_to_be32(inode->i_uid);
perms->group = cpu_to_be32(inode->i_gid); perms->group = cpu_to_be32(inode->i_gid);
perms->dev = cpu_to_be32(HFSPLUS_I(inode).dev); perms->dev = cpu_to_be32(HFSPLUS_I(inode)->dev);
} }
static int hfsplus_file_open(struct inode *inode, struct file *file) static int hfsplus_file_open(struct inode *inode, struct file *file)
{ {
if (HFSPLUS_IS_RSRC(inode)) if (HFSPLUS_IS_RSRC(inode))
inode = HFSPLUS_I(inode).rsrc_inode; inode = HFSPLUS_I(inode)->rsrc_inode;
if (!(file->f_flags & O_LARGEFILE) && i_size_read(inode) > MAX_NON_LFS) if (!(file->f_flags & O_LARGEFILE) && i_size_read(inode) > MAX_NON_LFS)
return -EOVERFLOW; return -EOVERFLOW;
atomic_inc(&HFSPLUS_I(inode).opencnt); atomic_inc(&HFSPLUS_I(inode)->opencnt);
return 0; return 0;
} }
@ -275,8 +277,8 @@ static int hfsplus_file_release(struct inode *inode, struct file *file)
struct super_block *sb = inode->i_sb; struct super_block *sb = inode->i_sb;
if (HFSPLUS_IS_RSRC(inode)) if (HFSPLUS_IS_RSRC(inode))
inode = HFSPLUS_I(inode).rsrc_inode; inode = HFSPLUS_I(inode)->rsrc_inode;
if (atomic_dec_and_test(&HFSPLUS_I(inode).opencnt)) { if (atomic_dec_and_test(&HFSPLUS_I(inode)->opencnt)) {
mutex_lock(&inode->i_mutex); mutex_lock(&inode->i_mutex);
hfsplus_file_truncate(inode); hfsplus_file_truncate(inode);
if (inode->i_flags & S_DEAD) { if (inode->i_flags & S_DEAD) {
@ -362,6 +364,7 @@ struct inode *hfsplus_new_inode(struct super_block *sb, int mode)
{ {
struct hfsplus_sb_info *sbi = HFSPLUS_SB(sb); struct hfsplus_sb_info *sbi = HFSPLUS_SB(sb);
struct inode *inode = new_inode(sb); struct inode *inode = new_inode(sb);
struct hfsplus_inode_info *hip;
if (!inode) if (!inode)
return NULL; return NULL;
@ -372,19 +375,21 @@ struct inode *hfsplus_new_inode(struct super_block *sb, int mode)
inode->i_gid = current_fsgid(); inode->i_gid = current_fsgid();
inode->i_nlink = 1; inode->i_nlink = 1;
inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME_SEC; inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME_SEC;
INIT_LIST_HEAD(&HFSPLUS_I(inode).open_dir_list);
mutex_init(&HFSPLUS_I(inode).extents_lock); hip = HFSPLUS_I(inode);
atomic_set(&HFSPLUS_I(inode).opencnt, 0); INIT_LIST_HEAD(&hip->open_dir_list);
HFSPLUS_I(inode).flags = 0; mutex_init(&hip->extents_lock);
memset(HFSPLUS_I(inode).first_extents, 0, sizeof(hfsplus_extent_rec)); atomic_set(&hip->opencnt, 0);
memset(HFSPLUS_I(inode).cached_extents, 0, sizeof(hfsplus_extent_rec)); hip->flags = 0;
HFSPLUS_I(inode).alloc_blocks = 0; memset(hip->first_extents, 0, sizeof(hfsplus_extent_rec));
HFSPLUS_I(inode).first_blocks = 0; memset(hip->cached_extents, 0, sizeof(hfsplus_extent_rec));
HFSPLUS_I(inode).cached_start = 0; hip->alloc_blocks = 0;
HFSPLUS_I(inode).cached_blocks = 0; hip->first_blocks = 0;
HFSPLUS_I(inode).phys_size = 0; hip->cached_start = 0;
HFSPLUS_I(inode).fs_blocks = 0; hip->cached_blocks = 0;
HFSPLUS_I(inode).rsrc_inode = NULL; hip->phys_size = 0;
hip->fs_blocks = 0;
hip->rsrc_inode = NULL;
if (S_ISDIR(inode->i_mode)) { if (S_ISDIR(inode->i_mode)) {
inode->i_size = 2; inode->i_size = 2;
sbi->folder_count++; sbi->folder_count++;
@ -395,12 +400,12 @@ struct inode *hfsplus_new_inode(struct super_block *sb, int mode)
inode->i_op = &hfsplus_file_inode_operations; inode->i_op = &hfsplus_file_inode_operations;
inode->i_fop = &hfsplus_file_operations; inode->i_fop = &hfsplus_file_operations;
inode->i_mapping->a_ops = &hfsplus_aops; inode->i_mapping->a_ops = &hfsplus_aops;
HFSPLUS_I(inode).clump_blocks = sbi->data_clump_blocks; hip->clump_blocks = sbi->data_clump_blocks;
} else if (S_ISLNK(inode->i_mode)) { } else if (S_ISLNK(inode->i_mode)) {
sbi->file_count++; sbi->file_count++;
inode->i_op = &page_symlink_inode_operations; inode->i_op = &page_symlink_inode_operations;
inode->i_mapping->a_ops = &hfsplus_aops; inode->i_mapping->a_ops = &hfsplus_aops;
HFSPLUS_I(inode).clump_blocks = 1; hip->clump_blocks = 1;
} else } else
sbi->file_count++; sbi->file_count++;
insert_inode_hash(inode); insert_inode_hash(inode);
@ -436,26 +441,27 @@ void hfsplus_inode_read_fork(struct inode *inode, struct hfsplus_fork_raw *fork)
{ {
struct super_block *sb = inode->i_sb; struct super_block *sb = inode->i_sb;
struct hfsplus_sb_info *sbi = HFSPLUS_SB(sb); struct hfsplus_sb_info *sbi = HFSPLUS_SB(sb);
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
u32 count; u32 count;
int i; int i;
memcpy(&HFSPLUS_I(inode).first_extents, &fork->extents, memcpy(&hip->first_extents, &fork->extents, sizeof(hfsplus_extent_rec));
sizeof(hfsplus_extent_rec));
for (count = 0, i = 0; i < 8; i++) for (count = 0, i = 0; i < 8; i++)
count += be32_to_cpu(fork->extents[i].block_count); count += be32_to_cpu(fork->extents[i].block_count);
HFSPLUS_I(inode).first_blocks = count; hip->first_blocks = count;
memset(HFSPLUS_I(inode).cached_extents, 0, sizeof(hfsplus_extent_rec)); memset(hip->cached_extents, 0, sizeof(hfsplus_extent_rec));
HFSPLUS_I(inode).cached_start = 0; hip->cached_start = 0;
HFSPLUS_I(inode).cached_blocks = 0; hip->cached_blocks = 0;
HFSPLUS_I(inode).alloc_blocks = be32_to_cpu(fork->total_blocks); hip->alloc_blocks = be32_to_cpu(fork->total_blocks);
inode->i_size = HFSPLUS_I(inode).phys_size = be64_to_cpu(fork->total_size); hip->phys_size = inode->i_size = be64_to_cpu(fork->total_size);
HFSPLUS_I(inode).fs_blocks = (inode->i_size + sb->s_blocksize - 1) >> sb->s_blocksize_bits; hip->fs_blocks =
inode_set_bytes(inode, HFSPLUS_I(inode).fs_blocks << sb->s_blocksize_bits); (inode->i_size + sb->s_blocksize - 1) >> sb->s_blocksize_bits;
HFSPLUS_I(inode).clump_blocks = inode_set_bytes(inode, hip->fs_blocks << sb->s_blocksize_bits);
hip->clump_blocks =
be32_to_cpu(fork->clump_size) >> sbi->alloc_blksz_shift; be32_to_cpu(fork->clump_size) >> sbi->alloc_blksz_shift;
if (!HFSPLUS_I(inode).clump_blocks) { if (!hip->clump_blocks) {
HFSPLUS_I(inode).clump_blocks = HFSPLUS_IS_RSRC(inode) ? hip->clump_blocks = HFSPLUS_IS_RSRC(inode) ?
sbi->rsrc_clump_blocks : sbi->rsrc_clump_blocks :
sbi->data_clump_blocks; sbi->data_clump_blocks;
} }
@ -463,10 +469,10 @@ void hfsplus_inode_read_fork(struct inode *inode, struct hfsplus_fork_raw *fork)
void hfsplus_inode_write_fork(struct inode *inode, struct hfsplus_fork_raw *fork) void hfsplus_inode_write_fork(struct inode *inode, struct hfsplus_fork_raw *fork)
{ {
memcpy(&fork->extents, &HFSPLUS_I(inode).first_extents, memcpy(&fork->extents, &HFSPLUS_I(inode)->first_extents,
sizeof(hfsplus_extent_rec)); sizeof(hfsplus_extent_rec));
fork->total_size = cpu_to_be64(inode->i_size); fork->total_size = cpu_to_be64(inode->i_size);
fork->total_blocks = cpu_to_be32(HFSPLUS_I(inode).alloc_blocks); fork->total_blocks = cpu_to_be32(HFSPLUS_I(inode)->alloc_blocks);
} }
int hfsplus_cat_read_inode(struct inode *inode, struct hfs_find_data *fd) int hfsplus_cat_read_inode(struct inode *inode, struct hfs_find_data *fd)
@ -477,7 +483,7 @@ int hfsplus_cat_read_inode(struct inode *inode, struct hfs_find_data *fd)
type = hfs_bnode_read_u16(fd->bnode, fd->entryoffset); type = hfs_bnode_read_u16(fd->bnode, fd->entryoffset);
HFSPLUS_I(inode).dev = 0; HFSPLUS_I(inode)->dev = 0;
if (type == HFSPLUS_FOLDER) { if (type == HFSPLUS_FOLDER) {
struct hfsplus_cat_folder *folder = &entry.folder; struct hfsplus_cat_folder *folder = &entry.folder;
@ -491,8 +497,8 @@ int hfsplus_cat_read_inode(struct inode *inode, struct hfs_find_data *fd)
inode->i_atime = hfsp_mt2ut(folder->access_date); inode->i_atime = hfsp_mt2ut(folder->access_date);
inode->i_mtime = hfsp_mt2ut(folder->content_mod_date); inode->i_mtime = hfsp_mt2ut(folder->content_mod_date);
inode->i_ctime = hfsp_mt2ut(folder->attribute_mod_date); inode->i_ctime = hfsp_mt2ut(folder->attribute_mod_date);
HFSPLUS_I(inode).create_date = folder->create_date; HFSPLUS_I(inode)->create_date = folder->create_date;
HFSPLUS_I(inode).fs_blocks = 0; HFSPLUS_I(inode)->fs_blocks = 0;
inode->i_op = &hfsplus_dir_inode_operations; inode->i_op = &hfsplus_dir_inode_operations;
inode->i_fop = &hfsplus_dir_operations; inode->i_fop = &hfsplus_dir_operations;
} else if (type == HFSPLUS_FILE) { } else if (type == HFSPLUS_FILE) {
@ -523,7 +529,7 @@ int hfsplus_cat_read_inode(struct inode *inode, struct hfs_find_data *fd)
inode->i_atime = hfsp_mt2ut(file->access_date); inode->i_atime = hfsp_mt2ut(file->access_date);
inode->i_mtime = hfsp_mt2ut(file->content_mod_date); inode->i_mtime = hfsp_mt2ut(file->content_mod_date);
inode->i_ctime = hfsp_mt2ut(file->attribute_mod_date); inode->i_ctime = hfsp_mt2ut(file->attribute_mod_date);
HFSPLUS_I(inode).create_date = file->create_date; HFSPLUS_I(inode)->create_date = file->create_date;
} else { } else {
printk(KERN_ERR "hfs: bad catalog entry used to create inode\n"); printk(KERN_ERR "hfs: bad catalog entry used to create inode\n");
res = -EIO; res = -EIO;
@ -538,7 +544,7 @@ int hfsplus_cat_write_inode(struct inode *inode)
hfsplus_cat_entry entry; hfsplus_cat_entry entry;
if (HFSPLUS_IS_RSRC(inode)) if (HFSPLUS_IS_RSRC(inode))
main_inode = HFSPLUS_I(inode).rsrc_inode; main_inode = HFSPLUS_I(inode)->rsrc_inode;
if (!main_inode->i_nlink) if (!main_inode->i_nlink)
return 0; return 0;
@ -582,9 +588,9 @@ int hfsplus_cat_write_inode(struct inode *inode)
sizeof(struct hfsplus_cat_file)); sizeof(struct hfsplus_cat_file));
hfsplus_inode_write_fork(inode, &file->data_fork); hfsplus_inode_write_fork(inode, &file->data_fork);
if (S_ISREG(inode->i_mode)) if (S_ISREG(inode->i_mode))
HFSPLUS_I(inode).dev = inode->i_nlink; HFSPLUS_I(inode)->dev = inode->i_nlink;
if (S_ISCHR(inode->i_mode) || S_ISBLK(inode->i_mode)) if (S_ISCHR(inode->i_mode) || S_ISBLK(inode->i_mode))
HFSPLUS_I(inode).dev = kdev_t_to_nr(inode->i_rdev); HFSPLUS_I(inode)->dev = kdev_t_to_nr(inode->i_rdev);
hfsplus_set_perms(inode, &file->permissions); hfsplus_set_perms(inode, &file->permissions);
if ((file->permissions.rootflags | file->permissions.userflags) & HFSPLUS_FLG_IMMUTABLE) if ((file->permissions.rootflags | file->permissions.userflags) & HFSPLUS_FLG_IMMUTABLE)
file->flags |= cpu_to_be16(HFSPLUS_FILE_LOCKED); file->flags |= cpu_to_be16(HFSPLUS_FILE_LOCKED);

View File

@ -23,13 +23,14 @@
static int hfsplus_ioctl_getflags(struct file *file, int __user *user_flags) static int hfsplus_ioctl_getflags(struct file *file, int __user *user_flags)
{ {
struct inode *inode = file->f_path.dentry->d_inode; struct inode *inode = file->f_path.dentry->d_inode;
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
unsigned int flags = 0; unsigned int flags = 0;
if (HFSPLUS_I(inode).rootflags & HFSPLUS_FLG_IMMUTABLE) if (hip->rootflags & HFSPLUS_FLG_IMMUTABLE)
flags |= FS_IMMUTABLE_FL; flags |= FS_IMMUTABLE_FL;
if (HFSPLUS_I(inode).rootflags & HFSPLUS_FLG_APPEND) if (hip->rootflags & HFSPLUS_FLG_APPEND)
flags |= FS_APPEND_FL; flags |= FS_APPEND_FL;
if (HFSPLUS_I(inode).userflags & HFSPLUS_FLG_NODUMP) if (hip->userflags & HFSPLUS_FLG_NODUMP)
flags |= FS_NODUMP_FL; flags |= FS_NODUMP_FL;
return put_user(flags, user_flags); return put_user(flags, user_flags);
@ -38,6 +39,7 @@ static int hfsplus_ioctl_getflags(struct file *file, int __user *user_flags)
static int hfsplus_ioctl_setflags(struct file *file, int __user *user_flags) static int hfsplus_ioctl_setflags(struct file *file, int __user *user_flags)
{ {
struct inode *inode = file->f_path.dentry->d_inode; struct inode *inode = file->f_path.dentry->d_inode;
struct hfsplus_inode_info *hip = HFSPLUS_I(inode);
unsigned int flags; unsigned int flags;
int err = 0; int err = 0;
@ -58,7 +60,7 @@ static int hfsplus_ioctl_setflags(struct file *file, int __user *user_flags)
mutex_lock(&inode->i_mutex); mutex_lock(&inode->i_mutex);
if (flags & (FS_IMMUTABLE_FL|FS_APPEND_FL) || if (flags & (FS_IMMUTABLE_FL|FS_APPEND_FL) ||
HFSPLUS_I(inode).rootflags & (HFSPLUS_FLG_IMMUTABLE|HFSPLUS_FLG_APPEND)) { hip->rootflags & (HFSPLUS_FLG_IMMUTABLE|HFSPLUS_FLG_APPEND)) {
if (!capable(CAP_LINUX_IMMUTABLE)) { if (!capable(CAP_LINUX_IMMUTABLE)) {
err = -EPERM; err = -EPERM;
goto out_unlock_inode; goto out_unlock_inode;
@ -72,22 +74,22 @@ static int hfsplus_ioctl_setflags(struct file *file, int __user *user_flags)
} }
if (flags & FS_IMMUTABLE_FL) { if (flags & FS_IMMUTABLE_FL) {
inode->i_flags |= S_IMMUTABLE; inode->i_flags |= S_IMMUTABLE;
HFSPLUS_I(inode).rootflags |= HFSPLUS_FLG_IMMUTABLE; hip->rootflags |= HFSPLUS_FLG_IMMUTABLE;
} else { } else {
inode->i_flags &= ~S_IMMUTABLE; inode->i_flags &= ~S_IMMUTABLE;
HFSPLUS_I(inode).rootflags &= ~HFSPLUS_FLG_IMMUTABLE; hip->rootflags &= ~HFSPLUS_FLG_IMMUTABLE;
} }
if (flags & FS_APPEND_FL) { if (flags & FS_APPEND_FL) {
inode->i_flags |= S_APPEND; inode->i_flags |= S_APPEND;
HFSPLUS_I(inode).rootflags |= HFSPLUS_FLG_APPEND; hip->rootflags |= HFSPLUS_FLG_APPEND;
} else { } else {
inode->i_flags &= ~S_APPEND; inode->i_flags &= ~S_APPEND;
HFSPLUS_I(inode).rootflags &= ~HFSPLUS_FLG_APPEND; hip->rootflags &= ~HFSPLUS_FLG_APPEND;
} }
if (flags & FS_NODUMP_FL) if (flags & FS_NODUMP_FL)
HFSPLUS_I(inode).userflags |= HFSPLUS_FLG_NODUMP; hip->userflags |= HFSPLUS_FLG_NODUMP;
else else
HFSPLUS_I(inode).userflags &= ~HFSPLUS_FLG_NODUMP; hip->userflags &= ~HFSPLUS_FLG_NODUMP;
inode->i_ctime = CURRENT_TIME_SEC; inode->i_ctime = CURRENT_TIME_SEC;
mark_inode_dirty(inode); mark_inode_dirty(inode);

View File

@ -33,11 +33,11 @@ struct inode *hfsplus_iget(struct super_block *sb, unsigned long ino)
if (!(inode->i_state & I_NEW)) if (!(inode->i_state & I_NEW))
return inode; return inode;
INIT_LIST_HEAD(&HFSPLUS_I(inode).open_dir_list); INIT_LIST_HEAD(&HFSPLUS_I(inode)->open_dir_list);
mutex_init(&HFSPLUS_I(inode).extents_lock); mutex_init(&HFSPLUS_I(inode)->extents_lock);
HFSPLUS_I(inode).flags = 0; HFSPLUS_I(inode)->flags = 0;
HFSPLUS_I(inode).rsrc_inode = NULL; HFSPLUS_I(inode)->rsrc_inode = NULL;
atomic_set(&HFSPLUS_I(inode).opencnt, 0); atomic_set(&HFSPLUS_I(inode)->opencnt, 0);
if (inode->i_ino >= HFSPLUS_FIRSTUSER_CNID) { if (inode->i_ino >= HFSPLUS_FIRSTUSER_CNID) {
read_inode: read_inode:
@ -151,8 +151,8 @@ static void hfsplus_evict_inode(struct inode *inode)
truncate_inode_pages(&inode->i_data, 0); truncate_inode_pages(&inode->i_data, 0);
end_writeback(inode); end_writeback(inode);
if (HFSPLUS_IS_RSRC(inode)) { if (HFSPLUS_IS_RSRC(inode)) {
HFSPLUS_I(HFSPLUS_I(inode).rsrc_inode).rsrc_inode = NULL; HFSPLUS_I(HFSPLUS_I(inode)->rsrc_inode)->rsrc_inode = NULL;
iput(HFSPLUS_I(inode).rsrc_inode); iput(HFSPLUS_I(inode)->rsrc_inode);
} }
} }
@ -491,7 +491,7 @@ static struct inode *hfsplus_alloc_inode(struct super_block *sb)
static void hfsplus_destroy_inode(struct inode *inode) static void hfsplus_destroy_inode(struct inode *inode)
{ {
kmem_cache_free(hfsplus_inode_cachep, &HFSPLUS_I(inode)); kmem_cache_free(hfsplus_inode_cachep, HFSPLUS_I(inode));
} }
#define HFSPLUS_INODE_SIZE sizeof(struct hfsplus_inode_info) #define HFSPLUS_INODE_SIZE sizeof(struct hfsplus_inode_info)