Add filesystem driver
This commit is contained in:
@@ -1,6 +1,8 @@
|
||||
import { dwordin, dwordout } from "../../../lib/libts/dword";
|
||||
import { portin, portout } from "../../../lib/libts/port";
|
||||
import { Logger } from "../../../lib/libstd/logger/logger.kmod";
|
||||
import { sysfs_mkdir, sysfs_writeFile } from "../../filesystem/sysfs";
|
||||
import { Path } from "../../../lib/libstd/path";
|
||||
|
||||
const KDRIVER_PCI_CONFIG_ADDR = 0xcf8;
|
||||
const KDRIVER_PCI_CONFIG_DATA = 0xcfc;
|
||||
@@ -37,13 +39,11 @@ export function kdriver_dev_pci_checkDevice(
|
||||
const classCode = kdriver_dev_pci_getClassCode(bus, device, func);
|
||||
const subclass = kdriver_dev_pci_getSubclass(bus, device, func);
|
||||
|
||||
const filename = bus + ":" + device + ":" + func;
|
||||
|
||||
Logger.log(
|
||||
"[PCI] Found device pci:" +
|
||||
bus +
|
||||
":" +
|
||||
device +
|
||||
":" +
|
||||
func +
|
||||
filename +
|
||||
" (vendor:" +
|
||||
vendorId.toString(16) +
|
||||
", device:" +
|
||||
@@ -54,6 +54,14 @@ export function kdriver_dev_pci_checkDevice(
|
||||
subclass.toString(16) +
|
||||
")"
|
||||
);
|
||||
|
||||
const dirname = Path.join("/pci", filename);
|
||||
|
||||
sysfs_mkdir(dirname);
|
||||
sysfs_writeFile(Path.join(dirname, "vendor"), vendorId);
|
||||
sysfs_writeFile(Path.join(dirname, "device"), deviceId);
|
||||
sysfs_writeFile(Path.join(dirname, "class"), classCode);
|
||||
sysfs_writeFile(Path.join(dirname, "subclass"), subclass);
|
||||
}
|
||||
|
||||
export function kdriver_dev_pci_getDeviceId(
|
||||
|
||||
138
src/os/src/kernel/filesystem/sysfs.ts
Normal file
138
src/os/src/kernel/filesystem/sysfs.ts
Normal file
@@ -0,0 +1,138 @@
|
||||
import { Logger } from "../../lib/libstd/logger/logger.kmod";
|
||||
import { Path } from "../../lib/libstd/path";
|
||||
import type {
|
||||
KFilesystemDriver,
|
||||
KFilesystemEntity,
|
||||
KFilesystemMemdata,
|
||||
KFilesystemStat,
|
||||
} from "../../types/filesystem/fs";
|
||||
|
||||
const sysfs_data: KFilesystemMemdata = [];
|
||||
|
||||
export function sysfs_driver(): KFilesystemDriver {
|
||||
return {
|
||||
id: "sysfs",
|
||||
init: sysfs_init,
|
||||
listDir(path: string): KFilesystemEntity[] | null {
|
||||
return sysfs_listDir(path);
|
||||
},
|
||||
readFile(path: string): unknown {
|
||||
return sysfs_readFile(path);
|
||||
},
|
||||
writeFile(path: string, content: unknown): void {
|
||||
throw new Error("Cannot write to sysfs files.");
|
||||
},
|
||||
createFile(path: string, content: unknown): void {
|
||||
throw new Error("Cannot create files in sysfs.");
|
||||
},
|
||||
mkdir(path: string): void {
|
||||
throw new Error("Cannot create directories in sysfs.");
|
||||
},
|
||||
stat(path: string): KFilesystemStat | null {
|
||||
return sysfs_statEntity(path);
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
export function sysfs_init(): void {
|
||||
sysfs_data.push({
|
||||
name: "root",
|
||||
path: "/",
|
||||
type: "folder",
|
||||
size: 0,
|
||||
contents: null,
|
||||
});
|
||||
|
||||
sysfs_mkdir("/pci");
|
||||
}
|
||||
|
||||
export function sysfs_getEntity(path: string): KFilesystemEntity | null {
|
||||
for (let i = 0; i < sysfs_data.length; i++) {
|
||||
const entity = sysfs_data[i]!;
|
||||
|
||||
if (entity.path === path) return entity;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
export function sysfs_statEntity(path: string): KFilesystemStat | null {
|
||||
const entity = sysfs_getEntity(path);
|
||||
if (!entity) return null;
|
||||
|
||||
return {
|
||||
name: entity.name,
|
||||
type: entity.type,
|
||||
size: entity.size,
|
||||
};
|
||||
}
|
||||
|
||||
export function sysfs_mkdir(path: string): void {
|
||||
if (sysfs_getEntity(path)) return;
|
||||
|
||||
const parent = Path.dirname(path);
|
||||
if (!sysfs_getEntity(parent)) return;
|
||||
|
||||
sysfs_data.push({
|
||||
name: Path.filename(path),
|
||||
path,
|
||||
type: "folder",
|
||||
size: 0,
|
||||
contents: null,
|
||||
});
|
||||
}
|
||||
|
||||
export function sysfs_createFile(path: string, content: unknown): void {
|
||||
if (sysfs_getEntity(path)) return;
|
||||
|
||||
const parent = Path.dirname(path);
|
||||
if (!sysfs_getEntity(parent)) return;
|
||||
|
||||
const size = String(content).length;
|
||||
|
||||
sysfs_data.push({
|
||||
name: Path.filename(path),
|
||||
path,
|
||||
type: "file",
|
||||
size,
|
||||
contents: content,
|
||||
});
|
||||
}
|
||||
|
||||
export function sysfs_writeFile(path: string, content: unknown): void {
|
||||
const entity = sysfs_getEntity(path);
|
||||
if (!entity) return sysfs_createFile(path, content);
|
||||
|
||||
if (entity.type !== "file") return;
|
||||
|
||||
entity.contents = content;
|
||||
entity.size = String(content).length;
|
||||
}
|
||||
|
||||
export function sysfs_readFile(path: string): unknown {
|
||||
const entity = sysfs_getEntity(path);
|
||||
if (!entity) return null;
|
||||
|
||||
if (entity.type !== "file") return null;
|
||||
|
||||
return entity.contents;
|
||||
}
|
||||
|
||||
export function sysfs_listDir(path: string): KFilesystemEntity[] | null {
|
||||
const entity = sysfs_getEntity(path);
|
||||
if (!entity) return null;
|
||||
|
||||
if (entity.type !== "folder") return null;
|
||||
|
||||
const contents: KFilesystemEntity[] = [];
|
||||
|
||||
for (let i = 0; i < sysfs_data.length; i++) {
|
||||
const e = sysfs_data[i]!;
|
||||
|
||||
if (Path.dirname(e.path) === path) {
|
||||
contents.push(e);
|
||||
}
|
||||
}
|
||||
|
||||
return contents;
|
||||
}
|
||||
@@ -7,10 +7,16 @@ import {
|
||||
kdriver_etc_serial_read,
|
||||
kdriver_etc_serial_transmit,
|
||||
} from "./drivers/etc/serial";
|
||||
import { sysfs_driver, sysfs_readFile } from "./filesystem/sysfs";
|
||||
import {
|
||||
kmod_drivers_init,
|
||||
kmod_drivers_register,
|
||||
} from "./modules/drivers/drivers.kmod";
|
||||
import {
|
||||
kmod_filesystem_init,
|
||||
kmod_filesystem_mount,
|
||||
kmod_filesystem_readFile,
|
||||
} from "./modules/filesystem/filesystem.kmod";
|
||||
import {
|
||||
kmod_graphics_vga_clear,
|
||||
kmod_graphics_vga_init,
|
||||
@@ -23,11 +29,18 @@ export function kmain() {
|
||||
kmod_drivers_register();
|
||||
Logger.log("[Kernel] Drivers initialized.");
|
||||
|
||||
Logger.log("[Kernel] Initializing PCI...");
|
||||
Logger.log("[Kernel] Initializing filesystem module...");
|
||||
kmod_filesystem_init();
|
||||
kmod_filesystem_mount("/sys", sysfs_driver);
|
||||
|
||||
Logger.log("[Kernel] Initializing PCI devices...");
|
||||
kdriver_dev_pci_detectDevices();
|
||||
|
||||
Logger.log("[Kernel] Initializing VGA module...");
|
||||
kmod_graphics_vga_init();
|
||||
kmod_graphics_vga_pushLine("[Kernel] Kernel initialized successfully.");
|
||||
kmod_graphics_vga_pushLine("Current date: " + getDate().toDateString());
|
||||
kmod_graphics_vga_pushLine(
|
||||
Number(kmod_filesystem_readFile("/sys/pci/0:1:0/vendor")).toString(16)
|
||||
);
|
||||
}
|
||||
|
||||
111
src/os/src/kernel/modules/filesystem/filesystem.kmod.ts
Normal file
111
src/os/src/kernel/modules/filesystem/filesystem.kmod.ts
Normal file
@@ -0,0 +1,111 @@
|
||||
import { Logger } from "../../../lib/libstd/logger/logger.kmod";
|
||||
import type {
|
||||
KFilesystemDriver,
|
||||
KFilesystemEntity,
|
||||
KFilesystemMount,
|
||||
KFilesystemMountdata,
|
||||
KFilesystemStat,
|
||||
} from "../../../types/filesystem/fs";
|
||||
|
||||
const kmod_filesystem_data: KFilesystemMountdata = [];
|
||||
|
||||
export function kmod_filesystem_init(): void {}
|
||||
|
||||
export function kmod_filesystem_mount(
|
||||
mpoint: string,
|
||||
drv: () => KFilesystemDriver
|
||||
): void {
|
||||
const driver = drv();
|
||||
|
||||
driver.init();
|
||||
|
||||
kmod_filesystem_data.push({
|
||||
mountpoint: mpoint,
|
||||
driver: driver,
|
||||
});
|
||||
|
||||
Logger.log("[Filesystem] Mounted " + driver.id + " at " + mpoint);
|
||||
}
|
||||
|
||||
export function kmod_filesystem_findMount(p: string): KFilesystemMount | null {
|
||||
for (let i = 0; i < kmod_filesystem_data.length; i++) {
|
||||
const mount = kmod_filesystem_data[i]!;
|
||||
|
||||
if (p.startsWith(mount.mountpoint)) {
|
||||
return mount;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
export function kmod_filesystem_stripMountpoint(
|
||||
mount: KFilesystemMount,
|
||||
p: string
|
||||
): string {
|
||||
if (mount.mountpoint === "/") return p;
|
||||
|
||||
return p.slice(mount.mountpoint.length) || "/";
|
||||
}
|
||||
|
||||
export function kmod_filesystem_listDir(
|
||||
path: string
|
||||
): KFilesystemEntity[] | null {
|
||||
const mount = kmod_filesystem_findMount(path);
|
||||
if (!mount) return null;
|
||||
|
||||
const strippedPath = kmod_filesystem_stripMountpoint(mount, path);
|
||||
|
||||
return mount.driver.listDir(strippedPath);
|
||||
}
|
||||
|
||||
export function kmod_filesystem_readFile(path: string): unknown {
|
||||
const mount = kmod_filesystem_findMount(path);
|
||||
if (!mount) return null;
|
||||
|
||||
const strippedPath = kmod_filesystem_stripMountpoint(mount, path);
|
||||
|
||||
return mount.driver.readFile(strippedPath);
|
||||
}
|
||||
|
||||
export function kmod_filesystem_writeFile(
|
||||
path: string,
|
||||
content: unknown
|
||||
): void {
|
||||
const mount = kmod_filesystem_findMount(path);
|
||||
if (!mount) return;
|
||||
|
||||
const strippedPath = kmod_filesystem_stripMountpoint(mount, path);
|
||||
|
||||
mount.driver.writeFile(strippedPath, content);
|
||||
}
|
||||
|
||||
export function kmod_filesystem_createFile(
|
||||
path: string,
|
||||
content: unknown
|
||||
): void {
|
||||
const mount = kmod_filesystem_findMount(path);
|
||||
if (!mount) return;
|
||||
|
||||
const strippedPath = kmod_filesystem_stripMountpoint(mount, path);
|
||||
|
||||
mount.driver.createFile(strippedPath, content);
|
||||
}
|
||||
|
||||
export function kmod_filesystem_mkdir(path: string): void {
|
||||
const mount = kmod_filesystem_findMount(path);
|
||||
if (!mount) return;
|
||||
|
||||
const strippedPath = kmod_filesystem_stripMountpoint(mount, path);
|
||||
|
||||
mount.driver.mkdir(strippedPath);
|
||||
}
|
||||
|
||||
export function kmod_filesystem_stat(path: string): KFilesystemStat | null {
|
||||
const mount = kmod_filesystem_findMount(path);
|
||||
if (!mount) return null;
|
||||
|
||||
const strippedPath = kmod_filesystem_stripMountpoint(mount, path);
|
||||
|
||||
return mount.driver.stat(strippedPath);
|
||||
}
|
||||
30
src/os/src/lib/libstd/path.ts
Normal file
30
src/os/src/lib/libstd/path.ts
Normal file
@@ -0,0 +1,30 @@
|
||||
export const Path = {
|
||||
dirname(p: string): string {
|
||||
const parts = p.split("/");
|
||||
|
||||
parts.pop();
|
||||
|
||||
if (parts.length <= 1) return "/";
|
||||
|
||||
return parts.join("/");
|
||||
},
|
||||
filename(p: string): string {
|
||||
const parts = p.split("/");
|
||||
|
||||
const n = parts.pop();
|
||||
|
||||
if (!n) return "";
|
||||
return n;
|
||||
},
|
||||
join(p1: string, p2: string): string {
|
||||
if (p1.endsWith("/")) {
|
||||
p1 = p1.slice(0, -1);
|
||||
}
|
||||
|
||||
if (p2.startsWith("/")) {
|
||||
p2 = p2.slice(1);
|
||||
}
|
||||
|
||||
return p1 + "/" + p2;
|
||||
},
|
||||
};
|
||||
33
src/os/src/types/filesystem/fs.ts
Normal file
33
src/os/src/types/filesystem/fs.ts
Normal file
@@ -0,0 +1,33 @@
|
||||
export type KFilesystemMountdata = KFilesystemMount[];
|
||||
|
||||
export type KFilesystemMount = {
|
||||
mountpoint: string;
|
||||
driver: KFilesystemDriver;
|
||||
};
|
||||
|
||||
export type KFilesystemDriver = {
|
||||
id: string;
|
||||
init: () => void;
|
||||
listDir(path: string): KFilesystemEntity[] | null;
|
||||
readFile(path: string): unknown;
|
||||
writeFile(path: string, content: unknown): void;
|
||||
createFile(path: string, content: unknown): void;
|
||||
mkdir(path: string): void;
|
||||
stat(path: string): KFilesystemStat | null;
|
||||
};
|
||||
|
||||
export type KFilesystemMemdata = KFilesystemEntity[];
|
||||
|
||||
export type KFilesystemEntity = {
|
||||
name: string;
|
||||
path: string;
|
||||
size: number;
|
||||
contents: unknown;
|
||||
type: "file" | "folder";
|
||||
};
|
||||
|
||||
export type KFilesystemStat = {
|
||||
name: string;
|
||||
type: "file" | "folder";
|
||||
size: number;
|
||||
};
|
||||
Reference in New Issue
Block a user