feat: implement fsync(2) and hard link support [link(2)]
[lunaix-os.git] / lunaix-os / includes / lunaix / fs.h
1 #ifndef __LUNAIX_VFS_H
2 #define __LUNAIX_VFS_H
3
4 #include <hal/ahci/hba.h>
5 #include <lunaix/block.h>
6 #include <lunaix/ds/hashtable.h>
7 #include <lunaix/ds/hstr.h>
8 #include <lunaix/ds/llist.h>
9 #include <lunaix/status.h>
10
11 #define VFS_NAME_MAXLEN 128
12 #define VFS_MAX_FD 32
13
14 #define VFS_INODE_TYPE_DIR 0x1
15 #define VFS_INODE_TYPE_FILE 0x2
16 #define VFS_INODE_TYPE_DEVICE 0x4
17 #define VFS_INODE_TYPE_SYMLINK 0x8
18
19 #define VFS_ENOFS -2
20 #define VFS_EBADMNT -3
21
22 #define VFS_EENDOFDIR -5
23
24 #define VFS_EINVLD -8
25 #define VFS_EEOF -9
26
27 #define VFS_WALK_MKPARENT 0x1
28 #define VFS_WALK_FSRELATIVE 0x2
29 #define VFS_WALK_PARENT 0x4
30
31 #define VFS_IOBUF_FDIRTY 0x1
32
33 #define FSTYPE_ROFS 0x1
34
35 #define VFS_VALID_CHAR(chr)                                                    \
36     ('A' <= (chr) && (chr) <= 'Z' || 'a' <= (chr) && (chr) <= 'z' ||           \
37      '0' <= (chr) && (chr) <= '9' || (chr) == '.' || (chr) == '_' ||           \
38      (chr) == '-')
39
40 extern struct hstr vfs_ddot;
41 extern struct hstr vfs_dot;
42
43 struct v_dnode;
44
45 struct filesystem
46 {
47     struct hlist_node fs_list;
48     struct hstr fs_name;
49     uint32_t types;
50     int (*mount)(struct v_superblock* vsb, struct v_dnode* mount_point);
51     int (*unmount)(struct v_superblock* vsb);
52 };
53
54 struct v_superblock
55 {
56     struct llist_header sb_list;
57     int fs_id;
58     bdev_t dev;
59     struct v_dnode* root;
60     struct filesystem* fs;
61     uint32_t iobuf_size;
62     struct
63     {
64         uint32_t (*read_capacity)(struct v_superblock* vsb);
65         uint32_t (*read_usage)(struct v_superblock* vsb);
66     } ops;
67 };
68
69 struct dir_context
70 {
71     int index;
72     void* cb_data;
73     void (*read_complete_callback)(struct dir_context* dctx,
74                                    const char* name,
75                                    const int len,
76                                    const int dtype);
77 };
78
79 struct v_file_ops
80 {
81     int (*write)(struct v_file* file, void* buffer, size_t len);
82     int (*read)(struct v_file* file, void* buffer, size_t len);
83     int (*readdir)(struct v_file* file, struct dir_context* dctx);
84     int (*seek)(struct v_file* file, size_t offset);
85     int (*rename)(struct v_file* file, char* new_name);
86     int (*close)(struct v_file* file);
87     int (*sync)(struct v_file* file);
88 };
89
90 struct v_file
91 {
92     struct v_inode* inode;
93     struct v_dnode* dnode;
94     struct llist_header* f_list;
95     uint32_t f_pos;
96     void* data; // 允许底层FS绑定他的一些专有数据
97     struct v_file_ops ops;
98 };
99
100 struct v_fd
101 {
102     struct v_file* file;
103     int pos;
104 };
105
106 struct v_inode
107 {
108     uint32_t itype;
109     uint32_t ctime;
110     uint32_t mtime;
111     uint64_t lb_addr;
112     uint32_t open_count;
113     uint32_t link_count;
114     uint32_t lb_usage;
115     uint32_t fsize;
116     void* data; // 允许底层FS绑定他的一些专有数据
117     struct
118     {
119         int (*create)(struct v_inode* this, struct v_file* file);
120         int (*open)(struct v_inode* this, struct v_file* file);
121         int (*sync)(struct v_inode* this);
122         int (*mkdir)(struct v_inode* this, struct v_dnode* dnode);
123         int (*rmdir)(struct v_inode* this);
124         int (*unlink)(struct v_inode* this);
125         int (*link)(struct v_inode* this, struct v_dnode* new_name);
126         int (*dir_lookup)(struct v_inode* this, struct v_dnode* dnode);
127     } ops;
128 };
129
130 struct v_dnode
131 {
132     struct hstr name;
133     struct v_inode* inode;
134     struct v_dnode* parent;
135     struct hlist_node hash_list;
136     struct llist_header children;
137     struct llist_header siblings;
138     struct v_superblock* super_block;
139     struct
140     {
141         void (*destruct)(struct v_dnode* dnode);
142     } ops;
143 };
144
145 struct v_fdtable
146 {
147     struct v_fd* fds[VFS_MAX_FD];
148 };
149
150 /* --- file system manager --- */
151 void
152 fsm_init();
153
154 void
155 fsm_register(struct filesystem* fs);
156
157 struct filesystem*
158 fsm_get(const char* fs_name);
159
160 void
161 vfs_init();
162
163 struct v_dnode*
164 vfs_dcache_lookup(struct v_dnode* parent, struct hstr* str);
165
166 void
167 vfs_dcache_add(struct v_dnode* parent, struct v_dnode* dnode);
168
169 int
170 vfs_walk(struct v_dnode* start,
171          const char* path,
172          struct v_dnode** dentry,
173          struct hstr* component,
174          int walk_options);
175
176 int
177 vfs_mount(const char* target, const char* fs_name, bdev_t device);
178
179 int
180 vfs_unmount(const char* target);
181
182 int
183 vfs_mount_at(const char* fs_name, bdev_t device, struct v_dnode* mnt_point);
184
185 int
186 vfs_unmount_at(struct v_dnode* mnt_point);
187
188 int
189 vfs_mkdir(const char* path, struct v_dnode** dentry);
190
191 int
192 vfs_open(struct v_dnode* dnode, struct v_file** file);
193
194 int
195 vfs_close(struct v_file* file);
196
197 int
198 vfs_fsync(struct v_file* file);
199
200 struct v_superblock*
201 vfs_sb_alloc();
202
203 void
204 vfs_sb_free(struct v_superblock* sb);
205
206 struct v_dnode*
207 vfs_d_alloc();
208
209 void
210 vfs_d_free(struct v_dnode* dnode);
211
212 struct v_inode*
213 vfs_i_alloc();
214
215 void
216 vfs_i_free(struct v_inode* inode);
217 #endif /* __LUNAIX_VFS_H */