patch-2.4.0-test3 linux/fs/ncpfs/file.c

Next file: linux/fs/ncpfs/inode.c
Previous file: linux/fs/ncpfs/dir.c
Back to the patch index
Back to the overall index

diff -u --recursive --new-file v2.4.0-test2/linux/fs/ncpfs/file.c linux/fs/ncpfs/file.c
@@ -17,6 +17,7 @@
 #include <linux/mm.h>
 #include <linux/locks.h>
 #include <linux/malloc.h>
+#include <linux/vmalloc.h>
 
 #include <linux/ncp_fs.h>
 #include "ncplib_kernel.h"
@@ -26,7 +27,7 @@
 	return a < b ? a : b;
 }
 
-static int ncp_fsync(struct file *file, struct dentry *dentry)
+static int ncp_fsync(struct file *file, struct dentry *dentry, int datasync)
 {
 	return 0;
 }
@@ -46,12 +47,12 @@
 	}
 
 	DPRINTK("ncp_make_open: opened=%d, volume # %u, dir entry # %u\n",
-		NCP_FINFO(inode)->opened, 
+		atomic_read(&NCP_FINFO(inode)->opened), 
 		NCP_FINFO(inode)->volNumber, 
 		NCP_FINFO(inode)->dirEntNum);
 	error = -EACCES;
-	lock_super(inode->i_sb);
-	if (!NCP_FINFO(inode)->opened) {
+	down(&NCP_FINFO(inode)->open_sem);
+	if (!atomic_read(&NCP_FINFO(inode)->opened)) {
 		struct ncp_entry_info finfo;
 		int result;
 
@@ -88,15 +89,18 @@
 		 */
 	update:
 		ncp_update_inode(inode, &finfo);
+		atomic_set(&NCP_FINFO(inode)->opened, 1);
 	}
 
 	access = NCP_FINFO(inode)->access;
 	PPRINTK("ncp_make_open: file open, access=%x\n", access);
-	if (access == right || access == O_RDWR)
+	if (access == right || access == O_RDWR) {
+		atomic_inc(&NCP_FINFO(inode)->opened);
 		error = 0;
+	}
 
 out_unlock:
-	unlock_super(inode->i_sb);
+	up(&NCP_FINFO(inode)->open_sem);
 out:
 	return error;
 }
@@ -151,9 +155,9 @@
 
 	error = -EIO;
 	freelen = ncp_read_bounce_size(bufsize);
-	freepage = kmalloc(freelen, GFP_NFS);
+	freepage = vmalloc(freelen);
 	if (!freepage)
-		goto out;
+		goto outrel;
 	error = 0;
 	/* First read in as much as possible for each bufsize. */
 	while (already_read < count) {
@@ -166,9 +170,8 @@
 				pos, to_read, buf, &read_this_time, 
 				freepage, freelen);
 		if (error) {
-			kfree(freepage);
-			error = -EIO;	/* This is not exact, i know.. */
-			goto out;
+			error = -EIO;	/* NW errno -> Linux errno */
+			break;
 		}
 		pos += read_this_time;
 		buf += read_this_time;
@@ -178,7 +181,7 @@
 			break;
 		}
 	}
-	kfree(freepage);
+	vfree(freepage);
 
 	*ppos = pos;
 
@@ -188,6 +191,8 @@
 	
 	DPRINTK("ncp_file_read: exit %s/%s\n",
 		dentry->d_parent->d_name.name, dentry->d_name.name);
+outrel:
+	ncp_inode_close(inode);		
 out:
 	return already_read ? already_read : error;
 }
@@ -235,9 +240,11 @@
 
 	already_written = 0;
 
-	bouncebuffer = kmalloc(bufsize, GFP_NFS);
-	if (!bouncebuffer)
-		return -EIO;	/* -ENOMEM */
+	bouncebuffer = vmalloc(bufsize);
+	if (!bouncebuffer) {
+		errno = -EIO;	/* -ENOMEM */
+		goto outrel;
+	}
 	while (already_written < count) {
 		int written_this_time;
 		size_t to_write = min(bufsize - (pos % bufsize),
@@ -261,7 +268,7 @@
 			break;
 		}
 	}
-	kfree(bouncebuffer);
+	vfree(bouncebuffer);
 	inode->i_mtime = inode->i_atime = CURRENT_TIME;
 	
 	*ppos = pos;
@@ -271,15 +278,15 @@
 	}
 	DPRINTK("ncp_file_write: exit %s/%s\n",
 		dentry->d_parent->d_name.name, dentry->d_name.name);
+outrel:
+	ncp_inode_close(inode);		
 out:
 	return already_written ? already_written : errno;
 }
 
 static int ncp_release(struct inode *inode, struct file *file) {
-	if (NCP_FINFO(inode)->opened) {
-		if (ncp_make_closed(inode)) {
-			DPRINTK("ncp_release: failed to close\n");
-		}
+	if (ncp_make_closed(inode)) {
+		DPRINTK("ncp_release: failed to close\n");
 	}
 	return 0;
 }

FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)