1// Copyright (c) 2013 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#ifndef LIBRARIES_NACL_IO_FUSE_H_
6#define LIBRARIES_NACL_IO_FUSE_H_
7
8#include "osinttypes.h"
9#include "ostypes.h"
10
11// These interfaces are copied from the FUSE library.
12//
13// FUSE has two interfaces that can be implemented: low-level and high-level.
14// In nacl_io, we only support the high-level interface.
15//
16// See http://fuse.sourceforge.net/ for more information.
17
18// This struct is typically passed to functions that would normally use return
19// or receive an fd; that is, operations to open/create a node, or operations
20// that act on an already opened node.
21struct fuse_file_info {
22  // This is filled with the flags passed to open()
23  int flags;
24  // Deprecated in FUSE. Use fh instead.
25  unsigned long fh_old;
26  int writepage;
27  // Currently unsupported
28  unsigned int direct_io : 1;
29  // Currently unsupported
30  unsigned int keep_cache : 1;
31  // Currently unsupported
32  unsigned int flush : 1;
33  // Currently unsupported
34  unsigned int nonseekable : 1;
35  // Currently unsupported
36  unsigned int padding : 27;
37  // This value is not used by nacl_io. It can be filled by the developer when
38  // open() is called, and reused for subsequent calls on the same node.
39  uint64_t fh;
40  // Currently unsupported
41  uint64_t lock_owner;
42  // Currently unsupported
43  uint32_t poll_events;
44};
45
46// A dummy structure that currently exists only to match the FUSE interface.
47struct fuse_conn_info {};
48
49// A function of this type will be passed to readdir (see below). The developer
50// should call this function once for each directory entry.
51//
52// See the documentation for readdir() below for more information on how to use
53// this function.
54typedef int (*fuse_fill_dir_t)(void* buf,
55                               const char* name,
56                               const struct stat* stbuf,
57                               off_t off);
58
59// This structure defines the interface to create a user filesystem. Pass this
60// to
61// nacl_io_register_fs_type(). (see nacl_io.h)
62//
63// Example:
64//
65//     struct fuse_operations g_my_fuse_operations = { ... };
66//     ...
67//     nacl_io_register_fs_type("myfusefs", &g_my_fuse_operations);
68//     ...
69//     mount("", "/fs/fuse", "myfusefs", 0, NULL);
70//
71// It is not necessary to implement every function -- nacl_io will first check
72// if the function pointer is NULL before calling it. If it is NULL and
73// required by the current operation, the call will fail and return ENOSYS in
74// errno.
75//
76// Except where specified below, each function should return one of the
77// following values:
78// == 0: operation completed successfully.
79// <  0: operation failed. The error is a negative errno. e.g. -EACCES, -EPERM,
80//       etc. The sign will be flipped when the error is actually set.
81//
82// Some functions (e.g. read, write) also return a positive count, which is the
83// number of bytes read/written.
84//
85struct fuse_operations {
86  // Currently unsupported
87  unsigned int flag_nopath : 1;
88  unsigned int flag_reserved : 31;
89
90  // Called by stat()/fstat(), but only when fuse_operations.fgetattr is NULL.
91  // Also called by open() to determine if the path is a directory or a regular
92  // file.
93  int (*getattr)(const char* path, struct stat*);
94  // Not called currently.
95  int (*readlink)(const char*, char*, size_t);
96  // Called when O_CREAT is passed to open(), but only if fuse_operations.create
97  // is non-NULL.
98  int (*mknod)(const char* path, mode_t, dev_t);
99  // Called by mkdir()
100  int (*mkdir)(const char* path, mode_t);
101  // Called by unlink()
102  int (*unlink)(const char* path);
103  // Called by rmdir()
104  int (*rmdir)(const char* path);
105  // Not called currently.
106  int (*symlink)(const char*, const char*);
107  // Called by rename()
108  int (*rename)(const char* path, const char* new_path);
109  // Not called currently.
110  int (*link)(const char*, const char*);
111  // Called by chmod()/fchmod()
112  int (*chmod)(const char*, mode_t);
113  // Not called currently.
114  int (*chown)(const char*, uid_t, gid_t);
115  // Called by truncate(), as well as open() when O_TRUNC is passed.
116  int (*truncate)(const char* path, off_t);
117  // Called by open()
118  int (*open)(const char* path, struct fuse_file_info*);
119  // Called by read(). Note that FUSE specifies that all reads will fill the
120  // entire requested buffer. If this function returns less than that, the
121  // remainder of the buffer is zeroed.
122  int (*read)(const char* path,
123              char* buf,
124              size_t count,
125              off_t,
126              struct fuse_file_info*);
127  // Called by write(). Note that FUSE specifies that a write should always
128  // return the full count, unless an error occurs.
129  int (*write)(const char* path,
130               const char* buf,
131               size_t count,
132               off_t,
133               struct fuse_file_info*);
134  // Not called currently.
135  int (*statfs)(const char*, struct statvfs*);
136  // Not called currently.
137  int (*flush)(const char*, struct fuse_file_info*);
138  // Called when the last reference to this node is released. This is only
139  // called for regular files. For directories, fuse_operations.releasedir is
140  // called instead.
141  int (*release)(const char* path, struct fuse_file_info*);
142  // Called by fsync(). The datasync paramater is not currently supported.
143  int (*fsync)(const char* path, int datasync, struct fuse_file_info*);
144  // Not called currently.
145  int (*setxattr)(const char*, const char*, const char*, size_t, int);
146  // Not called currently.
147  int (*getxattr)(const char*, const char*, char*, size_t);
148  // Not called currently.
149  int (*listxattr)(const char*, char*, size_t);
150  // Not called currently.
151  int (*removexattr)(const char*, const char*);
152  // Called by getdents(), which is called by the more standard functions
153  // opendir()/readdir().
154  int (*opendir)(const char* path, struct fuse_file_info*);
155  // Called by getdents(), which is called by the more standard function
156  // readdir().
157  //
158  // NOTE: it is the responsibility of this function to add the "." and ".."
159  // entries.
160  //
161  // This function can be implemented one of two ways:
162  // 1) Ignore the offset, and always write every entry in a given directory.
163  //    In this case, you should always call filler() with an offset of 0. You
164  //    can ignore the return value of the filler.
165  //
166  //   int my_readdir(const char* path, void* buf, fuse_fill_dir_t filler,
167  //                  off_t offset, struct fuse_file_info*) {
168  //     ...
169  //     filler(buf, ".", NULL, 0);
170  //     filler(buf, "..", NULL, 0);
171  //     filler(buf, "file1", &file1stat, 0);
172  //     filler(buf, "file2", &file2stat, 0);
173  //     return 0;
174  //   }
175  //
176  // 2) Only write entries starting from offset. Always pass the correct offset
177  //    to the filler function. When the filler function returns 1, the buffer
178  //    is full so you can exit readdir.
179  //
180  //   int my_readdir(const char* path, void* buf, fuse_fill_dir_t filler,
181  //                  off_t offset, struct fuse_file_info*) {
182  //     ...
183  //     size_t kNumEntries = 4;
184  //     const char* my_entries[] = { ".", "..", "file1", "file2" };
185  //     int entry_index = offset / sizeof(dirent);
186  //     offset = entry_index * sizeof(dirent);
187  //     while (entry_index < kNumEntries) {
188  //       int result = filler(buf, my_entries[entry_index], NULL, offset);
189  //       if (filler == 1) {
190  //         // buffer filled, we're done.
191  //         return 0;
192  //       }
193  //       offset += sizeof(dirent);
194  //       entry_index++;
195  //     }
196  //
197  //     // No more entries, we're done.
198  //     return 0;
199  //   }
200  //
201  int (*readdir)(const char* path,
202                 void* buf,
203                 fuse_fill_dir_t filldir,
204                 off_t,
205                 struct fuse_file_info*);
206  // Called when the last reference to this node is released. This is only
207  // called for directories. For regular files, fuse_operations.release is
208  // called instead.
209  int (*releasedir)(const char* path, struct fuse_file_info*);
210  // Not called currently.
211  int (*fsyncdir)(const char*, int, struct fuse_file_info*);
212  // Called when a filesystem of this type is initialized.
213  void* (*init)(struct fuse_conn_info* conn);
214  // Called when a filesystem of this type is unmounted.
215  void (*destroy)(void*);
216  // Called by access()
217  int (*access)(const char* path, int mode);
218  // Called when O_CREAT is passed to open()
219  int (*create)(const char* path, mode_t mode, struct fuse_file_info*);
220  // Called by ftruncate()
221  int (*ftruncate)(const char* path, off_t, struct fuse_file_info*);
222  // Called by stat()/fstat(). If this function pointer is non-NULL, it is
223  // called, otherwise fuse_operations.getattr will be called.
224  int (*fgetattr)(const char* path, struct stat*, struct fuse_file_info*);
225  // Not called currently.
226  int (*lock)(const char*, struct fuse_file_info*, int cmd, struct flock*);
227  // Called by utime()/utimes()/futimes()/futimens() etc.
228  int (*utimens)(const char*, const struct timespec tv[2]);
229  // Not called currently.
230  int (*bmap)(const char*, size_t blocksize, uint64_t* idx);
231  // Not called currently.
232  int (*ioctl)(const char*,
233               int cmd,
234               void* arg,
235               struct fuse_file_info*,
236               unsigned int flags,
237               void* data);
238  // Not called currently.
239  int (*poll)(const char*,
240              struct fuse_file_info*,
241              struct fuse_pollhandle* ph,
242              unsigned* reventsp);
243  // Not called currently.
244  int (*write_buf)(const char*,
245                   struct fuse_bufvec* buf,
246                   off_t off,
247                   struct fuse_file_info*);
248  // Not called currently.
249  int (*read_buf)(const char*,
250                  struct fuse_bufvec** bufp,
251                  size_t size,
252                  off_t off,
253                  struct fuse_file_info*);
254  // Not called currently.
255  int (*flock)(const char*, struct fuse_file_info*, int op);
256  // Not called currently.
257  int (*fallocate)(const char*, int, off_t, off_t, struct fuse_file_info*);
258};
259
260#endif  // LIBRARIES_NACL_IO_FUSE_H_
261