aboutsummaryrefslogtreecommitdiffstats
path: root/mm
diff options
context:
space:
mode:
Diffstat (limited to 'mm')
-rw-r--r--mm/swapfile.c64
1 files changed, 39 insertions, 25 deletions
diff --git a/mm/swapfile.c b/mm/swapfile.c
index 14590775212d..fc687b234eb5 100644
--- a/mm/swapfile.c
+++ b/mm/swapfile.c
@@ -1889,6 +1889,43 @@ static struct swap_info_struct *alloc_swap_info(void)
1889 return p; 1889 return p;
1890} 1890}
1891 1891
1892static int claim_swapfile(struct swap_info_struct *p, struct inode *inode)
1893{
1894 int error;
1895
1896 if (S_ISBLK(inode->i_mode)) {
1897 p->bdev = bdgrab(I_BDEV(inode));
1898 error = blkdev_get(p->bdev,
1899 FMODE_READ | FMODE_WRITE | FMODE_EXCL,
1900 sys_swapon);
1901 if (error < 0) {
1902 p->bdev = NULL;
1903 error = -EINVAL;
1904 goto bad_swap;
1905 }
1906 p->old_block_size = block_size(p->bdev);
1907 error = set_blocksize(p->bdev, PAGE_SIZE);
1908 if (error < 0)
1909 goto bad_swap;
1910 p->flags |= SWP_BLKDEV;
1911 } else if (S_ISREG(inode->i_mode)) {
1912 p->bdev = inode->i_sb->s_bdev;
1913 mutex_lock(&inode->i_mutex);
1914 if (IS_SWAPFILE(inode)) {
1915 error = -EBUSY;
1916 goto bad_swap;
1917 }
1918 } else {
1919 error = -EINVAL;
1920 goto bad_swap;
1921 }
1922
1923 return 0;
1924
1925bad_swap:
1926 return error;
1927}
1928
1892SYSCALL_DEFINE2(swapon, const char __user *, specialfile, int, swap_flags) 1929SYSCALL_DEFINE2(swapon, const char __user *, specialfile, int, swap_flags)
1893{ 1930{
1894 struct swap_info_struct *p; 1931 struct swap_info_struct *p;
@@ -1942,32 +1979,9 @@ SYSCALL_DEFINE2(swapon, const char __user *, specialfile, int, swap_flags)
1942 } 1979 }
1943 } 1980 }
1944 1981
1945 if (S_ISBLK(inode->i_mode)) { 1982 error = claim_swapfile(p, inode);
1946 p->bdev = bdgrab(I_BDEV(inode)); 1983 if (unlikely(error))
1947 error = blkdev_get(p->bdev,
1948 FMODE_READ | FMODE_WRITE | FMODE_EXCL,
1949 sys_swapon);
1950 if (error < 0) {
1951 p->bdev = NULL;
1952 error = -EINVAL;
1953 goto bad_swap;
1954 }
1955 p->old_block_size = block_size(p->bdev);
1956 error = set_blocksize(p->bdev, PAGE_SIZE);
1957 if (error < 0)
1958 goto bad_swap;
1959 p->flags |= SWP_BLKDEV;
1960 } else if (S_ISREG(inode->i_mode)) {
1961 p->bdev = inode->i_sb->s_bdev;
1962 mutex_lock(&inode->i_mutex);
1963 if (IS_SWAPFILE(inode)) {
1964 error = -EBUSY;
1965 goto bad_swap;
1966 }
1967 } else {
1968 error = -EINVAL;
1969 goto bad_swap; 1984 goto bad_swap;
1970 }
1971 1985
1972 swapfilepages = i_size_read(inode) >> PAGE_SHIFT; 1986 swapfilepages = i_size_read(inode) >> PAGE_SHIFT;
1973 1987