Commit 5a302308 authored by Andrew Morton's avatar Andrew Morton Committed by Linus Torvalds

[PATCH] rename block_symlink() to page_symlink()

block_symlink() is not a "block" function at all.  It is a pure
pagecache/address_space function.  Seeing driverfs calling it was
the last straw.

The patch renames it to `page_symlink()' and moves it into fs/namei.c
parent ddedde1d
......@@ -2327,46 +2327,6 @@ int brw_page(int rw, struct page *page,
return 0;
}
int block_symlink(struct inode *inode, const char *symname, int len)
{
struct address_space *mapping = inode->i_mapping;
struct page *page = grab_cache_page(mapping, 0);
int err = -ENOMEM;
char *kaddr;
if (!page)
goto fail;
err = mapping->a_ops->prepare_write(NULL, page, 0, len-1);
if (err)
goto fail_map;
kaddr = page_address(page);
memcpy(kaddr, symname, len-1);
mapping->a_ops->commit_write(NULL, page, 0, len-1);
/*
* Notice that we are _not_ going to block here - end of page is
* unmapped, so this will only try to map the rest of page, see
* that it is unmapped (typically even will not look into inode -
* ->i_size will be enough for everything) and zero it out.
* OTOH it's obviously correct and should make the page up-to-date.
*/
if (!PageUptodate(page)) {
err = mapping->a_ops->readpage(NULL, page);
wait_on_page_locked(page);
} else {
unlock_page(page);
}
page_cache_release(page);
if (err < 0)
goto fail;
mark_inode_dirty(inode);
return 0;
fail_map:
unlock_page(page);
page_cache_release(page);
fail:
return err;
}
/*
* Sanity checks for try_to_free_buffers.
*/
......
......@@ -171,7 +171,7 @@ static int driverfs_symlink(struct inode * dir, struct dentry *dentry, const cha
inode = driverfs_get_inode(dir->i_sb, S_IFLNK|S_IRWXUGO, 0);
if (inode) {
int l = strlen(symname)+1;
error = block_symlink(inode, symname, l);
error = page_symlink(inode, symname, l);
if (!error) {
d_instantiate(dentry, inode);
dget(dentry);
......
......@@ -31,7 +31,6 @@
#include "ext2.h"
#include <linux/pagemap.h>
#include <linux/buffer_head.h> /* for block_symlink() */
/*
* Couple of helper functions - make the code slightly cleaner.
......@@ -165,7 +164,7 @@ static int ext2_symlink (struct inode * dir, struct dentry * dentry,
/* slow symlink */
inode->i_op = &page_symlink_inode_operations;
inode->i_mapping->a_ops = &ext2_aops;
err = block_symlink(inode, symname, l);
err = page_symlink(inode, symname, l);
if (err)
goto out_fail;
} else {
......
......@@ -1092,7 +1092,7 @@ static int commit_write_fn(handle_t *handle, struct buffer_head *bh)
/*
* We need to pick up the new inode size which generic_commit_write gave us
* `file' can be NULL - eg, when called from block_symlink().
* `file' can be NULL - eg, when called from page_symlink().
*
* ext3 never places buffers on inode->i_mapping->private_list. metadata
* buffers are managed internally.
......
......@@ -987,11 +987,11 @@ static int ext3_symlink (struct inode * dir,
inode->i_op = &page_symlink_inode_operations;
inode->i_mapping->a_ops = &ext3_aops;
/*
* block_symlink() calls back into ext3_prepare/commit_write.
* page_symlink() calls into ext3_prepare/commit_write.
* We have a transaction open. All is sweetness. It also sets
* i_size in generic_commit_write().
*/
err = block_symlink(inode, symname, l);
err = page_symlink(inode, symname, l);
if (err)
goto out_no_entry;
} else {
......
......@@ -4,7 +4,6 @@
* Copyright (C) 1991, 1992 Linus Torvalds
*/
#include <linux/buffer_head.h> /* for block_symlink() */
#include "minix.h"
static inline void inc_count(struct inode *inode)
......@@ -111,7 +110,7 @@ static int minix_symlink(struct inode * dir, struct dentry *dentry,
inode->i_mode = S_IFLNK | 0777;
minix_set_inode(inode, 0);
err = block_symlink(inode, symname, i);
err = page_symlink(inode, symname, i);
if (err)
goto out_fail;
......
......@@ -2136,6 +2136,46 @@ int page_follow_link(struct dentry *dentry, struct nameidata *nd)
return res;
}
int page_symlink(struct inode *inode, const char *symname, int len)
{
struct address_space *mapping = inode->i_mapping;
struct page *page = grab_cache_page(mapping, 0);
int err = -ENOMEM;
char *kaddr;
if (!page)
goto fail;
err = mapping->a_ops->prepare_write(NULL, page, 0, len-1);
if (err)
goto fail_map;
kaddr = page_address(page);
memcpy(kaddr, symname, len-1);
mapping->a_ops->commit_write(NULL, page, 0, len-1);
/*
* Notice that we are _not_ going to block here - end of page is
* unmapped, so this will only try to map the rest of page, see
* that it is unmapped (typically even will not look into inode -
* ->i_size will be enough for everything) and zero it out.
* OTOH it's obviously correct and should make the page up-to-date.
*/
if (!PageUptodate(page)) {
err = mapping->a_ops->readpage(NULL, page);
wait_on_page_locked(page);
} else {
unlock_page(page);
}
page_cache_release(page);
if (err < 0)
goto fail;
mark_inode_dirty(inode);
return 0;
fail_map:
unlock_page(page);
page_cache_release(page);
fail:
return err;
}
struct inode_operations page_symlink_inode_operations = {
readlink: page_readlink,
follow_link: page_follow_link,
......
......@@ -29,7 +29,6 @@
#include <linux/init.h>
#include <linux/string.h>
#include <linux/smp_lock.h>
#include <linux/buffer_head.h> /* for block_symlink() */
#include <asm/uaccess.h>
......@@ -235,7 +234,7 @@ static int ramfs_symlink(struct inode * dir, struct dentry *dentry, const char *
inode = ramfs_get_inode(dir->i_sb, S_IFLNK|S_IRWXUGO, 0);
if (inode) {
int l = strlen(symname)+1;
error = block_symlink(inode, symname, l);
error = page_symlink(inode, symname, l);
if (!error) {
d_instantiate(dentry, inode);
dget(dentry);
......
......@@ -117,7 +117,7 @@ static int sysv_symlink(struct inode * dir, struct dentry * dentry,
goto out;
sysv_set_inode(inode, 0);
err = block_symlink(inode, symname, l);
err = page_symlink(inode, symname, l);
if (err)
goto out_fail;
......
......@@ -143,7 +143,7 @@ static int ufs_symlink (struct inode * dir, struct dentry * dentry,
/* slow symlink */
inode->i_op = &page_symlink_inode_operations;
inode->i_mapping->a_ops = &ufs_aops;
err = block_symlink(inode, symname, l);
err = page_symlink(inode, symname, l);
if (err)
goto out_fail;
} else {
......
......@@ -499,7 +499,7 @@ static int umsdos_symlink_x (struct inode *dir, struct dentry *dentry,
}
len = strlen (symname) + 1;
ret = block_symlink(dentry->d_inode, symname, len);
ret = page_symlink(dentry->d_inode, symname, len);
if (ret < 0)
goto out_unlink;
out:
......
......@@ -192,7 +192,6 @@ void FASTCALL(unlock_buffer(struct buffer_head *bh));
*/
int try_to_release_page(struct page * page, int gfp_mask);
int block_flushpage(struct page *page, unsigned long offset);
int block_symlink(struct inode *, const char *, int);
int block_write_full_page(struct page*, get_block_t*);
int block_read_full_page(struct page*, get_block_t*);
int block_prepare_write(struct page*, unsigned, unsigned, get_block_t*);
......
......@@ -1244,6 +1244,7 @@ extern int vfs_readlink(struct dentry *, char *, int, const char *);
extern int vfs_follow_link(struct nameidata *, const char *);
extern int page_readlink(struct dentry *, char *, int);
extern int page_follow_link(struct dentry *, struct nameidata *);
extern int page_symlink(struct inode *inode, const char *symname, int len);
extern struct inode_operations page_symlink_inode_operations;
extern void generic_fillattr(struct inode *, struct kstat *);
......
......@@ -277,7 +277,7 @@ EXPORT_SYMBOL(vfs_follow_link);
EXPORT_SYMBOL(page_readlink);
EXPORT_SYMBOL(page_follow_link);
EXPORT_SYMBOL(page_symlink_inode_operations);
EXPORT_SYMBOL(block_symlink);
EXPORT_SYMBOL(page_symlink);
EXPORT_SYMBOL(vfs_readdir);
EXPORT_SYMBOL(__get_lease);
EXPORT_SYMBOL(lease_get_mtime);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment