mirror of
				git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
				synced 2025-10-31 16:54:21 +00:00 
			
		
		
		
	[PATCH] sanitize blkdev_get() and friends
* get rid of fake struct file/struct dentry in __blkdev_get() * merge __blkdev_get() and do_open() * get rid of flags argument of blkdev_get() Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
		
							parent
							
								
									e5eb8caa83
								
							
						
					
					
						commit
						572c489215
					
				
					 8 changed files with 30 additions and 51 deletions
				
			
		|  | @ -2332,7 +2332,7 @@ static int pkt_open_dev(struct pktcdvd_device *pd, fmode_t write) | |||
| 	 * so bdget() can't fail. | ||||
| 	 */ | ||||
| 	bdget(pd->bdev->bd_dev); | ||||
| 	if ((ret = blkdev_get(pd->bdev, FMODE_READ, O_RDONLY))) | ||||
| 	if ((ret = blkdev_get(pd->bdev, FMODE_READ))) | ||||
| 		goto out; | ||||
| 
 | ||||
| 	if ((ret = bd_claim(pd->bdev, pd))) | ||||
|  | @ -2765,7 +2765,7 @@ static int pkt_new_dev(struct pktcdvd_device *pd, dev_t dev) | |||
| 	bdev = bdget(dev); | ||||
| 	if (!bdev) | ||||
| 		return -ENOMEM; | ||||
| 	ret = blkdev_get(bdev, FMODE_READ, O_RDONLY | O_NONBLOCK); | ||||
| 	ret = blkdev_get(bdev, FMODE_READ | FMODE_NDELAY); | ||||
| 	if (ret) | ||||
| 		return ret; | ||||
| 
 | ||||
|  |  | |||
|  | @ -65,7 +65,7 @@ static int raw_open(struct inode *inode, struct file *filp) | |||
| 	if (!bdev) | ||||
| 		goto out; | ||||
| 	igrab(bdev->bd_inode); | ||||
| 	err = blkdev_get(bdev, filp->f_mode, 0); | ||||
| 	err = blkdev_get(bdev, filp->f_mode); | ||||
| 	if (err) | ||||
| 		goto out; | ||||
| 	err = bd_claim(bdev, raw_open); | ||||
|  |  | |||
|  | @ -99,7 +99,7 @@ int dasd_scan_partitions(struct dasd_block *block) | |||
| 	struct block_device *bdev; | ||||
| 
 | ||||
| 	bdev = bdget_disk(block->gdp, 0); | ||||
| 	if (!bdev || blkdev_get(bdev, FMODE_READ, 1) < 0) | ||||
| 	if (!bdev || blkdev_get(bdev, FMODE_READ) < 0) | ||||
| 		return -ENODEV; | ||||
| 	/*
 | ||||
| 	 * See fs/partition/check.c:register_disk,rescan_partitions | ||||
|  |  | |||
|  | @ -844,9 +844,8 @@ struct block_device *open_by_devnum(dev_t dev, fmode_t mode) | |||
| { | ||||
| 	struct block_device *bdev = bdget(dev); | ||||
| 	int err = -ENOMEM; | ||||
| 	int flags = mode & FMODE_WRITE ? O_RDWR : O_RDONLY; | ||||
| 	if (bdev) | ||||
| 		err = blkdev_get(bdev, mode, flags); | ||||
| 		err = blkdev_get(bdev, mode); | ||||
| 	return err ? ERR_PTR(err) : bdev; | ||||
| } | ||||
| 
 | ||||
|  | @ -975,8 +974,6 @@ void bd_set_size(struct block_device *bdev, loff_t size) | |||
| } | ||||
| EXPORT_SYMBOL(bd_set_size); | ||||
| 
 | ||||
| static int __blkdev_get(struct block_device *bdev, fmode_t mode, unsigned flags, | ||||
| 			int for_part); | ||||
| static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part); | ||||
| 
 | ||||
| /*
 | ||||
|  | @ -986,7 +983,7 @@ static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part); | |||
|  *    mutex_lock_nested(whole->bd_mutex, 1) | ||||
|  */ | ||||
| 
 | ||||
