用户elf加载备份

This commit is contained in:
XIAOYI12 2024-08-14 21:58:29 +08:00
parent ec1ef4e6c2
commit b0e065958d
19 changed files with 147601 additions and 80 deletions

View File

@ -8,7 +8,7 @@ out/%.obj : %.c Makefile
out/%.obj : %.cpp Makefile out/%.obj : %.cpp Makefile
$(CPP) -c $*.cpp -o out/$*.obj $(CPP) -c $*.cpp -o out/$*.obj
out/%.obj : %.asm Makefile out/%.obj : %.asm Makefile
nasm -f elf $*.asm -o out/$*.obj nasm -f elf_i386 $*.asm -o out/$*.obj
clean: clean:
rm out/* rm out/*

View File

@ -1,7 +1,7 @@
#include "../include/stdio.h" #include "../include/stdio.h"
int main(){ int main(){
debug_test();
while (1); while (1);
return 0; return 0;
} }

View File

@ -2,5 +2,6 @@
#define CRASHPOWEROS_STDIO_H #define CRASHPOWEROS_STDIO_H
void put_char(char c); void put_char(char c);
void debug_test();
#endif #endif

View File

@ -8,7 +8,7 @@ out/%.obj : %.c Makefile
out/%.obj : %.cpp Makefile out/%.obj : %.cpp Makefile
$(CPP) -c $*.cpp -o out/$*.obj $(CPP) -c $*.cpp -o out/$*.obj
out/%.obj : %.asm Makefile out/%.obj : %.asm Makefile
nasm -f elf $*.asm -o out/$*.obj nasm -f elf_i386 $*.asm -o out/$*.obj
clean: clean:
rm out/* rm out/*

View File

@ -1,11 +1,11 @@
#include "../include/stdio.h" #include "../include/stdio.h"
void putc(char c){ void hlt(){
while (1);
} }
int main(){ int main(){
putc('A'); hlt();
while (1); //put_char('A');
return 0; return 0;
} }

View File

@ -1,6 +1,8 @@
global put_char global put_char
global debug_test
put_char: put_char:
ret
push edx push edx
push eax push eax
mov edx,[ss:esp+12] mov edx,[ss:esp+12]
@ -9,3 +11,10 @@ put_char:
pop eax pop eax
pop edx pop edx
ret ret
debug_test:
push edx
mov edx,0x02
int 31h
pop edx
ret

View File

@ -40,7 +40,7 @@ copy_page_physical:
popf ; Pop EFLAGS back. popf ; Pop EFLAGS back.
pop ebx ; Get the original value of EBX back. pop ebx ; Get the original value of EBX back.
switch_to: switch_to: ;void switch_to(struct context *prev, struct context *next);
mov eax, [esp+4] mov eax, [esp+4]
mov [eax+0], esp mov [eax+0], esp

View File

@ -32,8 +32,7 @@ char read_serial() {
int is_transmit_empty() { return io_in8(SERIAL_PORT + 5) & 0x20; } int is_transmit_empty() { return io_in8(SERIAL_PORT + 5) & 0x20; }
void write_serial(char a) { void write_serial(char a) {
while (is_transmit_empty() == 0) return;
; while (is_transmit_empty() == 0);
io_out8(SERIAL_PORT, a); io_out8(SERIAL_PORT, a);
} }

View File

@ -4,17 +4,21 @@
#include "../include/common.h" #include "../include/common.h"
#include "../include/multiboot2.h" #include "../include/multiboot2.h"
#include "../include/timer.h" #include "../include/timer.h"
#include "../include/bmp.h"
uint32_t width, height; uint32_t width, height;
uint32_t c_width, c_height; // 字符绘制总宽高 uint32_t c_width, c_height; // 字符绘制总宽高
int32_t x, y; int32_t x, y;
int32_t cx, cy; // 字符坐标 int32_t cx, cy; // 字符坐标
uint32_t color, back_color; uint32_t color, back_color;
uint32_t *screen; uint32_t *screen;
uint32_t *char_buffer; uint32_t *char_buffer;
extern uint8_t ascfont[]; extern uint8_t ascfont[];
extern uint8_t plfont[]; extern uint8_t plfont[];
extern uint8_t bafont[]; extern uint8_t bafont[];
extern uint8_t logo_bmp[];
bool vbe_status = false; bool vbe_status = false;
@ -54,44 +58,18 @@ void vbe_scroll() {
screen[i] = back_color; screen[i] = back_color;
} }
} }
/*
if (cy >= c_height) {
cy = c_height - 1;
for (int i = 0; i < height; i++) {
for (int j = 0; j < width; j++) {
screen[j + i * width] = screen[j + (i + 16) * width];
}
}
}
if (y == height - height % 16) {
cy = c_height - 1;
for (int i = 0; i < height; i++) {
for (int j = 0; j < width; j++) {
(screen)[j + i * width] = (screen)[j + (i + 16 - height % 16) * width];
}
}
}
for (int i = 0; i < width; i++) {
for (int j = 0; j < 28; j++) {
screen[height * (width + j) + i] = back_color;
}
}
*/
} }
void vbe_draw_char(char c, int32_t x, int32_t y) { void vbe_draw_char(char c, int32_t x, int32_t y) {
if (c == ' ') { if (c == ' ') {
for (int i = 0; i < 16; i++) { for (int i = 0; i < 16; i++) {
for (int j = 0; j < 9; j++) { for (int j = 0; j < 9; j++) {
screen[(y + i) * width + x + j] = back_color; //screen[(y + i) * width + x + j] = back_color;
} }
} }
return; return;
} }
uint8_t *font = bafont; uint8_t *font = bafont;
//uint8_t *font = ascfont; //uint8_t *font = ascfont;
@ -104,13 +82,6 @@ void vbe_draw_char(char c, int32_t x, int32_t y) {
} //else screen[(y + i) * width + x + j] = back_color; } //else screen[(y + i) * width + x + j] = back_color;
} }
} }
for (int i = 0; i < 16; i++) {
for (int j = 0; j < 9; j++) {
if (font[i] & (0x80 >> j)) {
screen[(y + i) * width + x + j] = color;
} //else screen[(y + i) * width + x + j + 1] = back_color;
}
}
} }
int cur_task() { int cur_task() {
@ -147,7 +118,9 @@ void vbe_putchar(char ch) {
if (cy != 0) cy -= 1; if (cy != 0) cy -= 1;
if (cy == 0) cx = 0, cy = 0; if (cy == 0) cx = 0, cy = 0;
} }
//draw_rect(x, y, x + 9, y + 16, back_color); int x = (cx+1) * 9 - 7;
int y = cy * 16;
draw_rect(x, y, x + 9, y + 16, back_color);
return; return;
} }
@ -158,10 +131,10 @@ void vbe_putchar(char ch) {
void vbe_write(const char *data, size_t size) { void vbe_write(const char *data, size_t size) {
static const long hextable[] = { static const long hextable[] = {
[0 ... 255] = -1, // bit aligned access into this table is considerably [0 ... 255] = -1,
['0'] = 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, // faster for most modern processors, ['0'] = 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,
['A'] = 10, 11, 12, 13, 14, 15, // for the space conscious, reduce to ['A'] = 10, 11, 12, 13, 14, 15,
['a'] = 10, 11, 12, 13, 14, 15 // signed char. ['a'] = 10, 11, 12, 13, 14, 15
}; };
for (;*data; ++data){ for (;*data; ++data){
@ -215,4 +188,7 @@ void initVBE(multiboot_t *info) {
c_height = height / 16; c_height = height / 16;
vbe_clear(); vbe_clear();
Bmp *bmp = (Bmp*) &logo_bmp;
display(bmp,0,0,false);
} }

View File

@ -3,6 +3,7 @@
#include "../include/vfs.h" #include "../include/vfs.h"
#include "../include/vdisk.h" #include "../include/vdisk.h"
#include "../include/printf.h" #include "../include/printf.h"
bool read_sector(l9660_fs *fs, void *buf, uint32_t sector); bool read_sector(l9660_fs *fs, void *buf, uint32_t sector);
#define l9660_seekdir(dir, pos) (l9660_seek(&(dir)->file, L9660_SEEK_SET, (pos))) #define l9660_seekdir(dir, pos) (l9660_seek(&(dir)->file, L9660_SEEK_SET, (pos)))
#define l9660_telldir(dir) (l9660_tell(&(dir)->file)) #define l9660_telldir(dir) (l9660_tell(&(dir)->file))

View File

@ -3225,5 +3225,6 @@ int elf32Validate(Elf32_Ehdr *hdr);
void load_segment(Elf32_Phdr *phdr,page_directory_t *pdt, void *elf); void load_segment(Elf32_Phdr *phdr,page_directory_t *pdt, void *elf);
uint32_t load_elf(Elf32_Ehdr *hdr,page_directory_t *pdt); uint32_t load_elf(Elf32_Ehdr *hdr,page_directory_t *pdt);
void elf32LoadData(Elf32_Ehdr *elfhdr, uint8_t *ptr); void elf32LoadData(Elf32_Ehdr *elfhdr, uint8_t *ptr);
uint32_t elf32_get_max_vaddr(Elf32_Ehdr *hdr);
#endif /* elf.h */ #endif /* elf.h */

View File

@ -79,6 +79,14 @@ typedef struct mmap_entry_t {
uint32_t type; uint32_t type;
} __attribute__((packed)) mmap_entry_t; } __attribute__((packed)) mmap_entry_t;
typedef struct {
uint32_t type;
uint32_t size;
uint32_t biosdev;
uint32_t partition;
uint32_t sub_partition;
} multiboot_tag_bootdev_t;
// 声明全局的 multiboot_t * 指针 // 声明全局的 multiboot_t * 指针
// 内核未建立分页机制前暂存的指针 // 内核未建立分页机制前暂存的指针
extern multiboot_t *mboot_ptr_tmp; extern multiboot_t *mboot_ptr_tmp;

View File

@ -31,6 +31,7 @@ struct context{
uint32_t eip; uint32_t eip;
uint32_t ds; uint32_t ds;
uint32_t cs; uint32_t cs;
uint32_t ss;
}; };
// 进程控制块 PCB // 进程控制块 PCB
@ -40,11 +41,11 @@ struct task_struct {
int mem_size; // 内存利用率 int mem_size; // 内存利用率
char *name; // 进程名 char *name; // 进程名
void *stack; // 进程的内核栈地址 void *stack; // 进程的内核栈地址
header_t *head; header_t *head; // 进程堆
header_t *tail; header_t *tail;
bool isUser; bool isUser; // 是否是用户进程
uint32_t program_break; uint32_t program_break; // 进程堆基址
uint32_t program_break_end; uint32_t program_break_end; // 进程堆尾
page_directory_t *pgd_dir; // 进程页表 page_directory_t *pgd_dir; // 进程页表
struct context context; // 上下文信息 struct context context; // 上下文信息
struct task_struct *next; // 链表指针 struct task_struct *next; // 链表指针

View File

@ -75,6 +75,13 @@ void kernel_main(multiboot_t *multiboot) {
} }
initVBE(multiboot); initVBE(multiboot);
char* cmdline = multiboot->cmdline;
if(cmdline != NULL){
printf("Multiboot command line: %s\n",cmdline);
}
printf("CPOS_Kernel %s (GRUB Multiboot) on an i386.\n",OS_VERSION); printf("CPOS_Kernel %s (GRUB Multiboot) on an i386.\n",OS_VERSION);
printf("Memory Size: %dMB\n",(multiboot->mem_upper + multiboot->mem_lower) / 1024 + 1); printf("Memory Size: %dMB\n",(multiboot->mem_upper + multiboot->mem_lower) / 1024 + 1);
gdt_install(); gdt_install();

View File

@ -44,8 +44,10 @@ void panic_pane(char* msg,enum PANIC_TYPE type){
back_color = 0x1e90ff; back_color = 0x1e90ff;
color = 0xffffff; color = 0xffffff;
screen_clear(); screen_clear();
if(panic_bmp != NULL) if(panic_bmp != NULL){
display(panic_bmp,0,0,true); display(panic_bmp,0,0,false);
} else klogf(false,"Cannot draw panic image.\n");
cx = 10; cx = 10;
cy = c_height - 10; cy = c_height - 10;

View File

@ -5,8 +5,6 @@
#include "../include/graphics.h" #include "../include/graphics.h"
#include "../include/io.h" #include "../include/io.h"
extern asm_syscall_handler();
void syscall_handler(registers_t regs){ void syscall_handler(registers_t regs){
io_cli(); io_cli();
printf("Syscall is enable.\n"); printf("Syscall is enable.\n");
@ -18,5 +16,5 @@ void syscall_handler(registers_t regs){
} }
void syscall_install(){ void syscall_install(){
register_interrupt_handler(31,asm_syscall_handler); register_interrupt_handler(31,syscall_handler);
} }

View File

@ -140,7 +140,7 @@ void task_kill(int pid) {
return; return;
} }
argv->state = TASK_DEATH; argv->state = TASK_DEATH;
printf("Taskkill process PID:%d Name:%s\n", current->pid, current->name); printf("Taskkill process PID:%d Name:%s\n", argv->pid, argv->name);
printf("Task [%s] exit code: -130.\n", argv->name); printf("Task [%s] exit code: -130.\n", argv->name);
kfree(argv); kfree(argv);
@ -175,15 +175,17 @@ void change_task_to(registers_t *reg,struct task_struct *next) {
prev->context.ds = reg->ds; prev->context.ds = reg->ds;
prev->context.cs = reg->cs; prev->context.cs = reg->cs;
prev->context.eax = reg->eax; prev->context.eax = reg->eax;
prev->context.ss = reg->ss;
switch_to(&(prev->context), &(current->context)); switch_to(&(prev->context), &(current->context));
reg->ds = current->context.ds; reg->ds = current->context.ds;
reg->cs = current->context.cs; reg->cs = current->context.cs;
reg->eip = current->context.eip; reg->eip = current->context.eip;
reg->eax = current->context.eax; reg->eax = current->context.eax;
reg->ss = current->context.ss;
} }
} }
int32_t user_process(char *path, char *name){ int32_t user_process(char *path, char *name){ // 用户进程创建
can_sche = 0; can_sche = 0;
if(path == NULL){ if(path == NULL){
return -1; return -1;
@ -216,6 +218,8 @@ int32_t user_process(char *path, char *name){
page_switch(page); page_switch(page);
printf("TASK I\n");
for (int i = USER_START; i < USER_END;i++) { for (int i = USER_START; i < USER_END;i++) {
page_t *pg = get_page(i,1,page, false); page_t *pg = get_page(i,1,page, false);
alloc_frame(pg,0,1); alloc_frame(pg,0,1);
@ -223,8 +227,10 @@ int32_t user_process(char *path, char *name){
char* buffer = user_alloc(new_task,size); char* buffer = user_alloc(new_task,size);
printf("TASK II\n");
memset(buffer,0,size); memset(buffer,0,size);
vfs_readfile(path,buffer); vfs_readfile(path,buffer); //能加载, 但是执行一会就不知道跳哪里去了,给自己爆了
Elf32_Ehdr *ehdr = buffer; Elf32_Ehdr *ehdr = buffer;
if(!elf32Validate(ehdr)){ if(!elf32Validate(ehdr)){
@ -233,6 +239,7 @@ int32_t user_process(char *path, char *name){
} }
uint32_t main = load_elf(ehdr,page); uint32_t main = load_elf(ehdr,page);
printf("Task [PID: %d] start_function: %08x\n",new_task->pid,main);
uint32_t *stack_top = (uint32_t * )((uint32_t) new_task + STACK_SIZE); uint32_t *stack_top = (uint32_t * )((uint32_t) new_task + STACK_SIZE);
@ -262,7 +269,7 @@ int32_t user_process(char *path, char *name){
} }
int32_t kernel_thread(int (*fn)(void *), void *arg, char *name) { int32_t kernel_thread(int (*fn)(void *), void *arg, char *name) { // 内核进程(线程) 创建
io_cli(); io_cli();
struct task_struct *new_task = (struct task_struct *) kmalloc(STACK_SIZE); struct task_struct *new_task = (struct task_struct *) kmalloc(STACK_SIZE);
assert(new_task != NULL, "kern_thread: kmalloc error"); assert(new_task != NULL, "kern_thread: kmalloc error");
@ -316,7 +323,6 @@ void kthread_exit() {
register uint32_t val asm ("eax"); register uint32_t val asm ("eax");
printf("Task [PID: %d] exited with value %d\n", current->pid,val); printf("Task [PID: %d] exited with value %d\n", current->pid,val);
task_kill(current->pid); task_kill(current->pid);
current->state = TASK_DEATH;
while (1); while (1);
} }

View File

@ -13,8 +13,22 @@ bool elf32Validate(Elf32_Ehdr *hdr) {
hdr->e_ident[EI_MAG2] == ELFMAG2 && hdr->e_ident[EI_MAG3] == ELFMAG3; hdr->e_ident[EI_MAG2] == ELFMAG2 && hdr->e_ident[EI_MAG3] == ELFMAG3;
} }
uint32_t elf32_get_max_vaddr(Elf32_Ehdr *hdr) {
Elf32_Phdr *phdr = (Elf32_Phdr *) ((uint32_t) hdr + hdr->e_phoff);
uint32_t max = 0;
for (int i = 0; i < hdr->e_phnum; i++) {
uint32_t size = MAX(
phdr->p_filesz,
phdr->p_memsz); // 如果memsz大于filesz 说明这是bss段我们以最大的为准
max = MAX(max, phdr->p_vaddr + size);
phdr++;
}
return max;
}
void load_segment(Elf32_Phdr *phdr, page_directory_t *pdt, void *elf) { void load_segment(Elf32_Phdr *phdr, page_directory_t *pdt, void *elf) {
unsigned int p = div_round_up(phdr->p_memsz, 0x1000); unsigned int p = div_round_up(phdr->p_memsz, 0x1000);
int d = phdr->p_paddr; int d = phdr->p_paddr;
if (d & 0x00000fff) { if (d & 0x00000fff) {
unsigned e = d + phdr->p_memsz; unsigned e = d + phdr->p_memsz;
@ -26,14 +40,47 @@ void load_segment(Elf32_Phdr *phdr,page_directory_t *pdt, void *elf) {
alloc_frame(get_page(d + i * 0x1000, 1, pdt, false), 0, 1); alloc_frame(get_page(d + i * 0x1000, 1, pdt, false), 0, 1);
} }
memcpy(phdr->p_vaddr, elf + phdr->p_offset, phdr->p_filesz); memcpy(phdr->p_vaddr, elf + phdr->p_offset, phdr->p_filesz);
if (phdr->p_memsz > phdr->p_filesz) { // 这个是bss段 if (phdr->p_memsz > phdr->p_filesz) { // 这个是bss段
memset(phdr->p_vaddr + phdr->p_filesz, 0, phdr->p_memsz - phdr->p_filesz); memset(phdr->p_vaddr + phdr->p_filesz, 0, phdr->p_memsz - phdr->p_filesz);
} }
} }
static uint32_t reload_elf_file(uint8_t *file_buffer) {
Elf32_Ehdr *elf_hdr = (Elf32_Ehdr *) file_buffer;
//检测文件类型
if ((elf_hdr->e_ident[0] != 0x7f) || (elf_hdr->e_ident[1] != 'E') ||
(elf_hdr->e_ident[2] != 'L') || (elf_hdr->e_ident[3] != 'F')) {
return 0;
}
for (int i = 0; i < elf_hdr->e_phnum; i++) {
Elf32_Phdr *phdr = (Elf32_Phdr *) (file_buffer + elf_hdr->e_phoff) + i;
if (phdr->p_type != PT_LOAD) {
continue;
}
//获取源文件地址以及需要加载的位置
uint8_t *src = file_buffer + phdr->p_offset;
//printf("POFFSET: %08x\n",phdr->p_offset);
uint8_t *dest = (uint8_t *) phdr->p_paddr;
for (int j = 0; j < phdr->p_filesz; j++) {
*dest++ = *src++;
}
//计算结束地址, 对bss区域进行清零
dest = (uint8_t *) phdr->p_paddr + phdr->p_filesz;
for (int j = 0; j < phdr->p_memsz - phdr->p_filesz; j++) {
*dest++ = 0;
}
}
//返回进入的地址
return elf_hdr->e_entry;
}
uint32_t load_elf(Elf32_Ehdr *hdr, page_directory_t *pdt) { uint32_t load_elf(Elf32_Ehdr *hdr, page_directory_t *pdt) {
Elf32_Phdr *phdr = (Elf32_Phdr *) ((uint32_t) hdr + hdr->e_phoff); Elf32_Phdr *phdr = (Elf32_Phdr *) ((uint32_t) hdr + hdr->e_phoff);
for (int i = 0; i < hdr->e_phnum; i++) { for (int i = 0; i < hdr->e_phnum; i++) {
if (phdr->p_type != PT_LOAD) {
continue;
}
load_segment(phdr, pdt, (void *) hdr); load_segment(phdr, pdt, (void *) hdr);
phdr++; phdr++;
} }

147465
src/util/logo.c Normal file

File diff suppressed because it is too large Load Diff