From 3b9efe808de75ef53254ff85a9daae9b4e0aa52d Mon Sep 17 00:00:00 2001
From: Florian Fainelli <florian@openwrt.org>
Date: Sun, 16 Mar 2008 20:32:45 +0000
Subject: [PATCH] Fix compilation of fuse with 2.6.24

SVN-Revision: 10609
---
 package/fuse/patches/300-2.6.24_fixes.patch | 246 ++++++++++++++++++++
 1 file changed, 246 insertions(+)
 create mode 100644 package/fuse/patches/300-2.6.24_fixes.patch

diff --git a/package/fuse/patches/300-2.6.24_fixes.patch b/package/fuse/patches/300-2.6.24_fixes.patch
new file mode 100644
index 0000000000..e8f761e371
--- /dev/null
+++ b/package/fuse/patches/300-2.6.24_fixes.patch
@@ -0,0 +1,246 @@
+# HG changeset patch
+# User mszeredi
+# Date 1197485983 0
+# Node ID 5b8914cfe0fb7ccfb6e7f61512374d8541f2a193
+# Parent 81a85541800582144b7381e0b022c10245facc61
+Fix kernel module compile for 2.6.24
+
+--- a/kernel/dir.c	Wed Dec 12 14:33:17 2007 +0000
++++ b/kernel/dir.c	Wed Dec 12 18:59:43 2007 +0000
+@@ -191,7 +191,7 @@ static int invalid_nodeid(u64 nodeid)
+ 	return !nodeid || nodeid == FUSE_ROOT_ID;
+ }
+ 
+-static struct dentry_operations fuse_dentry_operations = {
++struct dentry_operations fuse_dentry_operations = {
+ 	.d_revalidate	= fuse_dentry_revalidate,
+ };
+ 
+@@ -378,6 +378,7 @@ static int fuse_create_open(struct inode
+ 	}
+ 	fuse_put_request(fc, forget_req);
+ 	d_instantiate(entry, inode);
++	fuse_invalidate_attr(dir);
+ 	fuse_change_timeout(entry, &outentry);
+ 	file = lookup_instantiate_filp(nd, entry, generic_file_open);
+ 	if (IS_ERR(file)) {
+@@ -619,6 +620,9 @@ static int fuse_rename(struct inode *old
+ 	err = req->out.h.error;
+ 	fuse_put_request(fc, req);
+ 	if (!err) {
++		/* ctime changes */
++		fuse_invalidate_attr(oldent->d_inode);
++
+ 		fuse_invalidate_attr(olddir);
+ 		if (olddir != newdir)
+ 			fuse_invalidate_attr(newdir);
+--- a/kernel/fuse_i.h	Wed Dec 12 14:33:17 2007 +0000
++++ b/kernel/fuse_i.h	Wed Dec 12 18:59:43 2007 +0000
+@@ -47,6 +47,9 @@
+ #endif
+ #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,23)
+ #  define KERNEL_2_6_23_PLUS
++#endif
++#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,24)
++#  define KERNEL_2_6_24_PLUS
+ #endif
+ 
+ #if defined(__arm__) && LINUX_VERSION_CODE < KERNEL_VERSION(2,6,20)
+@@ -647,3 +650,5 @@ int fuse_valid_type(int m);
+  * Is task allowed to perform filesystem operation?
+  */
+ int fuse_allow_task(struct fuse_conn *fc, struct task_struct *task);
++
++extern struct dentry_operations fuse_dentry_operations;
+--- a/kernel/inode.c	Wed Dec 12 14:33:17 2007 +0000
++++ b/kernel/inode.c	Wed Dec 12 18:59:43 2007 +0000
+@@ -520,21 +520,26 @@ static struct inode *get_root_inode(stru
+ #ifdef HAVE_EXPORTFS_H
+ #include <linux/exportfs.h>
+ #endif
+-static struct dentry *fuse_get_dentry(struct super_block *sb, void *vobjp)
++
++struct fuse_inode_handle
+ {
+-	__u32 *objp = vobjp;
+-	unsigned long nodeid = objp[0];
+-	__u32 generation = objp[1];
++	u64 nodeid;
++	u32 generation;
++};
++
++static struct dentry *fuse_get_dentry(struct super_block *sb,
++				      struct fuse_inode_handle *handle)
++{
+ 	struct inode *inode;
+ 	struct dentry *entry;
+ 
+-	if (nodeid == 0)
++	if (handle->nodeid == 0)
+ 		return ERR_PTR(-ESTALE);
+ 
+-	inode = ilookup5(sb, nodeid, fuse_inode_eq, &nodeid);
++	inode = ilookup5(sb, handle->nodeid, fuse_inode_eq, &handle->nodeid);
+ 	if (!inode)
+ 		return ERR_PTR(-ESTALE);
+-	if (inode->i_generation != generation) {
++	if (inode->i_generation != handle->generation) {
+ 		iput(inode);
+ 		return ERR_PTR(-ESTALE);
+ 	}
+@@ -544,42 +549,130 @@ static struct dentry *fuse_get_dentry(st
+ 		iput(inode);
+ 		return ERR_PTR(-ENOMEM);
+ 	}
++	entry->d_op = &fuse_dentry_operations;
+ 
+ 	return entry;
+ }
+ 
+-static int fuse_encode_fh(struct dentry *dentry, __u32 *fh, int *max_len,
+-			  int connectable)
++static int fuse_encode_fh(struct dentry *dentry, u32 *fh, int *max_len,
++			   int connectable)
+ {
+ 	struct inode *inode = dentry->d_inode;
+ 	int len = *max_len;
+ 	int type = 1;
++	u64 nodeid;
++	u32 generation;
+ 
+-	if (len < 2 || (connectable && len < 4))
+-		return 255;
++	if (len < 3 || (connectable && len < 6))
++		return  255;
+ 
+-	len = 2;
+-	fh[0] = get_fuse_inode(inode)->nodeid;
+-	fh[1] = inode->i_generation;
++	nodeid = get_fuse_inode(inode)->nodeid;
++	generation = inode->i_generation;
++
++	len = 3;
++	fh[0] = (u32)(nodeid >> 32);
++	fh[1] = (u32)(nodeid & 0xffffffff);
++	fh[2] = generation;
++
+ 	if (connectable && !S_ISDIR(inode->i_mode)) {
+ 		struct inode *parent;
+ 
+ 		spin_lock(&dentry->d_lock);
+ 		parent = dentry->d_parent->d_inode;
+-		fh[2] = get_fuse_inode(parent)->nodeid;
+-		fh[3] = parent->i_generation;
++		nodeid = get_fuse_inode(parent)->nodeid;
++		generation = parent->i_generation;
++
++		fh[3] = (u32)(nodeid >> 32);
++		fh[4] = (u32)(nodeid & 0xffffffff);
++		fh[5] = generation;
+ 		spin_unlock(&dentry->d_lock);
+-		len = 4;
++
++		len = 6;
+ 		type = 2;
+ 	}
++
+ 	*max_len = len;
+ 	return type;
+ }
+ 
++#ifdef KERNEL_2_6_24_PLUS
++static struct dentry *fuse_fh_to_dentry(struct super_block *sb,
++		struct fid *fid, int fh_len, int fh_type)
++{
++	struct fuse_inode_handle handle;
++
++	if (fh_len < 3 || fh_type > 2)
++		return NULL;
++
++	handle.nodeid = (u64) fid->raw[0] << 32;
++	handle.nodeid |= (u64) fid->raw[1];
++	handle.generation = fid->raw[2];
++	return fuse_get_dentry(sb, &handle);
++}
++
++static struct dentry *fuse_fh_to_parent(struct super_block *sb,
++		struct fid *fid, int fh_len, int fh_type)
++{
++	struct fuse_inode_handle parent;
++
++	if (fh_type != 2 || fh_len < 6)
++		return NULL;
++
++	parent.nodeid = (u64) fid->raw[3] << 32;
++	parent.nodeid |= (u64) fid->raw[4];
++	parent.generation = fid->raw[5];
++	return fuse_get_dentry(sb, &parent);
++}
++
++
++static const struct export_operations fuse_export_operations = {
++	.fh_to_dentry	= fuse_fh_to_dentry,
++	.fh_to_parent	= fuse_fh_to_parent,
++	.encode_fh	= fuse_encode_fh,
++};
++#else
++static struct dentry *fuse_get_dentry_old(struct super_block *sb, void *objp)
++{
++	return fuse_get_dentry(sb, objp);
++}
++
++static struct dentry *fuse_decode_fh(struct super_block *sb, u32 *fh,
++			int fh_len, int fileid_type,
++			int (*acceptable)(void *context, struct dentry *de),
++			void *context)
++{
++	struct fuse_inode_handle handle;
++	struct fuse_inode_handle parent;
++
++	if (fh_len < 3 || fileid_type > 2)
++		return NULL;
++
++	if (fileid_type == 2) {
++		if (fh_len < 6)
++			return NULL;
++
++		parent.nodeid = (u64) fh[3] << 32;
++		parent.nodeid |= (u64) fh[4];
++		parent.generation = fh[5];
++	} else {
++		parent.nodeid = 0;
++		parent.generation = 0;
++	}
++
++	handle.nodeid = (u64) fh[0] << 32;
++	handle.nodeid |= (u64) fh[1];
++	handle.generation = fh[2];
++
++	return ret = fuse_export_operations.
++		find_exported_dentry(sb, &handle, &parent, acceptable, context);
++}
++
+ static struct export_operations fuse_export_operations = {
+-	.get_dentry	= fuse_get_dentry,
++	.get_dentry	= fuse_get_dentry_old,
+ 	.encode_fh      = fuse_encode_fh,
++	.decode_fh	= fuse_decode_fh,
+ };
++#endif
+ #endif
+ 
+ static struct super_operations fuse_super_operations = {
+@@ -845,8 +938,12 @@ static decl_subsys(fuse, NULL, NULL);
+ static decl_subsys(fuse, NULL, NULL);
+ static decl_subsys(connections, NULL, NULL);
+ 
++#ifdef KERNEL_2_6_24_PLUS
++static void fuse_inode_init_once(struct kmem_cache *cachep, void *foo)
++#else
+ static void fuse_inode_init_once(void *foo, struct kmem_cache *cachep,
+ 				 unsigned long flags)
++#endif
+ {
+ 	struct inode * inode = foo;
+ 
+
-- 
GitLab