VFS, DeviceFS: Implement a device filesystem
For now, we just have a version device. (this will allow us to get rid of sys_getversion!!) More should be implemented soon.
This commit is contained in:
parent
a198cf8d8d
commit
0a7d4a530d
@ -8,6 +8,39 @@
|
||||
|
||||
typedef long ssize_t;
|
||||
|
||||
int print_version()
|
||||
{
|
||||
char version[4096];
|
||||
|
||||
FILE* verfile = fopen("/dev/version", "r");
|
||||
if (!verfile)
|
||||
{
|
||||
perror("fopen");
|
||||
return 1;
|
||||
}
|
||||
|
||||
size_t nread = fread(version, 4096, 1, verfile);
|
||||
if (ferror(verfile))
|
||||
{
|
||||
perror("fread");
|
||||
return 1;
|
||||
}
|
||||
|
||||
printf("Read %zd bytes\n", nread);
|
||||
|
||||
version[nread] = 0;
|
||||
|
||||
if (fclose(verfile) < 0)
|
||||
{
|
||||
perror("fclose");
|
||||
return 1;
|
||||
}
|
||||
|
||||
printf("Your kernel version is %s\n\n", version);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
if (gettid() == 0) // why are we the idle task?
|
||||
@ -21,10 +54,7 @@ int main()
|
||||
|
||||
sleep(1);
|
||||
|
||||
char version[40];
|
||||
syscall(SYS_getversion, version, sizeof(version));
|
||||
|
||||
printf("Your kernel version is %s\n\n", version);
|
||||
if (print_version()) return 1;
|
||||
|
||||
sleep(2);
|
||||
|
||||
|
@ -38,6 +38,7 @@ namespace VFS
|
||||
Node* resolve_path(const char* filename, Node* root = nullptr);
|
||||
|
||||
void mount(Node* mountpoint, Node* mounted);
|
||||
void mount(const char* pathname, Node* mounted);
|
||||
|
||||
void unmount(Node* mountpoint);
|
||||
|
||||
|
9
kernel/include/fs/devices/DeviceFS.h
Normal file
9
kernel/include/fs/devices/DeviceFS.h
Normal file
@ -0,0 +1,9 @@
|
||||
#pragma once
|
||||
#include "fs/VFS.h"
|
||||
|
||||
namespace DeviceFS
|
||||
{
|
||||
VFS::Node* get();
|
||||
|
||||
VFS::Node* finddir(VFS::Node* node, const char* filename);
|
||||
}
|
9
kernel/include/fs/devices/Version.h
Normal file
9
kernel/include/fs/devices/Version.h
Normal file
@ -0,0 +1,9 @@
|
||||
#pragma once
|
||||
#include "fs/VFS.h"
|
||||
|
||||
namespace VersionDevice
|
||||
{
|
||||
VFS::Node* create_new();
|
||||
|
||||
ssize_t read(VFS::Node* node, size_t offset, size_t size, char* buffer);
|
||||
}
|
@ -134,6 +134,11 @@ void VFS::mount(Node* mountpoint, Node* mounted)
|
||||
mountpoint->flags |= VFS_MOUNTPOINT;
|
||||
}
|
||||
|
||||
void VFS::mount(const char* pathname, Node* mounted)
|
||||
{
|
||||
return mount(resolve_path(pathname), mounted);
|
||||
}
|
||||
|
||||
void VFS::unmount(Node* mountpoint)
|
||||
{
|
||||
if (!mountpoint) return;
|
||||
|
35
kernel/src/fs/devices/DeviceFS.cpp
Normal file
35
kernel/src/fs/devices/DeviceFS.cpp
Normal file
@ -0,0 +1,35 @@
|
||||
#include "fs/devices/DeviceFS.h"
|
||||
#include "fs/devices/Version.h"
|
||||
#include "std/stdlib.h"
|
||||
#include "std/string.h"
|
||||
|
||||
#define DEVFS_MAX_FILES 32
|
||||
|
||||
VFS::Node* devfs_root = nullptr;
|
||||
|
||||
VFS::Node* devfs_files[DEVFS_MAX_FILES];
|
||||
int devfs_file_count = 0;
|
||||
|
||||
VFS::Node* DeviceFS::get()
|
||||
{
|
||||
if (devfs_root) return devfs_root;
|
||||
devfs_root = new VFS::Node;
|
||||
devfs_root->length = 0;
|
||||
devfs_root->inode = 0;
|
||||
devfs_root->type = VFS_DIRECTORY;
|
||||
devfs_root->find_func = DeviceFS::finddir;
|
||||
strncpy(devfs_root->name, "dev", sizeof(devfs_root->name));
|
||||
|
||||
devfs_files[devfs_file_count++] = VersionDevice::create_new();
|
||||
return devfs_root;
|
||||
}
|
||||
|
||||
VFS::Node* DeviceFS::finddir(VFS::Node* node, const char* filename)
|
||||
{
|
||||
if (!node) return 0;
|
||||
for (int i = 0; i < devfs_file_count; i++)
|
||||
{
|
||||
if (strncmp(devfs_files[i]->name, filename, sizeof(VFS::Node::name)) == 0) { return devfs_files[i]; }
|
||||
}
|
||||
return 0;
|
||||
}
|
26
kernel/src/fs/devices/Version.cpp
Normal file
26
kernel/src/fs/devices/Version.cpp
Normal file
@ -0,0 +1,26 @@
|
||||
#include "fs/devices/Version.h"
|
||||
#include "config.h"
|
||||
#include "std/stdio.h"
|
||||
#include "std/stdlib.h"
|
||||
#include "std/string.h"
|
||||
|
||||
VFS::Node* VersionDevice::create_new()
|
||||
{
|
||||
VFS::Node* dev = new VFS::Node;
|
||||
dev->read_func = VersionDevice::read;
|
||||
dev->inode = 0;
|
||||
dev->length = strlen(moon_version()) + 5;
|
||||
dev->type = VFS_FILE;
|
||||
strncpy(dev->name, "version", sizeof(dev->name));
|
||||
return dev;
|
||||
}
|
||||
|
||||
ssize_t VersionDevice::read(VFS::Node* node, size_t offset, size_t size, char* buffer)
|
||||
{
|
||||
if (!node) return -1;
|
||||
if (offset > node->length) return -1;
|
||||
if (offset + size > node->length) { size = node->length - offset; }
|
||||
if (offset > 0) return -1;
|
||||
snprintf(buffer, size + 1, "moon %s", moon_version()); // FIXME: Support offseting this read
|
||||
return (ssize_t)size;
|
||||
}
|
@ -5,6 +5,7 @@
|
||||
#include "config.h"
|
||||
#include "cpu/CPU.h"
|
||||
#include "fs/VFS.h"
|
||||
#include "fs/devices/DeviceFS.h"
|
||||
#include "gdt/GDT.h"
|
||||
#include "init/Init.h"
|
||||
#include "init/InitRD.h"
|
||||
@ -158,30 +159,13 @@ extern "C" void _start()
|
||||
|
||||
Init::finish_kernel_boot();
|
||||
|
||||
VFS::mkdir("/", "dev");
|
||||
VFS::mount("/dev", DeviceFS::get());
|
||||
|
||||
Interrupts::enable();
|
||||
|
||||
kinfoln("Interrupts enabled");
|
||||
|
||||
kinfoln("Trying VFS");
|
||||
|
||||
if (VFS::mkdir("/", "rootfs") < 0) { kerrorln("Unable to create directory rootfs"); }
|
||||
else
|
||||
{
|
||||
VFS::mount(VFS::resolve_path("/rootfs"), VFS::root());
|
||||
VFS::Node* node = VFS::resolve_path("/rootfs/sys/config");
|
||||
if (!node) kerrorln("unable to find /sys/config in VFS");
|
||||
else
|
||||
{
|
||||
kinfoln("Found '%s'", node->name);
|
||||
char* buffer = (char*)kmalloc(node->length + 1);
|
||||
buffer[node->length] = 0;
|
||||
ssize_t nread = VFS::read(node, 0, node->length, buffer);
|
||||
kdbgln("Read %zd bytes", nread);
|
||||
kinfoln("Read: %s", buffer);
|
||||
kfree(buffer);
|
||||
}
|
||||
}
|
||||
|
||||
PCI::scan([](PCI::Device& dev) {
|
||||
kinfoln("Found PCI device %x:%x, %s", dev.id().vendor, dev.id().device, pci_type_name(dev.type()));
|
||||
});
|
||||
|
Loading…
Reference in New Issue
Block a user