Merge master.kernel.org:/pub/scm/linux/kernel/git/lethal/sh-2.6
[pandora-kernel.git] / fs / ext3 / namei.c
index b8f5cd1..85d132c 100644 (file)
  *  Big-endian to little-endian byte-swapping/bitmaps by
  *        David S. Miller (davem@caip.rutgers.edu), 1995
  *  Directory entry file type support and forward compatibility hooks
- *     for B-tree directories by Theodore Ts'o (tytso@mit.edu), 1998
+ *     for B-tree directories by Theodore Ts'o (tytso@mit.edu), 1998
  *  Hash Tree Directory indexing (c)
- *     Daniel Phillips, 2001
+ *     Daniel Phillips, 2001
  *  Hash Tree Directory indexing porting
- *     Christopher Li, 2002
+ *     Christopher Li, 2002
  *  Hash Tree Directory indexing cleanup
- *     Theodore Ts'o, 2002
+ *     Theodore Ts'o, 2002
  */
 
 #include <linux/fs.h>
@@ -76,7 +76,7 @@ static struct buffer_head *ext3_append(handle_t *handle,
 #ifdef DX_DEBUG
 #define dxtrace(command) command
 #else
-#define dxtrace(command) 
+#define dxtrace(command)
 #endif
 
 struct fake_dirent
@@ -169,7 +169,7 @@ static struct ext3_dir_entry_2* dx_pack_dirents (char *base, int size);
 static void dx_insert_block (struct dx_frame *frame, u32 hash, u32 block);
 static int ext3_htree_next_block(struct inode *dir, __u32 hash,
                                 struct dx_frame *frame,
-                                struct dx_frame *frames, 
+                                struct dx_frame *frames,
                                 __u32 *start_hash);
 static struct buffer_head * ext3_dx_find_entry(struct dentry *dentry,
                       struct ext3_dir_entry_2 **res_dir, int *err);
@@ -250,7 +250,7 @@ static void dx_show_index (char * label, struct dx_entry *entries)
 }
 
 struct stats
-{ 
+{
        unsigned names;
        unsigned space;
        unsigned bcount;
@@ -278,7 +278,7 @@ static struct stats dx_show_leaf(struct dx_hash_info *hinfo, struct ext3_dir_ent
                                       ((char *) de - base));
                        }
                        space += EXT3_DIR_REC_LEN(de->name_len);
-                       names++;
+                       names++;
                }
                de = (struct ext3_dir_entry_2 *) ((char *) de + le16_to_cpu(de->rec_len));
        }