| static int do_open(struct block_device *bdev, struct file *file, int for_part) | ||||
| static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) | ||||
| { | ||||
| 	struct gendisk *disk; | ||||
| 	struct hd_struct *part = NULL; | ||||
|  | @ -994,9 +991,9 @@ static int do_open(struct block_device *bdev, struct file *file, int for_part) | |||
| 	int partno; | ||||
| 	int perm = 0; | ||||
| 
 | ||||
| 	if (file->f_mode & FMODE_READ) | ||||
| 	if (mode & FMODE_READ) | ||||
| 		perm |= MAY_READ; | ||||
| 	if (file->f_mode & FMODE_WRITE) | ||||
| 	if (mode & FMODE_WRITE) | ||||
| 		perm |= MAY_WRITE; | ||||
| 	/*
 | ||||
| 	 * hooks: /n/, see "layering violations". | ||||
|  | @ -1007,15 +1004,7 @@ static int do_open(struct block_device *bdev, struct file *file, int for_part) | |||
| 		return ret; | ||||
| 	} | ||||
| 
 | ||||
| 	if (file->f_flags & O_NDELAY) | ||||
| 		file->f_mode |= FMODE_NDELAY; | ||||
| 	if (file->f_flags & O_EXCL) | ||||
| 		file->f_mode |= FMODE_EXCL; | ||||
| 	if ((file->f_flags & O_ACCMODE) == 3) | ||||
| 		file->f_mode |= FMODE_WRITE_IOCTL; | ||||
| 
 | ||||
| 	ret = -ENXIO; | ||||
| 	file->f_mapping = bdev->bd_inode->i_mapping; | ||||
| 
 | ||||
| 	lock_kernel(); | ||||
| 
 | ||||
|  | @ -1034,7 +1023,7 @@ static int do_open(struct block_device *bdev, struct file *file, int for_part) | |||
| 		if (!partno) { | ||||
| 			struct backing_dev_info *bdi; | ||||
| 			if (disk->fops->open) { | ||||
| 				ret = disk->fops->open(bdev, file->f_mode); | ||||
| 				ret = disk->fops->open(bdev, mode); | ||||
| 				if (ret) | ||||
| 					goto out_clear; | ||||
| 			} | ||||
|  | @ -1054,7 +1043,7 @@ static int do_open(struct block_device *bdev, struct file *file, int for_part) | |||
| 			if (!whole) | ||||
| 				goto out_clear; | ||||
| 			BUG_ON(for_part); | ||||
| 			ret = __blkdev_get(whole, file->f_mode, file->f_flags, 1); | ||||
| 			ret = __blkdev_get(whole, mode, 1); | ||||
| 			if (ret) | ||||
| 				goto out_clear; | ||||
| 			bdev->bd_contains = whole; | ||||
|  | @ -1075,7 +1064,7 @@ static int do_open(struct block_device *bdev, struct file *file, int for_part) | |||
| 		disk = NULL; | ||||
| 		if (bdev->bd_contains == bdev) { | ||||
| 			if (bdev->bd_disk->fops->open) { | ||||
| 				ret = bdev->bd_disk->fops->open(bdev, file->f_mode); | ||||
| 				ret = bdev->bd_disk->fops->open(bdev, mode); | ||||
| 				if (ret) | ||||
| 					goto out_unlock_bdev; | ||||
| 			} | ||||
|  | @ -1095,7 +1084,7 @@ static int do_open(struct block_device *bdev, struct file *file, int for_part) | |||
| 	bdev->bd_part = NULL; | ||||
| 	bdev->bd_inode->i_data.backing_dev_info = &default_backing_dev_info; | ||||
| 	if (bdev != bdev->bd_contains) | ||||
| 		__blkdev_put(bdev->bd_contains, file->f_mode, 1); | ||||
| 		__blkdev_put(bdev->bd_contains, mode, 1); | ||||
| 	bdev->bd_contains = NULL; | ||||
|  out_unlock_bdev: | ||||
| 	mutex_unlock(&bdev->bd_mutex); | ||||
|  | @ -1111,28 +1100,9 @@ static int do_open(struct block_device *bdev, struct file *file, int for_part) | |||
| 	return ret; | ||||
| } | ||||
| 
 | ||||
| static int __blkdev_get(struct block_device *bdev, fmode_t mode, unsigned flags, | ||||
| 			int for_part) | ||||
| int blkdev_get(struct block_device *bdev, fmode_t mode) | ||||
| { | ||||
| 	/*
 | ||||
| 	 * This crockload is due to bad choice of ->open() type. | ||||
| 	 * It will go away. | ||||
| 	 * For now, block device ->open() routine must _not_ | ||||
| 	 * examine anything in 'inode' argument except ->i_rdev. | ||||
| 	 */ | ||||
| 	struct file fake_file = {}; | ||||
| 	struct dentry fake_dentry = {}; | ||||
| 	fake_file.f_mode = mode; | ||||
| 	fake_file.f_flags = flags; | ||||
| 	fake_file.f_path.dentry = &fake_dentry; | ||||
| 	fake_dentry.d_inode = bdev->bd_inode; | ||||
| 
 | ||||
| 	return do_open(bdev, &fake_file, for_part); | ||||
| } | ||||
| 
 | ||||
