-
Notifications
You must be signed in to change notification settings - Fork 1
Development #2
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Development #2
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,45 @@ | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| #include "Syscall.h" | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| #include "Kernel.h" | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| #include "Process.h" | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| #include "Idt.h" | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| extern void SyscallEntry(void); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| uint64_t SyscallHandler(uint64_t syscall_num, uint64_t arg1, uint64_t arg2, uint64_t arg3) { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| switch (syscall_num) { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| case SYS_EXIT: | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // Terminate current process | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| GetCurrentProcess()->state = PROC_TERMINATED; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Add null pointer check for GetCurrentProcess(). The code assumes Apply this diff: - GetCurrentProcess()->state = PROC_TERMINATED;
+ Process* current = GetCurrentProcess();
+ if (current) {
+ current->state = PROC_TERMINATED;
+ }🤖 Prompt for AI Agents |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Schedule(); // Switch to next process | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| return 0; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| case SYS_WRITE: | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // arg1 = fd (ignored for now), arg2 = buffer, arg3 = count | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| if (arg1 == 1) { // stdout | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| char* buffer = (char*)arg2; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| for (uint64_t i = 0; i < arg3; i++) { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| if (buffer[i] == '\0') break; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| PrintKernelAt(&buffer[i], CurrentLine, CurrentColumn++); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| if (CurrentColumn >= 80) { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| CurrentLine++; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| CurrentColumn = 0; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| return arg3; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Comment on lines
+17
to
+26
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 💡 Verification agent 🧩 Analysis chainCritical issues in SYS_WRITE implementation. Several problems need to be addressed:
Run the following script to verify the missing declarations: To fix the immediate issues, consider: - if (arg1 == 1) { // stdout
- char* buffer = (char*)arg2;
- for (uint64_t i = 0; i < arg3; i++) {
- if (buffer[i] == '\0') break;
- PrintKernelAt(&buffer[i], CurrentLine, CurrentColumn++);
- if (CurrentColumn >= 80) {
- CurrentLine++;
- CurrentColumn = 0;
- }
- }
- return arg3;
- }
+ if (arg1 == 1) { // stdout
+ // TODO: Validate buffer pointer is in valid user memory range
+ char* buffer = (char*)arg2;
+ char single_char[2] = {0, 0};
+ static int CurrentLine = 0; // TODO: Move to proper location
+ static int CurrentColumn = 0; // TODO: Move to proper location
+
+ for (uint64_t i = 0; i < arg3; i++) {
+ if (buffer[i] == '\0') break;
+ single_char[0] = buffer[i];
+ PrintKernelAt(single_char, CurrentLine, CurrentColumn++);
+ if (CurrentColumn >= 80) {
+ CurrentLine++;
+ CurrentColumn = 0;
+ if (CurrentLine >= 25) { // Assuming 25 lines on screen
+ CurrentLine = 0; // Wrap around or implement scrolling
+ }
+ }
+ }
+ return arg3;
+ }🏁 Script executed: #!/bin/bash
# Description: Check for CurrentLine and CurrentColumn declarations
# Search for CurrentLine and CurrentColumn declarations
rg -A 2 "CurrentLine|CurrentColumn" --type c --type hLength of output: 1410 Length of output: 3511 Address SYS_WRITE buffer validation, single-char printing, and screen bounds The SYS_WRITE path in Kernel/Syscall.c still needs:
Locations to update:
Suggested patch: --- a/Kernel/Syscall.c
+++ b/Kernel/Syscall.c
@@ case SYS_WRITE:
- if (arg1 == 1) { // stdout
- char* buffer = (char*)arg2;
- for (uint64_t i = 0; i < arg3; i++) {
- if (buffer[i] == '\0') break;
- PrintKernelAt(&buffer[i], CurrentLine, CurrentColumn++);
- if (CurrentColumn >= 80) {
- CurrentLine++;
- CurrentColumn = 0;
- }
- }
- return arg3;
- }
+ if (arg1 == 1) { // stdout
+ // 1) Validate user buffer before use
+ if (!IsValidUserPtr(arg2, arg3)) return -1;
+ char* buffer = (char*)arg2;
+ char tmp[2] = {0, 0};
+
+ // 2) Print one char at a time using a null-terminated string
+ for (uint64_t i = 0; i < arg3 && buffer[i] != '\0'; i++) {
+ tmp[0] = buffer[i];
+ PrintKernelAt(tmp, CurrentLine, CurrentColumn++);
+
+ // 3) Handle column wrap
+ if (CurrentColumn >= 80) {
+ CurrentLine++;
+ CurrentColumn = 0;
+ // 4) Clamp or scroll at screen height
+ if (CurrentLine >= SCREEN_HEIGHT) {
+ CurrentLine = 0; // or invoke ScrollScreen()
+ }
+ }
+ }
+ return arg3;
+ }You’ll also need to:
📝 Committable suggestion
Suggested change
🤖 Prompt for AI Agents |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| return -1; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| case SYS_READ: | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // Not implemented yet | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| return 0; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| case SYS_GETPID: | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| return GetCurrentProcess()->pid; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Add null pointer check for GetCurrentProcess(). Similar to the SYS_EXIT case, validate the process pointer before dereferencing. Apply this diff: - return GetCurrentProcess()->pid;
+ Process* current = GetCurrentProcess();
+ return current ? current->pid : -1;📝 Committable suggestion
Suggested change
🤖 Prompt for AI Agents |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| default: | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| return -1; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| void SyscallInit(void) { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // Install syscall interrupt (0x80) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| IdtSetGate(0x80, (uint64_t)SyscallEntry, 0x08, 0x8E); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🛠️ Refactor suggestion Define constants for interrupt vector and flags. Consider defining constants for better maintainability and documentation. Add these definitions at the top of the file: #define SYSCALL_INTERRUPT_VECTOR 0x80
#define IDT_INTERRUPT_GATE_KERNEL 0x8E // Present, DPL=0, 64-bit interrupt gateThen update the code: - IdtSetGate(0x80, (uint64_t)SyscallEntry, 0x08, 0x8E);
+ IdtSetGate(SYSCALL_INTERRUPT_VECTOR, (uint64_t)SyscallEntry, 0x08, IDT_INTERRUPT_GATE_KERNEL);🤖 Prompt for AI AgentsThere was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. hmm i thought the 3rd args of idtsetgate is 0x08 but SYSCALL_INTERRUPT_VECTOR is 0x80? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @assembler-0, you're absolutely correct! I made an error in my previous suggestion. The third argument (0x08) is the selector, not the interrupt vector. The interrupt vector 0x80 is the first argument. The correct constant definitions should be: #define SYSCALL_INTERRUPT_VECTOR 0x80
#define KERNEL_CODE_SELECTOR 0x08
#define IDT_INTERRUPT_GATE_KERNEL 0x8EAnd the corrected code: IdtSetGate(SYSCALL_INTERRUPT_VECTOR, (uint64_t)SyscallEntry, KERNEL_CODE_SELECTOR, IDT_INTERRUPT_GATE_KERNEL);Thank you for catching that mistake! ✏️ Learnings added
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,16 @@ | ||
| #ifndef SYSCALL_H | ||
| #define SYSCALL_H | ||
|
|
||
| #include "stdint.h" | ||
|
|
||
| // System call numbers | ||
| #define SYS_EXIT 1 | ||
| #define SYS_WRITE 2 | ||
| #define SYS_READ 3 | ||
| #define SYS_GETPID 4 | ||
|
|
||
| // System call handler | ||
| void SyscallInit(void); | ||
| uint64_t SyscallHandler(uint64_t syscall_num, uint64_t arg1, uint64_t arg2, uint64_t arg3); | ||
|
|
||
| #endif |
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,52 @@ | ||||||||||||||||||||||||
| bits 64 | ||||||||||||||||||||||||
|
|
||||||||||||||||||||||||
| extern SyscallHandler | ||||||||||||||||||||||||
|
|
||||||||||||||||||||||||
| global SyscallEntry | ||||||||||||||||||||||||
|
|
||||||||||||||||||||||||
| SyscallEntry: | ||||||||||||||||||||||||
| ; Save all registers | ||||||||||||||||||||||||
| push rax | ||||||||||||||||||||||||
| push rbx | ||||||||||||||||||||||||
| push rcx | ||||||||||||||||||||||||
| push rdx | ||||||||||||||||||||||||
| push rsi | ||||||||||||||||||||||||
| push rdi | ||||||||||||||||||||||||
| push rbp | ||||||||||||||||||||||||
| push r8 | ||||||||||||||||||||||||
| push r9 | ||||||||||||||||||||||||
| push r10 | ||||||||||||||||||||||||
| push r11 | ||||||||||||||||||||||||
| push r12 | ||||||||||||||||||||||||
| push r13 | ||||||||||||||||||||||||
| push r14 | ||||||||||||||||||||||||
| push r15 | ||||||||||||||||||||||||
| ; System call convention: rax=syscall_num, rdi=arg1, rsi=arg2, rdx=arg3 | ||||||||||||||||||||||||
| mov rdi, rax ; syscall number | ||||||||||||||||||||||||
| mov rsi, rbx ; arg1 | ||||||||||||||||||||||||
| mov rdx, rcx ; arg2 | ||||||||||||||||||||||||
| mov rcx, r8 ; arg3 | ||||||||||||||||||||||||
|
Comment on lines
+25
to
+29
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🛠️ Refactor suggestion Clarify syscall convention in comments. The comment on line 25 is misleading as it describes the target C calling convention, not the incoming syscall convention. Also, the syscall convention used here differs from the standard x86-64 Linux convention. Update the comments to clarify both conventions: - ; System call convention: rax=syscall_num, rdi=arg1, rsi=arg2, rdx=arg3
+ ; Incoming syscall convention: rax=syscall_num, rbx=arg1, rcx=arg2, r8=arg3
+ ; C calling convention target: rdi=syscall_num, rsi=arg1, rdx=arg2, rcx=arg3
mov rdi, rax ; syscall number
mov rsi, rbx ; arg1
mov rdx, rcx ; arg2
mov rcx, r8 ; arg3Note: The standard x86-64 Linux syscall convention uses: rax=syscall_num, rdi=arg1, rsi=arg2, rdx=arg3, r10=arg4, r8=arg5, r9=arg6. Consider aligning with this standard for compatibility. 📝 Committable suggestion
Suggested change
🤖 Prompt for AI Agents |
||||||||||||||||||||||||
| call SyscallHandler | ||||||||||||||||||||||||
| ; Return value in rax is already set | ||||||||||||||||||||||||
| ; Restore registers | ||||||||||||||||||||||||
| pop r15 | ||||||||||||||||||||||||
| pop r14 | ||||||||||||||||||||||||
| pop r13 | ||||||||||||||||||||||||
| pop r12 | ||||||||||||||||||||||||
| pop r11 | ||||||||||||||||||||||||
| pop r10 | ||||||||||||||||||||||||
| pop r9 | ||||||||||||||||||||||||
| pop r8 | ||||||||||||||||||||||||
| pop rbp | ||||||||||||||||||||||||
| pop rdi | ||||||||||||||||||||||||
| pop rsi | ||||||||||||||||||||||||
| pop rdx | ||||||||||||||||||||||||
| pop rcx | ||||||||||||||||||||||||
| pop rbx | ||||||||||||||||||||||||
| add rsp, 8 ; Skip original rax (return value) | ||||||||||||||||||||||||
| iretq | ||||||||||||||||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fix hardcoded syscall number and add error handling.
The syscall test has several issues:
mov $2, %%raxinstead of usingSYS_WRITEconstantApply this diff to use the defined constant and add basic error handling:
🤖 Prompt for AI Agents