@@ -464,7 +464,7 @@ static void dx_release (struct dx_frame *frames)
  */
 static int ext3_htree_next_block(struct inode *dir, __u32 hash,
                                 struct dx_frame *frame,
-                                struct dx_frame *frames, 
+                                struct dx_frame *frames,
                                 __u32 *start_hash)
 {
        struct dx_frame *p;
@@ -632,7 +632,7 @@ int ext3_htree_fill_tree(struct file *dir_file, __u32 start_hash,
                }
                count += ret;
                hashval = ~0;
-               ret = ext3_htree_next_block(dir, HASH_NB_ALWAYS, 
+               ret = ext3_htree_next_block(dir, HASH_NB_ALWAYS,
                                            frame, frames, &hashval);
                *next_hash = hashval;
                if (ret < 0) {
@@ -649,7 +649,7 @@ int ext3_htree_fill_tree(struct file *dir_file, __u32 start_hash,
                        break;
        }
        dx_release(frames);
-       dxtrace(printk("Fill tree: returned %d entries, next hash: %x\n", 
+       dxtrace(printk("Fill tree: returned %d entries, next hash: %x\n",
                       count, *next_hash));
        return count;
 errout:
@@ -1000,7 +1000,12 @@ static struct dentry *ext3_lookup(struct inode * dir, struct dentry *dentry, str
        if (bh) {
                unsigned long ino = le32_to_cpu(de->inode);
                brelse (bh);
-               inode = iget(dir->i_sb, ino);
+               if (!ext3_valid_inum(dir->i_sb, ino)) {
+                       ext3_error(dir->i_sb, "ext3_lookup",
+                                  "bad inode number: %lu", ino);
+                       inode = NULL;
+               } else
+                       inode = iget(dir->i_sb, ino);
 
                if (!inode)
                        return ERR_PTR(-EACCES);
@@ -1028,7 +1033,13 @@ struct dentry *ext3_get_parent(struct dentry *child)
                return ERR_PTR(-ENOENT);
        ino = le32_to_cpu(de->inode);
        brelse(bh);
-       inode = iget(child->d_inode->i_sb, ino);
+
+       if (!ext3_valid_inum(child->d_inode->i_sb, ino)) {
+               ext3_error(child->d_inode->i_sb, "ext3_get_parent",
+                          "bad inode number: %lu", ino);
+               inode = NULL;
+       } else
+               inode = iget(child->d_inode->i_sb, ino);
 
        if (!inode)
                return ERR_PTR(-EACCES);
@@ -1039,7 +1050,7 @@ struct dentry *ext3_get_parent(struct dentry *child)
                parent = ERR_PTR(-ENOMEM);
        }
        return parent;
-} 
+}
 
 #define S_SHIFT 12
 static unsigned char ext3_type_by_mode[S_IFMT >> S_SHIFT] = {
@@ -1187,7 +1198,7 @@ errout:
  * add_dirent_to_buf will attempt search the directory block for
  * space.  It will return -ENOSPC if no space is available, and -EIO
  * and -EEXIST if directory entry already exists.
- * 
+ *
  * NOTE!  bh is NOT released in the case where ENOSPC is returned.  In
  * all other cases bh is released.
  */
@@ -1379,7 +1390,6 @@ static int ext3_add_entry (handle_t *handle, struct dentry *dentry,
        int     dx_fallback=0;
 #endif
        unsigned blocksize;
-       unsigned nlen, rlen;
        u32 block, blocks;
 
        sb = dir->i_sb;
@@ -1417,8 +1427,7 @@ static int ext3_add_entry (handle_t *handle, struct dentry *dentry,
                return retval;
        de = (struct ext3_dir_entry_2 *) bh->b_data;
        de->inode = 0;
-       de->rec_len = cpu_to_le16(rlen = blocksize);
-       nlen = 0;
+       de->rec_len = cpu_to_le16(blocksize);
        return add_dirent_to_buf(handle, dentry, inode, de, bh);
 }
 
@@ -1563,7 +1572,7 @@ cleanup:
  * ext3_delete_entry deletes a directory entry by merging it with the
  * previous entry
  */
-static int ext3_delete_entry (handle_t *handle, 
+static int ext3_delete_entry (handle_t *handle,
                              struct inode * dir,
                              struct ext3_dir_entry_2 * de_del,
                              struct buffer_head * bh)
@@ -1634,12 +1643,12 @@ static int ext3_add_nondir(handle_t *handle,
  * is so far negative - it has no inode.
  *
  * If the create succeeds, we fill in the inode information
- * with d_instantiate(). 
+ * with d_instantiate().
  */
 static int ext3_create (struct inode * dir, struct dentry * dentry, int mode,
                struct nameidata *nd)
 {
-       handle_t *handle; 
+       handle_t *handle;
        struct inode * inode;
        int err, retries = 0;
 
@@ -1679,7 +1688,7 @@ static int ext3_mknod (struct inode * dir, struct dentry *dentry,
 
 retry:
        handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS(dir->i_sb) +
-                                       EXT3_INDEX_EXTRA_TRANS_BLOCKS + 3 +
+                                       EXT3_INDEX_EXTRA_TRANS_BLOCKS + 3 +
                                        2*EXT3_QUOTA_INIT_BLOCKS(dir->i_sb));
        if (IS_ERR(handle))
                return PTR_ERR(handle);
@@ -1804,10 +1813,10 @@ static int empty_dir (struct inode * inode)
        de1 = (struct ext3_dir_entry_2 *)
                        ((char *) de + le16_to_cpu(de->rec_len));
        if (le32_to_cpu(de->inode) != inode->i_ino ||
-                       !le32_to_cpu(de1->inode) || 
+                       !le32_to_cpu(de1->inode) ||
                        strcmp (".", de->name) ||
                        strcmp ("..", de1->name)) {
-               ext3_warning (inode->i_sb, "empty_dir",
+               ext3_warning (inode->i_sb, "empty_dir",
                              "bad directory (dir #%lu) - no `.' or `..'",
                              inode->i_ino);
                brelse (bh);
@@ -1874,7 +1883,7 @@ int ext3_orphan_add(handle_t *handle, struct inode *inode)
         * being truncated, or files being unlinked. */
 
        /* @@@ FIXME: Observation from aviro:
-        * I think I can trigger J_ASSERT in ext3_orphan_add().  We block 
+        * I think I can trigger J_ASSERT in ext3_orphan_add().  We block
         * here (on lock_super()), so race with ext3_link() which might bump
         * ->i_nlink. For, say it, character device. Not a regular file,
         * not a directory, not a symlink and ->i_nlink > 0.
@@ -1910,8 +1919,8 @@ int ext3_orphan_add(handle_t *handle, struct inode *inode)
        if (!err)
                list_add(&EXT3_I(inode)->i_orphan, &EXT3_SB(sb)->s_orphan);
 
-       jbd_debug(4, "superblock will point to %ld\n", inode->i_ino);
-       jbd_debug(4, "orphan inode %ld will point to %d\n",
+       jbd_debug(4, "superblock will point to %lu\n", inode->i_ino);
+       jbd_debug(4, "orphan inode %lu will point to %d\n",
                        inode->i_ino, NEXT_ORPHAN(inode));
 out_unlock:
        unlock_super(sb);
@@ -2120,7 +2129,7 @@ static int ext3_symlink (struct inode * dir,
 
 retry:
        handle = ext3_journal_start(dir, EXT3_DATA_TRANS_BLOCKS(dir->i_sb) +
-                                       EXT3_INDEX_EXTRA_TRANS_BLOCKS + 5 +
+                                       EXT3_INDEX_EXTRA_TRANS_BLOCKS + 5 +
                                        2*EXT3_QUOTA_INIT_BLOCKS(dir->i_sb));
        if (IS_ERR(handle))
                return PTR_ERR(handle);
@@ -2218,7 +2227,7 @@ static int ext3_rename (struct inode * old_dir, struct dentry *old_dentry,
                DQUOT_INIT(new_dentry->d_inode);
        handle = ext3_journal_start(old_dir, 2 *
                                        EXT3_DATA_TRANS_BLOCKS(old_dir->i_sb) +
-                                       EXT3_INDEX_EXTRA_TRANS_BLOCKS + 2);
+                                       EXT3_INDEX_EXTRA_TRANS_BLOCKS + 2);
        if (IS_ERR(handle))
                return PTR_ERR(handle);
 
@@ -2384,4 +2393,4 @@ struct inode_operations ext3_special_inode_operations = {
        .removexattr    = generic_removexattr,
 #endif
        .permission     = ext3_permission,
-}; 
+};