linux/fs/freevxfs/vxfs_immed.c
<<
>>
Prefs
   1/*
   2 * Copyright (c) 2000-2001 Christoph Hellwig.
   3 * All rights reserved.
   4 *
   5 * Redistribution and use in source and binary forms, with or without
   6 * modification, are permitted provided that the following conditions
   7 * are met:
   8 * 1. Redistributions of source code must retain the above copyright
   9 *    notice, this list of conditions, and the following disclaimer,
  10 *    without modification.
  11 * 2. The name of the author may not be used to endorse or promote products
  12 *    derived from this software without specific prior written permission.
  13 *
  14 * Alternatively, this software may be distributed under the terms of the
  15 * GNU General Public License ("GPL").
  16 *
  17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
  18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  20 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
  21 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  27 * SUCH DAMAGE.
  28 */
  29
  30/*
  31 * Veritas filesystem driver - support for 'immed' inodes.
  32 */
  33#include <linux/fs.h>
  34#include <linux/pagemap.h>
  35#include <linux/namei.h>
  36
  37#include "vxfs.h"
  38#include "vxfs_extern.h"
  39#include "vxfs_inode.h"
  40
  41
  42static void *   vxfs_immed_follow_link(struct dentry *, struct nameidata *);
  43
  44static int      vxfs_immed_readpage(struct file *, struct page *);
  45
  46/*
  47 * Inode operations for immed symlinks.
  48 *
  49 * Unliked all other operations we do not go through the pagecache,
  50 * but do all work directly on the inode.
  51 */
  52const struct inode_operations vxfs_immed_symlink_iops = {
  53        .readlink =             generic_readlink,
  54        .follow_link =          vxfs_immed_follow_link,
  55};
  56
  57/*
  58 * Address space operations for immed files and directories.
  59 */
  60const struct address_space_operations vxfs_immed_aops = {
  61        .readpage =             vxfs_immed_readpage,
  62};
  63
  64/**
  65 * vxfs_immed_follow_link - follow immed symlink
  66 * @dp:         dentry for the link
  67 * @np:         pathname lookup data for the current path walk
  68 *
  69 * Description:
  70 *   vxfs_immed_follow_link restarts the pathname lookup with
  71 *   the data obtained from @dp.
  72 *
  73 * Returns:
  74 *   Zero on success, else a negative error code.
  75 */
  76static void *
  77vxfs_immed_follow_link(struct dentry *dp, struct nameidata *np)
  78{
  79        struct vxfs_inode_info          *vip = VXFS_INO(dp->d_inode);
  80        nd_set_link(np, vip->vii_immed.vi_immed);
  81        return NULL;
  82}
  83
  84/**
  85 * vxfs_immed_readpage - read part of an immed inode into pagecache
  86 * @file:       file context (unused)
  87 * @page:       page frame to fill in.
  88 *
  89 * Description:
  90 *   vxfs_immed_readpage reads a part of the immed area of the
  91 *   file that hosts @pp into the pagecache.
  92 *
  93 * Returns:
  94 *   Zero on success, else a negative error code.
  95 *
  96 * Locking status:
  97 *   @page is locked and will be unlocked.
  98 */
  99static int
 100vxfs_immed_readpage(struct file *fp, struct page *pp)
 101{
 102        struct vxfs_inode_info  *vip = VXFS_INO(pp->mapping->host);
 103        u_int64_t       offset = (u_int64_t)pp->index << PAGE_CACHE_SHIFT;
 104        caddr_t         kaddr;
 105
 106        kaddr = kmap(pp);
 107        memcpy(kaddr, vip->vii_immed.vi_immed + offset, PAGE_CACHE_SIZE);
 108        kunmap(pp);
 109        
 110        flush_dcache_page(pp);
 111        SetPageUptodate(pp);
 112        unlock_page(pp);
 113
 114        return 0;
 115}
 116