| int blkdev_get(struct block_device *bdev, fmode_t mode, unsigned flags) | ||||
| { | ||||
| 	return __blkdev_get(bdev, mode, flags, 0); | ||||
| 	return __blkdev_get(bdev, mode, 0); | ||||
| } | ||||
| EXPORT_SYMBOL(blkdev_get); | ||||
| 
 | ||||
|  | @ -1149,15 +1119,24 @@ static int blkdev_open(struct inode * inode, struct file * filp) | |||
| 	 */ | ||||
| 	filp->f_flags |= O_LARGEFILE; | ||||
| 
 | ||||
| 	if (filp->f_flags & O_NDELAY) | ||||
| 		filp->f_mode |= FMODE_NDELAY; | ||||
| 	if (filp->f_flags & O_EXCL) | ||||
| 		filp->f_mode |= FMODE_EXCL; | ||||
| 	if ((filp->f_flags & O_ACCMODE) == 3) | ||||
| 		filp->f_mode |= FMODE_WRITE_IOCTL; | ||||
| 
 | ||||
| 	bdev = bd_acquire(inode); | ||||
| 	if (bdev == NULL) | ||||
| 		return -ENOMEM; | ||||
| 
 | ||||
| 	res = do_open(bdev, filp, 0); | ||||
| 	filp->f_mapping = bdev->bd_inode->i_mapping; | ||||
| 
 | ||||
| 	res = blkdev_get(bdev, filp->f_mode); | ||||
| 	if (res) | ||||
| 		return res; | ||||
| 
 | ||||
| 	if (!(filp->f_flags & O_EXCL) ) | ||||
| 	if (!(filp->f_mode & FMODE_EXCL)) | ||||
| 		return 0; | ||||
| 
 | ||||
| 	if (!(res = bd_claim(bdev, filp))) | ||||
|  | @ -1327,7 +1306,7 @@ struct block_device *open_bdev_exclusive(const char *path, fmode_t mode, void *h | |||
| 	if (IS_ERR(bdev)) | ||||
| 		return bdev; | ||||
| 
 | ||||
| 	error = blkdev_get(bdev, mode, 0); | ||||
| 	error = blkdev_get(bdev, mode); | ||||
| 	if (error) | ||||
| 		return ERR_PTR(error); | ||||
| 	error = -EACCES; | ||||
|  |  | |||
|  | @ -1268,7 +1268,7 @@ static ssize_t o2hb_region_dev_write(struct o2hb_region *reg, | |||
| 		goto out; | ||||
| 
 | ||||
| 	reg->hr_bdev = I_BDEV(filp->f_mapping->host); | ||||
| 	ret = blkdev_get(reg->hr_bdev, FMODE_WRITE | FMODE_READ, 0); | ||||
| 	ret = blkdev_get(reg->hr_bdev, FMODE_WRITE | FMODE_READ); | ||||
| 	if (ret) { | ||||
| 		reg->hr_bdev = NULL; | ||||
| 		goto out; | ||||
|  |  | |||
|  | @ -485,7 +485,7 @@ void register_disk(struct gendisk *disk) | |||
| 		goto exit; | ||||
| 
 | ||||
| 	bdev->bd_invalidated = 1; | ||||
| 	err = blkdev_get(bdev, FMODE_READ, 0); | ||||
| 	err = blkdev_get(bdev, FMODE_READ); | ||||
| 	if (err < 0) | ||||
| 		goto exit; | ||||
| 	blkdev_put(bdev, FMODE_READ); | ||||
|  |  | |||
|  | @ -1722,7 +1722,7 @@ extern int blkdev_driver_ioctl(struct inode *inode, struct file *file, | |||
| 			       struct gendisk *disk, unsigned cmd, | ||||
| 			       unsigned long arg); | ||||
| extern long compat_blkdev_ioctl(struct file *, unsigned, unsigned long); | ||||
| extern int blkdev_get(struct block_device *, fmode_t, unsigned); | ||||
| extern int blkdev_get(struct block_device *, fmode_t); | ||||
| extern int blkdev_put(struct block_device *, fmode_t); | ||||
| extern int bd_claim(struct block_device *, void *); | ||||
| extern void bd_release(struct block_device *); | ||||
|  |  | |||
|  | @ -172,7 +172,7 @@ static int swsusp_swap_check(void) /* This is called before saving image */ | |||
| 		return res; | ||||
| 
 | ||||
| 	root_swap = res; | ||||
| 	res = blkdev_get(resume_bdev, FMODE_WRITE, O_RDWR); | ||||
| 	res = blkdev_get(resume_bdev, FMODE_WRITE); | ||||
| 	if (res) | ||||
| 		return res; | ||||
| 
 | ||||
|  |  | |||
		Loading…
	
	Add table
		
		Reference in a new issue
	
	 Al Viro
						Al Viro