+++ /dev/null
-/*********************************************************
- * Copyright (C) 2007 VMware, Inc. All rights reserved.
- *
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the
- * Free Software Foundation version 2 and no later version.
- *
- * This program is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
- * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
- * for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
- *
- *********************************************************/
-
-#include <linux/autoconf.h>
-#include <linux/version.h>
-
-/*
- * In 2.4.3, the s_maxbytes field was added to struct super_block.
- * However, we can't simply condition on 2.4.3 as the field's starting point
- * because the 2.4.2-2 kernel in RH7.1 also contained it, and if we don't set
- * it, the generic write path in the page cache will fail.
- */
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 4, 3)
-
-#include <linux/fs.h>
-
-void test(void)
-{
- struct super_block sb;
-
- sb.s_maxbytes = 0;
-}
-#endif
* 2.4.20-wolk4.0s.
*/
-#ifdef VMW_HAVE_EPOLL // {
+#if defined(VMW_HAVE_EPOLL) || \
+ LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 9) // {
#define compat_poll_wqueues struct poll_wqueues
#else // } {
#define compat_poll_wqueues poll_table
EXTRA_CFLAGS := $(CC_OPTS) $(INCLUDE)
-EXTRA_CFLAGS += $(call vm_check_build, $(AUTOCONF_DIR)/setnice.c, -DVMW_HAVE_SET_USER_NICE, )
-EXTRA_CFLAGS += $(call vm_check_build, $(AUTOCONF_DIR)/epoll.c, -DVMW_HAVE_EPOLL, )
-EXTRA_CFLAGS += $(call vm_check_build, $(AUTOCONF_DIR)/maxbytes.c, -DVMW_SB_HAS_MAXBYTES, )
-EXTRA_CFLAGS += $(call vm_check_build, $(AUTOCONF_DIR)/cachecreate.c, -DVMW_KMEMCR_HAS_DTOR, )
EXTRA_CFLAGS += $(call vm_check_build, $(AUTOCONF_DIR)/cachector.c, -DVMW_KMEMCR_CTOR_HAS_3_ARGS, )
EXTRA_CFLAGS += $(call vm_check_build, $(AUTOCONF_DIR)/cachector1.c, -DVMW_KMEMCR_CTOR_HAS_2_ARGS, )
#include "vm_assert.h"
/* HGFS dentry operations. */
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 75)
static int HgfsDentryRevalidate(struct dentry *dentry,
struct nameidata *nd);
-#else
-static int HgfsDentryRevalidate(struct dentry *dentry,
- int flags);
-#endif
/* HGFS dentry operations structure. */
struct dentry_operations HgfsDentryOperations = {
*----------------------------------------------------------------------
*/
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 75)
static int
HgfsDentryRevalidate(struct dentry *dentry, // IN: Dentry to revalidate
struct nameidata *nd) // IN: Lookup flags & intent
-#else
-static int
-HgfsDentryRevalidate(struct dentry *dentry, // IN: Dentry to revalidate
- int flags) // IN: Lookup flags (e.g. LOOKUP_CONTINUE)
-#endif
{
int error;
LOG(6, (KERN_DEBUG "VMware hgfs: HgfsDentryRevalidate: calling "
#include "rpcout.h"
#include "hgfs.h"
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 5, 25)
-#define KERNEL_25_FS 0
-#else
-#define KERNEL_25_FS 1
-#endif
-
-#define HGFS_BD_THREAD_NAME "VMware hgfs backdoor handler"
-
/* Synchronization primitives. */
spinlock_t hgfsBigLock = SPIN_LOCK_UNLOCKED;
/* HGFS filesystem high-level operations. */
-#if KERNEL_25_FS /* { */
-# if defined VMW_GETSB_2618
+#if defined VMW_GETSB_2618
static int HgfsGetSb(struct file_system_type *fs_type,
int flags,
const char *dev_name,
void *rawData,
struct vfsmount *mnt);
-# elif LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 70)
+#else
static struct super_block *HgfsGetSb(struct file_system_type *fs_type,
int flags,
const char *dev_name,
void *rawData);
-# else
-static struct super_block *HgfsGetSb(struct file_system_type *fs_type,
- int flags,
- char *dev_name,
- void *rawData);
-# endif
-#else /* } { */
-static struct super_block *HgfsReadSuper24(struct super_block *sb,
- void *rawData,
- int flags);
-#endif /* } */
+#endif
/* HGFS filesystem type structure. */
static struct file_system_type hgfsType = {
.name = HGFS_NAME,
.fs_flags = FS_BINARY_MOUNTDATA,
-#if KERNEL_25_FS
.get_sb = HgfsGetSb,
.kill_sb = kill_anon_super,
-#else
- .read_super = HgfsReadSuper24,
-#endif
};
static void
HgfsInodeCacheCtor(COMPAT_KMEM_CACHE_CTOR_ARGS(slabElem)) // IN: slab item to initialize
{
-#ifdef VMW_EMBED_INODE
HgfsInodeInfo *iinfo = (HgfsInodeInfo *)slabElem;
/*
* much of the VFS inode members.
*/
inode_init_once(&iinfo->inode);
-#endif
}
* it. Note that we'll initialize it anyway, because the default value is
* MAX_NON_LFS, which caps our filesize at 2^32 bytes.
*/
-#ifdef VMW_SB_HAS_MAXBYTES
sb->s_maxbytes = MAX_LFS_FILESIZE;
-#endif
/*
* These two operations will make sure that our block size and the bits
* HGFS filesystem high-level operations.
*/
-#if KERNEL_25_FS
#if defined VMW_GETSB_2618
/*
*-----------------------------------------------------------------------------
*-----------------------------------------------------------------------------
*/
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 70)
static struct super_block *
HgfsGetSb(struct file_system_type *fs_type,
int flags,
const char *dev_name,
void *rawData)
-#else
-static struct super_block *
-HgfsGetSb(struct file_system_type *fs_type,
- int flags,
- char *dev_name,
- void *rawData)
-#endif
{
return get_sb_nodev(fs_type, flags, rawData, HgfsReadSuper);
}
#endif
-#else
-
-
-/*
- *-----------------------------------------------------------------------------
- *
- * HgfsReadSuper24 --
- *
- * Compatibility wrapper for 2.4.x kernels read_super.
- * Converts success to sb, and failure to NULL.
- *
- * Results:
- * The initialized superblock on success
- * NULL on failure
- *
- * Side effects:
- * None
- *
- *-----------------------------------------------------------------------------
- */
-
-static struct super_block *
-HgfsReadSuper24(struct super_block *sb,
- void *rawData,
- int flags) {
- return HgfsReadSuper(sb, rawData, flags) ? NULL : sb;
-}
-#endif
/*
}
LOG(4, (KERN_DEBUG "VMware hgfs: Module Loaded\n"));
-#ifdef HGFS_ENABLE_WRITEBACK
- LOG(4, (KERN_DEBUG "VMware hgfs: writeback cache enabled\n"));
-#endif
-
return TRUE;
}
#include "hgfsProto.h"
#include "vm_basic_types.h"
-static struct inode *HgfsInodeLookup(struct super_block *sb,
- ino_t ino);
static void HgfsSetFileType(struct inode *inode,
HgfsAttrInfo const *attr);
static int HgfsUnpackGetattrReply(HgfsReq *req,
* Private function implementations.
*/
-/*
- *----------------------------------------------------------------------
- *
- * HgfsInodeLookup --
- *
- * The equivalent of ilookup() in the Linux kernel. We have an HGFS
- * specific implementation in order to hack around the lack of
- * ilookup() on older kernels.
- *
- * Results:
- * Pointer to the VFS inode using the current inode number if it
- * already exists in the inode cache, NULL otherwise.
- *
- * Side effects:
- * None
- *
- *----------------------------------------------------------------------
- */
-
-static struct inode *
-HgfsInodeLookup(struct super_block *sb, // IN: Superblock of this fs
- ino_t ino) // IN: Inode number to look up
-{
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 42)
- return ilookup(sb, ino);
-#else
- struct inode *inode;
- HgfsInodeInfo *iinfo;
-
- /*
- * Note that returning NULL in both of these cases will make the
- * caller think that no such inode exists, which is correct. In the first
- * case, we failed to allocate an inode inside iget(), meaning the inode
- * number didn't already exist in the inode cache. In the second case, the
- * inode got marked bad inside read_inode, also indicative of a new inode
- * allocation.
- */
- inode = HgfsGetInode(sb, ino);
- if (inode == NULL) {
- LOG(4, (KERN_DEBUG "VMware hgfs: HgfsInodeLookup: iget ran out of "
- "memory and returned NULL\n"));
- return NULL;
- }
- if (is_bad_inode(inode)) {
- LOG(4, (KERN_DEBUG "VMware hgfs: HgfsInodeLookup: inode marked bad\n"));
- goto iput_and_exit;
- }
-
- /*
- * Our read_inode function should guarantee that if we're here, iinfo should
- * have been allocated already.
- */
- iinfo = INODE_GET_II_P(inode);
- ASSERT(iinfo);
- if (iinfo == NULL) {
- LOG(4, (KERN_DEBUG "VMware hgfs: HgfsInodeLookup: found corrupt inode, "
- "bailing out\n"));
- goto iput_and_exit;
- }
-
- /*
- * It's HGFS's job to make sure this is set to TRUE in all inodes on which
- * we hold a reference. If it is set to TRUE, we return the inode, just as
- * ilookup() does.
- *
- * XXX: Note that there exists a race here and in HgfsIget (between the time
- * that the inode is unlocked and isReferencedInode is set), but I'm hoping
- * that it doesn't matter because anyone executing this code can't posibly
- * be "CONFIG_PREEMPT=y".
- */
- if (iinfo->isReferencedInode) {
- goto exit;
- }
-
- iput_and_exit:
- iput(inode);
- inode = NULL;
-
- exit:
- return inode;
-#endif
-}
-
-
/*
*----------------------------------------------------------------------
*
* XXX: Is this worth the value? We're mixing server-provided inode
* numbers with our own randomly chosen inode numbers.
*
- * XXX: This logic is also racy. After our call to HgfsInodeLookup(), it's
+ * XXX: This logic is also racy. After our call to ilookup(), it's
* possible another caller came in and grabbed that inode number, which
* will cause us to collide in iget() and step on their inode.
*/
if (attr->mask & HGFS_ATTR_VALID_FILEID) {
struct inode *oldInode;
- oldInode = HgfsInodeLookup(sb, attr->hostFileId);
+ oldInode = ilookup(sb, attr->hostFileId);
if (oldInode) {
/*
* If this inode's inode number was generated via iunique(), we
*
* HgfsGetInode --
*
- * This function replaces iget() and should be called instead of it. In newer
- * kernels that have removed the iget() interface, GetInode() obtains an inode
- * and if it is a new one, then initializes the inode by calling
- * HgfsDoReadInode(). In older kernels that support the iget() interface,
- * HgfsDoReadInode() is called by iget() internally.
+ * This function replaces iget() and should be called instead of it.
+ * HgfsGetInode() obtains an inode and, if it is a new one, initializes
+ * it calling HgfsDoReadInode().
*
* Results:
* A new inode object on success, NULL on error.
HgfsGetInode(struct super_block *sb, // IN: file system superblock object
ino_t ino) // IN: inode number to assign to new inode
{
-#ifdef VMW_USE_IGET_LOCKED
struct inode *inode;
inode = iget_locked(sb, ino);
unlock_new_inode(inode);
}
return inode;
-#else
- return iget(sb, ino);
-#endif
}
* allocation and mark the inode "bad" if the allocation fails. This'll
* make all subsequent operations on the inode fail, which is what we want.
*/
-#ifndef VMW_EMBED_INODE
- iinfo = kmem_cache_alloc(hgfsInodeCache, GFP_KERNEL);
- if (!iinfo) {
- LOG(4, (KERN_DEBUG "VMware hgfs: HgfsDoReadInode: no memory for "
- "iinfo!\n"));
- make_bad_inode(inode);
- return;
- }
-#endif
INODE_SET_II_P(inode, iinfo);
INIT_LIST_HEAD(&iinfo->files);
iinfo->hostFileId = 0;
#include <linux/errno.h>
#include <linux/pagemap.h>
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0) && \
- LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 27)
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 27)
#include <linux/namei.h>
#endif
#include "fsutil.h"
#include "vm_assert.h"
-/*
- * The inode_operations structure changed in 2.5.18:
- * before:
- * . 'getattr' was defined but unused
- * . 'revalidate' was defined and used
- * after:
- * 1) 'getattr' changed and became used
- * 2) 'revalidate' was removed
- *
- * Note: Mandrake backported 1) but not 2) starting with 2.4.8-26mdk
- *
- * --hpreg
- */
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 18)
-# define HGFS_GETATTR_ONLY 1
-#else
-# undef HGFS_GETATTR_ONLY
-#endif
-
-
/* Private functions. */
static int HgfsDelete(struct inode *dir,
struct dentry *dentry,
HgfsReq *req);
/* HGFS inode operations. */
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 75)
static int HgfsCreate(struct inode *dir,
struct dentry *dentry,
int mode,
static struct dentry *HgfsLookup(struct inode *dir,
struct dentry *dentry,
struct nameidata *nd);
-#else
-static int HgfsCreate(struct inode *dir,
- struct dentry *dentry,
- int mode);
-static struct dentry *HgfsLookup(struct inode *dir,
- struct dentry *dentry);
-#endif
static int HgfsMkdir(struct inode *dir,
struct dentry *dentry,
int mode);
static int HgfsSymlink(struct inode *dir,
struct dentry *dentry,
const char *symname);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0) && \
- LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 27)
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 27)
static int HgfsPermission(struct inode *inode,
int mask,
struct nameidata *nameidata);
static int HgfsPermission(struct inode *inode,
int mask);
#endif
-#ifdef HGFS_GETATTR_ONLY
static int HgfsGetattr(struct vfsmount *mnt,
struct dentry *dentry,
struct kstat *stat);
-#endif
#define HGFS_CREATE_DIR_MASK (HGFS_CREATE_DIR_VALID_FILE_NAME | \
HGFS_CREATE_DIR_VALID_SPECIAL_PERMS | \
.permission = HgfsPermission,
.setattr = HgfsSetattr,
-#ifdef HGFS_GETATTR_ONLY
/* Optional */
.getattr = HgfsGetattr,
-#else
- /* Optional */
- .revalidate = HgfsRevalidate,
-#endif
};
/* HGFS inode operations structure for files. */
.permission = HgfsPermission,
.setattr = HgfsSetattr,
-#ifdef HGFS_GETATTR_ONLY
/* Optional */
.getattr = HgfsGetattr,
-#else
- /* Optional */
- .revalidate = HgfsRevalidate,
-#endif
};
/*
*----------------------------------------------------------------------
*/
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 75)
static int
HgfsCreate(struct inode *dir, // IN: Parent dir to create in
struct dentry *dentry, // IN: Dentry containing name to create
int mode, // IN: Mode of file to be created
struct nameidata *nd) // IN: Intent, vfsmount, ...
-#else
-static int
-HgfsCreate(struct inode *dir, // IN: Parent dir to create in
- struct dentry *dentry, // IN: Dentry containing name to create
- int mode) // IN: Mode of file to be created
-#endif
{
HgfsAttrInfo attr;
int result;
*----------------------------------------------------------------------
*/
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 75)
static struct dentry *
HgfsLookup(struct inode *dir, // IN: Inode of parent directory
struct dentry *dentry, // IN: Dentry containing name to look up
- struct nameidata *nd) // IN: Intent, vfsmount, ...
-#else
-static struct dentry *
-HgfsLookup(struct inode *dir, // IN: Inode of parent directory
- struct dentry *dentry) // IN: Dentry containing name to look up
-#endif
+ struct nameidata *nd) // IN: Intent, vfsmount, ...
{
HgfsAttrInfo attr;
struct inode *inode;
*----------------------------------------------------------------------------
*/
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0)
static int
HgfsAccessInt(struct dentry *dentry, // IN: dentry to check access for
int mask) // IN: access mode requested.
}
return ret;
}
-#endif
/*
*----------------------------------------------------------------------
*/
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0) && \
- LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 27)
-static int
-HgfsPermission(struct inode *inode, int mask, struct nameidata *nd)
-#else
static int
-HgfsPermission(struct inode *inode, int mask)
+HgfsPermission(struct inode *inode,
+ int mask
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 27)
+ , struct nameidata *nd
#endif
+ )
{
LOG(8, ("VMware hgfs: %s: inode->mode: %8x mask: %8x\n", __func__,
inode->i_mode, mask));
/*
* For sys_access, we go to the host for permission checking;
* otherwise return 0.
- *
- * XXX When the kernel version is less than 2.6.0, we didn't have a good way
- * to tell whether this is for sys_access. Simply returning 0 is not what we
- * want. Need to fix it.
*/
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 0)
#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 27)
if (nd != NULL && (nd->flags & LOOKUP_ACCESS)) { /* For sys_access. */
#else
if (mask & MAY_ACCESS) { /* For sys_access. */
#endif
- struct dentry *dentry;
- dentry = list_entry(inode->i_dentry.next, struct dentry, d_alias);
+ struct dentry *dentry = list_entry(inode->i_dentry.next,
+ struct dentry, d_alias);
return HgfsAccessInt(dentry, mask & (MAY_READ | MAY_WRITE | MAY_EXEC));
}
-#endif
return 0;
}
-#ifdef HGFS_GETATTR_ONLY
/*
*-----------------------------------------------------------------------------
*
return 0;
}
-#endif
/*
* Public function implementations.
* Macros for accessing members that are private to this code in
* sb/inode/file structs.
*/
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 5, 42)
-#define HGFS_SET_SB_TO_COMMON(sb, common) do { (sb)->u.generic_sbp = (common); } while (0)
-#define HGFS_SB_TO_COMMON(sb) ((HgfsSuperInfo *)(sb)->u.generic_sbp)
-#else
#define HGFS_SET_SB_TO_COMMON(sb, common) do { (sb)->s_fs_info = (common); } while (0)
#define HGFS_SB_TO_COMMON(sb) ((HgfsSuperInfo *)(sb)->s_fs_info)
-#endif
-#ifdef VMW_EMBED_INODE
#define INODE_GET_II_P(_inode) container_of(_inode, HgfsInodeInfo, inode)
-#elif defined VMW_INODE_2618
-#define INODE_GET_II_P(inode) ((HgfsInodeInfo *)(inode)->i_private)
-#else
-#define INODE_GET_II_P(inode) ((HgfsInodeInfo *)(inode)->u.generic_ip)
-#endif
#if defined VMW_INODE_2618
#define INODE_SET_II_P(inode, info) do { (inode)->i_private = (info); } while (0)
#define INODE_SET_II_P(inode, info) do { (inode)->u.generic_ip = (info); } while (0)
#endif
-/* 2.5.x kernels support nanoseconds timestamps. */
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 5, 48)
-#define HGFS_DECLARE_TIME(unixtm) time_t unixtm
-#define HGFS_EQUAL_TIME(unixtm1, unixtm2) (unixtm1 == unixtm2)
-#define HGFS_SET_TIME(unixtm,nttime) HgfsConvertFromNtTime(&unixtm, nttime)
-#define HGFS_GET_TIME(unixtm) HgfsConvertToNtTime(unixtm, 0L)
-#define HGFS_GET_CURRENT_TIME() HgfsConvertToNtTime(CURRENT_TIME, 0L)
-/*
- * Beware! This macro returns list of two elements. Do not add braces around.
- */
-#define HGFS_PRINT_TIME(unixtm) unixtm, 0L
-#else
#define HGFS_DECLARE_TIME(unixtm) struct timespec unixtm
#define HGFS_EQUAL_TIME(unixtm1, unixtm2) timespec_equal(&unixtm1, &unixtm2)
#define HGFS_SET_TIME(unixtm,nttime) HgfsConvertFromNtTimeNsec(&unixtm, nttime)
* Beware! This macro returns list of two elements. Do not add braces around.
*/
#define HGFS_PRINT_TIME(unixtm) unixtm.tv_sec, unixtm.tv_nsec
-#endif
-
-/*
- * The writeback support we're using (set_page_dirty()) was added in
- * 2.5.12, so we only support writeback from then on.
- */
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 12)
-#define HGFS_ENABLE_WRITEBACK
-#endif
/*
* For files opened in our actual Host/Guest filesystem, the
* HGFS specific per-inode data.
*/
typedef struct HgfsInodeInfo {
-#ifdef VMW_EMBED_INODE
/* Embedded inode. */
struct inode inode;
-#endif
/* Inode number given by the host. */
uint64 hostFileId;
#include "compat_fs.h"
#include "compat_kernel.h"
#include "compat_pagemap.h"
-#ifdef HGFS_ENABLE_WRITEBACK
#include <linux/writeback.h>
-#endif
#include "cpName.h"
#include "hgfsProto.h"
/* HGFS address space operations. */
static int HgfsReadpage(struct file *file,
struct page *page);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 52)
static int HgfsWritepage(struct page *page,
struct writeback_control *wbc);
-#else
-static int HgfsWritepage(struct page *page);
-#endif
/*
* Write aop interface has changed in 2.6.28. Specifically,
.prepare_write = HgfsPrepareWrite,
.commit_write = HgfsCommitWrite,
#endif
-#ifdef HGFS_ENABLE_WRITEBACK
.set_page_dirty = __set_page_dirty_nobuffers,
-#endif
};
*-----------------------------------------------------------------------------
*/
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 5, 52)
static int
HgfsWritepage(struct page *page, // IN: Page to write from
struct writeback_control *wbc) // IN: Ignored
-#else
-static int
-HgfsWritepage(struct page *page) // IN: Page to write from
-#endif
{
struct inode *inode;
HgfsHandle handle;
unsigned pageFrom, // IN: Starting page offset
unsigned pageTo) // IN: Ending page offset
{
-#ifndef HGFS_ENABLE_WRITEBACK
- ASSERT(page);
-#else
loff_t offset;
loff_t currentFileSize;
kunmap_atomic(kaddr, KM_USER0);
flush_dcache_page(page);
}
-#endif
}
{
HgfsDoWriteBegin(page, pageFrom, pageTo);
- /*
- * Prior to 2.4.10, our caller expected to call page_address(page) between
- * the calls to prepare_write() and commit_write(). This meant filesystems
- * had to kmap() the page in prepare_write() and kunmap() it in
- * commit_write(). In 2.4.10, the call to page_address() was replaced with
- * __copy_to_user(), and while its not clear to me why this is safer,
- * nfs_prepare_write() dropped the kmap()/kunmap() calls in the same patch,
- * so the two events must be related.
- */
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 4, 10)
- kmap(page);
-#endif
return 0;
}
currentFileSize = compat_i_size_read(inode);
offset = (loff_t)page->index << PAGE_CACHE_SHIFT;
- /* See comment in HgfsPrepareWrite. */
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 4, 10)
- kunmap(page);
-#endif
-
if (writeTo > currentFileSize) {
compat_i_size_write(inode, writeTo);
}
SetPageUptodate(page);
}
-#ifdef HGFS_ENABLE_WRITEBACK
/*
* Check if this is a partial write to a new page, which was
* initialized in HgfsDoWriteBegin.
set_page_dirty(page);
return 0;
}
-#endif
+
/*
* We've recieved a partial write to page that is not uptodate, so
* do the write now while the page is still locked. Another
/* Hgfs filesystem superblock operations */
-#ifdef VMW_EMBED_INODE
static struct inode *HgfsAllocInode(struct super_block *sb);
static void HgfsDestroyInode(struct inode *inode);
-#endif
-#ifndef VMW_USE_IGET_LOCKED
-static void HgfsReadInode(struct inode *inode);
-#endif
-static void HgfsClearInode(struct inode *inode);
static void HgfsPutSuper(struct super_block *sb);
#if defined VMW_STATFS_2618
static int HgfsStatfs(struct dentry *dentry,
#endif
struct super_operations HgfsSuperOperations = {
-#ifdef VMW_EMBED_INODE
.alloc_inode = HgfsAllocInode,
.destroy_inode = HgfsDestroyInode,
-#endif
-#ifndef VMW_USE_IGET_LOCKED
- .read_inode = HgfsReadInode,
-#endif
- .clear_inode = HgfsClearInode,
.put_super = HgfsPutSuper,
.statfs = HgfsStatfs,
};
-#ifdef VMW_EMBED_INODE
/*
*-----------------------------------------------------------------------------
*
kmem_cache_free(hgfsInodeCache, INODE_GET_II_P(inode));
}
-#endif
-
-
-#ifndef VMW_USE_IGET_LOCKED
-/*
- *-----------------------------------------------------------------------------
- *
- * HgfsReadInode --
- *
- * Hgfs superblock 'read_inode' method. Called by the kernel to fill in a
- * VFS inode, given its hgfs inode number. Needed by iget().
- *
- * Results:
- * None
- *
- * Side effects:
- * None
- *
- *-----------------------------------------------------------------------------
- */
-
-static void
-HgfsReadInode(struct inode *inode) // IN/OUT: VFS inode to fill in
-{
- HgfsDoReadInode(inode);
-}
-#endif
-
-
-/*
- *-----------------------------------------------------------------------------
- *
- * HgfsClearInode --
- *
- * Hgfs superblock 'clear_inode' method. Called by the kernel when it is
- * about to destroy a VFS inode.
- *
- * Results:
- * None
- *
- * Side effects:
- * None
- *
- *-----------------------------------------------------------------------------
- */
-
-static void
-HgfsClearInode(struct inode *inode) // IN: The VFS inode
-{
-#ifdef VMW_EMBED_INODE
- /* Do nothing. HgfsDestroyInode will do the dirty work. */
-#else
- HgfsInodeInfo *iinfo;
-
- ASSERT(inode);
-
- /* The HGFS inode information may be partially constructed --hpreg */
- iinfo = INODE_GET_II_P(inode);
- if (iinfo) {
- kmem_cache_free(hgfsInodeCache, iinfo);
- }
-#endif
-}
/*
*-----------------------------------------------------------------------------