X-Git-Url: https://git.karo-electronics.de/?a=blobdiff_plain;f=fs%2Fisofs%2Fnamei.c;h=8299889a835ea5c9b95c7d71afcabdb4610310c1;hb=ae937debe178b4327fd67d604ee83a20f22aa0de;hp=c04b3a14a3e94b07744214a18de0a9452d35b3b7;hpb=c45aa055c32b488fc3fd73c760df372b09acf69a;p=mv-sheeva.git diff --git a/fs/isofs/namei.c b/fs/isofs/namei.c index c04b3a14a3e..8299889a835 100644 --- a/fs/isofs/namei.c +++ b/fs/isofs/namei.c @@ -15,7 +15,7 @@ * some sanity tests. */ static int -isofs_cmp(struct dentry * dentry, const char * compare, int dlen) +isofs_cmp(struct dentry *dentry, const char *compare, int dlen) { struct qstr qstr; @@ -48,24 +48,24 @@ isofs_cmp(struct dentry * dentry, const char * compare, int dlen) */ static unsigned long isofs_find_entry(struct inode *dir, struct dentry *dentry, - unsigned long *block_rv, unsigned long* offset_rv, - char * tmpname, struct iso_directory_record * tmpde) + unsigned long *block_rv, unsigned long *offset_rv, + char *tmpname, struct iso_directory_record *tmpde) { unsigned long bufsize = ISOFS_BUFFER_SIZE(dir); unsigned char bufbits = ISOFS_BUFFER_BITS(dir); unsigned long block, f_pos, offset, block_saved, offset_saved; - struct buffer_head * bh = NULL; + struct buffer_head *bh = NULL; struct isofs_sb_info *sbi = ISOFS_SB(dir->i_sb); if (!ISOFS_I(dir)->i_first_extent) return 0; - + f_pos = 0; offset = 0; block = 0; while (f_pos < dir->i_size) { - struct iso_directory_record * de; + struct iso_directory_record *de; int de_len, match, i, dlen; char *dpnt; @@ -111,10 +111,17 @@ isofs_find_entry(struct inode *dir, struct dentry *dentry, dlen = de->name_len[0]; dpnt = de->name; + /* Basic sanity check, whether name doesn't exceed dir entry */ + if (de_len < dlen + sizeof(struct iso_directory_record)) { + printk(KERN_NOTICE "iso9660: Corrupted directory entry" + " in block %lu of inode %lu\n", block, + dir->i_ino); + return 0; + } if (sbi->s_rock && ((i = get_rock_ridge_filename(de, tmpname, dir)))) { - dlen = i; /* possibly -1 */ + dlen = i; /* possibly -1 */ dpnt = tmpname; #ifdef CONFIG_JOLIET } else if (sbi->s_joliet_level) { @@ -145,8 +152,8 @@ isofs_find_entry(struct inode *dir, struct dentry *dentry, isofs_normalize_block_and_offset(de, &block_saved, &offset_saved); - *block_rv = block_saved; - *offset_rv = offset_saved; + *block_rv = block_saved; + *offset_rv = offset_saved; brelse(bh); return 1; } @@ -155,10 +162,11 @@ isofs_find_entry(struct inode *dir, struct dentry *dentry, return 0; } -struct dentry *isofs_lookup(struct inode * dir, struct dentry * dentry, struct nameidata *nd) +struct dentry *isofs_lookup(struct inode *dir, struct dentry *dentry, struct nameidata *nd) { int found; - unsigned long block, offset; + unsigned long uninitialized_var(block); + unsigned long uninitialized_var(offset); struct inode *inode; struct page *page; @@ -170,17 +178,17 @@ struct dentry *isofs_lookup(struct inode * dir, struct dentry * dentry, struct n lock_kernel(); found = isofs_find_entry(dir, dentry, - &block, &offset, - page_address(page), - 1024 + page_address(page)); + &block, &offset, + page_address(page), + 1024 + page_address(page)); __free_page(page); inode = NULL; if (found) { inode = isofs_iget(dir->i_sb, block, offset); - if (!inode) { + if (IS_ERR(inode)) { unlock_kernel(); - return ERR_PTR(-EACCES); + return ERR_CAST(inode); } } unlock_kernel();