From 6179308e3f6e4c64013e5db5da9b30a22abca704 Mon Sep 17 00:00:00 2001 From: Anton Kling Date: Sat, 14 Dec 2024 15:13:01 +0100 Subject: sb: Allow input to be "ignored" This removes edge cases from read calls and makes bugs harder to introduce. --- kernel/fs/procfs.c | 23 ++++++++--------------- kernel/lib/sb.c | 32 ++++++++++++++++++++++++++++++++ kernel/lib/sb.h | 2 ++ userland/libc/crt0.s | 14 -------------- userland/libc/crt1.s | 14 ++++++++++++++ 5 files changed, 56 insertions(+), 29 deletions(-) delete mode 100644 userland/libc/crt0.s create mode 100644 userland/libc/crt1.s diff --git a/kernel/fs/procfs.c b/kernel/fs/procfs.c index 69022d4..bfe3aac 100644 --- a/kernel/fs/procfs.c +++ b/kernel/fs/procfs.c @@ -23,8 +23,7 @@ void process_close(vfs_fd_t *fd) { int procfs_read(u8 *buffer, u64 offset, u64 len, vfs_fd_t *fd) { struct sb builder; sb_init_buffer(&builder, buffer, len); - - size_t read_amount = 0; + sb_set_ignore(&builder, offset); process_t *p = ready_queue; for (; p; p = p->next) { @@ -32,13 +31,11 @@ int procfs_read(u8 *buffer, u64 offset, u64 len, vfs_fd_t *fd) { entry.d_ino = p->pid; ksnprintf(entry.d_name, sizeof(entry.d_name), "%u", p->pid); - if (read_amount >= offset) { - if (0 == sb_append_buffer(&builder, (u8 *)&entry, sizeof(entry))) { - break; - } + if (0 == sb_append_buffer(&builder, (u8 *)&entry, sizeof(entry))) { + break; } - read_amount += sizeof(struct dirent); } + return sv_length(SB_TO_SV(builder)); } @@ -70,27 +67,23 @@ int process_read(u8 *buffer, u64 offset, u64 len, vfs_fd_t *fd) { struct sb builder; sb_init_buffer(&builder, buffer, len); + sb_set_ignore(&builder, offset); int id = fd->inode->inode_num; if (PROCESS_ROOT == id) { - size_t read_amount = 0; for (size_t i = 0; i < ARRAY_LENGTH(process_entries); i++) { if (0 == strlen(process_entries[i].d_name)) { continue; } - if (read_amount >= offset) { - if (0 == sb_append_buffer(&builder, (u8 *)&process_entries[i], - sizeof(struct dirent))) { - break; - } + if (0 == sb_append_buffer(&builder, (u8 *)&process_entries[i], + sizeof(struct dirent))) { + break; } - read_amount += sizeof(struct dirent); } return sv_length(SB_TO_SV(builder)); } if (PROCESS_NAME == id) { struct sv program_name = C_TO_SV(p->program_name); - sv_take(program_name, &program_name, offset); sb_append_sv(&builder, program_name); return sv_length(SB_TO_SV(builder)); } diff --git a/kernel/lib/sb.c b/kernel/lib/sb.c index 6f716ac..ca302f7 100644 --- a/kernel/lib/sb.c +++ b/kernel/lib/sb.c @@ -11,6 +11,7 @@ void sb_init(struct sb *ctx) { } int sb_init_capacity(struct sb *ctx, size_t starting_capacity) { + ctx->to_ignore = 0; ctx->length = 0; ctx->prebuffer = 0; ctx->string = kmalloc(starting_capacity); @@ -27,6 +28,7 @@ void sb_init_buffer(struct sb *ctx, char *buffer, size_t size) { ctx->capacity = size; ctx->length = 0; ctx->prebuffer = 1; + ctx->to_ignore = 0; } void sb_free(struct sb *ctx) { @@ -40,8 +42,13 @@ void sb_free(struct sb *ctx) { ctx->string = NULL; } +void sb_set_ignore(struct sb *ctx, size_t n) { + ctx->to_ignore = n; +} + void sb_reset(struct sb *ctx) { ctx->length = 0; + ctx->to_ignore = 0; } int sb_isempty(const struct sb *ctx) { @@ -64,6 +71,10 @@ int sb_increase_buffer(struct sb *ctx, size_t min) { } int sb_append_char(struct sb *ctx, char c) { + if (ctx->to_ignore > 0) { + ctx->to_ignore--; + return 1; + } if (1 > ctx->capacity - ctx->length) { if (!sb_increase_buffer(ctx, 1)) { return 0; @@ -82,6 +93,13 @@ int sb_delete_right(struct sb *ctx, size_t n) { int sb_append(struct sb *ctx, const char *s) { size_t l = strlen(s); + if (ctx->to_ignore >= l) { + ctx->to_ignore -= l; + return 1; + } + l -= ctx->to_ignore; + s += ctx->to_ignore; + ctx->to_ignore = 0; if (l > ctx->capacity - ctx->length) { if (!sb_increase_buffer(ctx, l)) { return 0; @@ -97,6 +115,13 @@ int sb_prepend_sv(struct sb *ctx, struct sv sv) { } int sb_prepend_buffer(struct sb *ctx, const char *buffer, size_t length) { + if (ctx->to_ignore >= length) { + ctx->to_ignore -= length; + return 1; + } + length -= ctx->to_ignore; + buffer += ctx->to_ignore; + ctx->to_ignore = 0; if (length > ctx->capacity - ctx->length) { if (!sb_increase_buffer(ctx, length)) { return 0; @@ -109,6 +134,13 @@ int sb_prepend_buffer(struct sb *ctx, const char *buffer, size_t length) { } int sb_append_buffer(struct sb *ctx, const char *buffer, size_t length) { + if (ctx->to_ignore >= length) { + ctx->to_ignore -= length; + return 1; + } + length -= ctx->to_ignore; + buffer += ctx->to_ignore; + ctx->to_ignore = 0; if (length > ctx->capacity - ctx->length) { if (!sb_increase_buffer(ctx, length)) { return 0; diff --git a/kernel/lib/sb.h b/kernel/lib/sb.h index 7832015..4d910e3 100644 --- a/kernel/lib/sb.h +++ b/kernel/lib/sb.h @@ -8,12 +8,14 @@ struct sb { char *string; size_t length; size_t capacity; + size_t to_ignore; uint8_t prebuffer; }; struct sv; void sb_init(struct sb *ctx); +void sb_set_ignore(struct sb *ctx, size_t n); int sb_init_capacity(struct sb *ctx, size_t starting_capacity); void sb_init_buffer(struct sb *ctx, char *buffer, size_t size); void sb_free(struct sb *ctx); diff --git a/userland/libc/crt0.s b/userland/libc/crt0.s deleted file mode 100644 index c950949..0000000 --- a/userland/libc/crt0.s +++ /dev/null @@ -1,14 +0,0 @@ -.global _start -.extern main -_start: - call _libc_setup - call main - mov %eax, %ebx - mov $8, %eax - int $0x80 -l: - nop - nop - nop - nop - jmp l diff --git a/userland/libc/crt1.s b/userland/libc/crt1.s new file mode 100644 index 0000000..c950949 --- /dev/null +++ b/userland/libc/crt1.s @@ -0,0 +1,14 @@ +.global _start +.extern main +_start: + call _libc_setup + call main + mov %eax, %ebx + mov $8, %eax + int $0x80 +l: + nop + nop + nop + nop + jmp l -- cgit v1.2.3