|
[ source navigation ] [ diff markup ] [ identifier search ] [ general search ] |
|||
|
001 /* Copyright (C) 2005,2006 David Decotigny !! 001 /* Copyright (C) 2005 David Decotigny 002 Copyright (C) 2000-2005 The KOS Team (Thoma 002 Copyright (C) 2000-2005 The KOS Team (Thomas Petazzoni, David 003 Decotigny, Julien M 003 Decotigny, Julien Munier) 004 004 005 This program is free software; you can redi 005 This program is free software; you can redistribute it and/or 006 modify it under the terms of the GNU Genera 006 modify it under the terms of the GNU General Public License 007 as published by the Free Software Foundatio 007 as published by the Free Software Foundation; either version 2 008 of the License, or (at your option) any lat 008 of the License, or (at your option) any later version. 009 009 010 This program is distributed in the hope tha 010 This program is distributed in the hope that it will be useful, 011 but WITHOUT ANY WARRANTY; without even the 011 but WITHOUT ANY WARRANTY; without even the implied warranty of 012 MERCHANTABILITY or FITNESS FOR A PARTICULAR 012 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 013 GNU General Public License for more details 013 GNU General Public License for more details. 014 014 015 You should have received a copy of the GNU 015 You should have received a copy of the GNU General Public License 016 along with this program; if not, write to t 016 along with this program; if not, write to the Free Software 017 Foundation, Inc., 59 Temple Place - Suite 3 017 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, 018 USA. 018 USA. 019 */ 019 */ 020 #ifndef _SOS_FS_H_ 020 #ifndef _SOS_FS_H_ 021 #define _SOS_FS_H_ 021 #define _SOS_FS_H_ 022 022 023 023 024 /** 024 /** 025 * @file fs.h 025 * @file fs.h 026 * 026 * 027 * (Virtual) Filesystem management. 027 * (Virtual) Filesystem management. 028 * 028 * 029 * SOS provides a complete Unix-like file syst 029 * SOS provides a complete Unix-like file system service. Supported 030 * features of this service are: 030 * features of this service are: 031 * - mountpoints 031 * - mountpoints 032 * - generic file system support (FS) throug 032 * - generic file system support (FS) through object-oriented 033 * specialization (so-called VFS) 033 * specialization (so-called VFS) 034 * - hard & symbolic links 034 * - hard & symbolic links 035 * - regular files and directories 035 * - regular files and directories 036 * - block and character device special file 036 * - block and character device special files (from article 9 onward) 037 * - file mapping 037 * - file mapping 038 * - basic permission management ("rwx" only 038 * - basic permission management ("rwx" only, no notion of owner) 039 * - chroot 039 * - chroot 040 * - separation of disk node and namespace n 040 * - separation of disk node and namespace notions allowing hard links 041 * and to move/rename/remove files or dire 041 * and to move/rename/remove files or directories that are in use 042 * - basic FS interface (open/read/seek/crea 042 * - basic FS interface (open/read/seek/creat/mkdir/rename/link 043 * / symlink/chmod/mount/fcntl/ioctl...) 043 * / symlink/chmod/mount/fcntl/ioctl...) 044 * - deferred writes (ie file caching). @see 044 * - deferred writes (ie file caching). @see sync(3) 045 * 045 * 046 * Among the unsupported features: 046 * Among the unsupported features: 047 * - no user-based permission (uid/gid, ACLS 047 * - no user-based permission (uid/gid, ACLS) 048 * - no modification / access time accountin 048 * - no modification / access time accounting 049 * - no Fifo/socket special files (yet) 049 * - no Fifo/socket special files (yet) 050 * - no generic support library for common f 050 * - no generic support library for common fcntl commands 051 * (F_SETOWN/GETLEASE/NOTIFY, etc.) 051 * (F_SETOWN/GETLEASE/NOTIFY, etc.) 052 * - no flock-style functions 052 * - no flock-style functions 053 * 053 * 054 * Rationale 054 * Rationale 055 * ========= 055 * ========= 056 * The VFS layer is based on 3 central concept 056 * The VFS layer is based on 3 central concepts: 057 * 057 * 058 * - The meta-information for each file store !! 058 * - The meta-information for each file stored on disk (struct 059 * permissions, ... (struct sos_fs_node for !! 059 * sos_fs_node for SOS, inode for Unix) 060 * 060 * 061 * It is sufficient to know where this meta 061 * It is sufficient to know where this meta-information is located 062 * on disk (a simple sector number most of 062 * on disk (a simple sector number most of the time) to build the 063 * corresponding struct sos_fs_node into me 063 * corresponding struct sos_fs_node into memory and to retrieve the 064 * data of the file from the disk 064 * data of the file from the disk 065 * 065 * 066 * For example, consider that we know a sec 066 * For example, consider that we know a sector that holds the meta 067 * information is located at sector 64589 o !! 067 * information (ie size, permissions) is located at sector 64589 on 068 * this meta information directly from disk !! 068 * disk. By retrieving this meta information directly from disk, we 069 * struct sos_fs_node, which would (for exa !! 069 * can build the struct sos_fs_node, which would (for example) tell 070 * corresponding file spans (for example) o !! 070 * that the corresponding file spans (for example) over sectors 071 * 4539 and 6575, is 1.7kB long !! 071 * 4345, 5645, 4539 and 6575, is 1.7kB long 072 * 072 * 073 * Everything is stored this way on the dis 073 * Everything is stored this way on the disk, even the 074 * directories. From the disk contents' poi 074 * directories. From the disk contents' point of view, a directory 075 * is simply a file whose contents represen 075 * is simply a file whose contents represent a list of mappings 076 * "name" -> meta-information location 076 * "name" -> meta-information location 077 * 077 * 078 * - One or many nodes in the file hierarchy 078 * - One or many nodes in the file hierarchy pointing to this data 079 * (struct sos_fs_nscache_node for SOS, str 079 * (struct sos_fs_nscache_node for SOS, struct dentry for Linux). This 080 * tells that the entry "toto" in directory 080 * tells that the entry "toto" in directory "/home/zorglub" 081 * corresponds to the given struct sos_fs_n 081 * corresponds to the given struct sos_fs_node 082 * 082 * 083 * Actually, with the struct sos_fs_node ab 083 * Actually, with the struct sos_fs_node above, we can reach any 084 * file in the system. However, dealing wit 084 * file in the system. However, dealing with mountpoints requires 085 * an intermediary data structure because a 085 * an intermediary data structure because a directory on a disk 086 * cannot make reference to children struct 086 * cannot make reference to children struct sos_fs_node on other 087 * disk. This is one of the reasons why the 087 * disk. This is one of the reasons why there is this struct 088 * sos_fs_nscache_node. Another reason is t 088 * sos_fs_nscache_node. Another reason is that we kind-of "cache" the 089 * most used struct sos_fs_node: those that 089 * most used struct sos_fs_node: those that lead from the global 090 * root ("/") to the files and directories 090 * root ("/") to the files and directories currently being used 091 * (hence the name "nscache" for "namespace 091 * (hence the name "nscache" for "namespace cache"). This speeds-up 092 * the path-resolving process (aka "lookup" 092 * the path-resolving process (aka "lookup"), as the most-used path 093 * are already in-memory and the struct sos 093 * are already in-memory and the struct sos_fs_node are already 094 * in-memory too. 094 * in-memory too. 095 * 095 * 096 * A struct sos_fs_nscache_node can have at 096 * A struct sos_fs_nscache_node can have at most 1 parent (the ".." 097 * entry). It can also have 0 parent in cas 097 * entry). It can also have 0 parent in case the node is being used 098 * by a process (file is opened or mapped), 098 * by a process (file is opened or mapped), but the file is 099 * actually "removed", ie un-reachable from 099 * actually "removed", ie un-reachable from any directory. 100 * 100 * 101 * Many such structures can reference the s 101 * Many such structures can reference the same underlying struct 102 * sos_fs_node, which enables the support o 102 * sos_fs_node, which enables the support of "hard links". 103 * 103 * 104 * - The "opened file" strucures. They store 104 * - The "opened file" strucures. They store the information 105 * pertaining to a particular usage of a fi 105 * pertaining to a particular usage of a file. The most important 106 * thing they store is the "file pointer", 106 * thing they store is the "file pointer", which holds the 107 * location in the file where the next read 107 * location in the file where the next read/write operation should 108 * start 108 * start 109 * 109 * 110 * Each process has at least 2 such opened 110 * Each process has at least 2 such opened files: its "current 111 * working directory" (RTFM chdir) and its 111 * working directory" (RTFM chdir) and its "process root" (RTFM 112 * chroot). Those are heritated across fork 112 * chroot). Those are heritated across fork() and can be changed by 113 * appropriate syscalls (resp. chdir/chroot 113 * appropriate syscalls (resp. chdir/chroot). The main "root" of 114 * the system is the process root of the "i 114 * the system is the process root of the "init" process. The usual 115 * opened files (think of open() and opendi 115 * opened files (think of open() and opendir()) are stored in the 116 * file descriptor array (fds[]). This is t 116 * file descriptor array (fds[]). This is the index in this array 117 * that is commonly called a "file descript 117 * that is commonly called a "file descriptor". 118 * 118 * 119 * 119 * 120 * The whole VFS layer comprises a series of o 120 * The whole VFS layer comprises a series of objects that can be 121 * specialized to implement different FS suppo 121 * specialized to implement different FS support (fat, ext2, ffs, ...): 122 * 122 * 123 * - The notion of "file system manager", whi 123 * - The notion of "file system manager", which basically is a 124 * container to a FS name (eg "FAT", "EXT2" 124 * container to a FS name (eg "FAT", "EXT2", etc...) and a series of 125 * functions responsible for initializing a 125 * functions responsible for initializing a particular "mounting" of 126 * a FS (the "mount" method). This is SOS's 126 * a FS (the "mount" method). This is SOS's struct sos_fs_manager_type 127 * 127 * 128 * - The notion of "file system instance" whi 128 * - The notion of "file system instance" which contains the data 129 * proper to a particular mounting of an FS 129 * proper to a particular mounting of an FS. Its most important job 130 * is to allocate new struct sos_fs_node on 130 * is to allocate new struct sos_fs_node on disk, or to retrieve the 131 * meta-information (ie struct sos_fs_node) 131 * meta-information (ie struct sos_fs_node) located at the given 132 * location on disk. This is roughly THE pr 132 * location on disk. This is roughly THE primary physical interface 133 * between the VFS and the disks. This is S 133 * between the VFS and the disks. This is SOS's struct 134 * sos_fs_manager_instance, aka the Linux's 134 * sos_fs_manager_instance, aka the Linux's superblock 135 * 135 * 136 * For each struct sos_fs_node that it allo 136 * For each struct sos_fs_node that it allocates, or that is loads 137 * from disk into memory, this "instance ma 137 * from disk into memory, this "instance manager" is responsible 138 * for inidicating the functions that imple 138 * for inidicating the functions that implement the FS-dedicated 139 * routine such as read/write/mmap/ioctl/.. 139 * routine such as read/write/mmap/ioctl/... for this precise node. 140 * 140 * 141 * The nodes (struct sos_fs_node) of a stru 141 * The nodes (struct sos_fs_node) of a struct 142 * sos_fs_manager_instance that are current 142 * sos_fs_manager_instance that are currently loaded in memory are 143 * stored in a hash-table. The key of this 143 * stored in a hash-table. The key of this map is the location of the 144 * meta-information on disk. That way, it i 144 * meta-information on disk. That way, it is very fast to look for 145 * the given meta-information whose locatio 145 * the given meta-information whose location on disk is knows: if 146 * it has already been loaded into memory, 146 * it has already been loaded into memory, its memory address is 147 * quickly resolved thanks to this hash tab 147 * quickly resolved thanks to this hash table. 148 */ 148 */ 149 149 150 #include <sos/types.h> 150 #include <sos/types.h> 151 #include <sos/errno.h> 151 #include <sos/errno.h> 152 #include <sos/hash.h> 152 #include <sos/hash.h> 153 #include <sos/umem_vmm.h> 153 #include <sos/umem_vmm.h> 154 154 155 /* Forward declarations (structures defined in 155 /* Forward declarations (structures defined in this file) */ 156 struct sos_fs_manager_type; 156 struct sos_fs_manager_type; 157 struct sos_fs_manager_instance; 157 struct sos_fs_manager_instance; 158 struct sos_fs_statfs; 158 struct sos_fs_statfs; 159 struct sos_fs_node; 159 struct sos_fs_node; 160 struct sos_fs_opened_file; 160 struct sos_fs_opened_file; 161 struct sos_fs_stat; 161 struct sos_fs_stat; 162 162 163 #include "fs_nscache.h" 163 #include "fs_nscache.h" 164 #include <sos/blkdev.h> << 165 164 166 /** 165 /** 167 * The type of filesystem object. 166 * The type of filesystem object. 168 * 167 * 169 * Each struct sos_fs_node has a type. Here ar 168 * Each struct sos_fs_node has a type. Here are the supported types. 170 */ 169 */ 171 typedef enum { 170 typedef enum { 172 SOS_FS_NODE_REGULAR_FILE = 0x42, 171 SOS_FS_NODE_REGULAR_FILE = 0x42, 173 SOS_FS_NODE_DIRECTORY = 0x24, 172 SOS_FS_NODE_DIRECTORY = 0x24, 174 SOS_FS_NODE_SYMLINK = 0x84, 173 SOS_FS_NODE_SYMLINK = 0x84, 175 SOS_FS_NODE_DEVICE_CHAR = 0x48, << 176 SOS_FS_NODE_DEVICE_BLOCK = 0x12 << 177 } sos_fs_node_type_t; 174 } sos_fs_node_type_t; 178 175 179 176 180 #define SOS_FS_MANAGER_NAME_MAXLEN 32 177 #define SOS_FS_MANAGER_NAME_MAXLEN 32 181 /** 178 /** 182 * Description of a supported Filesystem type. 179 * Description of a supported Filesystem type. 183 * 180 * 184 * These descriptions are listed in an interna 181 * These descriptions are listed in an internal list (see 185 * fs.c:fs_list), and each time we want to mou 182 * fs.c:fs_list), and each time we want to mount a FS, we precise a 186 * name (eg "FAT", "EXT2", ...). The VFS will 183 * name (eg "FAT", "EXT2", ...). The VFS will look for this name into 187 * the list of supported filesystem types, and 184 * the list of supported filesystem types, and, when found, call its 188 * sos_fs_manager_type::mount() method. 185 * sos_fs_manager_type::mount() method. 189 * 186 * 190 * New filesystem types are registered using s 187 * New filesystem types are registered using sos_fs_register_fs_type() 191 */ 188 */ 192 struct sos_fs_manager_type 189 struct sos_fs_manager_type 193 { 190 { 194 char name[SOS_FS_MANAGER_NAME_MAXLEN]; 191 char name[SOS_FS_MANAGER_NAME_MAXLEN]; 195 192 196 /** 193 /** 197 * Responsible for making sure the underlyin 194 * Responsible for making sure the underlying device (if any) really 198 * stores the correct filesystem format, for 195 * stores the correct filesystem format, for creating the hash of fs 199 * nodes and for calling sos_fs_register_fs_ 196 * nodes and for calling sos_fs_register_fs_instance 200 * 197 * 201 * @param device May be NULL 198 * @param device May be NULL 202 * 199 * 203 * @note mandatory, may block 200 * @note mandatory, may block 204 */ 201 */ 205 sos_ret_t (*mount)(struct sos_fs_manager_typ 202 sos_ret_t (*mount)(struct sos_fs_manager_type * this, 206 struct sos_fs_node * devi 203 struct sos_fs_node * device, 207 const char * args, 204 const char * args, 208 struct sos_fs_manager_ins 205 struct sos_fs_manager_instance ** mounted_fs); 209 206 210 /** 207 /** 211 * Responsible for de-allocating the hash of 208 * Responsible for de-allocating the hash of fs nodes and for 212 * calling sos_fs_unregister_fs_instance 209 * calling sos_fs_unregister_fs_instance 213 * 210 * 214 * @note mandatory, may block 211 * @note mandatory, may block 215 */ 212 */ 216 sos_ret_t (*umount)(struct sos_fs_manager_ty 213 sos_ret_t (*umount)(struct sos_fs_manager_type * this, 217 struct sos_fs_manager_in 214 struct sos_fs_manager_instance * mounted_fs); 218 215 219 /** Free of use */ 216 /** Free of use */ 220 void * custom_data; 217 void * custom_data; 221 218 222 /** List of filesystem instances of this typ 219 /** List of filesystem instances of this type currently mounted 223 somewhere in the system */ 220 somewhere in the system */ 224 struct sos_fs_manager_instance * instances; 221 struct sos_fs_manager_instance * instances; 225 222 226 /** Linkage for the list of filesystem types 223 /** Linkage for the list of filesystem types registered in the 227 system */ 224 system */ 228 struct sos_fs_manager_type *prev, *next; 225 struct sos_fs_manager_type *prev, *next; 229 }; 226 }; 230 227 231 228 232 /** 229 /** 233 * Data related to a particular "mounting" of !! 230 * Data related to a particular "mounting" of a file system. A so-called "superblock" under Linux 234 * so-called "superblock" under Linux << 235 * 231 * 236 * This holds the FUNDAMENTAL functions respon 232 * This holds the FUNDAMENTAL functions responsible for loading struct 237 * sos_fs_node from disk, or for allocating th 233 * sos_fs_node from disk, or for allocating thom on disk. It also 238 * holds the hash-table of struct sos_fs_node 234 * holds the hash-table of struct sos_fs_node already loaded into 239 * memory. 235 * memory. 240 */ 236 */ 241 struct sos_fs_manager_instance 237 struct sos_fs_manager_instance 242 { 238 { 243 /** 239 /** 244 * @note Publicly readable. Written only by 240 * @note Publicly readable. Written only by sos_fs_manager_type::mount() 245 */ 241 */ 246 struct sos_fs_manager_type * fs_type; 242 struct sos_fs_manager_type * fs_type; 247 243 248 /** 244 /** 249 * Usually, a filesystem relies on a device 245 * Usually, a filesystem relies on a device (disk, network, ram, 250 * ...) to fetch its data. This is the locat 246 * ...) to fetch its data. This is the location of the device. 251 * 247 * 252 * @note Publicly readable. Written only by 248 * @note Publicly readable. Written only by fs.c 253 */ 249 */ 254 struct sos_fs_node * device; 250 struct sos_fs_node * device; 255 251 256 #define SOS_FS_MOUNT_SYNC (1 << 0) 252 #define SOS_FS_MOUNT_SYNC (1 << 0) 257 #define SOS_FS_MOUNT_READONLY (1 << 1) 253 #define SOS_FS_MOUNT_READONLY (1 << 1) 258 #define SOS_FS_MOUNT_NOEXEC (1 << 2) 254 #define SOS_FS_MOUNT_NOEXEC (1 << 2) 259 /** 255 /** 260 * Is this FS read-only, without EXEC file p 256 * Is this FS read-only, without EXEC file permission, write-through 261 * ? Or-red combination of the SOS_FS_MOUNT_ 257 * ? Or-red combination of the SOS_FS_MOUNT_ flags 262 * 258 * 263 * @note Publicly readable. Written only by 259 * @note Publicly readable. Written only by fs.c 264 */ 260 */ 265 sos_ui32_t flags; 261 sos_ui32_t flags; 266 262 267 /** 263 /** 268 * The namespace node that is the root of TH 264 * The namespace node that is the root of THIS file system mounting 269 * 265 * 270 * @note Publicly readable. Written only by 266 * @note Publicly readable. Written only by fs.c 271 */ 267 */ 272 struct sos_fs_nscache_node * root; 268 struct sos_fs_nscache_node * root; 273 269 274 /** 270 /** 275 * List of dirty nodes. These are the nodes 271 * List of dirty nodes. These are the nodes that need to be written 276 * back to disk. With FS supporting deferred 272 * back to disk. With FS supporting deferred-writes, the 277 * sos_fs_sync() function will use this list 273 * sos_fs_sync() function will use this list to flush the dirty 278 * nodes back to disk. 274 * nodes back to disk. 279 * 275 * 280 * @note Reserved to fs.c 276 * @note Reserved to fs.c 281 */ 277 */ 282 struct sos_fs_node * dirty_nodes; 278 struct sos_fs_node * dirty_nodes; 283 279 284 /** 280 /** 285 * Build a fresh new FS node at the given lo 281 * Build a fresh new FS node at the given location. This implies 286 * the allocation of a new sos_fs_node struc 282 * the allocation of a new sos_fs_node structure in memory 287 * 283 * 288 * @note Mandatory, may block. Appropriate l 284 * @note Mandatory, may block. Appropriate locking MUST be implemented 289 */ 285 */ 290 sos_ret_t (*fetch_node_from_disk)(struct sos 286 sos_ret_t (*fetch_node_from_disk)(struct sos_fs_manager_instance * this, 291 sos_ui64_t 287 sos_ui64_t storage_location, 292 struct sos 288 struct sos_fs_node ** result); 293 289 294 /** 290 /** 295 * Build a fresh new FS node ON THE DISK of 291 * Build a fresh new FS node ON THE DISK of the given type (dir, 296 * plain file, symlink, ...), completely emp 292 * plain file, symlink, ...), completely empty ; return a newly 297 * allocated IN-MEMORY node structure repres 293 * allocated IN-MEMORY node structure representing it 298 * 294 * 299 * @param open_creat_flags is the open_flags 295 * @param open_creat_flags is the open_flags parameter passed to 300 * sos_fs_open() when O_CREAT is set. 0 when 296 * sos_fs_open() when O_CREAT is set. 0 when allocated trough 301 * creat/mkdir/mknod/symlink 297 * creat/mkdir/mknod/symlink 302 * 298 * 303 * @note Mandatory, may block. Appropriate l 299 * @note Mandatory, may block. Appropriate locking MUST be implemented 304 */ 300 */ 305 sos_ret_t (*allocate_new_node)(struct sos_fs 301 sos_ret_t (*allocate_new_node)(struct sos_fs_manager_instance * this, 306 sos_fs_node_t 302 sos_fs_node_type_t type, 307 const struct 303 const struct sos_process * creator, 308 sos_ui32_t ac 304 sos_ui32_t access_rights, 309 sos_ui32_t op 305 sos_ui32_t open_creat_flags, 310 struct sos_fs 306 struct sos_fs_node ** result); 311 307 312 /** 308 /** 313 * Return filesystem status (RTFM df) 309 * Return filesystem status (RTFM df) 314 * 310 * 315 * @note Optional, may block. Appropriate lo 311 * @note Optional, may block. Appropriate locking MUST be implemented 316 */ 312 */ 317 sos_ret_t (*statfs)(struct sos_fs_manager_in 313 sos_ret_t (*statfs)(struct sos_fs_manager_instance * this, 318 struct sos_fs_statfs * r 314 struct sos_fs_statfs * result); 319 315 320 /** 316 /** 321 * Comparison callback called when looking f 317 * Comparison callback called when looking for file/dirs in the 322 * namespace cache. Normally, a usual lexico 318 * namespace cache. Normally, a usual lexicographical comparison is 323 * done (when this function points to NULL). 319 * done (when this function points to NULL). But for some FS, it 324 * might be useful to use another comparison 320 * might be useful to use another comparison function (eg for 325 * case-insensitive FS) 321 * case-insensitive FS) 326 * 322 * 327 * @note Optional (may be NULL), must NOT bl 323 * @note Optional (may be NULL), must NOT block 328 */ 324 */ 329 sos_bool_t (*nsnode_same_name)(const char * 325 sos_bool_t (*nsnode_same_name)(const char * name1, sos_ui16_t namelen1, 330 const char * 326 const char * name2, sos_ui16_t namelen2); 331 327 332 /** 328 /** 333 * Hash table of the struct sos_fs_node of t 329 * Hash table of the struct sos_fs_node of this filesystem instance 334 * loaded in memory: key=storage_location, e 330 * loaded in memory: key=storage_location, element=sos_fs_node 335 */ 331 */ 336 struct sos_hash_table * nodecache; 332 struct sos_hash_table * nodecache; 337 333 338 /** 334 /** 339 * Unique identifier of this FS (used in syn 335 * Unique identifier of this FS (used in sync method, updated by 340 * fs.c). This enables sync_all_fs to be res 336 * fs.c). This enables sync_all_fs to be resilient to mount/umount 341 * and (un)register_fs_type/instance 337 * and (un)register_fs_type/instance 342 */ 338 */ 343 sos_ui64_t uid; 339 sos_ui64_t uid; 344 340 345 void * custom_data; 341 void * custom_data; 346 342 347 /** Linkage for the list of instances for th 343 /** Linkage for the list of instances for the underlying fs type */ 348 struct sos_fs_manager_instance * prev, * nex 344 struct sos_fs_manager_instance * prev, * next; 349 }; 345 }; 350 346 351 347 352 /** 348 /** 353 * The CENTRAL data structure of the whole thi 349 * The CENTRAL data structure of the whole thing. A so-called "inode" 354 * 350 * 355 * This represents the meta-information relate 351 * This represents the meta-information related to a file on disk: its 356 * permission, where its data is located. Actu 352 * permission, where its data is located. Actually, in SOS, these 357 * information are not stored in this structur 353 * information are not stored in this structure. Instead, we define a 358 * series of methods in this structure that MU 354 * series of methods in this structure that MUST be implemented by the 359 * FS and that realize the higher level operat 355 * FS and that realize the higher level operations needed by the 360 * OS. These operations will rely on the meta- 356 * OS. These operations will rely on the meta-information that the FS 361 * code MUST define and manage by itself (henc 357 * code MUST define and manage by itself (hence the 362 * sos_fs_node::custom_data field). 358 * sos_fs_node::custom_data field). 363 */ 359 */ 364 struct sos_fs_node 360 struct sos_fs_node 365 { 361 { 366 /** 362 /** 367 * An struct sos_fs_node always belong to ex 363 * An struct sos_fs_node always belong to exactly ONE file system 368 */ 364 */ 369 struct sos_fs_manager_instance * fs; 365 struct sos_fs_manager_instance * fs; 370 366 371 /** 367 /** 372 * The so-called "inode": location of this n 368 * The so-called "inode": location of this node inside the FS 373 * instance. Updated by struct 369 * instance. Updated by struct 374 * sos_fs_manager_instance::fetch_node_from_ 370 * sos_fs_manager_instance::fetch_node_from_disk() 375 */ 371 */ 376 sos_ui64_t storage_location; 372 sos_ui64_t storage_location; 377 373 378 /** 374 /** 379 * Number of ON-DISK links to this node. 375 * Number of ON-DISK links to this node. 380 * 376 * 381 * - For everything but directories: the num 377 * - For everything but directories: the number of hard links to the file 382 * - For directories: 1 + the number of chil 378 * - For directories: 1 + the number of children nodes 383 * 379 * 384 * @note Publicly readable. Written only by 380 * @note Publicly readable. Written only by 385 * sos_fs_node_ops_dir::link() and sos_fs_no 381 * sos_fs_node_ops_dir::link() and sos_fs_node_ops_dir::unlink() 386 */ 382 */ 387 sos_count_t ondisk_lnk_cnt; 383 sos_count_t ondisk_lnk_cnt; 388 384 389 /** 385 /** 390 * Number of IN-MEMORY nscache_nodes referen 386 * Number of IN-MEMORY nscache_nodes referencing this FS node. 391 * 387 * 392 * Corresponds to the number of struct sos_f 388 * Corresponds to the number of struct sos_fs_nscache_node pointing 393 * to this node. This could be as much as on 389 * to this node. This could be as much as ondisk_lnk_cnt + 1, but is 394 * usually less 390 * usually less 395 * 391 * 396 * @note Reserved to fs.c 392 * @note Reserved to fs.c 397 */ 393 */ 398 sos_count_t inmem_ref_cnt; 394 sos_count_t inmem_ref_cnt; 399 395 400 /** 396 /** 401 * Directory, symlink, ... 397 * Directory, symlink, ... 402 * 398 * 403 * @see sos_fs_node_type_t 399 * @see sos_fs_node_type_t 404 * 400 * 405 * @note Publicly readable. Written only by 401 * @note Publicly readable. Written only by fs.c 406 */ 402 */ 407 sos_fs_node_type_t type; 403 sos_fs_node_type_t type; 408 404 409 #define SOS_FS_READABLE 00400 405 #define SOS_FS_READABLE 00400 410 #define SOS_FS_WRITABLE 00200 406 #define SOS_FS_WRITABLE 00200 411 #define SOS_FS_EXECUTABLE 00100 407 #define SOS_FS_EXECUTABLE 00100 412 /** 408 /** 413 * read/write, ... @see the SOS_FS_*ABLE fla 409 * read/write, ... @see the SOS_FS_*ABLE flags 414 * @note Publicly readable. Written only by 410 * @note Publicly readable. Written only by fs.c 415 */ 411 */ 416 sos_ui32_t access_rights; 412 sos_ui32_t access_rights; 417 413 418 /** 414 /** 419 * @note Reserved to fs.c 415 * @note Reserved to fs.c 420 */ 416 */ 421 sos_bool_t dirty; 417 sos_bool_t dirty; 422 418 423 /** 419 /** 424 * Incremented each time one of the opened f 420 * Incremented each time one of the opened files for this node is 425 * modified 421 * modified 426 * @note Publicly readable. Written only by 422 * @note Publicly readable. Written only by fs.c 427 */ 423 */ 428 sos_lcount_t generation; 424 sos_lcount_t generation; 429 425 430 /** << 431 * @note Available only for device files (ch << 432 * @note Publicly readable. Written only by << 433 * sos_fs_manager_instance::fetch_node_from_ << 434 */ << 435 struct sos_fs_dev_id_t << 436 { << 437 sos_ui32_t device_class; /**< aka "majo << 438 sos_ui32_t device_instance; /**< aka "mino << 439 } dev_id; << 440 << 441 /** Operations common to all node types */ 426 /** Operations common to all node types */ 442 struct sos_fs_node_ops_file *ops_file; 427 struct sos_fs_node_ops_file *ops_file; 443 428 444 /** Operations specific to some node types * 429 /** Operations specific to some node types */ 445 union 430 union 446 { 431 { 447 /** when type == SOS_FS_NODE_DIRECTORY */ 432 /** when type == SOS_FS_NODE_DIRECTORY */ 448 struct sos_fs_node_ops_dir *ops_dir; 433 struct sos_fs_node_ops_dir *ops_dir; 449 434 450 /** << 451 * when type == SOS_FS_NODE_DEVICE_BLOCK << 452 * The FS node has a link to some data per << 453 * not to any special operations << 454 * @see blkdev.c for a definition of this << 455 */ << 456 struct sos_blockdev_instance *block_device << 457 << 458 /** when type == SOS_FS_NODE_SYMLINK */ 435 /** when type == SOS_FS_NODE_SYMLINK */ 459 struct sos_fs_node_ops_symlink *ops_symli 436 struct sos_fs_node_ops_symlink *ops_symlink; 460 }; /* Anonymous union (gcc extension) */ 437 }; /* Anonymous union (gcc extension) */ 461 438 462 439 463 /** 440 /** 464 * Simply free this FS node from the kernel 441 * Simply free this FS node from the kernel memory: it does NOT 465 * mean that the corresponding on-disk node 442 * mean that the corresponding on-disk node is free ! Actually, the 466 * corresponding ON-DISK node is free iff on 443 * corresponding ON-DISK node is free iff ondisk_lnk_cnt == 0. No 467 * need to sync anything to disk, as the VFS 444 * need to sync anything to disk, as the VFS will sync the node 468 * before calling this method 445 * before calling this method 469 * 446 * 470 * @note Mandatory, may block, no special lo 447 * @note Mandatory, may block, no special locking needed 471 */ 448 */ 472 sos_ret_t (*destructor)(struct sos_fs_node * 449 sos_ret_t (*destructor)(struct sos_fs_node * this); 473 450 474 /** 451 /** 475 * Called when a process opens the node 452 * Called when a process opens the node 476 * 453 * 477 * @note Mandatory, may block. Appropriate l 454 * @note Mandatory, may block. Appropriate locking MUST be implemented 478 * @note FS-specific EXCPET for device speci << 479 * block) because they are handled in an uni << 480 * chardev/blockdev subsystems << 481 * @note As a consequence, FS code can safel << 482 * never a character or block device << 483 */ 455 */ 484 sos_ret_t (*new_opened_file)(struct sos_fs_n 456 sos_ret_t (*new_opened_file)(struct sos_fs_node * this, 485 const struct so 457 const struct sos_process * owner, 486 sos_ui32_t open 458 sos_ui32_t open_flags, 487 struct sos_fs_o 459 struct sos_fs_opened_file ** result_of); 488 460 489 /** 461 /** 490 * Called when a process opens the node 462 * Called when a process opens the node 491 * 463 * 492 * @note Mandatory, may block. Appropriate l 464 * @note Mandatory, may block. Appropriate locking MUST be implemented 493 * @note FS-specific EXCEPT for device speci << 494 * block) because they are handled in an uni << 495 * chardev/blockdev subsystems << 496 * @note As a consequence, FS code can safel << 497 * never a character or block device << 498 */ 465 */ 499 sos_ret_t (*close_opened_file)(struct sos_fs 466 sos_ret_t (*close_opened_file)(struct sos_fs_node * this, 500 struct sos_fs 467 struct sos_fs_opened_file * of); 501 468 502 /** 469 /** 503 * This should hold the meta information for 470 * This should hold the meta information for this node as needed by 504 * the FS instance. 471 * the FS instance. 505 */ 472 */ 506 void * custom_data; 473 void * custom_data; 507 474 508 /** Hash linkage entry for this FS node in t 475 /** Hash linkage entry for this FS node in the nodecache 509 dictionary */ 476 dictionary */ 510 struct sos_hash_linkage hlink_nodecache; 477 struct sos_hash_linkage hlink_nodecache; 511 478 512 /** Linkage to list the dirty nodes of the g 479 /** Linkage to list the dirty nodes of the given FS */ 513 struct sos_fs_node *prev_dirty, *next_dirty; 480 struct sos_fs_node *prev_dirty, *next_dirty; 514 }; 481 }; 515 482 516 483 517 484 518 /** 485 /** 519 * The list of methods implementing the basic 486 * The list of methods implementing the basic VFS operations on the 520 * given struct sos_fs_node 487 * given struct sos_fs_node 521 * 488 * 522 * @see sos_fs_node::ops_file 489 * @see sos_fs_node::ops_file 523 */ 490 */ 524 struct sos_fs_node_ops_file 491 struct sos_fs_node_ops_file 525 { 492 { 526 /** 493 /** 527 * Change size of file 494 * Change size of file 528 * 495 * 529 * @note Optional, may block. Appropriate lo 496 * @note Optional, may block. Appropriate locking MUST be implemented 530 */ 497 */ 531 sos_ret_t (*truncate)(struct sos_fs_node *th 498 sos_ret_t (*truncate)(struct sos_fs_node *this, 532 sos_lsoffset_t length) 499 sos_lsoffset_t length); 533 500 534 /** 501 /** 535 * Retrieve the status (eg size) of the file 502 * Retrieve the status (eg size) of the file 536 * 503 * 537 * @note Mandatory, may block. Appropriate l 504 * @note Mandatory, may block. Appropriate locking MUST be implemented 538 */ 505 */ 539 sos_ret_t (*stat)(struct sos_fs_node * this, 506 sos_ret_t (*stat)(struct sos_fs_node * this, 540 struct sos_fs_stat * resul 507 struct sos_fs_stat * result); 541 508 542 /** 509 /** 543 * Change the sos_fs_node::access_rights att !! 510 * Flush any change to disk 544 * 511 * 545 * @note Mandatory, may block. Appropriate l 512 * @note Mandatory, may block. Appropriate locking MUST be implemented 546 */ 513 */ 547 sos_ret_t (*chmod)(struct sos_fs_node * this !! 514 sos_ret_t (*sync)(struct sos_fs_node *this); 548 sos_ui32_t new_access_rig << 549 << 550 515 551 /** 516 /** 552 * Flush any change to the node back to the !! 517 * Change the sos_fs_node::access_rights attribute 553 * 518 * 554 * @note Mandatory, may block. Appropriate l 519 * @note Mandatory, may block. Appropriate locking MUST be implemented 555 */ 520 */ 556 sos_ret_t (*sync)(struct sos_fs_node *this); !! 521 sos_ret_t (*chmod)(struct sos_fs_node * this, >> 522 sos_ui32_t new_access_rights); 557 }; 523 }; 558 524 559 525 560 /** 526 /** 561 * The list of methods implementing the basic 527 * The list of methods implementing the basic VFS symlink operations 562 * 528 * 563 * @see sos_fs_node::ops_symlink 529 * @see sos_fs_node::ops_symlink 564 */ 530 */ 565 struct sos_fs_node_ops_symlink 531 struct sos_fs_node_ops_symlink 566 { 532 { 567 /** 533 /** 568 * Used by the _kernel_ to resolve the symli 534 * Used by the _kernel_ to resolve the symlinks. To change/create a 569 * symlink target, it is needed only from us 535 * symlink target, it is needed only from userland: the read/write 570 * methods are made for this 536 * methods are made for this 571 * 537 * 572 * @param target Pointer to the string repre 538 * @param target Pointer to the string representing the target's 573 * path, allocated for the fs_node's lifetim 539 * path, allocated for the fs_node's lifetime ! 574 * 540 * 575 * @note Mandatory, may block. Appropriate l 541 * @note Mandatory, may block. Appropriate locking MUST be implemented 576 */ 542 */ 577 sos_ret_t (*expand)(struct sos_fs_node *this 543 sos_ret_t (*expand)(struct sos_fs_node *this, 578 char const ** target, 544 char const ** target, 579 sos_size_t * target_len) 545 sos_size_t * target_len); 580 }; 546 }; 581 547 582 548 583 /** 549 /** 584 * The list of methods implementing the basic 550 * The list of methods implementing the basic VFS directory operations 585 * 551 * 586 * @see sos_fs_node::ops_dir 552 * @see sos_fs_node::ops_dir 587 */ 553 */ 588 struct sos_fs_node_ops_dir 554 struct sos_fs_node_ops_dir 589 { 555 { 590 /** 556 /** 591 * Look for the on-disk location of the sos_ 557 * Look for the on-disk location of the sos_fs_node having the given 592 * name 558 * name 593 * 559 * 594 * @note Mandatory, may block. Appropriate l 560 * @note Mandatory, may block. Appropriate locking MUST be implemented 595 */ 561 */ 596 sos_ret_t (*lookup)(struct sos_fs_node *this 562 sos_ret_t (*lookup)(struct sos_fs_node *this, 597 const char * name, sos_u 563 const char * name, sos_ui16_t namelen, 598 sos_ui64_t * result_stor 564 sos_ui64_t * result_storage_location); 599 565 600 /** 566 /** 601 * Add a new reference in the current sos_fs 567 * Add a new reference in the current sos_fs_node to the on-disk 602 * location of the given sos_fs_node 568 * location of the given sos_fs_node 603 * 569 * 604 * @note Responsible for updating this->ondi 570 * @note Responsible for updating this->ondisk_lnk_cnt 605 * @note Mandatory for writable directories, 571 * @note Mandatory for writable directories, may block. Appropriate 606 * locking MUST be implemented 572 * locking MUST be implemented 607 */ 573 */ 608 sos_ret_t (*link)(struct sos_fs_node *this, 574 sos_ret_t (*link)(struct sos_fs_node *this, 609 const struct sos_process * 575 const struct sos_process *actor, 610 const char * entry_name, s 576 const char * entry_name, sos_ui16_t entry_namelen, 611 struct sos_fs_node * node) 577 struct sos_fs_node * node); 612 578 613 /** 579 /** 614 * Remove the entry in the current sos_fs_no 580 * Remove the entry in the current sos_fs_node for the on-disk 615 * location with the given name 581 * location with the given name 616 * 582 * 617 * @note Responsible for updating this->ondi 583 * @note Responsible for updating this->ondisk_lnk_cnt 618 * @note Mandatory for writable directories, 584 * @note Mandatory for writable directories, may block. Appropriate 619 * locking MUST be implemented 585 * locking MUST be implemented 620 */ 586 */ 621 sos_ret_t (*unlink)(struct sos_fs_node *this 587 sos_ret_t (*unlink)(struct sos_fs_node *this, 622 const struct sos_process 588 const struct sos_process *actor, 623 const char * entry_name, 589 const char * entry_name, sos_ui16_t entry_namelen); 624 }; 590 }; 625 591 626 592 627 /** 593 /** 628 * The data structure holding information and 594 * The data structure holding information and method related to a 629 * particular usage of a file. A so-called "st 595 * particular usage of a file. A so-called "struct file" 630 * 596 * 631 * This represents the kernel structure behind 597 * This represents the kernel structure behind a "file descriptor" or 632 * behind a chdir/chroot. Among other things, 598 * behind a chdir/chroot. Among other things, it holds the methods 633 * responsible for reading/writing into the fi 599 * responsible for reading/writing into the file, and for moving the 634 * file pointer (see @sos_fs_opened_file::posi 600 * file pointer (see @sos_fs_opened_file::position) inside it. 635 */ 601 */ 636 struct sos_fs_opened_file 602 struct sos_fs_opened_file 637 { 603 { 638 /** The process that opened the file/dir */ 604 /** The process that opened the file/dir */ 639 const struct sos_process * owner; 605 const struct sos_process * owner; 640 606 641 /** 607 /** 642 * The reference to the sos_fs_nscache_node 608 * The reference to the sos_fs_nscache_node and, hence, to the underlying sos_fs_node. 643 * 609 * 644 * Used to cache the in-memory fs nodes 610 * Used to cache the in-memory fs nodes 645 */ 611 */ 646 struct sos_fs_nscache_node * direntry; 612 struct sos_fs_nscache_node * direntry; 647 613 648 /** Use for memory-management */ 614 /** Use for memory-management */ 649 sos_count_t ref_cnt; 615 sos_count_t ref_cnt; 650 616 651 /** 617 /** 652 * Always > 0 (ie max size = 2^63-1 = 9.2 10 618 * Always > 0 (ie max size = 2^63-1 = 9.2 10^18). We make it 653 * "signed" here to limit its range. Because 619 * "signed" here to limit its range. Because we must be able to 654 * seek to the begining of the file with SEE 620 * seek to the begining of the file with SEEK_END and a negative 655 * offset, so the max size of the file must 621 * offset, so the max size of the file must be reachable by a lseek 656 * offset 622 * offset 657 * 623 * 658 * @note reserved to filesystem instance cod 624 * @note reserved to filesystem instance code. Not modified nor used 659 * by fs.c 625 * by fs.c 660 */ 626 */ 661 sos_lsoffset_t position; 627 sos_lsoffset_t position; 662 628 663 /** 629 /** 664 * Incremented each time this opened file is 630 * Incremented each time this opened file is modified 665 * 631 * 666 * Used to implement a readdir method resili 632 * Used to implement a readdir method resilient to 667 * creat/mkdir/rmdir/unlink 633 * creat/mkdir/rmdir/unlink 668 */ 634 */ 669 sos_lcount_t generation; 635 sos_lcount_t generation; 670 636 671 /** 637 /** 672 * @see SOS_FS_OPEN_* flags 638 * @see SOS_FS_OPEN_* flags 673 */ 639 */ 674 sos_ui32_t open_flags; 640 sos_ui32_t open_flags; 675 641 676 /** Operations common to all node types */ 642 /** Operations common to all node types */ 677 struct sos_fs_ops_opened_file * ops_file; 643 struct sos_fs_ops_opened_file * ops_file; 678 644 679 /** Operations specific to some node types * 645 /** Operations specific to some node types */ 680 union 646 union 681 { 647 { 682 /** when direntry->fs_node->type == SOS_FS 648 /** when direntry->fs_node->type == SOS_FS_NODE_DIRECTORY */ 683 struct sos_fs_ops_opened_dir * ops_di 649 struct sos_fs_ops_opened_dir * ops_dir; 684 << 685 /** when direntry->fs_node->type == SOS_FS << 686 struct sos_fs_ops_opened_chardev * ops_ch << 687 << 688 /** when direntry->fs_node->type == SOS_FS << 689 struct sos_fs_ops_opened_blockdev * ops_bl << 690 }; /* Anonymous union (gcc extension) */ 650 }; /* Anonymous union (gcc extension) */ 691 651 692 /** 652 /** 693 * Called upon fork() to duplicate all the o 653 * Called upon fork() to duplicate all the opened files 694 * << 695 * @note FS-specific EXCEPT for device speci << 696 * block) because they are handled in an uni << 697 * chardev/blockdev subsystems << 698 * @note As a consequence, FS code can safel << 699 * never a character or block device << 700 */ 654 */ 701 sos_ret_t (*duplicate)(struct sos_fs_opened_ 655 sos_ret_t (*duplicate)(struct sos_fs_opened_file *this, 702 const struct sos_proc 656 const struct sos_process * for_owner, 703 struct sos_fs_opened_ 657 struct sos_fs_opened_file **result); 704 658 705 void * custom_data; 659 void * custom_data; 706 }; 660 }; 707 661 708 662 709 /** 663 /** 710 * Reference position for sos_fs_seek 664 * Reference position for sos_fs_seek 711 */ 665 */ 712 typedef enum { SOS_SEEK_SET=42, 666 typedef enum { SOS_SEEK_SET=42, 713 SOS_SEEK_CUR=24, 667 SOS_SEEK_CUR=24, 714 SOS_SEEK_END=84 } sos_seek_when 668 SOS_SEEK_END=84 } sos_seek_whence_t; 715 /** 669 /** 716 * The list of methods implementing the basic 670 * The list of methods implementing the basic VFS opened file 717 * operations 671 * operations 718 * 672 * 719 * See the Unix manual pages, they basically f 673 * See the Unix manual pages, they basically form the interfaces to to 720 * these functions 674 * these functions 721 * 675 * 722 * @see sos_fs_opened_file::ops_file 676 * @see sos_fs_opened_file::ops_file 723 */ 677 */ 724 struct sos_fs_ops_opened_file 678 struct sos_fs_ops_opened_file 725 { 679 { 726 /** 680 /** 727 * @note Mandatory, may block. Appropriate l 681 * @note Mandatory, may block. Appropriate locking MUST be implemented 728 * @note Please call sos_fs_mark_dirty() if 682 * @note Please call sos_fs_mark_dirty() if disk contents is changed 729 */ 683 */ 730 sos_ret_t (*seek)(struct sos_fs_opened_file 684 sos_ret_t (*seek)(struct sos_fs_opened_file *this, 731 sos_lsoffset_t offset, 685 sos_lsoffset_t offset, 732 sos_seek_whence_t whence, 686 sos_seek_whence_t whence, 733 /* out */ sos_lsoffset_t * 687 /* out */ sos_lsoffset_t * result_position); 734 688 735 /** 689 /** 736 * @note Mandatory, may block. Appropriate l 690 * @note Mandatory, may block. Appropriate locking MUST be implemented 737 * @note Please call sos_fs_mark_dirty() if 691 * @note Please call sos_fs_mark_dirty() if disk contents is changed 738 */ 692 */ 739 sos_ret_t (*read)(struct sos_fs_opened_file 693 sos_ret_t (*read)(struct sos_fs_opened_file *this, 740 sos_uaddr_t dest_buf, 694 sos_uaddr_t dest_buf, 741 sos_size_t * /* in/out */l 695 sos_size_t * /* in/out */len); 742 696 743 /** 697 /** 744 * @note Optional (might be NULL), may block 698 * @note Optional (might be NULL), may block. Appropriate locking 745 * MUST be implemented 699 * MUST be implemented 746 * @note Please call sos_fs_mark_dirty() if 700 * @note Please call sos_fs_mark_dirty() if disk contents is changed 747 */ 701 */ 748 sos_ret_t (*write)(struct sos_fs_opened_file 702 sos_ret_t (*write)(struct sos_fs_opened_file *this, 749 sos_uaddr_t src_buf, 703 sos_uaddr_t src_buf, 750 sos_size_t * /* in/out */ 704 sos_size_t * /* in/out */len); 751 705 752 /** 706 /** 753 * @note Optional (might be NULL), may block 707 * @note Optional (might be NULL), may block. Appropriate locking 754 * MUST be implemented 708 * MUST be implemented 755 * @note Please call sos_fs_mark_dirty() if 709 * @note Please call sos_fs_mark_dirty() if disk contents is changed 756 */ 710 */ 757 sos_ret_t (*mmap)(struct sos_fs_opened_file 711 sos_ret_t (*mmap)(struct sos_fs_opened_file *this, 758 sos_uaddr_t *uaddr, sos_si 712 sos_uaddr_t *uaddr, sos_size_t size, 759 sos_ui32_t access_rights, 713 sos_ui32_t access_rights, 760 sos_ui32_t flags, 714 sos_ui32_t flags, 761 sos_luoffset_t offset); 715 sos_luoffset_t offset); 762 716 763 /** 717 /** 764 * @note Optional (might be NULL), may block 718 * @note Optional (might be NULL), may block. Appropriate locking 765 * MUST be implemented 719 * MUST be implemented 766 * @note Please call sos_fs_mark_dirty() if 720 * @note Please call sos_fs_mark_dirty() if disk contents is changed 767 */ 721 */ 768 sos_ret_t (*fcntl)(struct sos_fs_opened_file 722 sos_ret_t (*fcntl)(struct sos_fs_opened_file *this, 769 int req_id, 723 int req_id, 770 sos_ui32_t req_arg /* Usu 724 sos_ui32_t req_arg /* Usually: sos_uaddr_t */); 771 }; 725 }; 772 726 773 727 774 /** << 775 * The list of methods implementing the basic << 776 * operations << 777 * << 778 * @see sos_fs_opened_file::ops_file << 779 */ << 780 struct sos_fs_ops_opened_chardev << 781 { << 782 /** << 783 * @note Optional (might be NULL), may block << 784 * MUST be implemented << 785 * @note Please call sos_fs_mark_dirty() if << 786 */ << 787 sos_ret_t (*ioctl)(struct sos_fs_opened_file << 788 int req_id, << 789 sos_ui32_t req_arg /* Usu << 790 }; << 791 << 792 << 793 /** << 794 * The list of methods implementing the basic << 795 * operations << 796 * << 797 * @see sos_fs_opened_file::ops_file << 798 */ << 799 struct sos_fs_ops_opened_blockdev << 800 { << 801 /** << 802 * @note Optional (might be NULL), may block << 803 * MUST be implemented << 804 * @note Please call sos_fs_mark_dirty() if << 805 */ << 806 sos_ret_t (*ioctl)(struct sos_fs_opened_file << 807 int req_id, << 808 sos_ui32_t req_arg /* Usu << 809 }; << 810 << 811 << 812 /** Data structure that is to be filled by rea 728 /** Data structure that is to be filled by readdir */ 813 struct sos_fs_dirent 729 struct sos_fs_dirent 814 { 730 { 815 sos_ui64_t storage_location; 731 sos_ui64_t storage_location; 816 sos_si64_t offset_in_dirfile; 732 sos_si64_t offset_in_dirfile; 817 sos_ui32_t type; 733 sos_ui32_t type; 818 sos_ui16_t namelen; 734 sos_ui16_t namelen; 819 735 820 #define SOS_FS_DIRENT_NAME_MAXLEN 128 736 #define SOS_FS_DIRENT_NAME_MAXLEN 128 821 char name[SOS_FS_DIRENT_NAME_MAXLEN]; 737 char name[SOS_FS_DIRENT_NAME_MAXLEN]; 822 }; 738 }; 823 739 824 740 825 /** 741 /** 826 * The list of methods implementing the basic 742 * The list of methods implementing the basic VFS opened directory 827 * operations 743 * operations 828 * 744 * 829 * @see sos_fs_opened_file::ops_file 745 * @see sos_fs_opened_file::ops_file 830 */ 746 */ 831 struct sos_fs_ops_opened_dir 747 struct sos_fs_ops_opened_dir 832 { 748 { 833 /** 749 /** 834 * Each time it is called, responsible for f 750 * Each time it is called, responsible for filling the sos_fs_dirent 835 * structure, return -SOS_ENOENT when done. 751 * structure, return -SOS_ENOENT when done. 836 * 752 * 837 * @note Mandatory, may block. Appropriate l 753 * @note Mandatory, may block. Appropriate locking MUST be implemented 838 * @note Please call sos_fs_mark_dirty() if 754 * @note Please call sos_fs_mark_dirty() if disk contents is changed 839 */ 755 */ 840 sos_ret_t (*readdir)(struct sos_fs_opened_fi 756 sos_ret_t (*readdir)(struct sos_fs_opened_file *this, 841 struct sos_fs_dirent * 757 struct sos_fs_dirent * result); 842 }; 758 }; 843 759 844 760 845 761 846 /** 762 /** 847 * Used by the stat calls 763 * Used by the stat calls 848 * 764 * 849 * @see sos_fs_node_ops_file::stat 765 * @see sos_fs_node_ops_file::stat 850 */ 766 */ 851 struct sos_fs_stat 767 struct sos_fs_stat 852 { 768 { 853 struct sos_fs_dev_id_t st_rdev; << 854 sos_fs_node_type_t st_type; 769 sos_fs_node_type_t st_type; 855 sos_ui64_t st_storage_location; 770 sos_ui64_t st_storage_location; 856 sos_ui32_t st_access_rights; 771 sos_ui32_t st_access_rights; 857 sos_count_t st_nlink; 772 sos_count_t st_nlink; 858 sos_si64_t st_size; 773 sos_si64_t st_size; 859 }; 774 }; 860 775 861 776 862 /** 777 /** 863 * Used by the statvfs calls 778 * Used by the statvfs calls 864 * 779 * 865 * @see sos_fs_manager_instance::statfs 780 * @see sos_fs_manager_instance::statfs 866 */ 781 */ 867 struct sos_fs_statfs 782 struct sos_fs_statfs 868 { 783 { 869 struct sos_fs_dev_id_t f_rdev; << 870 sos_size_t f_sz_total; /**< Tot 784 sos_size_t f_sz_total; /**< Total size */ 871 sos_size_t f_sz_free; /**< Siz 785 sos_size_t f_sz_free; /**< Size left on device */ 872 sos_count_t f_node_total;/**< Tot 786 sos_count_t f_node_total;/**< Total allocatable FS nodes */ 873 sos_count_t f_node_avail;/**< Num 787 sos_count_t f_node_avail;/**< Number of available free FS nodes */ 874 sos_ui32_t f_flags; 788 sos_ui32_t f_flags; 875 }; 789 }; 876 790 877 791 878 /** 792 /** 879 * Must be called AFTER the FS manager types n 793 * Must be called AFTER the FS manager types needed to mount the root 880 * filesystem have been registered 794 * filesystem have been registered 881 */ 795 */ 882 sos_ret_t sos_fs_subsystem_setup(const char * 796 sos_ret_t sos_fs_subsystem_setup(const char * root_device, 883 const char * 797 const char * fs_type, 884 const char * 798 const char * mount_args, 885 struct sos_fs 799 struct sos_fs_manager_instance ** result_rootfs); 886 800 887 801 888 /* ****************************************** 802 /* *************************************************************** 889 * The Following functions are relatively stan 803 * The Following functions are relatively standard 890 * 804 * 891 * @see Unix manual pages for details 805 * @see Unix manual pages for details 892 */ 806 */ 893 807 894 808 895 /** 809 /** 896 * mount a file system 810 * mount a file system 897 * 811 * 898 * @param actor process calling mount 812 * @param actor process calling mount 899 * @param _src_path(len) may be NULL (as for v 813 * @param _src_path(len) may be NULL (as for virtfs or /proc) 900 * @fsname the name of the filesystem type to 814 * @fsname the name of the filesystem type to mount 901 * @args any args passed to the sos_fs_manager 815 * @args any args passed to the sos_fs_manager_type::mount method 902 * @result_fs the resulting filesystem instanc 816 * @result_fs the resulting filesystem instance 903 */ 817 */ 904 sos_ret_t sos_fs_mount(struct sos_process * ac 818 sos_ret_t sos_fs_mount(struct sos_process * actor, 905 const char * _src_path, 819 const char * _src_path, 906 sos_size_t _src_pathlen 820 sos_size_t _src_pathlen, 907 const char * _dst_path, 821 const char * _dst_path, 908 sos_size_t _dst_pathlen 822 sos_size_t _dst_pathlen, 909 const char * fsname, 823 const char * fsname, 910 sos_ui32_t mountflags, 824 sos_ui32_t mountflags, 911 const char * args, 825 const char * args, 912 struct sos_fs_manager_i 826 struct sos_fs_manager_instance ** /*out*/result_fs); 913 827 914 /** 828 /** 915 * unmount the filesystem at the given locatio 829 * unmount the filesystem at the given location 916 */ 830 */ 917 sos_ret_t sos_fs_umount(struct sos_process * a 831 sos_ret_t sos_fs_umount(struct sos_process * actor, 918 const char * _mountpoi 832 const char * _mountpoint_path, 919 sos_size_t _mountpoint 833 sos_size_t _mountpoint_pathlen); 920 834 921 /** 835 /** 922 * Flush all the dirty nodes of all the FS to 836 * Flush all the dirty nodes of all the FS to disk 923 */ 837 */ 924 sos_ret_t sos_fs_sync_all_fs(void); !! 838 sos_ret_t sos_fs_sync_all_fs(); 925 839 926 /** 840 /** 927 * Retrieve filesystem status, or return -SOS_ !! 841 * Retrieve filesystem status, or return -SOS_ENOSUP if filesystem 928 * cannot report this 842 * cannot report this 929 */ 843 */ 930 sos_ret_t sos_fs_vfstat(const struct sos_proce 844 sos_ret_t sos_fs_vfstat(const struct sos_process * actor, 931 const char * _path, 845 const char * _path, 932 sos_size_t _pathlen, 846 sos_size_t _pathlen, 933 struct sos_fs_statfs * 847 struct sos_fs_statfs * result); 934 848 935 /** 849 /** 936 * Open flags 850 * Open flags 937 */ 851 */ 938 #define SOS_FS_OPEN_EXCL (1 << 0) 852 #define SOS_FS_OPEN_EXCL (1 << 0) 939 #define SOS_FS_OPEN_CREAT (1 << 1) 853 #define SOS_FS_OPEN_CREAT (1 << 1) 940 #define SOS_FS_OPEN_TRUNC (1 << 2) !! 854 #define SOS_FS_OPEN_NOFOLLOW (1 << 2) 941 #define SOS_FS_OPEN_NOFOLLOW (1 << 3) !! 855 #define SOS_FS_OPEN_DIRECTORY (1 << 3) /* Incompatible with CREAT */ 942 #define SOS_FS_OPEN_DIRECTORY (1 << 4) /* In !! 856 #define SOS_FS_OPEN_SYNC (1 << 4) 943 #define SOS_FS_OPEN_SYNC (1 << 5) !! 857 #define SOS_FS_OPEN_KEEPONEXEC (1 << 5) /* By default, files are closed 944 #define SOS_FS_OPEN_CLOSEONEXEC (1 << 6) /* By !! 858 upon an exec() */ 945 op << 946 859 947 #define SOS_FS_OPEN_READ (1 << 16) 860 #define SOS_FS_OPEN_READ (1 << 16) 948 #define SOS_FS_OPEN_WRITE (1 << 17) 861 #define SOS_FS_OPEN_WRITE (1 << 17) 949 862 950 863 951 /** 864 /** 952 * FS access rights 865 * FS access rights 953 */ 866 */ 954 #define SOS_FS_S_IRUSR 00400 867 #define SOS_FS_S_IRUSR 00400 955 #define SOS_FS_S_IWUSR 00200 868 #define SOS_FS_S_IWUSR 00200 956 #define SOS_FS_S_IXUSR 00100 869 #define SOS_FS_S_IXUSR 00100 957 870 958 #define SOS_FS_S_IRWXALL 07777 /* For symlinks 871 #define SOS_FS_S_IRWXALL 07777 /* For symlinks */ 959 872 960 sos_ret_t sos_fs_open(const struct sos_process 873 sos_ret_t sos_fs_open(const struct sos_process *owner, 961 const char *_path, 874 const char *_path, 962 sos_size_t _pathlen, 875 sos_size_t _pathlen, 963 sos_ui32_t open_flags, 876 sos_ui32_t open_flags, 964 sos_ui32_t creat_access_ 877 sos_ui32_t creat_access_rights, 965 struct sos_fs_opened_fil 878 struct sos_fs_opened_file ** of); 966 879 967 sos_ret_t sos_fs_close(struct sos_fs_opened_fi 880 sos_ret_t sos_fs_close(struct sos_fs_opened_file * of); 968 881 969 sos_ret_t sos_fs_read(struct sos_fs_opened_fil 882 sos_ret_t sos_fs_read(struct sos_fs_opened_file * of, 970 sos_uaddr_t dest_buf, 883 sos_uaddr_t dest_buf, 971 sos_size_t * /* in/ou */ 884 sos_size_t * /* in/ou */len); 972 885 973 sos_ret_t sos_fs_readdir(struct sos_fs_opened_ 886 sos_ret_t sos_fs_readdir(struct sos_fs_opened_file * of, 974 struct sos_fs_dirent 887 struct sos_fs_dirent * result); 975 888 976 sos_ret_t sos_fs_write(struct sos_fs_opened_fi 889 sos_ret_t sos_fs_write(struct sos_fs_opened_file * of, 977 sos_uaddr_t src_buf, 890 sos_uaddr_t src_buf, 978 sos_size_t * /* in/out 891 sos_size_t * /* in/out */len); 979 892 980 sos_ret_t sos_fs_seek(struct sos_fs_opened_fil 893 sos_ret_t sos_fs_seek(struct sos_fs_opened_file *of, 981 sos_lsoffset_t offset, 894 sos_lsoffset_t offset, 982 sos_seek_whence_t whence 895 sos_seek_whence_t whence, 983 sos_lsoffset_t * result_ 896 sos_lsoffset_t * result_position); 984 897 985 sos_ret_t sos_fs_ftruncate(struct sos_fs_opene 898 sos_ret_t sos_fs_ftruncate(struct sos_fs_opened_file *of, 986 sos_lsoffset_t leng 899 sos_lsoffset_t length); 987 900 988 sos_ret_t sos_fs_mmap(struct sos_fs_opened_fil 901 sos_ret_t sos_fs_mmap(struct sos_fs_opened_file *of, 989 sos_uaddr_t *uaddr, sos_ 902 sos_uaddr_t *uaddr, sos_size_t size, 990 sos_ui32_t access_rights 903 sos_ui32_t access_rights, 991 sos_ui32_t flags, 904 sos_ui32_t flags, 992 sos_luoffset_t offset); 905 sos_luoffset_t offset); 993 906 994 sos_ret_t sos_fs_fsync(struct sos_fs_opened_fi 907 sos_ret_t sos_fs_fsync(struct sos_fs_opened_file * of); 995 908 996 sos_ret_t sos_fs_fcntl(struct sos_fs_opened_fi 909 sos_ret_t sos_fs_fcntl(struct sos_fs_opened_file *of, 997 int req_id, 910 int req_id, 998 sos_ui32_t req_arg /* U 911 sos_ui32_t req_arg /* Usually: sos_uaddr_t */); 999 912 1000 sos_ret_t sos_fs_ioctl(struct sos_fs_opened_f << 1001 int req_id, << 1002 sos_ui32_t req_arg /* << 1003 << 1004 sos_ret_t sos_fs_creat(const struct sos_proce 913 sos_ret_t sos_fs_creat(const struct sos_process * creator, 1005 const char * _path, 914 const char * _path, 1006 sos_size_t _pathlen, 915 sos_size_t _pathlen, 1007 sos_ui32_t access_righ 916 sos_ui32_t access_rights); 1008 917 1009 sos_ret_t sos_fs_link(const struct sos_proces 918 sos_ret_t sos_fs_link(const struct sos_process * creator, 1010 const char * _old_path, 919 const char * _old_path, 1011 sos_size_t _old_pathlen 920 sos_size_t _old_pathlen, 1012 const char * _dest_path 921 const char * _dest_path, 1013 sos_size_t _dest_pathle 922 sos_size_t _dest_pathlen); 1014 923 1015 sos_ret_t sos_fs_rename(const struct sos_proc 924 sos_ret_t sos_fs_rename(const struct sos_process * creator, 1016 const char * _old_pat 925 const char * _old_path, 1017 sos_size_t _old_pathl 926 sos_size_t _old_pathlen, 1018 const char * _dest_pa 927 const char * _dest_path, 1019 sos_size_t _dest_path 928 sos_size_t _dest_pathlen); 1020 929 1021 sos_ret_t sos_fs_unlink(const struct sos_proc 930 sos_ret_t sos_fs_unlink(const struct sos_process * actor, 1022 const char * _path, 931 const char * _path, 1023 sos_size_t _pathlen); 932 sos_size_t _pathlen); 1024 933 1025 sos_ret_t sos_fs_symlink(const struct sos_pro 934 sos_ret_t sos_fs_symlink(const struct sos_process * creator, 1026 const char * _path, 935 const char * _path, 1027 sos_size_t _pathlen, 936 sos_size_t _pathlen, 1028 sos_uaddr_t symlink_ 937 sos_uaddr_t symlink_target, 1029 sos_size_t symlink_t 938 sos_size_t symlink_target_len); 1030 << 1031 sos_ret_t sos_fs_mknod(const struct sos_proce << 1032 const char * _path, << 1033 sos_size_t _pathlen, << 1034 sos_fs_node_type_t typ << 1035 sos_ui32_t access_righ << 1036 const struct sos_fs_de << 1037 939 1038 sos_ret_t sos_fs_mkdir(const struct sos_proce 940 sos_ret_t sos_fs_mkdir(const struct sos_process * creator, 1039 const char * _path, 941 const char * _path, 1040 sos_size_t _pathlen, 942 sos_size_t _pathlen, 1041 sos_ui32_t access_righ 943 sos_ui32_t access_rights); 1042 944 1043 sos_ret_t sos_fs_rmdir(const struct sos_proce 945 sos_ret_t sos_fs_rmdir(const struct sos_process * actor, 1044 const char * _path, 946 const char * _path, 1045 sos_size_t _pathlen); 947 sos_size_t _pathlen); 1046 948 1047 sos_ret_t sos_fs_chmod(const struct sos_proce 949 sos_ret_t sos_fs_chmod(const struct sos_process * actor, 1048 const char * _path, 950 const char * _path, 1049 sos_size_t _pathlen, 951 sos_size_t _pathlen, 1050 sos_ui32_t access_righ 952 sos_ui32_t access_rights); 1051 953 1052 sos_ret_t sos_fs_stat(const struct sos_proces 954 sos_ret_t sos_fs_stat(const struct sos_process * actor, 1053 const char * _path, 955 const char * _path, 1054 sos_size_t _pathlen, 956 sos_size_t _pathlen, 1055 int nofollow, 957 int nofollow, 1056 struct sos_fs_stat * re 958 struct sos_fs_stat * result); 1057 959 1058 960 1059 /* ****************************************** 961 /* *************************************************************** 1060 * Restricted functions reserved to FS code a 962 * Restricted functions reserved to FS code and block/char devices 1061 */ 963 */ 1062 964 1063 /** 965 /** 1064 * Function to be called when proposing a new 966 * Function to be called when proposing a new File system type 1065 */ 967 */ 1066 sos_ret_t sos_fs_register_fs_type(struct sos_ 968 sos_ret_t sos_fs_register_fs_type(struct sos_fs_manager_type * fstype); 1067 sos_ret_t sos_fs_unregister_fs_type(struct so 969 sos_ret_t sos_fs_unregister_fs_type(struct sos_fs_manager_type * fstype); 1068 970 1069 /** 971 /** 1070 * Marthe given file as dirty, for FS support 972 * Marthe given file as dirty, for FS supporting deferred write access 1071 * mode 973 * mode 1072 */ 974 */ 1073 sos_ret_t sos_fs_mark_dirty(struct sos_fs_ope 975 sos_ret_t sos_fs_mark_dirty(struct sos_fs_opened_file * of); 1074 976 1075 /** 977 /** 1076 * Helper function to be called from the moun 978 * Helper function to be called from the mount() method of the FS 1077 * instance code. Responsible for creating an 979 * instance code. Responsible for creating and updating the "root" 1078 * field of the FS instance structure and for 980 * field of the FS instance structure and for connecting this FS in 1079 * the nscache 981 * the nscache 1080 * @param root_fsnode The root of the FS bein 982 * @param root_fsnode The root of the FS being mounted 1081 */ 983 */ 1082 sos_ret_t sos_fs_register_fs_instance(struct 984 sos_ret_t sos_fs_register_fs_instance(struct sos_fs_manager_instance * fs, 1083 struct 985 struct sos_fs_node * root_fsnode); 1084 986 1085 /** 987 /** 1086 * Helper function to be called from the umou 988 * Helper function to be called from the umount() method of the FS 1087 * instance code. Responsible for unregisteri 989 * instance code. Responsible for unregistering the instance from the 1088 * FS type's instances list and for disconnec 990 * FS type's instances list and for disconnecting this mountpoint in 1089 * the nscache. 991 * the nscache. 1090 */ 992 */ 1091 sos_ret_t sos_fs_unregister_fs_instance(struc 993 sos_ret_t sos_fs_unregister_fs_instance(struct sos_fs_manager_instance * fs); 1092 994 1093 995 1094 /* ****************************************** 996 /* *************************************************************** 1095 * Restricted functions reserved to syscall.c 997 * Restricted functions reserved to syscall.c 1096 */ 998 */ 1097 sos_ret_t sos_fs_ref_opened_file(struct sos_f 999 sos_ret_t sos_fs_ref_opened_file(struct sos_fs_opened_file * of); 1098 sos_ret_t _sos_fs_unref_opened_file(struct so 1000 sos_ret_t _sos_fs_unref_opened_file(struct sos_fs_opened_file ** of); 1099 #define sos_fs_unref_opened_file(f) _sos_fs_u 1001 #define sos_fs_unref_opened_file(f) _sos_fs_unref_opened_file(&(f)) 1100 1002 1101 1003 1102 /* ****************************************** 1004 /* *************************************************************** 1103 * Restricted functions to be used only by fs 1005 * Restricted functions to be used only by fs_nscache.c 1104 */ 1006 */ 1105 1007 1106 sos_ret_t sos_fs_ref_fsnode(struct sos_fs_nod 1008 sos_ret_t sos_fs_ref_fsnode(struct sos_fs_node * fsnode); 1107 1009 1108 sos_ret_t _sos_fs_unref_fsnode(struct sos_fs_ 1010 sos_ret_t _sos_fs_unref_fsnode(struct sos_fs_node * fsnode); 1109 #define sos_fs_unref_fsnode(n) \ 1011 #define sos_fs_unref_fsnode(n) \ 1110 ({ sos_ret_t __retval = _sos_fs_unref_fsnod 1012 ({ sos_ret_t __retval = _sos_fs_unref_fsnode(n); (n)=NULL; __retval; }) 1111 1013 1112 1014 1113 /* ****************************************** 1015 /* *************************************************************** 1114 * Restricted functions reserved to process.c 1016 * Restricted functions reserved to process.c and main.c:start_init() 1115 */ 1017 */ 1116 sos_ret_t sos_fs_new_opened_file(const struct 1018 sos_ret_t sos_fs_new_opened_file(const struct sos_process * proc, 1117 struct sos_f 1019 struct sos_fs_nscache_node * nsnode, 1118 sos_ui32_t o 1020 sos_ui32_t open_flags, 1119 struct sos_f 1021 struct sos_fs_opened_file ** result_of); 1120 1022 1121 1023 1122 sos_ret_t sos_fs_duplicate_opened_file(struct 1024 sos_ret_t sos_fs_duplicate_opened_file(struct sos_fs_opened_file * src_of, 1123 const 1025 const struct sos_process * dst_proc, 1124 struct 1026 struct sos_fs_opened_file ** result_of); 1125 1027 1126 1028 1127 1029 1128 #endif /* _SOS_FS_H_ */ 1030 #endif /* _SOS_FS_H_ */
[ source navigation ] | [ diff markup ] | [ identifier search ] | [ general search ] |