Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
nexedi
linux
Commits
7bbbc1b5
Commit
7bbbc1b5
authored
Jun 05, 2002
by
Oleg Drokin
Browse files
Options
Browse Files
Download
Plain Diff
Merge angband.namesys.com:/home/green/bk/linux-2.5
into angband.namesys.com:/home/green/bk_work/reiser3-linux-2.5
parents
ea1e2d62
72c45511
Changes
16
Hide whitespace changes
Inline
Side-by-side
Showing
16 changed files
with
515 additions
and
549 deletions
+515
-549
Documentation/Changes
Documentation/Changes
+1
-1
fs/reiserfs/bitmap.c
fs/reiserfs/bitmap.c
+5
-10
fs/reiserfs/dir.c
fs/reiserfs/dir.c
+7
-7
fs/reiserfs/file.c
fs/reiserfs/file.c
+6
-8
fs/reiserfs/fix_node.c
fs/reiserfs/fix_node.c
+13
-7
fs/reiserfs/inode.c
fs/reiserfs/inode.c
+28
-51
fs/reiserfs/ioctl.c
fs/reiserfs/ioctl.c
+2
-2
fs/reiserfs/journal.c
fs/reiserfs/journal.c
+54
-57
fs/reiserfs/namei.c
fs/reiserfs/namei.c
+84
-173
fs/reiserfs/prints.c
fs/reiserfs/prints.c
+4
-3
fs/reiserfs/procfs.c
fs/reiserfs/procfs.c
+5
-5
fs/reiserfs/stree.c
fs/reiserfs/stree.c
+2
-2
fs/reiserfs/super.c
fs/reiserfs/super.c
+279
-218
fs/reiserfs/tail_conversion.c
fs/reiserfs/tail_conversion.c
+1
-1
include/linux/reiserfs_fs.h
include/linux/reiserfs_fs.h
+13
-3
include/linux/reiserfs_fs_sb.h
include/linux/reiserfs_fs_sb.h
+11
-1
No files found.
Documentation/Changes
View file @
7bbbc1b5
...
...
@@ -314,7 +314,7 @@ o <http://oss.software.ibm.com/jfs>
Reiserfsprogs
-------------
o <ftp://ftp.namesys.com/pub/reiserfsprogs/reiserfsprogs-3.x.
0
b.tar.gz>
o <ftp://ftp.namesys.com/pub/reiserfsprogs/reiserfsprogs-3.x.
1
b.tar.gz>
LVM toolset
-----------
...
...
fs/reiserfs/bitmap.c
View file @
7bbbc1b5
...
...
@@ -103,7 +103,7 @@ static void _reiserfs_free_block (struct reiserfs_transaction_handle *th, unsign
if
(
nr
>=
sb_bmap_nr
(
rs
))
{
reiserfs_warning
(
"vs-4075: reiserfs_free_block: "
"block %lu is out of range on %s
\n
"
,
block
,
s
->
s_id
);
block
,
reiserfs_bdevname
(
s
)
);
return
;
}
...
...
@@ -113,7 +113,7 @@ static void _reiserfs_free_block (struct reiserfs_transaction_handle *th, unsign
if
(
!
reiserfs_test_and_clear_le_bit
(
offset
,
apbh
[
nr
]
->
b_data
))
{
reiserfs_warning
(
"vs-4080: reiserfs_free_block: "
"free_block (%s:%lu)[dev:blocknr]: bit already cleared
\n
"
,
s
->
s_id
,
block
);
reiserfs_bdevname
(
s
)
,
block
);
}
journal_mark_dirty
(
th
,
s
,
apbh
[
nr
]);
...
...
@@ -139,10 +139,8 @@ void reiserfs_free_block (struct reiserfs_transaction_handle *th,
/* preallocated blocks don't need to be run through journal_mark_freed */
void
reiserfs_free_prealloc_block
(
struct
reiserfs_transaction_handle
*
th
,
unsigned
long
block
)
{
struct
super_block
*
s
=
th
->
t_super
;
RFALSE
(
!
s
,
"vs-4060: trying to free block on nonexistent device"
);
RFALSE
(
is_reusable
(
s
,
block
,
1
)
==
0
,
"vs-4070: can not free such block"
);
RFALSE
(
!
th
->
t_super
,
"vs-4060: trying to free block on nonexistent device"
);
RFALSE
(
is_reusable
(
th
->
t_super
,
block
,
1
)
==
0
,
"vs-4070: can not free such block"
);
_reiserfs_free_block
(
th
,
block
)
;
}
...
...
@@ -670,10 +668,7 @@ int reiserfs_new_unf_blocknrs2 (struct reiserfs_transaction_handle *th,
return
ret
;
}
//
// a portion of this function, was derived from minix or ext2's
// analog. You should be able to tell which portion by looking at the
// ext2 code and comparing.
static
void
__discard_prealloc
(
struct
reiserfs_transaction_handle
*
th
,
struct
reiserfs_inode_info
*
ei
)
{
...
...
fs/reiserfs/dir.c
View file @
7bbbc1b5
...
...
@@ -24,9 +24,10 @@ struct file_operations reiserfs_dir_operations = {
};
int
reiserfs_dir_fsync
(
struct
file
*
filp
,
struct
dentry
*
dentry
,
int
datasync
)
{
lock_kernel
();
reiserfs_commit_for_inode
(
dentry
->
d_inode
)
;
unlock_kernel
()
;
struct
inode
*
inode
=
dentry
->
d_inode
;
reiserfs_write_lock
(
inode
->
i_sb
);
reiserfs_commit_for_inode
(
inode
)
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
return
0
;
}
...
...
@@ -50,7 +51,7 @@ static int reiserfs_readdir (struct file * filp, void * dirent, filldir_t filldi
struct
reiserfs_dir_entry
de
;
int
ret
=
0
;
lock_kernel
(
);
reiserfs_write_lock
(
inode
->
i_sb
);
reiserfs_check_lock_depth
(
"readdir"
)
;
...
...
@@ -109,7 +110,7 @@ static int reiserfs_readdir (struct file * filp, void * dirent, filldir_t filldi
if
(
!
d_name
[
d_reclen
-
1
])
d_reclen
=
strlen
(
d_name
);
if
(
d_reclen
>
REISERFS_MAX_NAME
_LEN
(
inode
->
i_sb
->
s_blocksize
)){
if
(
d_reclen
>
REISERFS_MAX_NAME
(
inode
->
i_sb
->
s_blocksize
)){
/* too big to send back to VFS */
continue
;
}
...
...
@@ -181,13 +182,12 @@ static int reiserfs_readdir (struct file * filp, void * dirent, filldir_t filldi
end:
// FIXME: ext2_readdir does not reset f_pos
filp
->
f_pos
=
next_pos
;
pathrelse
(
&
path_to_entry
);
reiserfs_check_path
(
&
path_to_entry
)
;
UPDATE_ATIME
(
inode
)
;
out:
unlock_kernel
(
);
reiserfs_write_unlock
(
inode
->
i_sb
);
return
ret
;
}
...
...
fs/reiserfs/file.c
View file @
7bbbc1b5
...
...
@@ -39,7 +39,7 @@ static int reiserfs_file_release (struct inode * inode, struct file * filp)
return
0
;
}
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
)
;
down
(
&
inode
->
i_sem
);
journal_begin
(
&
th
,
inode
->
i_sb
,
JOURNAL_PER_BALANCE_CNT
*
3
)
;
reiserfs_update_inode_transaction
(
inode
)
;
...
...
@@ -61,14 +61,12 @@ static int reiserfs_file_release (struct inode * inode, struct file * filp)
pop_journal_writer
(
windex
)
;
}
up
(
&
inode
->
i_sem
);
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
return
0
;
}
static
void
reiserfs_vfs_truncate_file
(
struct
inode
*
inode
)
{
lock_kernel
();
reiserfs_truncate_file
(
inode
,
1
)
;
unlock_kernel
();
}
/* Sync a reiserfs file. */
...
...
@@ -86,21 +84,21 @@ static int reiserfs_sync_file(
struct
inode
*
p_s_inode
=
p_s_dentry
->
d_inode
;
int
n_err
;
lock_kernel
()
;
reiserfs_write_lock
(
p_s_inode
->
i_sb
)
;
if
(
!
S_ISREG
(
p_s_inode
->
i_mode
))
BUG
();
n_err
=
sync_mapping_buffers
(
p_s_inode
->
i_mapping
)
;
reiserfs_commit_for_inode
(
p_s_inode
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
p_s_inode
->
i_sb
)
;
return
(
n_err
<
0
)
?
-
EIO
:
0
;
}
static
int
reiserfs_setattr
(
struct
dentry
*
dentry
,
struct
iattr
*
attr
)
{
struct
inode
*
inode
=
dentry
->
d_inode
;
int
error
;
lock_kernel
(
);
reiserfs_write_lock
(
inode
->
i_sb
);
if
(
attr
->
ia_valid
&
ATTR_SIZE
)
{
/* version 2 items will be caught by the s_maxbytes check
** done for us in vmtruncate
...
...
@@ -138,7 +136,7 @@ static int reiserfs_setattr(struct dentry *dentry, struct iattr *attr) {
inode_setattr
(
inode
,
attr
)
;
out:
unlock_kernel
(
);
reiserfs_write_unlock
(
inode
->
i_sb
);
return
error
;
}
...
...
fs/reiserfs/fix_node.c
View file @
7bbbc1b5
...
...
@@ -2092,21 +2092,27 @@ static void tb_buffer_sanity_check (struct super_block * p_s_sb,
if
(
p_s_bh
)
{
if
(
atomic_read
(
&
(
p_s_bh
->
b_count
))
<=
0
)
{
reiserfs_panic
(
p_s_sb
,
"tb_buffer_sanity_check(): negative or zero reference counter for buffer %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
reiserfs_panic
(
p_s_sb
,
"
jmacd-1:
tb_buffer_sanity_check(): negative or zero reference counter for buffer %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
}
if
(
!
buffer_uptodate
(
p_s_bh
)
)
{
reiserfs_panic
(
p_s_sb
,
"tb_buffer_sanity_check(): buffer is not up to date %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
reiserfs_panic
(
p_s_sb
,
"
jmacd-2:
tb_buffer_sanity_check(): buffer is not up to date %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
}
if
(
!
B_IS_IN_TREE
(
p_s_bh
)
)
{
reiserfs_panic
(
p_s_sb
,
"tb_buffer_sanity_check(): buffer is not in tree %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
reiserfs_panic
(
p_s_sb
,
"
jmacd-3:
tb_buffer_sanity_check(): buffer is not in tree %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
}
if
(
p_s_bh
->
b_bdev
!=
p_s_sb
->
s_bdev
||
p_s_bh
->
b_size
!=
p_s_sb
->
s_blocksize
||
p_s_bh
->
b_blocknr
>
SB_BLOCK_COUNT
(
p_s_sb
))
{
reiserfs_panic
(
p_s_sb
,
"tb_buffer_sanity_check(): check failed for buffer %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
if
(
p_s_bh
->
b_bdev
!=
p_s_sb
->
s_bdev
)
{
reiserfs_panic
(
p_s_sb
,
"jmacd-4: tb_buffer_sanity_check(): buffer has wrong device %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
}
if
(
p_s_bh
->
b_size
!=
p_s_sb
->
s_blocksize
)
{
reiserfs_panic
(
p_s_sb
,
"jmacd-5: tb_buffer_sanity_check(): buffer has wrong blocksize %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
}
if
(
p_s_bh
->
b_blocknr
>
SB_BLOCK_COUNT
(
p_s_sb
))
{
reiserfs_panic
(
p_s_sb
,
"jmacd-6: tb_buffer_sanity_check(): buffer block number too high %s[%d] (%b)
\n
"
,
descr
,
level
,
p_s_bh
);
}
}
}
...
...
fs/reiserfs/inode.c
View file @
7bbbc1b5
...
...
@@ -20,10 +20,7 @@
static
int
reiserfs_get_block
(
struct
inode
*
inode
,
sector_t
block
,
struct
buffer_head
*
bh_result
,
int
create
);
//
// initially this function was derived from minix or ext2's analog and
// evolved as the prototype did
//
void
reiserfs_delete_inode
(
struct
inode
*
inode
)
{
int
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
2
;
...
...
@@ -31,7 +28,7 @@ void reiserfs_delete_inode (struct inode * inode)
struct
reiserfs_transaction_handle
th
;
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
);
/* The = 0 happens when we abort creating a new inode for some reason like lack of space.. */
if
(
!
(
inode
->
i_state
&
I_NEW
)
&&
INODE_PKEY
(
inode
)
->
k_objectid
!=
0
)
{
/* also handles bad_inode case */
...
...
@@ -56,7 +53,7 @@ void reiserfs_delete_inode (struct inode * inode)
}
clear_inode
(
inode
);
/* note this must go after the journal_end to prevent deadlock */
inode
->
i_blocks
=
0
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
}
static
void
_make_cpu_key
(
struct
cpu_key
*
key
,
int
version
,
__u32
dirid
,
__u32
objectid
,
...
...
@@ -112,8 +109,7 @@ static void add_to_flushlist(struct inode *inode, struct buffer_head *bh) {
}
//
// FIXME: we might cache recently accessed indirect item (or at least
// first 15 pointers just like ext2 does
// FIXME: we might cache recently accessed indirect item
// Ugh. Not too eager for that....
// I cut the code until such time as I see a convincing argument (benchmark).
...
...
@@ -412,10 +408,10 @@ int reiserfs_bmap (struct inode * inode, sector_t block,
if
(
!
file_capable
(
inode
,
block
))
return
-
EFBIG
;
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
)
;
/* do not read the direct item */
_get_block_create_0
(
inode
,
block
,
bh_result
,
0
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
return
0
;
}
...
...
@@ -521,12 +517,7 @@ static inline int _allocate_block(struct reiserfs_transaction_handle *th,
#endif
return
reiserfs_new_unf_blocknrs
(
th
,
allocated_block_nr
,
tag
);
}
//
// initially this function was derived from ext2's analog and evolved
// as the prototype did. You'll need to look at the ext2 version to
// determine which parts are derivative, if any, understanding that
// there are only so many ways to code to a given interface.
//
int
reiserfs_get_block
(
struct
inode
*
inode
,
sector_t
block
,
struct
buffer_head
*
bh_result
,
int
create
)
{
...
...
@@ -554,17 +545,17 @@ int reiserfs_get_block (struct inode * inode, sector_t block,
loff_t
new_offset
=
(((
loff_t
)
block
)
<<
inode
->
i_sb
->
s_blocksize_bits
)
+
1
;
/* bad.... */
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
)
;
th
.
t_trans_id
=
0
;
version
=
get_inode_item_key_version
(
inode
);
if
(
block
<
0
)
{
unlock_kernel
(
);
reiserfs_write_unlock
(
inode
->
i_sb
);
return
-
EIO
;
}
if
(
!
file_capable
(
inode
,
block
))
{
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
return
-
EFBIG
;
}
...
...
@@ -576,7 +567,7 @@ int reiserfs_get_block (struct inode * inode, sector_t block,
/* find number of block-th logical block of the file */
ret
=
_get_block_create_0
(
inode
,
block
,
bh_result
,
create
|
GET_BLOCK_READ_DIRECT
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
return
ret
;
}
...
...
@@ -667,7 +658,7 @@ int reiserfs_get_block (struct inode * inode, sector_t block,
if
(
transaction_started
)
journal_end
(
&
th
,
inode
->
i_sb
,
jbegin_count
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
/* the item was found, so new blocks were not added to the file
** there is no need to make sure the inode is updated with this
...
...
@@ -866,7 +857,6 @@ int reiserfs_get_block (struct inode * inode, sector_t block,
retval
=
0
;
reiserfs_check_path
(
&
path
)
;
failure:
if
(
transaction_started
)
{
...
...
@@ -874,7 +864,7 @@ int reiserfs_get_block (struct inode * inode, sector_t block,
journal_end
(
&
th
,
inode
->
i_sb
,
jbegin_count
)
;
}
pop_journal_writer
(
windex
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
reiserfs_check_path
(
&
path
)
;
return
retval
;
}
...
...
@@ -1353,10 +1343,6 @@ int reiserfs_encode_fh(struct dentry *dentry, __u32 *data, int *lenp, int need_p
}
//
// initially this function was derived from minix or ext2's analog and
// evolved as the prototype did
//
/* looks for stat data, then copies fields to it, marks the buffer
containing stat data as dirty */
/* reiserfs inodes are never really dirty, since the dirty inode call
...
...
@@ -1379,11 +1365,11 @@ void reiserfs_write_inode (struct inode * inode, int do_sync) {
** ignored because the altered inode has already been logged.
*/
if
(
do_sync
&&
!
(
current
->
flags
&
PF_MEMALLOC
))
{
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
)
;
journal_begin
(
&
th
,
inode
->
i_sb
,
jbegin_count
)
;
reiserfs_update_sd
(
&
th
,
inode
);
journal_end_sync
(
&
th
,
inode
->
i_sb
,
jbegin_count
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
}
}
...
...
@@ -1725,7 +1711,8 @@ static int grab_tail_page(struct inode *p_s_inode,
** call prepare_write
*/
reiserfs_warning
(
"clm-6000: error reading block %lu on dev %s
\n
"
,
bh
->
b_blocknr
,
p_s_inode
->
i_sb
->
s_id
)
;
bh
->
b_blocknr
,
reiserfs_bdevname
(
p_s_inode
->
i_sb
))
;
error
=
-
EIO
;
goto
unlock
;
}
...
...
@@ -1750,7 +1737,6 @@ static int grab_tail_page(struct inode *p_s_inode,
void
reiserfs_truncate_file
(
struct
inode
*
p_s_inode
,
int
update_timestamps
)
{
struct
reiserfs_transaction_handle
th
;
int
windex
;
/* we want the offset for the first byte after the end of the file */
unsigned
long
offset
=
p_s_inode
->
i_size
&
(
PAGE_CACHE_SIZE
-
1
)
;
unsigned
blocksize
=
p_s_inode
->
i_sb
->
s_blocksize
;
...
...
@@ -1759,6 +1745,8 @@ void reiserfs_truncate_file(struct inode *p_s_inode, int update_timestamps) {
int
error
;
struct
buffer_head
*
bh
=
NULL
;
reiserfs_write_lock
(
p_s_inode
->
i_sb
);
if
(
p_s_inode
->
i_size
>
0
)
{
if
((
error
=
grab_tail_page
(
p_s_inode
,
&
page
,
&
bh
)))
{
// -ENOENT means we truncated past the end of the file,
...
...
@@ -1812,7 +1800,7 @@ void reiserfs_truncate_file(struct inode *p_s_inode, int update_timestamps) {
page_cache_release
(
page
)
;
}
re
turn
;
re
iserfs_write_unlock
(
p_s_inode
->
i_sb
)
;
}
static
int
map_block_for_writepage
(
struct
inode
*
inode
,
...
...
@@ -1836,7 +1824,7 @@ static int map_block_for_writepage(struct inode *inode,
kmap
(
bh_result
->
b_page
)
;
start_over:
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
)
;
journal_begin
(
&
th
,
inode
->
i_sb
,
jbegin_count
)
;
reiserfs_update_inode_transaction
(
inode
)
;
...
...
@@ -1894,7 +1882,7 @@ static int map_block_for_writepage(struct inode *inode,
goto
research
;
}
}
else
{
reiserfs_warning
(
"clm-6003: bad item inode %lu, device %s
\n
"
,
inode
->
i_ino
,
inode
->
i_sb
->
s_id
)
;
reiserfs_warning
(
"clm-6003: bad item inode %lu, device %s
\n
"
,
inode
->
i_ino
,
reiserfs_bdevname
(
inode
->
i_sb
)
)
;
retval
=
-
EIO
;
goto
out
;
}
...
...
@@ -1903,7 +1891,7 @@ static int map_block_for_writepage(struct inode *inode,
out:
pathrelse
(
&
path
)
;
journal_end
(
&
th
,
inode
->
i_sb
,
jbegin_count
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
/* this is where we fill in holes in the file. */
if
(
use_get_block
)
{
...
...
@@ -2033,18 +2021,13 @@ static int reiserfs_write_full_page(struct page *page) {
return
error
;
}
//
// this is exactly what 2.3.99-pre9's ext2_readpage is
//
static
int
reiserfs_readpage
(
struct
file
*
f
,
struct
page
*
page
)
{
return
block_read_full_page
(
page
,
reiserfs_get_block
);
}
//
// modified from ext2_writepage is
//
static
int
reiserfs_writepage
(
struct
page
*
page
)
{
struct
inode
*
inode
=
page
->
mapping
->
host
;
...
...
@@ -2053,9 +2036,6 @@ static int reiserfs_writepage (struct page * page)
}
//
// from ext2_prepare_write, but modified
//
int
reiserfs_prepare_write
(
struct
file
*
f
,
struct
page
*
page
,
unsigned
from
,
unsigned
to
)
{
struct
inode
*
inode
=
page
->
mapping
->
host
;
...
...
@@ -2065,9 +2045,6 @@ int reiserfs_prepare_write(struct file *f, struct page *page,
}
//
// this is exactly what 2.3.99-pre9's ext2_bmap is
//
static
int
reiserfs_aop_bmap
(
struct
address_space
*
as
,
long
block
)
{
return
generic_block_bmap
(
as
,
block
,
reiserfs_bmap
)
;
}
...
...
@@ -2086,13 +2063,13 @@ static int reiserfs_commit_write(struct file *f, struct page *page,
*/
if
(
pos
>
inode
->
i_size
)
{
struct
reiserfs_transaction_handle
th
;
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
)
;
journal_begin
(
&
th
,
inode
->
i_sb
,
1
)
;
reiserfs_update_inode_transaction
(
inode
)
;
inode
->
i_size
=
pos
;
reiserfs_update_sd
(
&
th
,
inode
)
;
journal_end
(
&
th
,
inode
->
i_sb
,
1
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
}
ret
=
generic_commit_write
(
f
,
page
,
from
,
to
)
;
...
...
@@ -2101,9 +2078,9 @@ static int reiserfs_commit_write(struct file *f, struct page *page,
** for any packed tails the file might have had
*/
if
(
f
&&
(
f
->
f_flags
&
O_SYNC
))
{
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
)
;
reiserfs_commit_for_inode
(
inode
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
inode
->
i_sb
);
}
return
ret
;
}
...
...
fs/reiserfs/ioctl.c
View file @
7bbbc1b5
...
...
@@ -49,7 +49,7 @@ int reiserfs_unpack (struct inode * inode, struct file * filp)
if
(
REISERFS_I
(
inode
)
->
i_flags
&
i_nopack_mask
)
{
return
0
;
}
lock_kernel
(
);
reiserfs_write_lock
(
inode
->
i_sb
);
/* we need to make sure nobody is changing the file size beneath
** us
...
...
@@ -88,6 +88,6 @@ int reiserfs_unpack (struct inode * inode, struct file * filp)
out:
up
(
&
inode
->
i_sem
)
;
unlock_kernel
();
reiserfs_write_unlock
(
inode
->
i_sb
);
return
retval
;
}
fs/reiserfs/journal.c
View file @
7bbbc1b5
...
...
@@ -99,21 +99,6 @@ static int journal_join(struct reiserfs_transaction_handle *th, struct super_blo
static
int
release_journal_dev
(
struct
super_block
*
super
,
struct
reiserfs_journal
*
journal
);
static
inline
struct
buffer_head
*
journ_get_hash_table
(
struct
super_block
*
s
,
int
block
)
{
return
__get_hash_table
(
SB_JOURNAL
(
s
)
->
j_dev_bd
,
block
,
s
->
s_blocksize
);
}
static
inline
struct
buffer_head
*
journ_getblk
(
struct
super_block
*
s
,
int
block
)
{
return
__getblk
(
SB_JOURNAL
(
s
)
->
j_dev_bd
,
block
,
s
->
s_blocksize
);
}
static
inline
struct
buffer_head
*
journ_bread
(
struct
super_block
*
s
,
int
block
)
{
return
__bread
(
SB_JOURNAL
(
s
)
->
j_dev_bd
,
block
,
s
->
s_blocksize
);
}
static
void
init_journal_hash
(
struct
super_block
*
p_s_sb
)
{
memset
(
SB_JOURNAL
(
p_s_sb
)
->
j_hash_table
,
0
,
JOURNAL_HASH_SIZE
*
sizeof
(
struct
reiserfs_journal_cnode
*
))
;
}
...
...
@@ -704,7 +689,7 @@ static int flush_commit_list(struct super_block *s, struct reiserfs_journal_list
count
=
0
;
for
(
i
=
0
;
atomic_read
(
&
(
jl
->
j_commit_left
))
>
1
&&
i
<
(
jl
->
j_len
+
1
)
;
i
++
)
{
/* everything but commit_bh */
bn
=
SB_ONDISK_JOURNAL_1st_BLOCK
(
s
)
+
(
jl
->
j_start
+
i
)
%
SB_ONDISK_JOURNAL_SIZE
(
s
);
tbh
=
journ_get_hash_table
(
s
,
bn
)
;
tbh
=
journ
al
_get_hash_table
(
s
,
bn
)
;
/* kill this sanity check */
if
(
count
>
(
orig_commit_left
+
2
))
{
...
...
@@ -733,7 +718,7 @@ reiserfs_panic(s, "journal-539: flush_commit_list: BAD count(%d) > orig_commit_l
for
(
i
=
0
;
atomic_read
(
&
(
jl
->
j_commit_left
))
>
1
&&
i
<
(
jl
->
j_len
+
1
)
;
i
++
)
{
/* everything but commit_bh */
bn
=
SB_ONDISK_JOURNAL_1st_BLOCK
(
s
)
+
(
jl
->
j_start
+
i
)
%
SB_ONDISK_JOURNAL_SIZE
(
s
)
;
tbh
=
journ_get_hash_table
(
s
,
bn
)
;
tbh
=
journ
al
_get_hash_table
(
s
,
bn
)
;
wait_on_buffer
(
tbh
)
;
if
(
!
buffer_uptodate
(
tbh
))
{
...
...
@@ -1426,7 +1411,7 @@ static int journal_transaction_is_valid(struct super_block *p_s_sb, struct buffe
offset
=
d_bh
->
b_blocknr
-
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
;
/* ok, we have a journal description block, lets see if the transaction was valid */
c_bh
=
journ_bread
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
c_bh
=
journ
al
_bread
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
((
offset
+
le32_to_cpu
(
desc
->
j_len
)
+
1
)
%
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
)))
;
if
(
!
c_bh
)
return
0
;
...
...
@@ -1481,7 +1466,7 @@ static int journal_read_transaction(struct super_block *p_s_sb, unsigned long cu
unsigned
long
trans_offset
;
int
i
;
d_bh
=
journ_bread
(
p_s_sb
,
cur_dblock
)
;
d_bh
=
journ
al
_bread
(
p_s_sb
,
cur_dblock
)
;
if
(
!
d_bh
)
return
1
;
desc
=
(
struct
reiserfs_journal_desc
*
)
d_bh
->
b_data
;
...
...
@@ -1505,7 +1490,7 @@ static int journal_read_transaction(struct super_block *p_s_sb, unsigned long cu
brelse
(
d_bh
)
;
return
1
;
}
c_bh
=
journ_bread
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
c_bh
=
journ
al
_bread
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
((
trans_offset
+
le32_to_cpu
(
desc
->
j_len
)
+
1
)
%
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
)))
;
if
(
!
c_bh
)
{
...
...
@@ -1536,7 +1521,7 @@ static int journal_read_transaction(struct super_block *p_s_sb, unsigned long cu
}
/* get all the buffer heads */
for
(
i
=
0
;
i
<
le32_to_cpu
(
desc
->
j_len
)
;
i
++
)
{
log_blocks
[
i
]
=
journ_getblk
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
(
trans_offset
+
1
+
i
)
%
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
));
log_blocks
[
i
]
=
journ
al
_getblk
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
(
trans_offset
+
1
+
i
)
%
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
));
if
(
i
<
JOURNAL_TRANS_HALF
)
{
real_blocks
[
i
]
=
sb_getblk
(
p_s_sb
,
le32_to_cpu
(
desc
->
j_realblock
[
i
]))
;
}
else
{
...
...
@@ -1606,16 +1591,13 @@ static int journal_read_transaction(struct super_block *p_s_sb, unsigned long cu
return
0
;
}
/*
** read and replay the log
** on a clean unmount, the journal header's next unflushed pointer will be to an invalid
** transaction. This tests that before finding all the transactions in the log, whic makes normal mount times fast.
**
** After a crash, this starts with the next unflushed transaction, and replays until it finds one too old, or invalid.
**
** On exit, it sets things up so the first transaction will work correctly.
*/
struct
buffer_head
*
reiserfs_breada
(
struct
super_block
*
sb
,
int
block
,
/* This function reads blocks starting from block and to max_block of bufsize
size (but no more than BUFNR blocks at a time). This proved to improve
mounting speed on self-rebuilding raid5 arrays at least.
Right now it is only used from journal code. But later we might use it
from other places.
Note: Do not use journal_getblk/sb_getblk functions here! */
struct
buffer_head
*
reiserfs_breada
(
struct
block_device
*
dev
,
int
block
,
int
bufsize
,
unsigned
int
max_block
)
{
struct
buffer_head
*
bhlist
[
BUFNR
];
...
...
@@ -1623,7 +1605,7 @@ struct buffer_head * reiserfs_breada (struct super_block *sb, int block,
struct
buffer_head
*
bh
;
int
i
,
j
;
bh
=
sb_getblk
(
sb
,
block
);
bh
=
__getblk
(
dev
,
block
,
bufsize
);
if
(
buffer_uptodate
(
bh
))
return
(
bh
);
...
...
@@ -1633,7 +1615,7 @@ struct buffer_head * reiserfs_breada (struct super_block *sb, int block,
bhlist
[
0
]
=
bh
;
j
=
1
;
for
(
i
=
1
;
i
<
blocks
;
i
++
)
{
bh
=
sb_getblk
(
sb
,
block
+
i
);
bh
=
__getblk
(
dev
,
block
+
i
,
bufsize
);
if
(
buffer_uptodate
(
bh
))
{
brelse
(
bh
);
break
;
...
...
@@ -1650,6 +1632,16 @@ struct buffer_head * reiserfs_breada (struct super_block *sb, int block,
brelse
(
bh
);
return
NULL
;
}
/*
** read and replay the log
** on a clean unmount, the journal header's next unflushed pointer will be to an invalid
** transaction. This tests that before finding all the transactions in the log, whic makes normal mount times fast.
**
** After a crash, this starts with the next unflushed transaction, and replays until it finds one too old, or invalid.
**
** On exit, it sets things up so the first transaction will work correctly.
*/
static
int
journal_read
(
struct
super_block
*
p_s_sb
)
{
struct
reiserfs_journal_desc
*
desc
;
unsigned
long
oldest_trans_id
=
0
;
...
...
@@ -1667,14 +1659,14 @@ static int journal_read(struct super_block *p_s_sb) {
cur_dblock
=
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
;
printk
(
"reiserfs: checking transaction log (%s) for (%s)
\n
"
,
__bdevname
(
SB_JOURNAL_DEV
(
p_s_sb
)),
p_s_sb
->
s_id
)
;
bdevname
(
SB_JOURNAL
(
p_s_sb
)
->
j_dev_bd
),
reiserfs_bdevname
(
p_s_sb
))
;
start
=
CURRENT_TIME
;
/* step 1, read in the journal header block. Check the transaction it says
** is the first unflushed, and if that transaction is not valid,
** replay is done
*/
SB_JOURNAL
(
p_s_sb
)
->
j_header_bh
=
journ_bread
(
p_s_sb
,
SB_JOURNAL
(
p_s_sb
)
->
j_header_bh
=
journ
al
_bread
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
));
if
(
!
SB_JOURNAL
(
p_s_sb
)
->
j_header_bh
)
{
...
...
@@ -1698,7 +1690,7 @@ static int journal_read(struct super_block *p_s_sb) {
** there is nothing more we can do, and it makes no sense to read
** through the whole log.
*/
d_bh
=
journ_bread
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
le32_to_cpu
(
jh
->
j_first_unflushed_offset
))
;
d_bh
=
journ
al
_bread
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
le32_to_cpu
(
jh
->
j_first_unflushed_offset
))
;
ret
=
journal_transaction_is_valid
(
p_s_sb
,
d_bh
,
NULL
,
NULL
)
;
if
(
!
ret
)
{
continue_replay
=
0
;
...
...
@@ -1716,7 +1708,9 @@ static int journal_read(struct super_block *p_s_sb) {
** all the valid transactions, and pick out the oldest.
*/
while
(
continue_replay
&&
cur_dblock
<
(
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
)))
{
d_bh
=
reiserfs_breada
(
p_s_sb
,
cur_dblock
,
/* Note that it is required for blocksize of primary fs device and journal
device to be the same */
d_bh
=
reiserfs_breada
(
SB_JOURNAL
(
p_s_sb
)
->
j_dev_bd
,
cur_dblock
,
p_s_sb
->
s_blocksize
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
))
;
ret
=
journal_transaction_is_valid
(
p_s_sb
,
d_bh
,
&
oldest_invalid_trans_id
,
&
newest_mount_id
)
;
if
(
ret
==
1
)
{
...
...
@@ -1925,13 +1919,20 @@ static int release_journal_dev( struct super_block *super,
result
=
0
;
if
(
journal
->
j_dev_bd
!=
NULL
)
{
result
=
blkdev_put
(
journal
->
j_dev_bd
,
BDEV_FS
);
journal
->
j_dev_bd
=
NULL
;
}
if
(
journal
->
j_dev_file
!=
NULL
)
{
/*
* journal block device was taken via filp_open
*/
result
=
filp_close
(
journal
->
j_dev_file
,
NULL
);
journal
->
j_dev_file
=
NULL
;
journal
->
j_dev_bd
=
NULL
;
}
else
if
(
journal
->
j_dev_bd
!=
NULL
)
{
/*
* journal block device was taken via bdget and blkdev_get
*/
result
=
blkdev_put
(
journal
->
j_dev_bd
,
BDEV_FS
);
journal
->
j_dev_bd
=
NULL
;
}
if
(
result
!=
0
)
{
reiserfs_warning
(
"sh-457: release_journal_dev: Cannot release journal device: %i"
,
result
);
...
...
@@ -1966,6 +1967,9 @@ static int journal_init_dev( struct super_block *super,
printk
(
"sh-458: journal_init_dev: cannot init journal device
\n
'%s': %i"
,
kdevname
(
jdev
),
result
);
else
if
(
!
kdev_same
(
jdev
,
super
->
s_dev
))
{
set_blocksize
(
journal
->
j_dev_bd
,
super
->
s_blocksize
);
}
return
result
;
}
...
...
@@ -1981,15 +1985,12 @@ static int journal_init_dev( struct super_block *super,
}
else
if
(
jdev_inode
->
i_bdev
==
NULL
)
{
printk
(
"journal_init_dev: bdev unintialized for '%s'"
,
jdev_name
);
result
=
-
ENOMEM
;
}
else
if
(
(
result
=
blkdev_get
(
jdev_inode
->
i_bdev
,
FMODE_READ
|
FMODE_WRITE
,
0
,
BDEV_FS
)
)
!=
0
)
{
printk
(
"journal_init_dev: Cannot load device '%s': %i"
,
jdev_name
,
result
);
}
else
}
else
{
/* ok */
SB_JOURNAL_DEV
(
super
)
=
to_kdev_t
(
jdev_inode
->
i_bdev
->
bd_dev
);
set_blocksize
(
journal
->
j_dev_bd
,
super
->
s_blocksize
);
}
}
else
{
result
=
PTR_ERR
(
journal
->
j_dev_file
);
journal
->
j_dev_file
=
NULL
;
...
...
@@ -2041,7 +2042,7 @@ int journal_init(struct super_block *p_s_sb, const char * j_dev_name, int old_fo
rs
=
SB_DISK_SUPER_BLOCK
(
p_s_sb
);
/* read journal header */
bhjh
=
journ_bread
(
p_s_sb
,
bhjh
=
journ
al
_bread
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
));
if
(
!
bhjh
)
{
printk
(
"sh-459: unable to read journal header
\n
"
)
;
...
...
@@ -2052,15 +2053,11 @@ int journal_init(struct super_block *p_s_sb, const char * j_dev_name, int old_fo
/* make sure that journal matches to the super block */
if
(
is_reiserfs_jr
(
rs
)
&&
(
jh
->
jh_journal
.
jp_journal_magic
!=
sb_jp_journal_magic
(
rs
)))
{
char
jname
[
32
];
char
fname
[
32
];
strcpy
(
jname
,
kdevname
(
SB_JOURNAL_DEV
(
p_s_sb
)
)
);
strcpy
(
fname
,
p_s_sb
->
s_id
);
printk
(
"sh-460: journal header magic %x (device %s) does not match "
"to magic found in super block %x (device %s)
\n
"
,
jh
->
jh_journal
.
jp_journal_magic
,
jname
,
sb_jp_journal_magic
(
rs
),
fname
);
jh
->
jh_journal
.
jp_journal_magic
,
kdevname
(
SB_JOURNAL_DEV
(
p_s_sb
)
)
,
sb_jp_journal_magic
(
rs
),
reiserfs_bdevname
(
p_s_sb
)
);
brelse
(
bhjh
);
release_journal_dev
(
p_s_sb
,
journal
);
return
1
;
...
...
@@ -2985,7 +2982,7 @@ static int do_journal_end(struct reiserfs_transaction_handle *th, struct super_b
rs
=
SB_DISK_SUPER_BLOCK
(
p_s_sb
)
;
/* setup description block */
d_bh
=
journ_getblk
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
SB_JOURNAL
(
p_s_sb
)
->
j_start
)
;
d_bh
=
journ
al
_getblk
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
SB_JOURNAL
(
p_s_sb
)
->
j_start
)
;
set_buffer_uptodate
(
d_bh
)
;
desc
=
(
struct
reiserfs_journal_desc
*
)(
d_bh
)
->
b_data
;
memset
(
desc
,
0
,
sizeof
(
struct
reiserfs_journal_desc
))
;
...
...
@@ -2993,7 +2990,7 @@ static int do_journal_end(struct reiserfs_transaction_handle *th, struct super_b
desc
->
j_trans_id
=
cpu_to_le32
(
SB_JOURNAL
(
p_s_sb
)
->
j_trans_id
)
;
/* setup commit block. Don't write (keep it clean too) this one until after everyone else is written */
c_bh
=
journ_getblk
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
c_bh
=
journ
al
_getblk
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
((
SB_JOURNAL
(
p_s_sb
)
->
j_start
+
SB_JOURNAL
(
p_s_sb
)
->
j_len
+
1
)
%
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
)))
;
commit
=
(
struct
reiserfs_journal_commit
*
)
c_bh
->
b_data
;
memset
(
commit
,
0
,
sizeof
(
struct
reiserfs_journal_commit
))
;
...
...
@@ -3084,7 +3081,7 @@ printk("journal-2020: do_journal_end: BAD desc->j_len is ZERO\n") ;
/* copy all the real blocks into log area. dirty log blocks */
if
(
test_bit
(
BH_JDirty
,
&
cn
->
bh
->
b_state
))
{
struct
buffer_head
*
tmp_bh
;
tmp_bh
=
journ_getblk
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
tmp_bh
=
journ
al
_getblk
(
p_s_sb
,
SB_ONDISK_JOURNAL_1st_BLOCK
(
p_s_sb
)
+
((
cur_write_start
+
jindex
)
%
SB_ONDISK_JOURNAL_SIZE
(
p_s_sb
)))
;
set_buffer_uptodate
(
tmp_bh
)
;
memcpy
(
tmp_bh
->
b_data
,
cn
->
bh
->
b_data
,
cn
->
bh
->
b_size
)
;
...
...
fs/reiserfs/namei.c
View file @
7bbbc1b5
...
...
@@ -195,13 +195,6 @@ static __u32 get_third_component (struct super_block * s,
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_match
(
struct
reiserfs_dir_entry
*
de
,
const
char
*
name
,
int
namelen
)
{
...
...
@@ -284,13 +277,6 @@ static int linear_search_in_dir_item (struct cpu_key * key, struct reiserfs_dir_
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
// may return NAME_FOUND, NAME_FOUND_INVISIBLE, NAME_NOT_FOUND
// FIXME: should add something like IOERROR
static
int
reiserfs_find_entry
(
struct
inode
*
dir
,
const
char
*
name
,
int
namelen
,
...
...
@@ -300,7 +286,7 @@ static int reiserfs_find_entry (struct inode * dir, const char * name, int namel
int
retval
;
if
(
namelen
>
REISERFS_MAX_NAME
_LEN
(
dir
->
i_sb
->
s_blocksize
))
if
(
namelen
>
REISERFS_MAX_NAME
(
dir
->
i_sb
->
s_blocksize
))
return
NAME_NOT_FOUND
;
/* we will search for this key in the tree */
...
...
@@ -330,13 +316,6 @@ static int reiserfs_find_entry (struct inode * dir, const char * name, int namel
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
struct
dentry
*
reiserfs_lookup
(
struct
inode
*
dir
,
struct
dentry
*
dentry
)
{
int
retval
;
...
...
@@ -344,21 +323,21 @@ static struct dentry * reiserfs_lookup (struct inode * dir, struct dentry * dent
struct
reiserfs_dir_entry
de
;
INITIALIZE_PATH
(
path_to_entry
);
if
(
dentry
->
d_name
.
len
>
REISERFS_MAX_NAME_LEN
(
dir
->
i_sb
->
s_blocksize
)
)
if
(
REISERFS_MAX_NAME
(
dir
->
i_sb
->
s_blocksize
)
<
dentry
->
d_name
.
len
)
return
ERR_PTR
(
-
ENAMETOOLONG
);
lock_kernel
(
);
reiserfs_write_lock
(
dir
->
i_sb
);
de
.
de_gen_number_bit_string
=
0
;
retval
=
reiserfs_find_entry
(
dir
,
dentry
->
d_name
.
name
,
dentry
->
d_name
.
len
,
&
path_to_entry
,
&
de
);
pathrelse
(
&
path_to_entry
);
if
(
retval
==
NAME_FOUND
)
{
inode
=
reiserfs_iget
(
dir
->
i_sb
,
(
struct
cpu_key
*
)
&
(
de
.
de_dir_id
));
if
(
!
inode
||
IS_ERR
(
inode
))
{
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
ERR_PTR
(
-
EACCES
);
}
}
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
if
(
retval
==
IO_ERROR
)
{
return
ERR_PTR
(
-
EIO
);
}
...
...
@@ -390,15 +369,15 @@ struct dentry *reiserfs_get_parent(struct dentry *child)
}
de
.
de_gen_number_bit_string
=
0
;
lock_kernel
(
);
reiserfs_write_lock
(
dir
->
i_sb
);
retval
=
reiserfs_find_entry
(
dir
,
".."
,
2
,
&
path_to_entry
,
&
de
);
pathrelse
(
&
path_to_entry
);
if
(
retval
!=
NAME_FOUND
)
{
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
ERR_PTR
(
-
ENOENT
);
}
inode
=
reiserfs_iget
(
dir
->
i_sb
,
(
struct
cpu_key
*
)
&
(
de
.
de_dir_id
));
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
if
(
!
inode
||
IS_ERR
(
inode
))
{
return
ERR_PTR
(
-
EACCES
);
...
...
@@ -412,14 +391,6 @@ struct dentry *reiserfs_get_parent(struct dentry *child)
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
/* add entry to the directory (entry can be hidden).
insert definition of when hidden directories are used here -Hans
...
...
@@ -447,7 +418,7 @@ static int reiserfs_add_entry (struct reiserfs_transaction_handle *th, struct in
if
(
!
namelen
)
return
-
EINVAL
;
if
(
namelen
>
REISERFS_MAX_NAME
_LEN
(
dir
->
i_sb
->
s_blocksize
))
if
(
namelen
>
REISERFS_MAX_NAME
(
dir
->
i_sb
->
s_blocksize
))
return
-
ENAMETOOLONG
;
/* each entry has unique key. compose it */
...
...
@@ -463,7 +434,7 @@ static int reiserfs_add_entry (struct reiserfs_transaction_handle *th, struct in
}
else
buffer
=
small_buf
;
paste_size
=
(
old_format_only
(
dir
->
i_sb
)
)
?
(
DEH_SIZE
+
namelen
)
:
buflen
;
paste_size
=
(
get_inode_sd_version
(
dir
)
==
STAT_DATA_V1
)
?
(
DEH_SIZE
+
namelen
)
:
buflen
;
/* fill buffer : directory entry head, name[, dir objectid | , stat data | ,stat data, dir objectid ] */
deh
=
(
struct
reiserfs_de_head
*
)
buffer
;
...
...
@@ -587,13 +558,6 @@ static int new_inode_init(struct inode *inode, struct inode *dir, int mode) {
return
0
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_create
(
struct
inode
*
dir
,
struct
dentry
*
dentry
,
int
mode
)
{
int
retval
;
...
...
@@ -601,15 +565,14 @@ static int reiserfs_create (struct inode * dir, struct dentry *dentry, int mode)
int
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
2
;
struct
reiserfs_transaction_handle
th
;
inode
=
new_inode
(
dir
->
i_sb
)
;
if
(
!
inode
)
{
if
(
!
(
inode
=
new_inode
(
dir
->
i_sb
)))
{
return
-
ENOMEM
;
}
retval
=
new_inode_init
(
inode
,
dir
,
mode
);
if
(
retval
)
return
retval
;
lock_kernel
(
);
reiserfs_write_lock
(
dir
->
i_sb
);
journal_begin
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
th
.
t_caller
=
"create"
;
retval
=
reiserfs_new_inode
(
&
th
,
dir
,
mode
,
0
,
0
/*i_size*/
,
dentry
,
inode
);
...
...
@@ -637,18 +600,11 @@ static int reiserfs_create (struct inode * dir, struct dentry *dentry, int mode)
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
out_failed:
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
retval
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_mknod
(
struct
inode
*
dir
,
struct
dentry
*
dentry
,
int
mode
,
int
rdev
)
{
int
retval
;
...
...
@@ -656,15 +612,14 @@ static int reiserfs_mknod (struct inode * dir, struct dentry *dentry, int mode,
struct
reiserfs_transaction_handle
th
;
int
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
3
;
inode
=
new_inode
(
dir
->
i_sb
)
;
if
(
!
inode
)
{
if
(
!
(
inode
=
new_inode
(
dir
->
i_sb
)))
{
return
-
ENOMEM
;
}
retval
=
new_inode_init
(
inode
,
dir
,
mode
);
if
(
retval
)
return
retval
;
lock_kernel
(
);
reiserfs_write_lock
(
dir
->
i_sb
);
journal_begin
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
retval
=
reiserfs_new_inode
(
&
th
,
dir
,
mode
,
0
,
0
/*i_size*/
,
dentry
,
inode
);
...
...
@@ -694,18 +649,11 @@ static int reiserfs_mknod (struct inode * dir, struct dentry *dentry, int mode,
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
out_failed:
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
retval
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_mkdir
(
struct
inode
*
dir
,
struct
dentry
*
dentry
,
int
mode
)
{
int
retval
;
...
...
@@ -714,15 +662,14 @@ static int reiserfs_mkdir (struct inode * dir, struct dentry *dentry, int mode)
int
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
3
;
mode
=
S_IFDIR
|
mode
;
inode
=
new_inode
(
dir
->
i_sb
)
;
if
(
!
inode
)
{
if
(
!
(
inode
=
new_inode
(
dir
->
i_sb
)))
{
return
-
ENOMEM
;
}
retval
=
new_inode_init
(
inode
,
dir
,
mode
);
if
(
retval
)
return
retval
;
lock_kernel
(
);
reiserfs_write_lock
(
dir
->
i_sb
);
journal_begin
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
/* inc the link count now, so another writer doesn't overflow it while
...
...
@@ -762,7 +709,7 @@ static int reiserfs_mkdir (struct inode * dir, struct dentry *dentry, int mode)
d_instantiate
(
dentry
,
inode
);
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
out_failed:
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
retval
;
}
...
...
@@ -779,14 +726,6 @@ static inline int reiserfs_empty_dir(struct inode *inode) {
return
1
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_rmdir
(
struct
inode
*
dir
,
struct
dentry
*
dentry
)
{
int
retval
;
...
...
@@ -801,7 +740,7 @@ static int reiserfs_rmdir (struct inode * dir, struct dentry *dentry)
/* we will be doing 2 balancings and update 2 stat data */
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
2
+
2
;
lock_kernel
(
);
reiserfs_write_lock
(
dir
->
i_sb
);
journal_begin
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
windex
=
push_journal_writer
(
"reiserfs_rmdir"
)
;
...
...
@@ -855,7 +794,7 @@ static int reiserfs_rmdir (struct inode * dir, struct dentry *dentry)
pop_journal_writer
(
windex
)
;
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
reiserfs_check_path
(
&
path
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
0
;
end_rmdir:
...
...
@@ -865,18 +804,10 @@ static int reiserfs_rmdir (struct inode * dir, struct dentry *dentry)
pathrelse
(
&
path
);
pop_journal_writer
(
windex
)
;
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
retval
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_unlink
(
struct
inode
*
dir
,
struct
dentry
*
dentry
)
{
int
retval
;
...
...
@@ -893,7 +824,7 @@ static int reiserfs_unlink (struct inode * dir, struct dentry *dentry)
two stat datas */
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
2
+
2
;
lock_kernel
(
);
reiserfs_write_lock
(
dir
->
i_sb
);
journal_begin
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
windex
=
push_journal_writer
(
"reiserfs_unlink"
)
;
...
...
@@ -918,7 +849,7 @@ static int reiserfs_unlink (struct inode * dir, struct dentry *dentry)
if
(
!
inode
->
i_nlink
)
{
printk
(
"reiserfs_unlink: deleting nonexistent file (%s:%lu), %d
\n
"
,
inode
->
i_sb
->
s_id
,
inode
->
i_ino
,
inode
->
i_nlink
);
reiserfs_bdevname
(
inode
->
i_sb
)
,
inode
->
i_ino
,
inode
->
i_nlink
);
inode
->
i_nlink
=
1
;
}
...
...
@@ -942,7 +873,7 @@ static int reiserfs_unlink (struct inode * dir, struct dentry *dentry)
pop_journal_writer
(
windex
)
;
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
reiserfs_check_path
(
&
path
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
0
;
end_unlink:
...
...
@@ -950,19 +881,12 @@ static int reiserfs_unlink (struct inode * dir, struct dentry *dentry)
pop_journal_writer
(
windex
)
;
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
reiserfs_check_path
(
&
path
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
retval
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_symlink
(
struct
inode
*
dir
,
struct
dentry
*
dentry
,
const
char
*
symname
)
static
int
reiserfs_symlink
(
struct
inode
*
parent_dir
,
struct
dentry
*
dentry
,
const
char
*
symname
)
{
int
retval
;
struct
inode
*
inode
;
...
...
@@ -972,24 +896,23 @@ static int reiserfs_symlink (struct inode * dir, struct dentry * dentry, const c
int
mode
=
S_IFLNK
|
S_IRWXUGO
;
int
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
3
;
inode
=
new_inode
(
dir
->
i_sb
)
;
if
(
!
inode
)
{
if
(
!
(
inode
=
new_inode
(
parent_dir
->
i_sb
)))
{
return
-
ENOMEM
;
}
retval
=
new_inode_init
(
inode
,
dir
,
mode
);
retval
=
new_inode_init
(
inode
,
parent_
dir
,
mode
);
if
(
retval
)
{
return
retval
;
}
lock_kernel
(
);
reiserfs_write_lock
(
parent_dir
->
i_sb
);
item_len
=
ROUND_UP
(
strlen
(
symname
));
if
(
item_len
>
MAX_DIRECT_ITEM_LEN
(
dir
->
i_sb
->
s_blocksize
))
{
if
(
item_len
>
MAX_DIRECT_ITEM_LEN
(
parent_
dir
->
i_sb
->
s_blocksize
))
{
retval
=
-
ENAMETOOLONG
;
drop_new_inode
(
inode
);
goto
out_failed
;
}
name
=
reiserfs_kmalloc
(
item_len
,
GFP_NOFS
,
dir
->
i_sb
);
name
=
reiserfs_kmalloc
(
item_len
,
GFP_NOFS
,
parent_
dir
->
i_sb
);
if
(
!
name
)
{
drop_new_inode
(
inode
);
retval
=
-
ENOMEM
;
...
...
@@ -998,17 +921,17 @@ static int reiserfs_symlink (struct inode * dir, struct dentry * dentry, const c
memcpy
(
name
,
symname
,
strlen
(
symname
));
padd_item
(
name
,
item_len
,
strlen
(
symname
));
journal_begin
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
journal_begin
(
&
th
,
parent_
dir
->
i_sb
,
jbegin_count
)
;
retval
=
reiserfs_new_inode
(
&
th
,
dir
,
mode
,
name
,
strlen
(
symname
),
retval
=
reiserfs_new_inode
(
&
th
,
parent_
dir
,
mode
,
name
,
strlen
(
symname
),
dentry
,
inode
);
reiserfs_kfree
(
name
,
item_len
,
dir
->
i_sb
);
reiserfs_kfree
(
name
,
item_len
,
parent_
dir
->
i_sb
);
if
(
retval
)
{
/* reiserfs_new_inode iputs for us */
goto
out_failed
;
}
reiserfs_update_inode_transaction
(
inode
)
;
reiserfs_update_inode_transaction
(
dir
)
;
reiserfs_update_inode_transaction
(
parent_
dir
)
;
inode
->
i_op
=
&
page_symlink_inode_operations
;
inode
->
i_mapping
->
a_ops
=
&
reiserfs_address_space_operations
;
...
...
@@ -1017,31 +940,23 @@ static int reiserfs_symlink (struct inode * dir, struct dentry * dentry, const c
//
//reiserfs_update_sd (&th, inode, READ_BLOCKS);
retval
=
reiserfs_add_entry
(
&
th
,
dir
,
dentry
->
d_name
.
name
,
dentry
->
d_name
.
len
,
inode
,
1
/*visible*/
);
retval
=
reiserfs_add_entry
(
&
th
,
parent_dir
,
dentry
->
d_name
.
name
,
dentry
->
d_name
.
len
,
inode
,
1
/*visible*/
);
if
(
retval
)
{
inode
->
i_nlink
--
;
reiserfs_update_sd
(
&
th
,
inode
);
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
journal_end
(
&
th
,
parent_
dir
->
i_sb
,
jbegin_count
)
;
iput
(
inode
);
goto
out_failed
;
}
d_instantiate
(
dentry
,
inode
);
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
journal_end
(
&
th
,
parent_
dir
->
i_sb
,
jbegin_count
)
;
out_failed:
unlock_kernel
(
);
reiserfs_write_unlock
(
parent_dir
->
i_sb
);
return
retval
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_link
(
struct
dentry
*
old_dentry
,
struct
inode
*
dir
,
struct
dentry
*
dentry
)
{
int
retval
;
...
...
@@ -1049,11 +964,12 @@ static int reiserfs_link (struct dentry * old_dentry, struct inode * dir, struct
int
windex
;
struct
reiserfs_transaction_handle
th
;
int
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
3
;
time_t
ctime
;
lock_kernel
(
);
reiserfs_write_lock
(
dir
->
i_sb
);
if
(
inode
->
i_nlink
>=
REISERFS_LINK_MAX
)
{
//FIXME: sd_nlink is 32 bit for new files
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
-
EMLINK
;
}
...
...
@@ -1070,19 +986,20 @@ static int reiserfs_link (struct dentry * old_dentry, struct inode * dir, struct
if
(
retval
)
{
pop_journal_writer
(
windex
)
;
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
retval
;
}
inode
->
i_nlink
++
;
inode
->
i_ctime
=
CURRENT_TIME
;
ctime
=
CURRENT_TIME
;
inode
->
i_ctime
=
ctime
;
reiserfs_update_sd
(
&
th
,
inode
);
atomic_inc
(
&
inode
->
i_count
)
;
d_instantiate
(
dentry
,
inode
);
pop_journal_writer
(
windex
)
;
journal_end
(
&
th
,
dir
->
i_sb
,
jbegin_count
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
dir
->
i_sb
);
return
0
;
}
...
...
@@ -1129,14 +1046,6 @@ static void set_ino_in_dir_entry (struct reiserfs_dir_entry * de, struct key * k
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
/*
* process, that is going to call fix_nodes/do_balance must hold only
* one path. If it holds 2 or more, it can get into endless waiting in
...
...
@@ -1151,10 +1060,12 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
INITIALIZE_PATH
(
dot_dot_entry_path
);
struct
item_head
new_entry_ih
,
old_entry_ih
,
dot_dot_ih
;
struct
reiserfs_dir_entry
old_de
,
new_de
,
dot_dot_de
;
struct
inode
*
old_inode
,
*
new_inode
;
struct
inode
*
old_inode
,
*
new_
dentry_
inode
;
int
windex
;
struct
reiserfs_transaction_handle
th
;
int
jbegin_count
;
umode_t
old_inode_mode
;
time_t
ctime
;
/* two balancings: old name removal, new name insertion or "save" link,
...
...
@@ -1163,33 +1074,34 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
jbegin_count
=
JOURNAL_PER_BALANCE_CNT
*
3
+
3
;
old_inode
=
old_dentry
->
d_inode
;
new_inode
=
new_dentry
->
d_inode
;
new_
dentry_
inode
=
new_dentry
->
d_inode
;
// make sure, that oldname still exists and points to an object we
// are going to rename
old_de
.
de_gen_number_bit_string
=
0
;
lock_kernel
(
);
reiserfs_write_lock
(
old_dir
->
i_sb
);
retval
=
reiserfs_find_entry
(
old_dir
,
old_dentry
->
d_name
.
name
,
old_dentry
->
d_name
.
len
,
&
old_entry_path
,
&
old_de
);
pathrelse
(
&
old_entry_path
);
if
(
retval
==
IO_ERROR
)
{
unlock_kernel
(
);
reiserfs_write_unlock
(
old_dir
->
i_sb
);
return
-
EIO
;
}
if
(
retval
!=
NAME_FOUND
||
old_de
.
de_objectid
!=
old_inode
->
i_ino
)
{
unlock_kernel
(
);
reiserfs_write_unlock
(
old_dir
->
i_sb
);
return
-
ENOENT
;
}
if
(
S_ISDIR
(
old_inode
->
i_mode
))
{
old_inode_mode
=
old_inode
->
i_mode
;
if
(
S_ISDIR
(
old_inode_mode
))
{
// make sure, that directory being renamed has correct ".."
// and that its new parent directory has not too many links
// already
if
(
new_inode
)
{
if
(
!
reiserfs_empty_dir
(
new_inode
))
{
unlock_kernel
(
);
if
(
new_
dentry_
inode
)
{
if
(
!
reiserfs_empty_dir
(
new_
dentry_
inode
))
{
reiserfs_write_unlock
(
old_dir
->
i_sb
);
return
-
ENOTEMPTY
;
}
}
...
...
@@ -1201,13 +1113,13 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
retval
=
reiserfs_find_entry
(
old_inode
,
".."
,
2
,
&
dot_dot_entry_path
,
&
dot_dot_de
);
pathrelse
(
&
dot_dot_entry_path
);
if
(
retval
!=
NAME_FOUND
)
{
unlock_kernel
(
);
reiserfs_write_unlock
(
old_dir
->
i_sb
);
return
-
EIO
;
}
/* inode number of .. must equal old_dir->i_ino */
if
(
dot_dot_de
.
de_objectid
!=
old_dir
->
i_ino
)
{
unlock_kernel
(
);
reiserfs_write_unlock
(
old_dir
->
i_sb
);
return
-
EIO
;
}
}
...
...
@@ -1219,16 +1131,14 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
retval
=
reiserfs_add_entry
(
&
th
,
new_dir
,
new_dentry
->
d_name
.
name
,
new_dentry
->
d_name
.
len
,
old_inode
,
0
);
if
(
retval
==
-
EEXIST
)
{
// FIXME: is it possible, that new_inode == 0 here? If yes, it
// is not clear how does ext2 handle that
if
(
!
new_inode
)
{
if
(
!
new_dentry_inode
)
{
reiserfs_panic
(
old_dir
->
i_sb
,
"vs-7050: new entry is found, new inode == 0
\n
"
);
}
}
else
if
(
retval
)
{
pop_journal_writer
(
windex
)
;
journal_end
(
&
th
,
old_dir
->
i_sb
,
jbegin_count
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
old_dir
->
i_sb
);
return
retval
;
}
...
...
@@ -1240,8 +1150,8 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
*/
reiserfs_update_inode_transaction
(
old_inode
)
;
if
(
new_inode
)
reiserfs_update_inode_transaction
(
new_inode
)
;
if
(
new_
dentry_
inode
)
reiserfs_update_inode_transaction
(
new_
dentry_
inode
)
;
while
(
1
)
{
// look for old name using corresponding entry key (found by reiserfs_find_entry)
...
...
@@ -1288,18 +1198,18 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
if
(
item_moved
(
&
new_entry_ih
,
&
new_entry_path
)
||
!
entry_points_to_object
(
new_dentry
->
d_name
.
name
,
new_dentry
->
d_name
.
len
,
&
new_de
,
new_inode
)
||
&
new_de
,
new_
dentry_
inode
)
||
item_moved
(
&
old_entry_ih
,
&
old_entry_path
)
||
!
entry_points_to_object
(
old_dentry
->
d_name
.
name
,
old_dentry
->
d_name
.
len
,
&
old_de
,
old_inode
))
{
reiserfs_restore_prepared_buffer
(
old_inode
->
i_sb
,
new_de
.
de_bh
);
reiserfs_restore_prepared_buffer
(
old_inode
->
i_sb
,
old_de
.
de_bh
);
if
(
S_ISDIR
(
old_inode
->
i
_mode
))
if
(
S_ISDIR
(
old_inode_mode
))
reiserfs_restore_prepared_buffer
(
old_inode
->
i_sb
,
dot_dot_de
.
de_bh
);
continue
;
}
if
(
S_ISDIR
(
old_inode
->
i
_mode
))
{
if
(
S_ISDIR
(
old_inode_mode
))
{
if
(
item_moved
(
&
dot_dot_ih
,
&
dot_dot_entry_path
)
||
!
entry_points_to_object
(
".."
,
2
,
&
dot_dot_de
,
old_dir
)
)
{
reiserfs_restore_prepared_buffer
(
old_inode
->
i_sb
,
old_de
.
de_bh
);
...
...
@@ -1309,7 +1219,7 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
}
}
RFALSE
(
S_ISDIR
(
old_inode
->
i
_mode
)
&&
RFALSE
(
S_ISDIR
(
old_inode_mode
)
&&
!
reiserfs_buffer_prepared
(
dot_dot_de
.
de_bh
),
""
);
break
;
...
...
@@ -1327,22 +1237,23 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
old_dir
->
i_ctime
=
old_dir
->
i_mtime
=
CURRENT_TIME
;
new_dir
->
i_ctime
=
new_dir
->
i_mtime
=
CURRENT_TIME
;
if
(
new_inode
)
{
if
(
new_
dentry_
inode
)
{
// adjust link number of the victim
if
(
S_ISDIR
(
new_inode
->
i_mode
))
{
new_inode
->
i_nlink
=
0
;
if
(
S_ISDIR
(
new_
dentry_
inode
->
i_mode
))
{
new_
dentry_
inode
->
i_nlink
=
0
;
}
else
{
new_inode
->
i_nlink
--
;
new_
dentry_
inode
->
i_nlink
--
;
}
new_inode
->
i_ctime
=
CURRENT_TIME
;
ctime
=
CURRENT_TIME
;
new_dentry_inode
->
i_ctime
=
ctime
;
}
if
(
S_ISDIR
(
old_inode
->
i
_mode
))
{
if
(
S_ISDIR
(
old_inode_mode
))
{
// adjust ".." of renamed directory
set_ino_in_dir_entry
(
&
dot_dot_de
,
INODE_PKEY
(
new_dir
));
journal_mark_dirty
(
&
th
,
new_dir
->
i_sb
,
dot_dot_de
.
de_bh
);
if
(
!
new_inode
)
if
(
!
new_
dentry_
inode
)
/* there (in new_dir) was no directory, so it got new link
(".." of renamed directory) */
INC_DIR_INODE_NLINK
(
new_dir
);
...
...
@@ -1367,15 +1278,15 @@ static int reiserfs_rename (struct inode * old_dir, struct dentry *old_dentry,
reiserfs_update_sd
(
&
th
,
old_dir
);
reiserfs_update_sd
(
&
th
,
new_dir
);
if
(
new_inode
)
{
if
(
new_inode
->
i_nlink
==
0
)
add_save_link
(
&
th
,
new_inode
,
0
/* not truncate */
);
reiserfs_update_sd
(
&
th
,
new_inode
);
if
(
new_
dentry_
inode
)
{
if
(
new_
dentry_
inode
->
i_nlink
==
0
)
add_save_link
(
&
th
,
new_
dentry_
inode
,
0
/* not truncate */
);
reiserfs_update_sd
(
&
th
,
new_
dentry_
inode
);
}
pop_journal_writer
(
windex
)
;
journal_end
(
&
th
,
old_dir
->
i_sb
,
jbegin_count
)
;
unlock_kernel
(
);
reiserfs_write_unlock
(
old_dir
->
i_sb
);
return
0
;
}
...
...
fs/reiserfs/prints.c
View file @
7bbbc1b5
...
...
@@ -337,7 +337,7 @@ void reiserfs_panic (struct super_block * sb, const char * fmt, ...)
/* this is not actually called, but makes reiserfs_panic() "noreturn" */
panic
(
"REISERFS: panic (device %s): %s
\n
"
,
sb
?
sb
->
s_id
:
"sb == 0"
,
error_buf
);
reiserfs_bdevname
(
sb
)
,
error_buf
);
}
...
...
@@ -490,6 +490,7 @@ char * reiserfs_hashname(int code)
return
"unknown"
;
}
/* return 1 if this is not super block */
static
int
print_super_block
(
struct
buffer_head
*
bh
)
{
...
...
@@ -509,8 +510,8 @@ static int print_super_block (struct buffer_head * bh)
return
1
;
}
printk
(
"%s
\'
s super block i
n block %ld
\n
======================
\n
"
,
b
devname
(
bh
->
b_bdev
),
b
h
->
b_blocknr
);
printk
(
"%s
\'
s super block i
s in block %ld
\n
"
,
bdevname
(
bh
->
b_bdev
),
bh
->
b_blocknr
);
printk
(
"Reiserfs version %s
\n
"
,
version
);
printk
(
"Block count %u
\n
"
,
sb_block_count
(
rs
));
printk
(
"Blocksize %d
\n
"
,
sb_blocksize
(
rs
));
...
...
fs/reiserfs/procfs.c
View file @
7bbbc1b5
...
...
@@ -36,7 +36,7 @@ static struct super_block *procinfo_prologue( kdev_t dev )
/* get super-block by device */
result
=
get_super
(
dev
);
if
(
result
!=
NULL
)
{
if
(
!
reiserfs_i
s_super
(
result
)
)
{
if
(
!
is_reiserf
s_super
(
result
)
)
{
printk
(
KERN_DEBUG
"reiserfs: procfs-52: "
"non-reiserfs super found
\n
"
);
drop_super
(
result
);
...
...
@@ -500,7 +500,7 @@ int reiserfs_journal_in_proc( char *buffer, char **start, off_t offset,
"prepare_retry:
\t
%12lu
\n
"
,
DJP
(
jp_journal_1st_block
),
DJP
(
jp_journal_dev
)
==
0
?
"none"
:
__bdevname
(
to_kdev_t
(
DJP
(
jp_journal_dev
))
),
bdevname
(
SB_JOURNAL
(
sb
)
->
j_dev_bd
),
DJP
(
jp_journal_dev
),
DJP
(
jp_journal_size
),
DJP
(
jp_journal_trans_max
),
...
...
@@ -556,13 +556,13 @@ static const char *proc_info_root_name = "fs/reiserfs";
int
reiserfs_proc_info_init
(
struct
super_block
*
sb
)
{
spin_lock_init
(
&
__PINFO
(
sb
).
lock
);
REISERFS_SB
(
sb
)
->
procdir
=
proc_mkdir
(
sb
->
s_id
,
proc_info_root
);
REISERFS_SB
(
sb
)
->
procdir
=
proc_mkdir
(
reiserfs_bdevname
(
sb
)
,
proc_info_root
);
if
(
REISERFS_SB
(
sb
)
->
procdir
)
{
REISERFS_SB
(
sb
)
->
procdir
->
owner
=
THIS_MODULE
;
return
0
;
}
reiserfs_warning
(
"reiserfs: cannot create /proc/%s/%s
\n
"
,
proc_info_root_name
,
sb
->
s_id
);
proc_info_root_name
,
reiserfs_bdevname
(
sb
)
);
return
1
;
}
...
...
@@ -573,7 +573,7 @@ int reiserfs_proc_info_done( struct super_block *sb )
__PINFO
(
sb
).
exiting
=
1
;
spin_unlock
(
&
__PINFO
(
sb
).
lock
);
if
(
proc_info_root
)
{
remove_proc_entry
(
sb
->
s_id
,
proc_info_root
);
remove_proc_entry
(
reiserfs_bdevname
(
sb
)
,
proc_info_root
);
REISERFS_SB
(
sb
)
->
procdir
=
NULL
;
}
return
0
;
...
...
fs/reiserfs/stree.c
View file @
7bbbc1b5
...
...
@@ -1715,13 +1715,13 @@ void reiserfs_do_truncate (struct reiserfs_transaction_handle *th,
/* Cut or delete file item. */
n_deleted
=
reiserfs_cut_from_item
(
th
,
&
s_search_path
,
&
s_item_key
,
p_s_inode
,
page
,
n_new_file_size
);
if
(
n_deleted
<
0
)
{
reiserfs_warning
(
"vs-5665: reiserfs_
truncate_file:
cut_from_item failed"
);
reiserfs_warning
(
"vs-5665: reiserfs_
do_truncate: reiserfs_
cut_from_item failed"
);
reiserfs_check_path
(
&
s_search_path
)
;
return
;
}
RFALSE
(
n_deleted
>
n_file_size
,
"PAP-5670: reiserfs_
truncate_file returns too big number
: deleted %d, file_size %lu, item_key %K"
,
"PAP-5670: reiserfs_
cut_from_item: too many bytes deleted
: deleted %d, file_size %lu, item_key %K"
,
n_deleted
,
n_file_size
,
&
s_item_key
);
/* Change key to search the last file item. */
...
...
fs/reiserfs/super.c
View file @
7bbbc1b5
...
...
@@ -24,6 +24,8 @@
#define REISERFS_OLD_BLOCKSIZE 4096
#define REISERFS_SUPER_MAGIC_STRING_OFFSET_NJ 20
static
struct
file_system_type
reiserfs_fs_type
;
const
char
reiserfs_3_5_magic_string
[]
=
REISERFS_SUPER_MAGIC_STRING
;
const
char
reiserfs_3_6_magic_string
[]
=
REISER2FS_SUPER_MAGIC_STRING
;
const
char
reiserfs_jr_magic_string
[]
=
REISER2FS_JR_SUPER_MAGIC_STRING
;
...
...
@@ -55,41 +57,32 @@ static int is_any_reiserfs_magic_string (struct reiserfs_super_block * rs)
is_reiserfs_jr
(
rs
));
}
int
is_reiserfs_super
(
struct
super_block
*
s
)
{
return
s
->
s_type
==
&
reiserfs_fs_type
;
}
static
int
reiserfs_remount
(
struct
super_block
*
s
,
int
*
flags
,
char
*
data
);
static
int
reiserfs_statfs
(
struct
super_block
*
s
,
struct
statfs
*
buf
);
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
void
reiserfs_write_super
(
struct
super_block
*
s
)
{
int
dirty
=
0
;
lock_kernel
()
;
reiserfs_write_lock
(
s
)
;
if
(
!
(
s
->
s_flags
&
MS_RDONLY
))
{
dirty
=
flush_old_commits
(
s
,
1
)
;
}
s
->
s_dirt
=
dirty
;
unlock_kernel
()
;
reiserfs_write_unlock
(
s
)
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
void
reiserfs_write_super_lockfs
(
struct
super_block
*
s
)
{
int
dirty
=
0
;
struct
reiserfs_transaction_handle
th
;
lock_kernel
()
;
reiserfs_write_lock
(
s
)
;
if
(
!
(
s
->
s_flags
&
MS_RDONLY
))
{
journal_begin
(
&
th
,
s
,
1
)
;
reiserfs_prepare_for_journal
(
s
,
SB_BUFFER_WITH_SB
(
s
),
1
);
...
...
@@ -98,7 +91,7 @@ static void reiserfs_write_super_lockfs (struct super_block * s)
journal_end
(
&
th
,
s
,
1
)
;
}
s
->
s_dirt
=
dirty
;
unlock_kernel
()
;
reiserfs_write_unlock
(
s
)
;
}
void
reiserfs_unlockfs
(
struct
super_block
*
s
)
{
...
...
@@ -362,13 +355,6 @@ void remove_save_link (struct inode * inode, int truncate)
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
void
reiserfs_put_super
(
struct
super_block
*
s
)
{
int
i
;
...
...
@@ -469,7 +455,7 @@ static void reiserfs_dirty_inode (struct inode * inode) {
inode
->
i_ino
)
;
return
;
}
lock_kernel
()
;
reiserfs_write_lock
(
inode
->
i_sb
)
;
/* this is really only used for atime updates, so they don't have
** to be included in O_SYNC or fsync
...
...
@@ -477,7 +463,7 @@ static void reiserfs_dirty_inode (struct inode * inode) {
journal_begin
(
&
th
,
inode
->
i_sb
,
1
)
;
reiserfs_update_sd
(
&
th
,
inode
);
journal_end
(
&
th
,
inode
->
i_sb
,
1
)
;
unlock_kernel
()
;
reiserfs_write_unlock
(
inode
->
i_sb
)
;
}
struct
super_operations
reiserfs_sops
=
...
...
@@ -503,100 +489,190 @@ static struct export_operations reiserfs_export_ops = {
get_dentry:
reiserfs_get_dentry
,
}
;
/* this was (ext2)parse_options */
static
int
parse_options
(
char
*
options
,
unsigned
long
*
mount_options
,
unsigned
long
*
blocks
,
char
**
jdev_name
)
{
char
*
this_char
;
/* this struct is used in reiserfs_getopt () for containing the value for those
mount options that have values rather than being toggles. */
typedef
struct
{
char
*
value
;
int
bitmask
;
/* bit which is to be set in mount_options bitmask when this
value is found, 0 is no bits are to be set */
}
arg_desc_t
;
/* this struct is used in reiserfs_getopt() for describing the set of reiserfs
mount options */
typedef
struct
{
char
*
option_name
;
int
arg_required
;
/* 0 if argument is not required, not 0 otherwise */
const
arg_desc_t
*
values
;
/* list of values accepted by an option */
int
bitmask
;
/* bit which is to be set in mount_options bitmask when this
option is selected, 0 is not bits are to be set */
}
opt_desc_t
;
/* possible values for "-o block-allocator=" and bits which are to be set in
s_mount_opt of reiserfs specific part of in-core super block */
const
arg_desc_t
balloc
[]
=
{
{
"noborder"
,
REISERFS_NO_BORDER
},
{
"no_unhashed_relocation"
,
REISERFS_NO_UNHASHED_RELOCATION
},
{
"hashed_relocation"
,
REISERFS_HASHED_RELOCATION
},
{
"test4"
,
REISERFS_TEST4
},
{
NULL
,
-
1
}
};
/* proceed only one option from a list *cur - string containing of mount options
opts - array of options which are accepted
opt_arg - if option is found and requires an argument and if it is specifed
in the input - pointer to the argument is stored here
bit_flags - if option requires to set a certain bit - it is set here
return -1 if unknown option is found, opt->arg_required otherwise */
static
int
reiserfs_getopt
(
char
**
cur
,
opt_desc_t
*
opts
,
char
**
opt_arg
,
unsigned
long
*
bit_flags
)
{
char
*
p
;
/* foo=bar,
^ ^ ^
| | +-- option_end
| +-- arg_start
+-- option_start
*/
const
opt_desc_t
*
opt
;
const
arg_desc_t
*
arg
;
p
=
*
cur
;
/* assume argument cannot contain commas */
*
cur
=
strchr
(
p
,
','
);
if
(
*
cur
)
{
*
(
*
cur
)
=
'\0'
;
(
*
cur
)
++
;
}
/* for every option in the list */
for
(
opt
=
opts
;
opt
->
option_name
;
opt
++
)
{
if
(
!
strncmp
(
p
,
opt
->
option_name
,
strlen
(
opt
->
option_name
)))
{
if
(
bit_flags
&&
opt
->
bitmask
!=
-
1
)
set_bit
(
opt
->
bitmask
,
bit_flags
);
break
;
}
}
if
(
!
opt
->
option_name
)
{
printk
(
"reiserfs_getopt: unknown option
\"
%s
\"\n
"
,
p
);
return
-
1
;
}
p
+=
strlen
(
opt
->
option_name
);
switch
(
*
p
)
{
case
'='
:
if
(
!
opt
->
arg_required
)
{
printk
(
"reiserfs_getopt: the option
\"
%s
\"
does not require an argument
\n
"
,
opt
->
option_name
);
return
-
1
;
}
break
;
case
0
:
if
(
opt
->
arg_required
)
{
printk
(
"reiserfs_getopt: the option
\"
%s
\"
requires an argument
\n
"
,
opt
->
option_name
);
return
-
1
;
}
break
;
default:
printk
(
"reiserfs_getopt: head of option
\"
%s
\"
is only correct
\n
"
,
opt
->
option_name
);
return
-
1
;
}
/* move to the argument, or to next option if argument is not required */
p
++
;
if
(
opt
->
arg_required
&&
!
strlen
(
p
)
)
{
/* this catches "option=," */
printk
(
"reiserfs_getopt: empty argument for
\"
%s
\"\n
"
,
opt
->
option_name
);
return
-
1
;
}
if
(
!
opt
->
values
)
{
/* *opt_arg contains pointer to argument */
*
opt_arg
=
p
;
return
opt
->
arg_required
;
}
/* values possible for this option are listed in opt->values */
for
(
arg
=
opt
->
values
;
arg
->
value
;
arg
++
)
{
if
(
!
strcmp
(
p
,
arg
->
value
))
{
if
(
bit_flags
&&
arg
->
bitmask
!=
-
1
)
set_bit
(
arg
->
bitmask
,
bit_flags
);
return
opt
->
arg_required
;
}
}
printk
(
"reiserfs_getopt: bad value
\"
%s
\"
for option
\"
%s
\"\n
"
,
p
,
opt
->
option_name
);
return
-
1
;
}
/* returns 0 if something is wrong in option string, 1 - otherwise */
static
int
reiserfs_parse_options
(
char
*
options
,
/* string given via mount's -o */
unsigned
long
*
mount_options
,
/* after the parsing phase, contains the
collection of bitflags defining what
mount options were selected. */
unsigned
long
*
blocks
,
/* strtol-ed from NNN of resize=NNN */
char
**
jdev_name
)
{
int
c
;
char
*
arg
=
NULL
;
char
*
pos
;
opt_desc_t
opts
[]
=
{
{
"notail"
,
0
,
0
,
NOTAIL
},
{
"conv"
,
0
,
0
,
REISERFS_CONVERT
},
{
"attrs"
,
0
,
0
,
REISERFS_ATTRS
},
{
"nolog"
,
0
,
0
,
-
1
},
{
"replayonly"
,
0
,
0
,
REPLAYONLY
},
{
"block-allocator"
,
'a'
,
balloc
,
-
1
},
{
"resize"
,
'r'
,
0
,
-
1
},
{
"jdev"
,
'j'
,
0
,
-
1
},
{
NULL
,
0
,
0
,
-
1
}
};
*
blocks
=
0
;
if
(
!
options
)
if
(
!
options
||
!*
options
)
/* use default configuration: create tails, journaling on, no
conversion to newest format */
conversion to newest format */
return
1
;
while
((
this_char
=
strsep
(
&
options
,
","
))
!=
NULL
)
{
if
(
!*
this_char
)
continue
;
if
((
value
=
strchr
(
this_char
,
'='
))
!=
NULL
)
*
value
++
=
0
;
if
(
!
strcmp
(
this_char
,
"notail"
))
{
set_bit
(
NOTAIL
,
mount_options
);
}
else
if
(
!
strcmp
(
this_char
,
"conv"
))
{
// if this is set, we update super block such that
// the partition will not be mounable by 3.5.x anymore
set_bit
(
REISERFS_CONVERT
,
mount_options
);
}
else
if
(
!
strcmp
(
this_char
,
"noborder"
))
{
/* this is used for benchmarking
experimental variations, it is not
intended for users to use, only for
developers who want to casually
hack in something to test */
set_bit
(
REISERFS_NO_BORDER
,
mount_options
);
}
else
if
(
!
strcmp
(
this_char
,
"no_unhashed_relocation"
))
{
set_bit
(
REISERFS_NO_UNHASHED_RELOCATION
,
mount_options
);
}
else
if
(
!
strcmp
(
this_char
,
"hashed_relocation"
))
{
set_bit
(
REISERFS_HASHED_RELOCATION
,
mount_options
);
}
else
if
(
!
strcmp
(
this_char
,
"test4"
))
{
set_bit
(
REISERFS_TEST4
,
mount_options
);
}
else
if
(
!
strcmp
(
this_char
,
"nolog"
))
{
reiserfs_warning
(
"reiserfs: nolog mount option not supported yet
\n
"
);
}
else
if
(
!
strcmp
(
this_char
,
"replayonly"
))
{
set_bit
(
REPLAYONLY
,
mount_options
);
}
else
if
(
!
strcmp
(
this_char
,
"resize"
))
{
if
(
value
&&
*
value
){
*
blocks
=
simple_strtoul
(
value
,
&
value
,
0
);
}
else
{
printk
(
"reiserfs: resize option requires a value
\n
"
);
for
(
pos
=
options
;
pos
;
)
{
c
=
reiserfs_getopt
(
&
pos
,
opts
,
&
arg
,
mount_options
);
if
(
c
==
-
1
)
/* wrong option is given */
return
0
;
if
(
c
==
'r'
)
{
char
*
p
;
p
=
0
;
/* "resize=NNN" */
*
blocks
=
simple_strtoul
(
arg
,
&
p
,
0
);
if
(
*
p
!=
'\0'
)
{
/* NNN does not look like a number */
printk
(
"reiserfs_parse_options: bad value %s
\n
"
,
arg
);
return
0
;
}
}
else
if
(
!
strcmp
(
this_char
,
"hash"
))
{
if
(
value
&&
*
value
)
{
/* if they specify any hash option, we force detection
** to make sure they aren't using the wrong hash
*/
if
(
!
strcmp
(
value
,
"rupasov"
))
{
set_bit
(
FORCE_RUPASOV_HASH
,
mount_options
);
set_bit
(
FORCE_HASH_DETECT
,
mount_options
);
}
else
if
(
!
strcmp
(
value
,
"tea"
))
{
set_bit
(
FORCE_TEA_HASH
,
mount_options
);
set_bit
(
FORCE_HASH_DETECT
,
mount_options
);
}
else
if
(
!
strcmp
(
value
,
"r5"
))
{
set_bit
(
FORCE_R5_HASH
,
mount_options
);
set_bit
(
FORCE_HASH_DETECT
,
mount_options
);
}
else
if
(
!
strcmp
(
value
,
"detect"
))
{
set_bit
(
FORCE_HASH_DETECT
,
mount_options
);
}
else
{
printk
(
"reiserfs: invalid hash function specified
\n
"
)
;
return
0
;
}
}
else
{
printk
(
"reiserfs: hash option requires a value
\n
"
);
return
0
;
}
}
else
if
(
!
strcmp
(
this_char
,
"jdev"
))
{
if
(
value
&&
*
value
&&
jdev_name
)
{
*
jdev_name
=
value
;
}
else
{
printk
(
"reiserfs: jdev option requires a value
\n
"
);
return
0
;
}
if
(
c
==
'j'
)
{
if
(
arg
&&
*
arg
&&
jdev_name
)
{
*
jdev_name
=
arg
;
}
}
else
{
printk
(
"reiserfs: Unrecognized mount option %s
\n
"
,
this_char
);
return
0
;
}
}
return
1
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_remount
(
struct
super_block
*
s
,
int
*
flags
,
char
*
data
)
static
int
reiserfs_remount
(
struct
super_block
*
s
,
int
*
mount_flags
,
char
*
arg
)
{
struct
reiserfs_super_block
*
rs
;
struct
reiserfs_transaction_handle
th
;
...
...
@@ -604,21 +680,21 @@ static int reiserfs_remount (struct super_block * s, int * flags, char * data)
unsigned
long
mount_options
;
rs
=
SB_DISK_SUPER_BLOCK
(
s
);
if
(
!
parse_options
(
data
,
&
mount_options
,
&
blocks
,
NULL
))
return
0
;
if
(
!
reiserfs_parse_options
(
arg
,
&
mount_options
,
&
blocks
,
NULL
))
return
-
EINVAL
;
if
(
blocks
)
{
int
rc
=
reiserfs_resize
(
s
,
blocks
);
if
(
rc
!=
0
)
return
rc
;
int
rc
=
reiserfs_resize
(
s
,
blocks
);
if
(
rc
!=
0
)
return
rc
;
}
if
((
unsigned
long
)(
*
flags
&
MS_RDONLY
)
==
(
s
->
s_flags
&
MS_RDONLY
))
{
/* there is nothing to do to remount read-only fs as read-only fs */
return
0
;
}
if
(
*
flags
&
MS_RDONLY
)
{
if
(
*
mount_flags
&
MS_RDONLY
)
{
/* remount rean-only */
if
(
s
->
s_flags
&
MS_RDONLY
)
/* it is read-only already */
return
0
;
/* try to remount file system with read-only permissions */
if
(
sb_umount_state
(
rs
)
==
REISERFS_VALID_FS
||
REISERFS_SB
(
s
)
->
s_mount_state
!=
REISERFS_VALID_FS
)
{
return
0
;
...
...
@@ -634,7 +710,7 @@ static int reiserfs_remount (struct super_block * s, int * flags, char * data)
REISERFS_SB
(
s
)
->
s_mount_state
=
sb_umount_state
(
rs
)
;
s
->
s_flags
&=
~
MS_RDONLY
;
/* now it is safe to call journal_begin */
journal_begin
(
&
th
,
s
,
10
)
;
/* Mount a partition which is read-only, read-write */
reiserfs_prepare_for_journal
(
s
,
SB_BUFFER_WITH_SB
(
s
),
1
)
;
REISERFS_SB
(
s
)
->
s_mount_state
=
sb_umount_state
(
rs
);
...
...
@@ -649,7 +725,7 @@ static int reiserfs_remount (struct super_block * s, int * flags, char * data)
SB_JOURNAL
(
s
)
->
j_must_wait
=
1
;
journal_end
(
&
th
,
s
,
10
)
;
if
(
!
(
*
flags
&
MS_RDONLY
)
)
if
(
!
(
*
mount_
flags
&
MS_RDONLY
)
)
finish_unfinished
(
s
);
return
0
;
...
...
@@ -658,14 +734,14 @@ static int reiserfs_remount (struct super_block * s, int * flags, char * data)
static
int
read_bitmaps
(
struct
super_block
*
s
)
{
int
i
,
bm
p
;
int
i
,
bm
ap_nr
;
SB_AP_BITMAP
(
s
)
=
reiserfs_kmalloc
(
sizeof
(
struct
buffer_head
*
)
*
SB_BMAP_NR
(
s
),
GFP_NOFS
,
s
);
if
(
SB_AP_BITMAP
(
s
)
==
0
)
return
1
;
for
(
i
=
0
,
bm
p
=
REISERFS_DISK_OFFSET_IN_BYTES
/
s
->
s_blocksize
+
1
;
i
<
SB_BMAP_NR
(
s
);
i
++
,
bm
p
=
s
->
s_blocksize
*
8
*
i
)
{
SB_AP_BITMAP
(
s
)[
i
]
=
sb_getblk
(
s
,
bm
p
);
for
(
i
=
0
,
bm
ap_nr
=
REISERFS_DISK_OFFSET_IN_BYTES
/
s
->
s_blocksize
+
1
;
i
<
SB_BMAP_NR
(
s
);
i
++
,
bm
ap_nr
=
s
->
s_blocksize
*
8
*
i
)
{
SB_AP_BITMAP
(
s
)[
i
]
=
sb_getblk
(
s
,
bm
ap_nr
);
if
(
!
buffer_uptodate
(
SB_AP_BITMAP
(
s
)[
i
]))
ll_rw_block
(
READ
,
1
,
SB_AP_BITMAP
(
s
)
+
i
);
}
...
...
@@ -735,7 +811,7 @@ static int read_super_block (struct super_block * s, int offset)
if
(
!
bh
)
{
printk
(
"sh-2006: read_super_block: "
"bread failed (dev %s, block %lu, size %lu)
\n
"
,
s
->
s_id
,
offset
/
s
->
s_blocksize
,
s
->
s_blocksize
);
reiserfs_bdevname
(
s
)
,
offset
/
s
->
s_blocksize
,
s
->
s_blocksize
);
return
1
;
}
...
...
@@ -755,7 +831,7 @@ static int read_super_block (struct super_block * s, int offset)
if
(
!
bh
)
{
printk
(
"sh-2007: read_super_block: "
"bread failed (dev %s, block %lu, size %lu)
\n
"
,
s
->
s_id
,
offset
/
s
->
s_blocksize
,
s
->
s_blocksize
);
reiserfs_bdevname
(
s
)
,
offset
/
s
->
s_blocksize
,
s
->
s_blocksize
);
return
1
;
}
...
...
@@ -763,7 +839,7 @@ static int read_super_block (struct super_block * s, int offset)
if
(
sb_blocksize
(
rs
)
!=
s
->
s_blocksize
)
{
printk
(
"sh-2011: read_super_block: "
"can't find a reiserfs filesystem on (dev %s, block %lu, size %lu)
\n
"
,
s
->
s_id
,
bh
->
b_blocknr
,
s
->
s_blocksize
);
reiserfs_bdevname
(
s
)
,
bh
->
b_blocknr
,
s
->
s_blocksize
);
brelse
(
bh
);
return
1
;
}
...
...
@@ -772,7 +848,7 @@ static int read_super_block (struct super_block * s, int offset)
brelse
(
bh
)
;
printk
(
"dev %s: Unfinished reiserfsck --rebuild-tree run detected. Please run
\n
"
"reiserfsck --rebuild-tree and wait for a completion. If that fails
\n
"
"get newer reiserfsprogs package
\n
"
,
s
->
s_id
);
"get newer reiserfsprogs package
\n
"
,
reiserfs_bdevname
(
s
)
);
return
1
;
}
...
...
@@ -884,7 +960,7 @@ __u32 find_hash_out (struct super_block * s)
(
(
r5hash
==
yurahash
)
&&
(
yurahash
==
GET_HASH_VALUE
(
deh_offset
(
&
(
de
.
de_deh
[
de
.
de_entry_num
]))))
)
)
{
reiserfs_warning
(
"reiserfs: Unable to automatically detect hash"
"function for device %s
\n
"
"please mount with -o hash={tea,rupasov,r5}
\n
"
,
s
->
s_id
);
"please mount with -o hash={tea,rupasov,r5}
\n
"
,
reiserfs_bdevname
(
s
)
);
hash
=
UNSET_HASH
;
break
;
}
...
...
@@ -896,7 +972,7 @@ __u32 find_hash_out (struct super_block * s)
hash
=
R5_HASH
;
else
{
reiserfs_warning
(
"reiserfs: Unrecognised hash function for "
"device %s
\n
"
,
s
->
s_id
);
"device %s
\n
"
,
reiserfs_bdevname
(
s
)
);
hash
=
UNSET_HASH
;
}
}
while
(
0
);
...
...
@@ -990,14 +1066,7 @@ int function2code (hashf_t func)
return
0
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_fill_super
(
struct
super_block
*
s
,
void
*
data
,
int
silent
)
static
int
reiserfs_fill_super
(
struct
super_block
*
s
,
void
*
data
,
int
silent
)
{
struct
inode
*
root_inode
;
int
j
;
...
...
@@ -1009,21 +1078,24 @@ static int reiserfs_fill_super(struct super_block *s, void *data, int silent)
struct
reiserfs_super_block
*
rs
;
char
*
jdev_name
;
struct
reiserfs_sb_info
*
sbi
;
int
errval
=
-
EINVAL
;
sbi
=
kmalloc
(
sizeof
(
struct
reiserfs_sb_info
),
GFP_KERNEL
);
if
(
!
sbi
)
return
-
ENOMEM
;
if
(
!
sbi
)
{
errval
=
-
ENOMEM
;
goto
error
;
}
s
->
u
.
generic_sbp
=
sbi
;
memset
(
sbi
,
0
,
sizeof
(
struct
reiserfs_sb_info
));
jdev_name
=
NULL
;
if
(
parse_options
((
char
*
)
data
,
&
(
sbi
->
s_mount_opt
),
&
blocks
,
&
jdev_name
)
==
0
)
{
return
-
EINVAL
;
if
(
reiserfs_
parse_options
((
char
*
)
data
,
&
(
sbi
->
s_mount_opt
),
&
blocks
,
&
jdev_name
)
==
0
)
{
goto
error
;
}
if
(
blocks
)
{
printk
(
"
reserfs
: resize option for remount only
\n
"
);
return
-
EINVAL
;
printk
(
"
jmacd-7: reiserfs_fill_super
: resize option for remount only
\n
"
);
goto
error
;
}
/* try old format (undistributed bitmap, super block in 8-th 1k block of a device) */
...
...
@@ -1031,14 +1103,14 @@ static int reiserfs_fill_super(struct super_block *s, void *data, int silent)
old_format
=
1
;
/* try new format (64-th 1k block), which can contain reiserfs super block */
else
if
(
read_super_block
(
s
,
REISERFS_DISK_OFFSET_IN_BYTES
))
{
printk
(
"sh-2021: reiserfs_fill_super: can not find reiserfs on %s
\n
"
,
s
->
s_id
);
printk
(
"sh-2021: reiserfs_fill_super: can not find reiserfs on %s
\n
"
,
reiserfs_bdevname
(
s
)
);
goto
error
;
}
sbi
->
s_mount_state
=
SB_REISERFS_STATE
(
s
);
sbi
->
s_mount_state
=
REISERFS_VALID_FS
;
if
(
old_format
?
read_old_bitmaps
(
s
)
:
read_bitmaps
(
s
))
{
printk
(
"reiserfs_fill_super: unable to read bitmap
\n
"
);
printk
(
"
jmacd-8:
reiserfs_fill_super: unable to read bitmap
\n
"
);
goto
error
;
}
#ifdef CONFIG_REISERFS_CHECK
...
...
@@ -1056,7 +1128,7 @@ static int reiserfs_fill_super(struct super_block *s, void *data, int silent)
*/
}
if
(
reread_meta_blocks
(
s
))
{
printk
(
"reiserfs_fill_super: unable to reread meta blocks after journal init
\n
"
)
;
printk
(
"
jmacd-9:
reiserfs_fill_super: unable to reread meta blocks after journal init
\n
"
)
;
goto
error
;
}
...
...
@@ -1071,7 +1143,7 @@ static int reiserfs_fill_super(struct super_block *s, void *data, int silent)
args
.
dirid
=
REISERFS_ROOT_PARENT_OBJECTID
;
root_inode
=
iget5_locked
(
s
,
REISERFS_ROOT_OBJECTID
,
reiserfs_find_actor
,
reiserfs_init_locked_inode
,
(
void
*
)(
&
args
));
if
(
!
root_inode
)
{
printk
(
"reiserfs_fill_super: get root inode failed
\n
"
);
printk
(
"
jmacd-10:
reiserfs_fill_super: get root inode failed
\n
"
);
goto
error
;
}
...
...
@@ -1155,7 +1227,7 @@ static int reiserfs_fill_super(struct super_block *s, void *data, int silent)
reiserfs_proc_register
(
s
,
"journal"
,
reiserfs_journal_in_proc
);
init_waitqueue_head
(
&
(
sbi
->
s_wait
));
return
0
;
return
(
0
)
;
error:
if
(
jinit_done
)
{
/* kill the commit thread, free journal ram */
...
...
@@ -1172,96 +1244,85 @@ static int reiserfs_fill_super(struct super_block *s, void *data, int silent)
if
(
SB_BUFFER_WITH_SB
(
s
))
brelse
(
SB_BUFFER_WITH_SB
(
s
));
kfree
(
sbi
);
s
->
u
.
generic_sbp
=
NULL
;
if
(
sbi
!=
NULL
)
{
kfree
(
sbi
);
}
return
-
EINVAL
;
s
->
u
.
generic_sbp
=
NULL
;
return
errval
;
}
//
// a portion of this function, particularly the VFS interface portion,
// was derived from minix or ext2's analog and evolved as the
// prototype did. You should be able to tell which portion by looking
// at the ext2 code and comparing. It's subfunctions contain no code
// used as a template unless they are so labeled.
//
static
int
reiserfs_statfs
(
struct
super_block
*
s
,
struct
statfs
*
buf
)
{
struct
reiserfs_super_block
*
rs
=
SB_DISK_SUPER_BLOCK
(
s
);
/* changed to accomodate gcc folks.*/
buf
->
f_type
=
REISERFS_SUPER_MAGIC
;
buf
->
f_bsize
=
s
->
s_blocksize
;
buf
->
f_blocks
=
sb_block_count
(
rs
)
-
sb_bmap_nr
(
rs
)
-
1
;
buf
->
f_namelen
=
(
REISERFS_MAX_NAME
(
s
->
s_blocksize
));
buf
->
f_ffree
=
-
1
;
buf
->
f_files
=
-
1
;
buf
->
f_bfree
=
sb_free_blocks
(
rs
);
buf
->
f_bavail
=
buf
->
f_bfree
;
buf
->
f_files
=
-
1
;
buf
->
f_ffree
=
-
1
;
buf
->
f_namelen
=
(
REISERFS_MAX_NAME_LEN
(
s
->
s_blocksize
));
buf
->
f_blocks
=
sb_block_count
(
rs
)
-
sb_bmap_nr
(
rs
)
-
1
;
buf
->
f_bsize
=
s
->
s_blocksize
;
/* changed to accomodate gcc folks.*/
buf
->
f_type
=
REISERFS_SUPER_MAGIC
;
return
0
;
}
static
struct
super_block
*
reiserfs_get_sb
(
struct
file_system_type
*
fs_type
,
int
flags
,
char
*
dev_name
,
void
*
data
)
static
struct
super_block
*
get_super_block
(
struct
file_system_type
*
fs_type
,
int
flags
,
char
*
dev_name
,
void
*
data
)
{
return
get_sb_bdev
(
fs_type
,
flags
,
dev_name
,
data
,
reiserfs_fill_super
);
return
get_sb_bdev
(
fs_type
,
flags
,
dev_name
,
data
,
reiserfs_fill_super
);
}
static
struct
file_system_type
reiserfs_fs_type
=
{
owner:
THIS_MODULE
,
name:
"reiserfs"
,
get_sb:
reiserfs_get_sb
,
kill_sb:
kill_block_super
,
fs_flags:
FS_REQUIRES_DEV
,
};
int
reiserfs_is_super
(
struct
super_block
*
s
)
static
int
__init
init_reiserfs_fs
(
void
)
{
return
s
->
s_type
==
&
reiserfs_fs_type
;
}
int
ret
;
//
// this is exactly what 2.3.99-pre9's init_ext2_fs is
//
static
int
__init
init_reiserfs_fs
(
void
)
{
int
err
=
init_inodecache
();
if
(
err
)
goto
out1
;
reiserfs_proc_info_global_init
();
reiserfs_proc_register_global
(
"version"
,
reiserfs_global_version_in_proc
);
err
=
register_filesystem
(
&
reiserfs_fs_type
);
if
(
err
)
goto
out
;
return
0
;
out:
reiserfs_proc_unregister_global
(
"version"
);
reiserfs_proc_info_global_done
();
destroy_inodecache
();
out1:
return
err
;
}
if
((
ret
=
init_inodecache
()))
{
return
ret
;
}
reiserfs_proc_info_global_init
();
reiserfs_proc_register_global
(
"version"
,
reiserfs_global_version_in_proc
);
MODULE_DESCRIPTION
(
"ReiserFS journaled filesystem"
);
MODULE_AUTHOR
(
"Hans Reiser <reiser@namesys.com>"
);
MODULE_LICENSE
(
"GPL"
);
ret
=
register_filesystem
(
&
reiserfs_fs_type
);
//
// this is exactly what 2.3.99-pre9's init_ext2_fs is
//
static
void
__exit
exit_reiserfs_fs
(
void
)
{
reiserfs_proc_
unregister_global
(
"version"
);
reiserfs_proc_info_global_done
();
unregister_filesystem
(
&
reiserfs_fs_type
);
destroy_inodecache
()
;
if
(
ret
==
0
)
{
return
0
;
}
reiserfs_proc_unregister_global
(
"version"
);
reiserfs_proc_
info_global_done
(
);
destroy_inodecache
();
return
ret
;
}
module_init
(
init_reiserfs_fs
)
;
module_exit
(
exit_reiserfs_fs
)
;
static
void
__exit
exit_reiserfs_fs
(
void
)
{
reiserfs_proc_unregister_global
(
"version"
);
reiserfs_proc_info_global_done
();
unregister_filesystem
(
&
reiserfs_fs_type
);
destroy_inodecache
();
}
static
struct
file_system_type
reiserfs_fs_type
=
{
owner:
THIS_MODULE
,
name:
"reiserfs"
,
get_sb:
get_super_block
,
kill_sb:
kill_block_super
,
fs_flags:
FS_REQUIRES_DEV
,
};
MODULE_DESCRIPTION
(
"ReiserFS journaled filesystem"
);
MODULE_AUTHOR
(
"Hans Reiser <reiser@namesys.com>"
);
MODULE_LICENSE
(
"GPL"
);
module_init
(
init_reiserfs_fs
);
module_exit
(
exit_reiserfs_fs
);
fs/reiserfs/tail_conversion.c
View file @
7bbbc1b5
...
...
@@ -214,7 +214,7 @@ int indirect2direct (struct reiserfs_transaction_handle *th,
copy_item_head
(
&
s_ih
,
PATH_PITEM_HEAD
(
p_s_path
));
tail_len
=
(
n_new_file_size
&
(
n_block_size
-
1
));
if
(
!
old_format_only
(
p_s_sb
)
)
if
(
get_inode_sd_version
(
p_s_inode
)
==
STAT_DATA_V2
)
round_tail_len
=
ROUND_UP
(
tail_len
);
else
round_tail_len
=
tail_len
;
...
...
include/linux/reiserfs_fs.h
View file @
7bbbc1b5
...
...
@@ -20,6 +20,7 @@
#include <asm/unaligned.h>
#include <linux/bitops.h>
#include <linux/proc_fs.h>
#include <linux/smp_lock.h>
#include <linux/buffer_head.h>
#include <linux/reiserfs_fs_i.h>
#include <linux/reiserfs_fs_sb.h>
...
...
@@ -1062,9 +1063,7 @@ static inline int entry_length (const struct buffer_head * bh,
#define B_I_E_NAME(bh,ih,entry_num) ((char *)(bh->b_data + ih_location(ih) + deh_location(B_I_DEH(bh,ih)+(entry_num))))
// two entries per block (at least)
//#define REISERFS_MAX_NAME_LEN(block_size)
//((block_size - BLKH_SIZE - IH_SIZE - DEH_SIZE * 2) / 2)
#define REISERFS_MAX_NAME_LEN(block_size) 255
#define REISERFS_MAX_NAME(block_size) 255
/* this structure is used for operations on directory entries. It is
...
...
@@ -1654,6 +1653,11 @@ extern wait_queue_head_t reiserfs_commit_thread_wait ;
*/
#define JOURNAL_BUFFER(j,n) ((j)->j_ap_blocks[((j)->j_start + (n)) % JOURNAL_BLOCK_COUNT])
// We need these to make journal.c code more readable
#define journal_get_hash_table(s, block) __get_hash_table(SB_JOURNAL(s)->j_dev_bd, block, s->s_blocksize)
#define journal_getblk(s, block) __getblk(SB_JOURNAL(s)->j_dev_bd, block, s->s_blocksize)
#define journal_bread(s, block) __bread(SB_JOURNAL(s)->j_dev_bd, block, s->s_blocksize)
void
reiserfs_commit_for_inode
(
struct
inode
*
)
;
void
reiserfs_update_inode_transaction
(
struct
inode
*
)
;
void
reiserfs_wait_on_write_block
(
struct
super_block
*
s
)
;
...
...
@@ -2073,6 +2077,12 @@ int reiserfs_unpack (struct inode * inode, struct file * filp);
/* ioctl's command */
#define REISERFS_IOC_UNPACK _IOW(0xCD,1,long)
/* Locking primitives */
/* Right now we are still falling back to (un)lock_kernel, but eventually that
would evolve into real per-fs locks */
#define reiserfs_write_lock( sb ) lock_kernel()
#define reiserfs_write_unlock( sb ) unlock_kernel()
#endif
/* _LINUX_REISER_FS_H */
...
...
include/linux/reiserfs_fs_sb.h
View file @
7bbbc1b5
...
...
@@ -408,6 +408,8 @@ struct reiserfs_sb_info
#define REISERFS_HASHED_RELOCATION 13
#define REISERFS_TEST4 14
#define REISERFS_ATTRS 15
#define REISERFS_TEST1 11
#define REISERFS_TEST2 12
#define REISERFS_TEST3 13
...
...
@@ -430,7 +432,7 @@ struct reiserfs_sb_info
void
reiserfs_file_buffer
(
struct
buffer_head
*
bh
,
int
list
);
int
reiserfs_i
s_super
(
struct
super_block
*
s
)
;
int
is_reiserf
s_super
(
struct
super_block
*
s
)
;
int
journal_mark_dirty
(
struct
reiserfs_transaction_handle
*
,
struct
super_block
*
,
struct
buffer_head
*
bh
)
;
int
flush_old_commits
(
struct
super_block
*
s
,
int
)
;
int
show_reiserfs_locks
(
void
)
;
...
...
@@ -456,4 +458,12 @@ int reiserfs_resize(struct super_block *, unsigned long) ;
#define SB_JOURNAL_MAX_TRANS_AGE(s) (SB_JOURNAL(s)->s_journal_max_trans_age)
#define SB_JOURNAL_DEV(s) (SB_JOURNAL(s)->j_dev)
/* A safe version of the "bdevname", which returns the "s_id" field of
* a superblock or else "Null superblock" if the super block is NULL.
*/
static
inline
char
*
reiserfs_bdevname
(
struct
super_block
*
s
)
{
return
(
s
==
NULL
)
?
"Null superblock"
:
s
->
s_id
;
}
#endif
/* _LINUX_REISER_FS_SB */
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment