aboutsummaryrefslogtreecommitdiffstats
path: root/fs/fuse/fuse_i.h
diff options
context:
space:
mode:
Diffstat (limited to 'fs/fuse/fuse_i.h')
-rw-r--r--fs/fuse/fuse_i.h223
1 files changed, 223 insertions, 0 deletions
diff --git a/fs/fuse/fuse_i.h b/fs/fuse/fuse_i.h
index eed6e89ce01f..50ad6a0c39bf 100644
--- a/fs/fuse/fuse_i.h
+++ b/fs/fuse/fuse_i.h
@@ -15,6 +15,12 @@
15#include <linux/backing-dev.h> 15#include <linux/backing-dev.h>
16#include <asm/semaphore.h> 16#include <asm/semaphore.h>
17 17
18/** Max number of pages that can be used in a single read request */
19#define FUSE_MAX_PAGES_PER_REQ 32
20
21/** If more requests are outstanding, then the operation will block */
22#define FUSE_MAX_OUTSTANDING 10
23
18/** FUSE inode */ 24/** FUSE inode */
19struct fuse_inode { 25struct fuse_inode {
20 /** Inode data */ 26 /** Inode data */
@@ -28,6 +34,123 @@ struct fuse_inode {
28 unsigned long i_time; 34 unsigned long i_time;
29}; 35};
30 36
37/** One input argument of a request */
38struct fuse_in_arg {
39 unsigned size;
40 const void *value;
41};
42
43/** The request input */
44struct fuse_in {
45 /** The request header */
46 struct fuse_in_header h;
47
48 /** True if the data for the last argument is in req->pages */
49 unsigned argpages:1;
50
51 /** Number of arguments */
52 unsigned numargs;
53
54 /** Array of arguments */
55 struct fuse_in_arg args[3];
56};
57
58/** One output argument of a request */
59struct fuse_arg {
60 unsigned size;
61 void *value;
62};
63
64/** The request output */
65struct fuse_out {
66 /** Header returned from userspace */
67 struct fuse_out_header h;
68
69 /** Last argument is variable length (can be shorter than
70 arg->size) */
71 unsigned argvar:1;
72
73 /** Last argument is a list of pages to copy data to */
74 unsigned argpages:1;
75
76 /** Zero partially or not copied pages */
77 unsigned page_zeroing:1;
78
79 /** Number or arguments */
80 unsigned numargs;
81
82 /** Array of arguments */
83 struct fuse_arg args[3];
84};
85
86struct fuse_req;
87struct fuse_conn;
88
89/**
90 * A request to the client
91 */
92struct fuse_req {
93 /** This can be on either unused_list, pending or processing
94 lists in fuse_conn */
95 struct list_head list;
96
97 /** refcount */
98 atomic_t count;
99
100 /** True if the request has reply */
101 unsigned isreply:1;
102
103 /** The request is preallocated */
104 unsigned preallocated:1;
105
106 /** The request was interrupted */
107 unsigned interrupted:1;
108
109 /** Request is sent in the background */
110 unsigned background:1;
111
112 /** Data is being copied to/from the request */
113 unsigned locked:1;
114
115 /** Request has been sent to userspace */
116 unsigned sent:1;
117
118 /** The request is finished */
119 unsigned finished:1;
120
121 /** The request input */
122 struct fuse_in in;
123
124 /** The request output */
125 struct fuse_out out;
126
127 /** Used to wake up the task waiting for completion of request*/
128 wait_queue_head_t waitq;
129
130 /** Data for asynchronous requests */
131 union {
132 struct fuse_init_in_out init_in_out;
133 } misc;
134
135 /** page vector */
136 struct page *pages[FUSE_MAX_PAGES_PER_REQ];
137
138 /** number of pages in vector */
139 unsigned num_pages;
140
141 /** offset of data on first page */
142 unsigned page_offset;
143
144 /** Inode used in the request */
145 struct inode *inode;
146
147 /** Second inode used in the request (or NULL) */
148 struct inode *inode2;
149
150 /** File used in the request (or NULL) */
151 struct file *file;
152};
153
31/** 154/**
32 * A Fuse connection. 155 * A Fuse connection.
33 * 156 *
@@ -39,9 +162,37 @@ struct fuse_conn {
39 /** The superblock of the mounted filesystem */ 162 /** The superblock of the mounted filesystem */
40 struct super_block *sb; 163 struct super_block *sb;
41 164
165 /** The opened client device */
166 struct file *file;
167
42 /** The user id for this mount */ 168 /** The user id for this mount */
43 uid_t user_id; 169 uid_t user_id;
44 170
171 /** Readers of the connection are waiting on this */
172 wait_queue_head_t waitq;
173
174 /** The list of pending requests */
175 struct list_head pending;
176
177 /** The list of requests being processed */
178 struct list_head processing;
179
180 /** Controls the maximum number of outstanding requests */
181 struct semaphore outstanding_sem;
182
183 /** This counts the number of outstanding requests if
184 outstanding_sem would go negative */
185 unsigned outstanding_debt;
186
187 /** The list of unused requests */
188 struct list_head unused_list;
189
190 /** The next unique request id */
191 u64 reqctr;
192
193 /** Connection failed (version mismatch) */
194 unsigned conn_error : 1;
195
45 /** Backing dev info */ 196 /** Backing dev info */
46 struct backing_dev_info bdi; 197 struct backing_dev_info bdi;
47}; 198};
@@ -71,13 +222,20 @@ static inline u64 get_node_id(struct inode *inode)
71 return get_fuse_inode(inode)->nodeid; 222 return get_fuse_inode(inode)->nodeid;
72} 223}
73 224
225/** Device operations */
226extern struct file_operations fuse_dev_operations;
227
74/** 228/**
75 * This is the single global spinlock which protects FUSE's structures 229 * This is the single global spinlock which protects FUSE's structures
76 * 230 *
77 * The following data is protected by this lock: 231 * The following data is protected by this lock:
78 * 232 *
233 * - the private_data field of the device file
79 * - the s_fs_info field of the super block 234 * - the s_fs_info field of the super block
235 * - unused_list, pending, processing lists in fuse_conn
236 * - the unique request ID counter reqctr in fuse_conn
80 * - the sb (super_block) field in fuse_conn 237 * - the sb (super_block) field in fuse_conn
238 * - the file (device file) field in fuse_conn
81 */ 239 */
82extern spinlock_t fuse_lock; 240extern spinlock_t fuse_lock;
83 241
@@ -87,3 +245,68 @@ extern spinlock_t fuse_lock;
87 */ 245 */
88void fuse_release_conn(struct fuse_conn *fc); 246void fuse_release_conn(struct fuse_conn *fc);
89 247
248/**
249 * Initialize the client device
250 */
251int fuse_dev_init(void);
252
253/**
254 * Cleanup the client device
255 */
256void fuse_dev_cleanup(void);
257
258/**
259 * Allocate a request
260 */
261struct fuse_req *fuse_request_alloc(void);
262
263/**
264 * Free a request
265 */
266void fuse_request_free(struct fuse_req *req);
267
268/**
269 * Reinitialize a request, the preallocated flag is left unmodified
270 */
271void fuse_reset_request(struct fuse_req *req);
272
273/**
274 * Reserve a preallocated request
275 */
276struct fuse_req *fuse_get_request(struct fuse_conn *fc);
277
278/**
279 * Reserve a preallocated request, only interruptible by SIGKILL
280 */
281struct fuse_req *fuse_get_request_nonint(struct fuse_conn *fc);
282
283/**
284 * Decrement reference count of a request. If count goes to zero put
285 * on unused list (preallocated) or free reqest (not preallocated).
286 */
287void fuse_put_request(struct fuse_conn *fc, struct fuse_req *req);
288
289/**
290 * Send a request (synchronous, interruptible)
291 */
292void request_send(struct fuse_conn *fc, struct fuse_req *req);
293
294/**
295 * Send a request (synchronous, non-interruptible except by SIGKILL)
296 */
297void request_send_nonint(struct fuse_conn *fc, struct fuse_req *req);
298
299/**
300 * Send a request with no reply
301 */
302void request_send_noreply(struct fuse_conn *fc, struct fuse_req *req);
303
304/**
305 * Send a request in the background
306 */
307void request_send_background(struct fuse_conn *fc, struct fuse_req *req);
308
309/**
310 * Send the INIT message
311 */
312void fuse_send_init(struct fuse_conn *fc);