Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

at v2.6.13 96 lines 2.1 kB view raw
1/* 2 * linux/fs/nfs/symlink.c 3 * 4 * Copyright (C) 1992 Rick Sladkey 5 * 6 * Optimization changes Copyright (C) 1994 Florian La Roche 7 * 8 * Jun 7 1999, cache symlink lookups in the page cache. -DaveM 9 * 10 * nfs symlink handling code 11 */ 12 13#define NFS_NEED_XDR_TYPES 14#include <linux/time.h> 15#include <linux/errno.h> 16#include <linux/sunrpc/clnt.h> 17#include <linux/nfs.h> 18#include <linux/nfs2.h> 19#include <linux/nfs_fs.h> 20#include <linux/pagemap.h> 21#include <linux/stat.h> 22#include <linux/mm.h> 23#include <linux/slab.h> 24#include <linux/string.h> 25#include <linux/smp_lock.h> 26#include <linux/namei.h> 27 28/* Symlink caching in the page cache is even more simplistic 29 * and straight-forward than readdir caching. 30 */ 31 32static int nfs_symlink_filler(struct inode *inode, struct page *page) 33{ 34 int error; 35 36 lock_kernel(); 37 error = NFS_PROTO(inode)->readlink(inode, page, 0, PAGE_SIZE); 38 unlock_kernel(); 39 if (error < 0) 40 goto error; 41 SetPageUptodate(page); 42 unlock_page(page); 43 return 0; 44 45error: 46 SetPageError(page); 47 unlock_page(page); 48 return -EIO; 49} 50 51static void *nfs_follow_link(struct dentry *dentry, struct nameidata *nd) 52{ 53 struct inode *inode = dentry->d_inode; 54 struct page *page; 55 void *err = ERR_PTR(nfs_revalidate_inode(NFS_SERVER(inode), inode)); 56 if (err) 57 goto read_failed; 58 page = read_cache_page(&inode->i_data, 0, 59 (filler_t *)nfs_symlink_filler, inode); 60 if (IS_ERR(page)) { 61 err = page; 62 goto read_failed; 63 } 64 if (!PageUptodate(page)) { 65 err = ERR_PTR(-EIO); 66 goto getlink_read_error; 67 } 68 nd_set_link(nd, kmap(page)); 69 return page; 70 71getlink_read_error: 72 page_cache_release(page); 73read_failed: 74 nd_set_link(nd, err); 75 return NULL; 76} 77 78static void nfs_put_link(struct dentry *dentry, struct nameidata *nd, void *cookie) 79{ 80 if (cookie) { 81 struct page *page = cookie; 82 kunmap(page); 83 page_cache_release(page); 84 } 85} 86 87/* 88 * symlinks can't do much... 89 */ 90struct inode_operations nfs_symlink_inode_operations = { 91 .readlink = generic_readlink, 92 .follow_link = nfs_follow_link, 93 .put_link = nfs_put_link, 94 .getattr = nfs_getattr, 95 .setattr = nfs_setattr, 96};