Restructure file module

This commit is contained in:
Riyyi
2026-08-02 13:04:53 +02:00
parent 3992c80e6b
commit 856befd876
3 changed files with 153 additions and 143 deletions
-143
View File
@@ -1,150 +1,7 @@
package file package file
import "core:fmt"
import "core:os"
import "core:strings"
// TODO: // TODO:
// - list files in directory // - list files in directory
// - get relative path // - get relative path
// - read file contents // - read file contents
// - write file contents // - write file contents
// -----------------------------------------
Asset :: struct #all_or_none {
relpath: string,
size: i64,
data: []u8,
}
DirectoryEntry :: struct #all_or_none {
relpath: string,
size: i64,
}
// -----------------------------------------
list_dir_by_path :: proc(path: string) -> [dynamic]DirectoryEntry {
if !os.is_dir(path) {
fmt.eprintln("error: path is not a directory:", path)
os.exit(1)
}
f, open_err := os.open(path, {.Read})
if open_err != nil {
fmt.eprintln("error: open failed:", open_err)
os.exit(1)
}
defer os.close(f)
result := [dynamic]DirectoryEntry{}
list_dir_impl(f, &result)
return result
}
list_dir :: proc(f: ^os.File) -> [dynamic]DirectoryEntry {
path := os.name(f)
if !os.is_dir(path) {
fmt.eprintln("error: path is not a directory:", path)
os.exit(1)
}
result := [dynamic]DirectoryEntry{}
list_dir_impl(f, &result)
return result
}
@(private)
list_dir_impl :: proc(f: ^os.File, builder: ^[dynamic]DirectoryEntry) {
entries, read_err := os.read_all_directory(f, context.allocator)
if read_err != nil {
fmt.eprintln("error: read directory failed:", read_err)
os.exit(1)
}
defer delete(entries)
// Reserve space for new entries
reserve(builder, cap(builder) + len(entries))
working_dir, wd_err := os.get_working_directory(context.allocator)
if wd_err != nil {
fmt.eprintln("error: get working directory failed:", wd_err)
os.exit(1)
}
defer delete(working_dir)
for entry, i in entries {
if entry.type == os.File_Type.Regular {
relpath, rel_err := strings.replace(
entry.fullpath,
working_dir,
".",
1,
context.allocator,
)
append(
builder,
DirectoryEntry{relpath = relpath, size = entry.size},
)
}
if entry.type == os.File_Type.Directory {
dir, dir_err := os.open(entry.fullpath, {.Read})
if dir_err != nil {
fmt.eprintln("error: open directory failed:", dir_err)
os.exit(1)
}
defer os.close(dir)
list_dir_impl(dir, builder) // recurse into directory
}
}
}
read_by_path :: proc(path: string) -> []u8 {
f, open_err := os.open(path, {.Read})
if open_err != nil {
fmt.eprintln("error: open failed:", open_err)
os.exit(1)
}
defer os.close(f)
if !os.is_file(path) {
fmt.eprintln("error: path is not a file:", path)
os.exit(1)
}
path := path // shadow parameter
path = strings.clone(path)
size, size_err := os.file_size(f)
if size_err != nil {
fmt.eprintln("error: get file size failed:", size_err)
os.exit(1)
}
data := make([]u8, size)
n, read_err := os.read_full(f, data)
if read_err != nil {
delete(data)
fmt.eprintln(
"error: file read failed:",
read_err,
"got",
n,
"of",
size,
"bytes",
)
os.exit(1)
}
return data
}
get_asset_by_path :: proc(path: string) -> Asset {
data := read_by_path(path)
return Asset{relpath = path, size = cast(i64)len(data), data = data}
}
+91
View File
@@ -0,0 +1,91 @@
package file
import "core:fmt"
import "core:os"
import "core:strings"
// -----------------------------------------
DirectoryEntry :: struct #all_or_none {
relpath: string,
size: i64,
}
// -----------------------------------------
list_dir_by_path :: proc(path: string) -> [dynamic]DirectoryEntry {
if !os.is_dir(path) {
fmt.eprintln("error: path is not a directory:", path)
os.exit(1)
}
f, open_err := os.open(path, {.Read})
if open_err != nil {
fmt.eprintln("error: open failed:", open_err)
os.exit(1)
}
defer os.close(f)
result := [dynamic]DirectoryEntry{}
list_dir_impl(f, &result)
return result
}
list_dir :: proc(f: ^os.File) -> [dynamic]DirectoryEntry {
path := os.name(f)
if !os.is_dir(path) {
fmt.eprintln("error: path is not a directory:", path)
os.exit(1)
}
result := [dynamic]DirectoryEntry{}
list_dir_impl(f, &result)
return result
}
@(private)
list_dir_impl :: proc(f: ^os.File, builder: ^[dynamic]DirectoryEntry) {
entries, read_err := os.read_all_directory(f, context.allocator)
if read_err != nil {
fmt.eprintln("error: read directory failed:", read_err)
os.exit(1)
}
defer delete(entries)
// Reserve space for new entries
reserve(builder, cap(builder) + len(entries))
working_dir, wd_err := os.get_working_directory(context.allocator)
if wd_err != nil {
fmt.eprintln("error: get working directory failed:", wd_err)
os.exit(1)
}
defer delete(working_dir)
for entry, i in entries {
if entry.type == os.File_Type.Regular {
relpath, rel_err := strings.replace(
entry.fullpath,
working_dir,
".",
1,
context.allocator,
)
append(
builder,
DirectoryEntry{relpath = relpath, size = entry.size},
)
}
if entry.type == os.File_Type.Directory {
dir, dir_err := os.open(entry.fullpath, {.Read})
if dir_err != nil {
fmt.eprintln("error: open directory failed:", dir_err)
os.exit(1)
}
defer os.close(dir)
list_dir_impl(dir, builder) // recurse into directory
}
}
}
+62
View File
@@ -0,0 +1,62 @@
package file
import "core:fmt"
import "core:os"
import "core:strings"
// -----------------------------------------
Asset :: struct #all_or_none {
relpath: string,
size: i64,
data: []u8,
}
// -----------------------------------------
read_by_path :: proc(path: string) -> []u8 {
f, open_err := os.open(path, {.Read})
if open_err != nil {
fmt.eprintln("error: open failed:", open_err)
os.exit(1)
}
defer os.close(f)
if !os.is_file(path) {
fmt.eprintln("error: path is not a file:", path)
os.exit(1)
}
path := path // shadow parameter
path = strings.clone(path)
size, size_err := os.file_size(f)
if size_err != nil {
fmt.eprintln("error: get file size failed:", size_err)
os.exit(1)
}
data := make([]u8, size)
n, read_err := os.read_full(f, data)
if read_err != nil {
delete(data)
fmt.eprintln(
"error: file read failed:",
read_err,
"got",
n,
"of",
size,
"bytes",
)
os.exit(1)
}
return data
}
get_asset_by_path :: proc(path: string) -> Asset {
data := read_by_path(path)
return Asset{relpath = path, size = cast(i64)len(data), data = data}
}