AquilaOS documentation
How it works, and its code
Loading...
Searching...
No Matches
mount.c
Go to the documentation of this file.
1
5
6#include <core/system.h>
7#include <core/string.h>
8#include <fs/vfs.h>
9#include <fs/devfs.h>
10#include <dev/dev.h>
11#include <ds/queue.h>
12
13/* the mounts, for /proc/mounts */
15
16MALLOC_DEFINE(M_MOUNTPOINT, "mountpoint", "mount point structure");
17
29int vfs_mount(const char *type, const char *dir, int flags, void *data, struct uio *uio)
30{
31 struct fs *fs = NULL;
32
33 /* find the filesystem */
34 for (struct fs_list *entry = registered_fs; entry; entry = entry->next) {
35 if (!strcmp(entry->name, type)) {
36 fs = entry->fs;
37 break;
38 }
39 }
40
41 if (!fs)
42 return -EINVAL;
43
44 /* the directory it goes on */
45 struct vnode *covered = NULL;
46 int err;
47
48 if ((err = vfs_lookup(dir, uio, &covered)))
49 return err;
50
51 if (!S_ISDIR(covered->mode)) {
53 return -ENOTDIR;
54 }
55
56 if (covered->mounted) {
58 return -EBUSY;
59 }
60
61 /* where it is, for /proc/mounts */
62 char *path = kmalloc(1024, &M_BUFFER, 0);
63
64 if (!path || vfs_vnode_path(covered, NULL, path, 1024))
65 err = path ? -ENAMETOOLONG : -ENOMEM;
66 else
67 err = fs->mount(covered, flags, data);
68
69 /* record the mount for /proc/mounts; with no memory for that, the
70 * mount stays but isn't listed, and a name that couldn't be copied
71 * shows as "?" */
72 struct mountpoint *mp;
73
74 if (err == 0 && (mp = kmalloc(sizeof(struct mountpoint), &M_MOUNTPOINT, 0))) {
75 struct {
76 char *dev;
77 char *opt;
78 } *args = data;
79
80 const char *dev = (args && args->dev) ? strdup(args->dev) : "none";
81 const char *t = strdup(type), *p = strdup(path);
82
83 mp->dev = dev ? dev : "?";
84 mp->type = t ? t : "?";
85 mp->path = p ? p : "?";
86 mp->options = "";
87
88 if (!enqueue(mounts, mp))
89 kfree(mp);
90 }
91
92 kfree(path);
93 vfs_close(covered);
94
95 return err;
96}
97
100static int root_dev(const char *name, dev_t *dev)
101{
102 if (strncmp(name, "/dev/hd", 7) || name[7] < 'a' || name[7] > 'd' ||
103 name[8] < '1' || name[8] > '4' || name[9])
104 return -ENODEV;
105
106 *dev = DEV(3, (name[7] - 'a') * 64 + name[8] - '0');
107 return 0;
108}
109
120int vfs_mount_root_dev(const char *name, const char *type)
121{
122 struct fs *fs = NULL;
123 dev_t rdev;
124 int err;
125
126 if ((err = root_dev(name, &rdev)))
127 return err;
128
129 if (!type)
130 type = "ext2";
131
132 for (struct fs_list *entry = registered_fs; entry; entry = entry->next) {
133 if (!strcmp(entry->name, type)) {
134 fs = entry->fs;
135 break;
136 }
137 }
138
139 if (!fs || !fs->load)
140 return -EINVAL;
141
142 struct vnode *dev = kmalloc(sizeof(struct vnode), &M_VNODE, M_ZERO);
143 if (!dev) return -ENOMEM;
144
145 dev->mode = S_IFBLK;
146 dev->rdev = rdev;
147 dev->fs = &devfs;
148 dev->ref = 1;
149
150 struct vnode *root = NULL;
151
152 if ((err = fs->load(dev, &root))) {
153 kfree(dev);
154 return err;
155 }
156
157 printk("kernel: root is %s (%s)\n", name, type);
158 return vfs_mount_root(root);
159}
int vfs_close(struct vnode *vnode)
Drops a reference to a vnode.
Definition close.c:18
#define DEV(major, minor)
Definition dev.h:76
struct fs devfs
Definition devfs.c:60
#define MALLOC_DEFINE(type, _name, _desc)
Definition kvmem.h:30
void * kmalloc(size_t size, struct malloc_type *type, int flags)
Allocates memory for one of the kernel's structures.
Definition kvmem.c:123
#define M_ZERO
Definition kvmem.h:26
void kfree(void *)
Frees an object that kmalloc() gave.
Definition kvmem.c:146
int vfs_lookup(const char *path, struct uio *uio, struct vnode **ref)
Finds the vnode a path names.
Definition lookup.c:349
int vfs_vnode_path(struct vnode *vnode, struct vnode *root, char *buf, size_t size)
Computes a vnode's path, for getcwd() and /proc/mounts: it goes up through .., and finds each directo...
Definition lookup.c:532
int vfs_mount_root_dev(const char *name, const char *type)
Mounts the root filesystem from a disk partition (the root=/dev/hda2 kernel argument).
Definition mount.c:120
struct queue * mounts
Definition mount.c:14
static int root_dev(const char *name, dev_t *dev)
Gets the device number of an ATA disk partition, by its name (/dev/hda1 to /dev/hdd4).
Definition mount.c:100
int vfs_mount(const char *type, const char *dir, int flags, void *data, struct uio *uio)
Mounts a filesystem of a type on a directory, for mount().
Definition mount.c:29
int printk(const char *fmt,...)
Writes a kernel message, to the message buffer and the consoles.
Definition printk.c:249
#define QUEUE_NEW()
Definition queue.h:40
#define NULL
Definition stddef.h:27
A device driver: its operations, any of which may be NULL.
Definition dev.h:28
The list of registered filesystem types.
Definition vfs.h:187
struct fs_list * next
the next entry of the list
Definition vfs.h:195
A filesystem type.
Definition vfs.h:98
int(*) mount(struct vnode *dir, int flags, void *data)
Definition vfs.h:102
char * name
Definition vfs.h:99
int(*) load(struct vnode *dev, struct vnode **super)
Definition vfs.h:101
A mount's description, as /proc/mounts shows it.
Definition vfs.h:307
const char * type
Definition vfs.h:310
const char * options
Definition vfs.h:311
const char * path
Definition vfs.h:309
const char * dev
Definition vfs.h:308
A queue.
Definition queue.h:29
int flags
Definition queue.h:33
Who does a filesystem operation: where its paths start, and its credentials and umask.
Definition vfs.h:60
A file in memory (a vnode): what its inode says, and the kernel's own state.
Definition vfs.h:113
struct vnode * covered
Definition vfs.h:149
mode_t mode
Definition vfs.h:118
struct vnode * mounted
for a directory that a filesystem is mounted on, that filesystem's root; for a mounted filesystem's r...
Definition vfs.h:148
dev_t rdev
Definition vfs.h:117
uint16_t dev_t
Definition types.h:18
int vfs_mount_root(struct vnode *vnode)
Makes a vnode the root of the filesystem tree.
Definition vfs.c:37
struct fs_list * registered_fs
The installed filesystems.
Definition vfs.c:25