diff --git a/README.md b/README.md deleted file mode 100644 index 7a6beca..0000000 --- a/README.md +++ /dev/null @@ -1,33 +0,0 @@ -an operating system made in nasm assembly and (in the future) zig, using the zig build system. -this project is based on [this video series](https://www.youtube.com/playlist?list=PLFjM7v6KGMpiH2G-kT781ByCNC_0pKpPN) by [nanobyte](https://www.youtube.com/@nanobyte-dev) - -# HOWTO - -## dependencies - -this project requires the nasm assembler, mtools for floppy disk generation and zig to build. -this project uses qemu as the default emulator, but this is optional - -## building - -```bash -git clone https://dario48.site/git/Dario48/zos.git -cd zos -zig build -``` - -## running - -- with the default emulator - -```bash -cd zos -zig build run -``` - -- with a different emulator - -```bash -cd zos -emulator_cmd zig-out/bin/main_floppy.img -``` diff --git a/build.zig b/build.zig index e4051ee..712b389 100644 --- a/build.zig +++ b/build.zig @@ -18,40 +18,16 @@ pub fn build(b: *std.Build) void { var floppy = createFloppy(b, "main_floppy.img"); floppy.run = formatFloppyFat12(b, floppy); - var installToFloppy = installImgToFloppy(b, floppy, initramfs, &.{ - NamedFile{ .file = .{ .runFile = kernel }, .name = "::kernel.bin" }, - NamedFile{ .file = .{ .simpleFile = b.path("src/reference_implementations/test.txt") }, .name = "::test.txt" }, - }); - const img_install = b.addInstallBinFile(floppy.obj, "main_floppy.img"); - img_install.step.dependOn(&installToFloppy); + img_install.step.dependOn(&installImgToFloppy(b, floppy, initramfs, kernel).step); b.getInstallStep().dependOn(&img_install.step); - const target = b.standardTargetOptions(.{}); - const fat_reference_mod = b.createModule(.{ - .root_source_file = b.path("src/reference_implementations/fat.zig"), - .target = target, - .link_libc = true, - }); - const run = b.addSystemCommand(&.{ "qemu-system-i386", "-fda" }); run.addFileArg(floppy.obj); const run_step = b.step("run", "run the os in qemu"); run_step.dependOn(&run.step); - - const fat_reference = b.addExecutable(.{ - .root_module = fat_reference_mod, - .name = "fat_reference_implementation", - .use_lld = false, - .use_llvm = false, - }); - - const fat_install = b.addInstallArtifact(fat_reference, .{}); - - const build_references = b.step("references", "build the reference implementations"); - build_references.dependOn(&fat_install.step); } const AddNasmFilesOptions = struct { @@ -67,11 +43,6 @@ const NasmFile = struct { const Floppydisk = NasmFile; -const NamedFile = struct { - file: union(enum) { runFile: NasmFile, simpleFile: std.Build.LazyPath }, - name: []const u8, -}; - fn createFloppy(b: *std.Build, name: []const u8) Floppydisk { const dd = b.addSystemCommand(&.{ "dd", "if=/dev/zero" }); const Floppy = dd.addPrefixedOutputFileArg("of=", name); @@ -92,7 +63,7 @@ fn formatFloppyFat12(b: *std.Build, floppy: Floppydisk) *std.Build.Step.Run { return mkfs; } -fn installImgToFloppy(b: *std.Build, floppy: Floppydisk, bootloader: NasmFile, additional_files: []const NamedFile) std.Build.Step { +fn installImgToFloppy(b: *std.Build, floppy: Floppydisk, bootloader: NasmFile, kernel: NasmFile) *std.Build.Step.Run { const dd = b.addSystemCommand(&.{"dd"}); dd.addPrefixedFileArg("if=", bootloader.obj); dd.addPrefixedFileArg("of=", floppy.obj); @@ -100,22 +71,14 @@ fn installImgToFloppy(b: *std.Build, floppy: Floppydisk, bootloader: NasmFile, a dd.step.dependOn(&floppy.run.step); dd.step.dependOn(&bootloader.run.step); - var mcopy_step = std.Build.Step.init(.{ .name = "mcopy", .owner = b, .id = .custom }); - mcopy_step.dependOn(&dd.step); - for (additional_files) |f| { - const mcopy = b.addSystemCommand(&.{"mcopy"}); - mcopy.addPrefixedFileArg("-i", floppy.obj); - switch (f.file) { - .runFile => |file| { - mcopy.addFileArg(file.obj); - mcopy_step.dependOn(&file.run.step); - }, - .simpleFile => |file| mcopy.addFileArg(file), - } - mcopy.addArg(f.name); - mcopy_step.dependOn(&mcopy.step); - } - return mcopy_step; + const mcopy = b.addSystemCommand(&.{"mcopy"}); + mcopy.addPrefixedFileArg("-i", floppy.obj); + mcopy.addFileArg(kernel.obj); + mcopy.addArg("::kernel.bin"); + mcopy.step.dependOn(&dd.step); + mcopy.step.dependOn(&kernel.run.step); + + return mcopy; } // adapted from https://codeberg.org/raddari/zig-nasm-lib.git diff --git a/build.zig.zon b/build.zig.zon index f29dbdf..365621b 100644 --- a/build.zig.zon +++ b/build.zig.zon @@ -28,7 +28,7 @@ // Tracks the earliest Zig version that the package considers to be a // supported use case. - .minimum_zig_version = "0.15.0", + .minimum_zig_version = "0.14.1", // This field is optional. // Each dependency must either provide a `url` and `hash`, or a `path`. diff --git a/src/reference_implementations/fat.zig b/src/reference_implementations/fat.zig deleted file mode 100644 index 61d7a0f..0000000 --- a/src/reference_implementations/fat.zig +++ /dev/null @@ -1,117 +0,0 @@ -const std = @import("std"); - -const Errors = error{ InvalidSyntax, ReadSectors, FileNotFound }; - -var buffer: [1024]u8 = undefined; - -var g_Fat: []u8 = undefined; - -const BootSector = extern struct { - BootJumpInstruction: [3]u8 align(1), - OemIdentifier: [8]u8 align(1), - BytesPerSector: u16 align(1), - SectorsPerCluster: u8 align(1), - ReservedSectors: u16 align(1), - FatCount: u8 align(1), - DirEntryCount: u16 align(1), - TotalSectors: u16 align(1), - MediaDescriptorType: u8 align(1), - SectorsPerFat: u16 align(1), - SectorsPerTrack: u16 align(1), - Heads: u16 align(1), - HiddenSectors: u32 align(1), - LargeSectorCount: u32 align(1), - - // ebr - DriveNumber: u8 align(1), - _Reserved: u8 align(1), - Signature: u8 align(1), - VolumeId: u32 align(1), - VolumeLaber: [11]u8 align(1), - SystemId: [8]u8 align(1), -}; - -var g_BootSector: BootSector = undefined; - -const DirectoryEntry = extern struct { - Name: [11]u8 align(1), - Attributes: u8 align(1), - _Reserved: u8 align(1), - CreatedTimeTenths: u8 align(1), - CreatedTime: u16 align(1), - CreatedDate: u16 align(1), - AccessedDate: u16 align(1), - FirstClusterHigh: u16 align(1), - ModifiedTime: u16 align(1), - ModifiedDate: u16 align(1), - FirstClusterLow: u16 align(1), - Size: u32 align(1), -}; - -var g_RootDirectory: []DirectoryEntry = undefined; - -fn readStruct(reader: *std.fs.File.Reader, T: type) !T { - var ret: [@sizeOf(T)]u8 = undefined; - _ = try reader.*.read(&ret); - return @bitCast(ret); -} - -fn readBootSector(disk: *std.fs.File) !void { - var reader = disk.*.reader(&buffer); - g_BootSector = try readStruct(&reader, BootSector); -} - -fn readSectors(disk: *std.fs.File, lba: u32, count: u32, bufferOut: *[]anyopaque) !void { - const dest: []u8 = try std.heap.smp_allocator.alloc(u8, g_BootSector.BytesPerSector * count); - defer std.heap.smp_allocator.free(dest); - var stream = disk.readerStreaming(&buffer); - try stream.seekTo(lba * g_BootSector.BytesPerSector); - if (try stream.readStreaming(dest) != g_BootSector.BytesPerSector * count) return Errors.ReadSectors; - @memcpy(@as(*[]u8, @ptrCast(bufferOut)).*, dest); -} - -fn readFat(disk: *std.fs.File) !void { - g_Fat = try std.heap.smp_allocator.alloc(u8, g_BootSector.SectorsPerFat * g_BootSector.BytesPerSector); - errdefer std.heap.smp_allocator.free(g_Fat); - try readSectors(disk, g_BootSector.ReservedSectors, g_BootSector.SectorsPerFat, &g_Fat); -} - -fn readRootDirectory(disk: std.fs.File) !void { - const lba: u32 = g_BootSector.ReservedSectors + g_BootSector.SectorsPerFat + g_BootSector.FatCount; - const size: u32 = @sizeOf(DirectoryEntry) * g_BootSector.DirEntryCount; - const sectors: u32 = (size / g_BootSector.BytesPerSector); - if (@rem(size, g_BootSector.BytesPerSector > 0)) - sectors += 1; - - g_RootDirectory = try std.heap.smp_allocator.alloc(DirectoryEntry, sectors * g_BootSector.BytesPerSector); - errdefer std.heap.smp_allocator.free(g_RootDirectory); - try readSectors(disk, lba, sectors, &g_RootDirectory); -} - -fn findFile(name: []const u8) !*DirectoryEntry { - for (g_RootDirectory, 0..) |Entry, i| - if (std.mem.eql(u8, Entry.Name, name)) - return &g_RootDirectory[i]; - return Errors.FileNotFound; -} - -pub fn main() !void { - if (std.os.argv.len < 3) { - std.log.err("syntax: {s} ", .{std.os.argv[0]}); - return Errors.InvalidSyntax; - } - - var disk = try std.fs.cwd().openFileZ(std.os.argv[1], .{ .mode = .read_only }); - - _ = &disk; - try readBootSector(&disk); - - try readFat(&disk); - defer std.heap.smp_allocator.free(g_Fat); - - try readRootDirectory(disk); - defer std.heap.smp_allocator.free(g_RootDirectory); - - const fileEntry = try findFile(std.os.argv[2]); - _ = fileEntry; -} diff --git a/src/reference_implementations/test.txt b/src/reference_implementations/test.txt deleted file mode 100644 index 20e13f9..0000000 --- a/src/reference_implementations/test.txt +++ /dev/null @@ -1,3 +0,0 @@ -testing file -aabaacaadaaeaafaagaahaaiaajaakaalaamaanaaoaapaaqaaraasaataauaavaawaaxaayaaz -tstngfl