added flush() call
diff --git a/ChangeLog b/ChangeLog
index 5631b3c..c5c5a5a 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,7 @@
+2004-05-18  Miklos Szeredi <mszeredi@inf.bme.hu>
+
+	* Added flush() call
+	
 2004-05-04  Miklos Szeredi <mszeredi@inf.bme.hu>
 
 	* Extended attributes support for 2.4 (patch by Cody Pisto)
diff --git a/include/fuse.h b/include/fuse.h
index 1cb7bbf..3babaf6 100644
--- a/include/fuse.h
+++ b/include/fuse.h
@@ -86,15 +86,25 @@
  *  - release() is called when an open file has:
  *       1) all file descriptors closed
  *       2) all memory mappings unmapped
- *    For every open() call there will be exactly one release() call
- *    with the same flags.  It is possible to have a file opened more
- *    than once, in which case only the last release will mean, that
- *    no more reads/writes will happen on the file.  This call need
- *    only be implemented if this information is required, otherwise
- *    set this function to NULL.
+ *  For every open() call there will be exactly one release() call
+ *  with the same flags.  It is possible to have a file opened more
+ *  than once, in which case only the last release will mean, that no
+ *  more reads/writes will happen on the file.  The return value of
+ *  release is ignored.  This call need only be implemented if this
+ *  information is required, otherwise set this function to NULL.
+ * 
+ *  - flush() is called when close() has been called on an open file.
+ *  NOTE: this does not mean that the file is released (e.g. after
+ *  fork() an open file will have two references which both must be
+ *  closed before the file is released).  The flush() method can be
+ *  called more than once for each open().  The return value of
+ *  flush() is passed on to the close() system call.  Implementing
+ *  this call is optional.  If it is not needed by the filesystem,
+ *  then set the callback pointer to NULL.
  * 
  *  - fsync() has a boolean 'datasync' parameter which if TRUE then do
- * an fdatasync() operation.  */
+ *  an fdatasync() operation.  
+ */
 struct fuse_operations {
     int (*getattr)     (const char *, struct stat *);
     int (*readlink)    (const char *, char *, size_t);
@@ -114,6 +124,7 @@
     int (*read)        (const char *, char *, size_t, off_t);
     int (*write)       (const char *, const char *, size_t, off_t);
     int (*statfs)      (const char *, struct statfs *);
+    int (*flush)       (const char *);
     int (*release)     (const char *, int);
     int (*fsync)       (const char *, int);
     int (*setxattr)    (const char *, const char *, const char *, size_t, int);
diff --git a/include/linux/fuse.h b/include/linux/fuse.h
index 63cf167..027cb5e 100644
--- a/include/linux/fuse.h
+++ b/include/linux/fuse.h
@@ -82,6 +82,7 @@
 	FUSE_GETXATTR      = 22,
 	FUSE_LISTXATTR     = 23,
 	FUSE_REMOVEXATTR   = 24,
+	FUSE_FLUSH         = 25,
 };
 
 /* Conservative buffer size for the client */
diff --git a/kernel/file.c b/kernel/file.c
index 2c9473f..c9a44fd 100644
--- a/kernel/file.c
+++ b/kernel/file.c
@@ -92,6 +92,22 @@
 	return 0;
 }
 
+static int fuse_flush(struct file *file)
+{
+	struct inode *inode = file->f_dentry->d_inode;
+	struct fuse_conn *fc = INO_FC(inode);
+	struct fuse_in in = FUSE_IN_INIT;
+	struct fuse_out out = FUSE_OUT_INIT;
+	
+	in.h.opcode = FUSE_FLUSH;
+	in.h.ino = inode->i_ino;
+	request_send(fc, &in, &out);
+	if (out.h.error == -ENOSYS)
+		return 0;
+	else
+		return out.h.error;
+}
+
 static int fuse_fsync(struct file *file, struct dentry *de, int datasync)
 {
 	struct inode *inode = de->d_inode;
@@ -470,6 +486,7 @@
 	.write		= generic_file_write,
 	.mmap		= generic_file_mmap,
 	.open		= fuse_open,
+	.flush		= fuse_flush,
 	.release	= fuse_release,
 	.fsync		= fuse_fsync,
 #ifdef KERNEL_2_6
diff --git a/lib/fuse.c b/lib/fuse.c
index fddcc33..9f5e8a9 100644
--- a/lib/fuse.c
+++ b/lib/fuse.c
@@ -829,6 +829,22 @@
     }
 }
 
+static void do_flush(struct fuse *f, struct fuse_in_header *in)
+{
+    char *path;
+    int res;
+
+    res = -ENOENT;
+    path = get_path(f, in->ino);
+    if(path != NULL) {
+        res = -ENOSYS;
+        if(f->op.flush)
+            res = f->op.flush(path);
+        free(path);
+    }
+    send_reply(f, in, res, NULL, 0);
+}
+
 static void do_release(struct fuse *f, struct fuse_in_header *in,
                        struct fuse_open_in *arg)
 {
@@ -1215,6 +1231,10 @@
         do_open(f, in, (struct fuse_open_in *) inarg);
         break;
 
+    case FUSE_FLUSH:
+        do_flush(f, in);
+        break;
+
     case FUSE_RELEASE:
         do_release(f, in, (struct fuse_open_in *) inarg);
         break;