Remove most code for a blank start
This commit is contained in:
commit
ef90f51688
3
.gitattributes
vendored
Normal file
3
.gitattributes
vendored
Normal file
@ -0,0 +1,3 @@
|
||||
*.img[[:space:]]*.vdi filter=lfs diff=lfs merge=lfs -text
|
||||
*.vdi filter=lfs diff=lfs merge=lfs -text
|
||||
*.img filter=lfs diff=lfs merge=lfs -text
|
10
.gitignore
vendored
Normal file
10
.gitignore
vendored
Normal file
@ -0,0 +1,10 @@
|
||||
*.bin
|
||||
*.dis
|
||||
*.o
|
||||
*.elf
|
||||
*/*.o
|
||||
bochsout.txt
|
||||
stuff/*
|
||||
cpu/memory.h
|
||||
os.iso
|
||||
disk.img
|
45
Makefile
Normal file
45
Makefile
Normal file
@ -0,0 +1,45 @@
|
||||
PLAT=i386
|
||||
C_SOURCES = $(wildcard kernel/*.c drivers/$(PLAT)/*.c drivers/$(PLAT)/*/*.c libc/*.c cpu/$(PLAT)/*.c fs/*.c)
|
||||
OBJ = $(C_SOURCES:.c=.o $(shell cat psinfo/$(PLAT)/o.txt))
|
||||
CC = $(shell cat psinfo/$(PLAT)/cc.txt)
|
||||
GDB = $(shell cat psinfo/$(PLAT)/gdb.txt)
|
||||
CFLAGS = -Wall -g -ffreestanding
|
||||
QFLAGS = -m 2G -boot d -cdrom os.iso -serial vc #-chardev socket,id=s1,port=3000,host=localhost -serial chardev:s1
|
||||
|
||||
all: os.iso
|
||||
|
||||
run: os.iso
|
||||
qemu-system-i386 $(QFLAGS) -monitor stdio
|
||||
|
||||
debug: os.iso kernel/kernel.elf
|
||||
qemu-system-i386 -s $(QFLAGS) &
|
||||
$(GDB) -ex "target remote localhost:1234" -ex "symbol-file kernel/kernel.elf"
|
||||
|
||||
os.iso: kernel/kernel.elf initrd/*
|
||||
cp kernel/kernel.elf iso/boot
|
||||
ruby makeinitrd.rb initrd iso/boot/initrd
|
||||
grub-mkrescue -o $@ iso
|
||||
|
||||
kernel/kernel.elf: $(OBJ)
|
||||
i386-elf-ld -T linker.ld -o $@ $^
|
||||
|
||||
%.o: %.c h_files
|
||||
$(CC) $(CFLAGS) -c $< -o $@
|
||||
|
||||
%.o: %.asm
|
||||
nasm $< -f elf -o $@
|
||||
|
||||
%.o: %.s
|
||||
i386-elf-as $< -o $@
|
||||
|
||||
h_files: cpu/$(PLAT)/memory.h
|
||||
rm -f cpu/memory.h
|
||||
cp cpu/$(PLAT)/memory.h cpu/memory.h
|
||||
|
||||
pipe:
|
||||
rm -f pipe.in pipe.out
|
||||
mkfifo pipe.in
|
||||
ln pipe.in pipe.out
|
||||
|
||||
clean:
|
||||
rm -rf $(OBJ) kernel/cstart.o cpu/memory.h os.iso */*.elf iso/boot/initrd.tar
|
57
bochsrc.txt
Normal file
57
bochsrc.txt
Normal file
@ -0,0 +1,57 @@
|
||||
# configuration file generated by Bochs
|
||||
plugin_ctrl: unmapped=1, biosdev=1, speaker=1, extfpuirq=1, parallel=1, serial=1, iodebug=1
|
||||
config_interface: textconfig
|
||||
display_library: sdl2
|
||||
memory: host=32, guest=32
|
||||
romimage: file="/usr/local/Cellar/bochs/2.6.9_2/share/bochs/BIOS-bochs-latest", address=0x0, options=none
|
||||
vgaromimage: file="/usr/local/Cellar/bochs/2.6.9_2/share/bochs/VGABIOS-lgpl-latest"
|
||||
boot: cdrom
|
||||
floppy_bootsig_check: disabled=0
|
||||
# no floppya
|
||||
# no floppyb
|
||||
ata0: enabled=1, ioaddr1=0x1f0, ioaddr2=0x3f0, irq=14
|
||||
ata0-master: type=cdrom, path="os.iso", status=inserted, model="Generic 1234", biosdetect=auto
|
||||
ata0-slave: type=none
|
||||
ata1: enabled=1, ioaddr1=0x170, ioaddr2=0x370, irq=15
|
||||
ata1-master: type=none
|
||||
ata1-slave: type=none
|
||||
ata2: enabled=0
|
||||
ata3: enabled=0
|
||||
optromimage1: file=none
|
||||
optromimage2: file=none
|
||||
optromimage3: file=none
|
||||
optromimage4: file=none
|
||||
optramimage1: file=none
|
||||
optramimage2: file=none
|
||||
optramimage3: file=none
|
||||
optramimage4: file=none
|
||||
pci: enabled=1, chipset=i440fx
|
||||
vga: extension=vbe, update_freq=5, realtime=1
|
||||
cpu: count=1:1:1, ips=640000000, quantum=16, model=bx_generic, reset_on_triple_fault=0, cpuid_limit_winnt=0, ignore_bad_msrs=1, mwait_is_nop=0
|
||||
cpuid: level=6, stepping=3, model=3, family=6, vendor_string="GenuineIntel", brand_string=" Intel(R) Pentium(R) 4 CPU "
|
||||
cpuid: mmx=1, apic=xapic, simd=sse2, sse4a=0, misaligned_sse=0, sep=1, movbe=0, adx=0
|
||||
cpuid: aes=0, sha=0, xsave=0, xsaveopt=0, avx_f16c=0, avx_fma=0, bmi=0, xop=0, fma4=0
|
||||
cpuid: tbm=0, x86_64=1, 1g_pages=0, pcid=0, fsgsbase=0, smep=0, smap=0, mwait=1, vmx=1
|
||||
print_timestamps: enabled=0
|
||||
debugger_log: -
|
||||
magic_break: enabled=0
|
||||
port_e9_hack: enabled=0
|
||||
private_colormap: enabled=0
|
||||
clock: sync=none, time0=local, rtc_sync=0
|
||||
# no cmosimage
|
||||
# no loader
|
||||
log: bochsout.txt
|
||||
logprefix: %t%e%d
|
||||
debug: action=ignore,pci=report,pci2isa=report,pci_ide=report
|
||||
info: action=report
|
||||
error: action=report
|
||||
panic: action=ask
|
||||
keyboard: type=mf, serial_delay=250, paste_delay=100000, user_shortcut=none
|
||||
mouse: type=ps2, enabled=1, toggle=ctrl+mbutton
|
||||
speaker: enabled=1, mode=gui
|
||||
parport1: enabled=1, file=none
|
||||
parport2: enabled=0
|
||||
com1: enabled=0
|
||||
com2: enabled=0
|
||||
com3: enabled=0
|
||||
com4: enabled=0
|
6
cpu/cpu_init.h
Normal file
6
cpu/cpu_init.h
Normal file
@ -0,0 +1,6 @@
|
||||
#ifndef CPU_INIT_H
|
||||
#define CPU_INIT_H
|
||||
|
||||
void cpu_init();
|
||||
|
||||
#endif
|
6
cpu/halt.h
Normal file
6
cpu/halt.h
Normal file
@ -0,0 +1,6 @@
|
||||
#ifndef HALT_H
|
||||
#define HALT_H
|
||||
|
||||
void halt() __attribute__((noreturn));
|
||||
|
||||
#endif
|
2
cpu/i386/cpu_init.c
Normal file
2
cpu/i386/cpu_init.c
Normal file
@ -0,0 +1,2 @@
|
||||
void cpu_init() {
|
||||
}
|
5
cpu/i386/halt.c
Normal file
5
cpu/i386/halt.c
Normal file
@ -0,0 +1,5 @@
|
||||
void halt() {
|
||||
asm volatile("cli;\
|
||||
hltlabel: hlt;\
|
||||
jmp hltlabel");
|
||||
}
|
6
cpu/i386/memory.c
Normal file
6
cpu/i386/memory.c
Normal file
@ -0,0 +1,6 @@
|
||||
#include "paging.h"
|
||||
#include <stdint.h>
|
||||
|
||||
void* alloc_memory(uint32_t num_blocks) {
|
||||
return alloc_kern_pages(num_blocks,1);
|
||||
}
|
9
cpu/i386/memory.h
Normal file
9
cpu/i386/memory.h
Normal file
@ -0,0 +1,9 @@
|
||||
#ifndef CPU_MEMORY_H
|
||||
#define CPU_MEMORY_H
|
||||
|
||||
#include <stdint.h>
|
||||
#define BLK_SZ 4096
|
||||
|
||||
void* alloc_memory(uint32_t blocks);
|
||||
|
||||
#endif
|
70
cpu/i386/paging.c
Normal file
70
cpu/i386/paging.c
Normal file
@ -0,0 +1,70 @@
|
||||
#include <stdint.h>
|
||||
#include "paging_helpers.h"
|
||||
#include "paging.h"
|
||||
uint32_t page_directory [1024] __attribute__((aligned(4096)));
|
||||
uint32_t page_tables [1048576] __attribute__((aligned(4096)));
|
||||
void* next_kern_virt=(void*)KERN_VIRT_START;
|
||||
void* next_kern_phys=(void*)KERN_PHYS_START;
|
||||
void set_directory_entry(int entry,char usr,char wr,char p,uint32_t* page_directory,uint32_t* page_tables) {
|
||||
int flags=p&1;
|
||||
flags=flags|((wr&1)<<1);
|
||||
flags=flags|((usr&1)<<2);
|
||||
page_directory[entry]=(((uint32_t)&(page_tables[entry*1024]))-0xC0000000)|flags;
|
||||
}
|
||||
|
||||
void set_table_entry(uint32_t page,uint32_t base_addr,char usr,char wr,char p,uint32_t* page_tables) {
|
||||
int flags=p&1;
|
||||
flags=flags|((wr&1)<<1);
|
||||
flags=flags|((usr&1)<<2);
|
||||
page_tables[page]=base_addr|flags;
|
||||
}
|
||||
|
||||
void alloc_pages(void* virt_addr_ptr,void* phys_addr_ptr,int num_pages,char usr,char wr,uint32_t* page_directory,uint32_t* page_tables) {
|
||||
uint32_t virt_addr=(uint32_t)virt_addr_ptr;
|
||||
uint32_t phys_addr=(uint32_t)phys_addr_ptr;
|
||||
int dir_entry=(virt_addr&0xFFC00000)>>22;
|
||||
int table_entry=(virt_addr&0x3FF000)>>12;
|
||||
for (int i=0;i<=num_pages;i++) {
|
||||
set_table_entry((dir_entry*1024)+table_entry,phys_addr,usr,wr,1,page_tables);
|
||||
table_entry++;
|
||||
phys_addr+=0x1000;
|
||||
if (table_entry==1024) {
|
||||
table_entry=0;
|
||||
set_directory_entry(dir_entry,usr,wr,1,page_directory,page_tables);
|
||||
dir_entry++;
|
||||
} else if (i==num_pages) {
|
||||
set_directory_entry(dir_entry,usr,wr,1,page_directory,page_tables);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void* alloc_kern_pages(int num_pages,char wr) {
|
||||
void* starting=next_kern_virt;
|
||||
alloc_pages(next_kern_virt,next_kern_phys,num_pages,1,wr,page_directory,page_tables);
|
||||
next_kern_virt+=num_pages*4096;
|
||||
next_kern_phys+=num_pages*4096;
|
||||
return starting;
|
||||
}
|
||||
|
||||
int dir_entry_present(int entry) {
|
||||
uint32_t dir_entry=page_directory[entry];
|
||||
return dir_entry&1;
|
||||
}
|
||||
|
||||
void* virt_to_phys(void* virt_addr_ptr) {
|
||||
uint32_t virt_addr=(uint32_t)virt_addr_ptr;
|
||||
int dir_num=(virt_addr&0xFFC00000)>>22;
|
||||
int table_num=(virt_addr&0x3FF000)>>12;
|
||||
int offset=(virt_addr&0xFFF);
|
||||
uint32_t table_entry=page_tables[(dir_num*1024)+table_num];
|
||||
table_entry=table_entry&0xFFFFF000;
|
||||
return (void*)(table_entry+offset);
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
void init_paging() {
|
||||
alloc_kern_pages(NUM_KERN_DIRS*1024,1);
|
||||
load_page_directory((uint32_t*)((uint32_t)page_directory-0xC0000000));
|
||||
}
|
21
cpu/i386/paging.h
Normal file
21
cpu/i386/paging.h
Normal file
@ -0,0 +1,21 @@
|
||||
#ifndef PAGING_H
|
||||
#define PAGING_H
|
||||
|
||||
#include <stdint.h>
|
||||
#include "paging_helpers.h"
|
||||
|
||||
#define NUM_KERN_DIRS 4
|
||||
#define KERN_VIRT_START 0xC0000000
|
||||
#define KERN_PHYS_START 0x0
|
||||
|
||||
|
||||
extern uint32_t page_directory[1024];
|
||||
extern uint32_t page_tables[1048576];
|
||||
void alloc_pages(void* virt_addr_ptr,void* phys_addr_ptr,int num_pages,char usr,char wr,uint32_t* page_directory,uint32_t* page_tables);
|
||||
void* alloc_kern_pages(int num_pages,char wr);
|
||||
int dir_entry_present(int entry);
|
||||
void* virt_to_phys(void* virt_addr_ptr);
|
||||
void init_paging();
|
||||
|
||||
|
||||
#endif
|
9
cpu/i386/paging_helpers.asm
Normal file
9
cpu/i386/paging_helpers.asm
Normal file
@ -0,0 +1,9 @@
|
||||
global load_page_directory
|
||||
load_page_directory:
|
||||
push ebp
|
||||
mov ebp, esp
|
||||
mov eax, [esp+8]
|
||||
mov cr3, eax
|
||||
mov esp, ebp
|
||||
pop ebp
|
||||
ret
|
6
cpu/i386/paging_helpers.h
Normal file
6
cpu/i386/paging_helpers.h
Normal file
@ -0,0 +1,6 @@
|
||||
#ifndef PAGING_HELPERS_H
|
||||
#define PAGING_HELPERS_H
|
||||
|
||||
void load_page_directory(uint32_t* dir);
|
||||
|
||||
#endif
|
29
cpu/i386/ports.c
Normal file
29
cpu/i386/ports.c
Normal file
@ -0,0 +1,29 @@
|
||||
unsigned char port_byte_in(unsigned short port) {
|
||||
unsigned char result;
|
||||
asm("in %%dx, %%al":"=a"(result):"d"(port));
|
||||
return result;
|
||||
}
|
||||
|
||||
void port_byte_out(unsigned short port,unsigned char data) {
|
||||
asm("out %%al, %%dx":: "a"(data),"d"(port));
|
||||
}
|
||||
|
||||
unsigned short port_word_in(unsigned short port) {
|
||||
unsigned short result;
|
||||
asm("in %%dx, %%ax":"=a"(result):"d"(port));
|
||||
return result;
|
||||
}
|
||||
|
||||
void port_word_out(unsigned short port,unsigned short data) {
|
||||
asm("out %%ax, %%dx":: "a" (data), "d" (port));
|
||||
}
|
||||
|
||||
unsigned long port_long_in(unsigned short port) {
|
||||
unsigned long result;
|
||||
asm("inl %%dx, %%eax":"=a"(result):"d"(port));
|
||||
return result;
|
||||
}
|
||||
|
||||
void port_long_out(unsigned short port,unsigned long data) {
|
||||
asm("outl %%eax, %%dx":: "a" (data), "d" (port));
|
||||
}
|
10
cpu/i386/ports.h
Normal file
10
cpu/i386/ports.h
Normal file
@ -0,0 +1,10 @@
|
||||
#ifndef PORTS_H
|
||||
#define PORTS_H
|
||||
|
||||
unsigned char port_byte_in(unsigned short port);
|
||||
void port_byte_out(unsigned short port,unsigned char data);
|
||||
unsigned short port_word_in(unsigned short port);
|
||||
void port_word_out(unsigned short port,unsigned short data);
|
||||
unsigned long port_long_in(unsigned short port);
|
||||
void port_long_out(unsigned short port,unsigned long data);
|
||||
#endif
|
6
drivers/parallel.h
Normal file
6
drivers/parallel.h
Normal file
@ -0,0 +1,6 @@
|
||||
#ifndef PARALLEL_H
|
||||
#define PARALLEL_H
|
||||
|
||||
void parallel_init();
|
||||
|
||||
#endif
|
44
drivers/pci.h
Normal file
44
drivers/pci.h
Normal file
@ -0,0 +1,44 @@
|
||||
#ifndef PCI_H
|
||||
#define PCI_H
|
||||
|
||||
typedef struct {
|
||||
uint16_t vend_id;
|
||||
uint16_t dev_id;
|
||||
uint16_t command;
|
||||
uint16_t status;
|
||||
uint8_t rev_id;
|
||||
uint8_t prog_if;
|
||||
uint8_t subclass;
|
||||
uint8_t class_code;
|
||||
uint8_t cache_line_size;
|
||||
uint8_t lat_timer;
|
||||
uint8_t header_type;
|
||||
uint8_t bist;
|
||||
} __attribute__((packed)) pci_dev_common_info;
|
||||
|
||||
typedef enum {
|
||||
PCI_CLASS_UNCLASSIFIED=0x0,
|
||||
PCI_CLASS_STORAGE=0x1,
|
||||
PCI_CLASS_NETWORK=0x2,
|
||||
PCI_CLASS_DISPLAY=0x3,
|
||||
PCI_CLASS_MULTIMEDIA=0x4,
|
||||
PCI_CLASS_MEMORY=0x5,
|
||||
PCI_CLASS_BRIDGE=0x6,
|
||||
PCI_CLASS_SIMPCOM=0x7,
|
||||
PCI_CLASS_BASEPERIPH=0x8,
|
||||
PCI_CLASS_INPDEV=0x9,
|
||||
PCI_CLASS_DOCK=0xa,
|
||||
PCI_CLASS_CPU=0xb,
|
||||
PCI_CLASS_SERBUS=0xc,
|
||||
PCI_CLASS_WIRELESS=0xd,
|
||||
PCI_CLASS_INTELLIGENT=0xe,
|
||||
PCI_CLASS_SATELLITE=0xf,
|
||||
PCI_CLASS_ENCRYPTION=0x10,
|
||||
PCI_CLASS_SIGPROCESS=0x11,
|
||||
} pci_class;
|
||||
|
||||
extern pci_dev_common_info** pci_devs;
|
||||
extern uint32_t pci_num_devs;
|
||||
void pci_init();
|
||||
|
||||
#endif
|
6
drivers/ps2.h
Normal file
6
drivers/ps2.h
Normal file
@ -0,0 +1,6 @@
|
||||
#ifndef PS2_EXT_H
|
||||
#define PS2_EXT_H
|
||||
|
||||
void ps2_init();
|
||||
|
||||
#endif
|
9
drivers/screen.h
Normal file
9
drivers/screen.h
Normal file
@ -0,0 +1,9 @@
|
||||
#ifndef SCREEN_H
|
||||
#define SCREEN_H
|
||||
|
||||
void screen_init();
|
||||
void screen_write_string(const char *string);
|
||||
void screen_clear();
|
||||
void screen_backspace();
|
||||
|
||||
#endif
|
7
drivers/serial.h
Normal file
7
drivers/serial.h
Normal file
@ -0,0 +1,7 @@
|
||||
#ifndef SERIAL_H
|
||||
#define SERIAL_H
|
||||
#include <stdint.h>
|
||||
|
||||
void serial_init();
|
||||
|
||||
#endif
|
7
drivers/timer.h
Normal file
7
drivers/timer.h
Normal file
@ -0,0 +1,7 @@
|
||||
#ifndef TIMER_H
|
||||
#define TIMER_H
|
||||
|
||||
void wait(int milli);
|
||||
void timer_init();
|
||||
|
||||
#endif
|
71
fs/devfs.c
Normal file
71
fs/devfs.c
Normal file
@ -0,0 +1,71 @@
|
||||
// #include "../kernel/vfs.h"
|
||||
// #include "../libc/stdlib.h"
|
||||
// #include "../libc/string.h"
|
||||
// #include "../libc/stdio.h"
|
||||
// #include "devfs.h"
|
||||
//
|
||||
// char** devices;
|
||||
// dev_drv* dev_drivers;
|
||||
// uint32_t num_devices;
|
||||
// uint32_t max_devices;
|
||||
//
|
||||
// char devfs_drv(fs_op op,FILE* stream,void* data1,void* data2) {
|
||||
// if (op==FSOP_MOUNT) {
|
||||
// return 1;
|
||||
// }
|
||||
// if (op==FSOP_OPEN) {
|
||||
// for (int i=0;i<num_devices;i++) {
|
||||
// if (strcmp(devices[i],stream->path)==0) {
|
||||
// return 1;
|
||||
// }
|
||||
// }
|
||||
// return 0;
|
||||
// }
|
||||
// if (op==FSOP_GETC) {
|
||||
// int i;
|
||||
// for (i=0;i<num_devices;i++) {
|
||||
// if (strcmp(devices[i],stream->path)==0) {
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// *((int*)data1)=dev_drivers[i]((char*)stream->path,0,stream->pos,0);
|
||||
// stream->pos+=1;
|
||||
// return 1;
|
||||
// }
|
||||
// if (op==FSOP_PUTC) {
|
||||
// int i;
|
||||
// for (i=0;i<num_devices;i++) {
|
||||
// if (strcmp(devices[i],stream->path)==0) {
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// dev_drivers[i]((char*)stream->path,*((int*)data1),stream->pos,1);
|
||||
// stream->pos+=1;
|
||||
// return 1;
|
||||
// }
|
||||
// if (op==FSOP_CLOSE) {
|
||||
// return 1;
|
||||
// }
|
||||
// return 0;
|
||||
// }
|
||||
//
|
||||
// void init_devfs() {
|
||||
// devices=malloc(sizeof(char*)*32);
|
||||
// dev_drivers=malloc(sizeof(dev_drv)*32);
|
||||
// num_devices=0;
|
||||
// max_devices=0;
|
||||
// register_fs(devfs_drv,"devfs");
|
||||
// mount("/dev/","","devfs");
|
||||
// }
|
||||
//
|
||||
// void add_dev(dev_drv drv,char* name) {
|
||||
// if (num_devices==max_devices) {
|
||||
// devices=realloc(devices,sizeof(char*)*(max_devices+32));
|
||||
// dev_drivers=realloc(dev_drivers,sizeof(dev_drv)*(max_devices+32));
|
||||
// max_devices+=32;
|
||||
// }
|
||||
// dev_drivers[num_devices]=drv;
|
||||
// devices[num_devices]=malloc(sizeof(char)*(strlen(name)+1));
|
||||
// strcpy(devices[num_devices],name);
|
||||
// num_devices++;
|
||||
// }
|
8
fs/devfs.h
Normal file
8
fs/devfs.h
Normal file
@ -0,0 +1,8 @@
|
||||
#ifndef DEVFS_H
|
||||
#define DEVFS_H
|
||||
|
||||
typedef int (*dev_drv)(char* filename,int c,long pos,char wr);
|
||||
|
||||
void init_devfs();
|
||||
void add_dev(dev_drv drv,char* name);
|
||||
#endif
|
85
fs/initrd.c
Normal file
85
fs/initrd.c
Normal file
@ -0,0 +1,85 @@
|
||||
// #include "../kernel/vfs.h"
|
||||
// #include "../cpu/halt.h"
|
||||
// #include "../libc/stdlib.h"
|
||||
// #include "../libc/stdio.h"
|
||||
// #include "../libc/string.h"
|
||||
//
|
||||
// char** names;
|
||||
// uint32_t* offsets;
|
||||
// uint32_t* sizes;
|
||||
// uint32_t num_files;
|
||||
// FILE* initrd_fd;
|
||||
//
|
||||
// char initrd_drv(fs_op op,FILE* stream,void* data1,void* data2) {
|
||||
// if (op==FSOP_MOUNT) {
|
||||
// return 1;
|
||||
// }
|
||||
// if (op==FSOP_OPEN) {
|
||||
// char file_exists=0;
|
||||
// for (int i=0;i<num_files;i++) {
|
||||
// if (strcmp(names[i],stream->path)==0) {
|
||||
// file_exists=1;
|
||||
// }
|
||||
// }
|
||||
// return file_exists;
|
||||
// }
|
||||
// if (op==FSOP_GETC) {
|
||||
// int i;
|
||||
// for (i=0;i<num_files;i++) {
|
||||
// if (strcmp(names[i],stream->path)==0) {
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// if (stream->pos>=sizes[i]) {
|
||||
// *((int*)data1)=EOF;
|
||||
// stream->eof=1;
|
||||
// return 1;
|
||||
// }
|
||||
// fseek(initrd_fd,offsets[i]+stream->pos,SEEK_SET);
|
||||
// *((int*)data1)=fgetc(initrd_fd);
|
||||
// stream->pos+=1;
|
||||
// return 1;
|
||||
// }
|
||||
// if (op==FSOP_CLOSE) {
|
||||
// return 1;
|
||||
// }
|
||||
// return 0;
|
||||
// }
|
||||
//
|
||||
// void init_initrd() {
|
||||
// initrd_fd=fopen("/dev/initrd","r");
|
||||
// if (!initrd_fd) {
|
||||
// printf("PANIC: Cannot open initrd!");
|
||||
// halt();
|
||||
// }
|
||||
// uint32_t max_files=32;
|
||||
// num_files=0;
|
||||
// names=malloc(sizeof(char*)*32);
|
||||
// offsets=malloc(sizeof(uint32_t)*32);
|
||||
// sizes=malloc(sizeof(uint32_t)*32);
|
||||
// for (uint32_t i=0;;i++) {
|
||||
// if (i==max_files) {
|
||||
// names=realloc(names,sizeof(char*)*(max_files+32));
|
||||
// offsets=realloc(offsets,sizeof(uint32_t)*(max_files+32));
|
||||
// sizes=realloc(sizes,sizeof(uint32_t)*(max_files+32));
|
||||
// max_files+=32;
|
||||
// }
|
||||
// uint32_t name_size;
|
||||
// fread(&name_size,4,1,initrd_fd);
|
||||
// if (name_size==0) {
|
||||
// break;
|
||||
// }
|
||||
// char* name=malloc(sizeof(char)*(name_size+1));
|
||||
// fread(name,1,name_size+1,initrd_fd);
|
||||
// long contents_size;
|
||||
// fread(&contents_size,4,1,initrd_fd);
|
||||
// long datapos=ftell(initrd_fd);
|
||||
// fseek(initrd_fd,contents_size,SEEK_CUR);
|
||||
// names[i]=name;
|
||||
// offsets[i]=datapos;
|
||||
// sizes[i]=contents_size;
|
||||
// num_files++;
|
||||
// }
|
||||
// fseek(initrd_fd,0,SEEK_SET);
|
||||
// register_fs(initrd_drv,"initrd");
|
||||
// }
|
6
fs/initrd.h
Normal file
6
fs/initrd.h
Normal file
@ -0,0 +1,6 @@
|
||||
#ifndef INITRD_H
|
||||
#define INITRD_H
|
||||
|
||||
uint32_t init_initrd();
|
||||
|
||||
#endif
|
2
initrd/hi.txt
Normal file
2
initrd/hi.txt
Normal file
@ -0,0 +1,2 @@
|
||||
Hello!
|
||||
This is hi.txt!
|
1
initrd/myfile.txt
Normal file
1
initrd/myfile.txt
Normal file
@ -0,0 +1 @@
|
||||
This is another file!
|
1
initrd/test.txt
Normal file
1
initrd/test.txt
Normal file
@ -0,0 +1 @@
|
||||
File 1
|
7
iso/boot/grub/grub.cfg
Normal file
7
iso/boot/grub/grub.cfg
Normal file
@ -0,0 +1,7 @@
|
||||
timeout=0
|
||||
|
||||
menuentry "My OS" {
|
||||
multiboot /boot/kernel.elf
|
||||
module /boot/initrd initrd
|
||||
boot
|
||||
}
|
BIN
iso/boot/initrd
Normal file
BIN
iso/boot/initrd
Normal file
Binary file not shown.
126
kernel/boot.s
Normal file
126
kernel/boot.s
Normal file
@ -0,0 +1,126 @@
|
||||
# Declare constants for the multiboot header.
|
||||
.set ALIGN, 1<<0 # align loaded modules on page boundaries
|
||||
.set MEMINFO, 1<<1 # provide memory map
|
||||
.set FLAGS, ALIGN | MEMINFO # this is the Multiboot 'flag' field
|
||||
.set MAGIC, 0x1BADB002 # 'magic number' lets bootloader find the header
|
||||
.set CHECKSUM, -(MAGIC + FLAGS) # checksum of above, to prove we are multiboot
|
||||
|
||||
# Declare a multiboot header that marks the program as a kernel.
|
||||
.section .multiboot
|
||||
.align 4
|
||||
.long MAGIC
|
||||
.long FLAGS
|
||||
.long CHECKSUM
|
||||
|
||||
# Allocate the initial stack.
|
||||
.section .bootstrap_stack, "aw", @nobits
|
||||
stack_bottom:
|
||||
.skip 16384 # 16 KiB
|
||||
stack_top:
|
||||
|
||||
.global int_stack_top
|
||||
|
||||
.section .interrupt_stack, "aw", @nobits
|
||||
int_stack_bottom:
|
||||
.skip 16384 # 16 KiB
|
||||
int_stack_top:
|
||||
|
||||
# Preallocate pages used for paging. Don't hard-code addresses and assume they
|
||||
# are available, as the bootloader might have loaded its multiboot structures or
|
||||
# modules there. This lets the bootloader know it must avoid the addresses.
|
||||
.section .bss, "aw", @nobits
|
||||
.align 4096
|
||||
boot_page_directory:
|
||||
.skip 4096
|
||||
boot_page_tables:
|
||||
boot_page_table1:
|
||||
.skip 4096
|
||||
boot_page_table2:
|
||||
.skip 4096
|
||||
boot_page_table3:
|
||||
.skip 4096
|
||||
boot_page_table4:
|
||||
.skip 4096
|
||||
# Further page tables may be required if the kernel grows beyond 3 MiB.
|
||||
|
||||
# The kernel entry point.
|
||||
.section .text
|
||||
.global _start
|
||||
.type _start, @function
|
||||
_start:
|
||||
cmp $0x2BADB002, %eax
|
||||
jnz no_multiboot
|
||||
# Physical address of boot_page_tables.
|
||||
# TODO: I recall seeing some assembly that used a macro to do the
|
||||
# conversions to and from physical. Maybe this should be done in this
|
||||
# code as well?
|
||||
movl $(boot_page_tables - 0xC0000000), %edi
|
||||
# First address to map is address 0.
|
||||
# TODO: Start at the first kernel page instead. Alternatively map the first
|
||||
# 1 MiB as it can be generally useful, and there's no need to
|
||||
# specially map the VGA buffer.
|
||||
movl $0, %esi
|
||||
# Map 4096 pages.
|
||||
movl $4096, %ecx
|
||||
|
||||
1:
|
||||
# Map physical address as "present, writable". Note that this maps
|
||||
# .text and .rodata as writable. Mind security and map them as non-writable.
|
||||
movl %esi, %edx
|
||||
orl $0x007, %edx
|
||||
movl %edx, (%edi)
|
||||
|
||||
# Size of page is 4096 bytes.
|
||||
addl $4096, %esi
|
||||
# Size of entries in boot_page_tables is 4 bytes.
|
||||
addl $4, %edi
|
||||
# Loop to the next entry if we haven't finished.
|
||||
loop 1b
|
||||
|
||||
# The page table is used at both page directory entry 0 (virtually from 0x0
|
||||
# to 0x3FFFFF) (thus identity mapping the kernel) and page directory entry
|
||||
# 768 (virtually from 0xC0000000 to 0xC03FFFFF) (thus mapping it in the
|
||||
# higher half). The kernel is identity mapped because enabling paging does
|
||||
# not change the next instruction, which continues to be physical. The CPU
|
||||
# would instead page fault if there was no identity mapping.
|
||||
|
||||
# Map the page table to both virtual addresses 0x00000000 and 0xC0000000.
|
||||
movl $(boot_page_table1 - 0xC0000000 + 0x007), boot_page_directory - 0xC0000000 + 0
|
||||
movl $(boot_page_table1 - 0xC0000000 + 0x007), boot_page_directory - 0xC0000000 + 768 * 4
|
||||
movl $(boot_page_table2 - 0xC0000000 + 0x007), boot_page_directory - 0xC0000000 + 769 * 4
|
||||
movl $(boot_page_table3 - 0xC0000000 + 0x007), boot_page_directory - 0xC0000000 + 770 * 4
|
||||
movl $(boot_page_table4 - 0xC0000000 + 0x007), boot_page_directory - 0xC0000000 + 771 * 4
|
||||
# Set cr3 to the address of the boot_page_directory.
|
||||
movl $(boot_page_directory - 0xC0000000), %ecx
|
||||
movl %ecx, %cr3
|
||||
|
||||
# Enable paging and the write-protect bit.
|
||||
movl %cr0, %ecx
|
||||
orl $0x80010000, %ecx
|
||||
movl %ecx, %cr0
|
||||
|
||||
# Jump to higher half with an absolute jump.
|
||||
lea 4f, %ecx
|
||||
jmp *%ecx
|
||||
|
||||
4:
|
||||
# At this point, paging is fully set up and enabled.
|
||||
|
||||
# Unmap the identity mapping as it is now unnecessary.
|
||||
movl $0, boot_page_directory + 0
|
||||
|
||||
# Reload crc3 to force a TLB flush so the changes to take effect.
|
||||
movl %cr3, %ecx
|
||||
movl %ecx, %cr3
|
||||
|
||||
# Set up the stack.
|
||||
mov $stack_top, %esp
|
||||
|
||||
# Enter the high-level kernel.
|
||||
add $0xC0000000, %ebx
|
||||
push %ebx
|
||||
call kmain
|
||||
|
||||
# Infinite loop if the system has nothing more to do.
|
||||
no_multiboot:
|
||||
loop: jmp loop
|
5
kernel/kernel.c
Normal file
5
kernel/kernel.c
Normal file
@ -0,0 +1,5 @@
|
||||
#include "../cpu/cpu_init.h"
|
||||
|
||||
void kmain() {
|
||||
cpu_init();
|
||||
}
|
37
libc/devbuf.c
Normal file
37
libc/devbuf.c
Normal file
@ -0,0 +1,37 @@
|
||||
#include "devbuf.h"
|
||||
#include "stdlib.h"
|
||||
#include "stdio.h"
|
||||
|
||||
devbuf* devbuf_init() {
|
||||
devbuf* buf=malloc(sizeof(devbuf));
|
||||
buf->rd=0;
|
||||
buf->wr=0;
|
||||
for (int i=0;i<256;i++) {
|
||||
buf->buf[i]=EOF;
|
||||
}
|
||||
}
|
||||
|
||||
void devbuf_add(char byte,devbuf* buf) {
|
||||
buf->buf[buf->wr]=byte;
|
||||
buf->wr++;
|
||||
if (buf->wr==buf->rd) {
|
||||
buf->wr--;
|
||||
}
|
||||
}
|
||||
|
||||
int devbuf_get(devbuf* buf) {
|
||||
if (buf->buf[buf->rd]==-1) {
|
||||
buf->rd++;
|
||||
if (buf->buf[buf->rd]==-1) {
|
||||
buf->rd--;
|
||||
while (buf->buf[buf->rd]==-1);
|
||||
}
|
||||
}
|
||||
int data=buf->buf[buf->rd];
|
||||
buf->buf[buf->rd]=-1;
|
||||
buf->rd++;
|
||||
if (buf->rd>buf->wr) {
|
||||
buf->rd=buf->wr-1;
|
||||
}
|
||||
return data;
|
||||
}
|
16
libc/devbuf.h
Normal file
16
libc/devbuf.h
Normal file
@ -0,0 +1,16 @@
|
||||
#ifndef DEVBUF_H
|
||||
#define DEVBUF_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
typedef struct {
|
||||
int buf[256];
|
||||
uint8_t rd;
|
||||
uint8_t wr;
|
||||
} devbuf;
|
||||
|
||||
devbuf* devbuf_init();
|
||||
void devbuf_add(char byte,devbuf* buf);
|
||||
int devbuf_get(devbuf* buf);
|
||||
|
||||
#endif
|
7
libc/math.c
Normal file
7
libc/math.c
Normal file
@ -0,0 +1,7 @@
|
||||
float ceilf(float num) {
|
||||
int inum=(int)num;
|
||||
if (num==(float)inum) {
|
||||
return (float)inum;
|
||||
}
|
||||
return (float)(inum+1);
|
||||
}
|
6
libc/math.h
Normal file
6
libc/math.h
Normal file
@ -0,0 +1,6 @@
|
||||
#ifndef MATH_H
|
||||
#define MATH_H
|
||||
|
||||
float ceilf(float num);
|
||||
|
||||
#endif
|
40
libc/stdio.h
Normal file
40
libc/stdio.h
Normal file
@ -0,0 +1,40 @@
|
||||
#ifndef STDIO_H
|
||||
#define STDIO_H
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
typedef struct {
|
||||
char* mntpnt;
|
||||
const char* path;
|
||||
uint32_t type;
|
||||
long pos;
|
||||
int eof;
|
||||
} FILE;
|
||||
|
||||
#define NO_FD 0xFFFFFFFF
|
||||
|
||||
#define SEEK_CUR 1
|
||||
#define SEEK_END 2
|
||||
#define SEEK_SET 3
|
||||
#define EOF -1
|
||||
|
||||
extern uint32_t stdin;
|
||||
extern uint32_t stdout;
|
||||
extern uint32_t stderr;
|
||||
|
||||
uint32_t fopen(const char* filename,const char* mode);
|
||||
int fgetc(FILE* stream);
|
||||
int getc();
|
||||
char* fgets(char* str,int count,FILE* stream);
|
||||
size_t fread(void* buffer,size_t size,size_t count,FILE* stream);
|
||||
int fputc(int c,FILE* stream);
|
||||
int putc(int c);
|
||||
int fputs(const char* s,FILE* stream);
|
||||
int puts(const char* s);
|
||||
int fprintf(FILE* stream,const char* format,...);
|
||||
int printf(const char* format,...);
|
||||
int fseek(FILE* stream,long offset,int origin);
|
||||
long ftell(FILE* stream);
|
||||
int fclose(FILE* file);
|
||||
|
||||
#endif
|
142
libc/stdlib.c
Normal file
142
libc/stdlib.c
Normal file
@ -0,0 +1,142 @@
|
||||
#include "../cpu/memory.h"
|
||||
#include "string.h"
|
||||
#include "stdlib.h"
|
||||
#include "math.h"
|
||||
#include <stdint.h>
|
||||
#define MAX_BLOCKS 512
|
||||
#define MALLOC_DEBUG 1
|
||||
typedef struct {
|
||||
char* bitmap;
|
||||
uint32_t bitmap_byt_size;
|
||||
uint32_t bitmap_bit_size;
|
||||
uint32_t avail_data_size;
|
||||
void* data_block;
|
||||
} heap_block;
|
||||
|
||||
|
||||
heap_block entries[MAX_BLOCKS];
|
||||
uint32_t num_used_entries;
|
||||
char get_bmap_bit(char* bmap,uint32_t index) {
|
||||
uint32_t byte=index/8;
|
||||
uint32_t bit=index%8;
|
||||
char entry=bmap[byte];
|
||||
return (entry&(1<<bit))>0;
|
||||
}
|
||||
void set_bmap_bit(char* bmap,uint32_t index) {
|
||||
uint32_t byte=index/8;
|
||||
uint32_t bit=index%8;
|
||||
bmap[byte]=bmap[byte]|(1<<bit);
|
||||
}
|
||||
void clear_bmap_bit(char* bmap,uint32_t index) {
|
||||
uint32_t byte=index/8;
|
||||
uint32_t bit=index%8;
|
||||
bmap[byte]=bmap[byte]&(~(1<<bit));
|
||||
}
|
||||
void reserve_block(uint32_t mem_blks) {
|
||||
uint32_t bmap_byts=((mem_blks*BLK_SZ)/4)/8;
|
||||
entries[num_used_entries].bitmap=alloc_memory((uint32_t)ceilf((double)bmap_byts/BLK_SZ));
|
||||
entries[num_used_entries].bitmap_byt_size=bmap_byts;
|
||||
entries[num_used_entries].bitmap_bit_size=bmap_byts*8;
|
||||
char* bmap=entries[num_used_entries].bitmap;
|
||||
char bmap_byt_sz=entries[num_used_entries].bitmap_byt_size;
|
||||
for(uint32_t i=0;i<bmap_byt_sz;i++) {
|
||||
bmap[i]=0;
|
||||
}
|
||||
entries[num_used_entries].avail_data_size=mem_blks*BLK_SZ;
|
||||
entries[num_used_entries].data_block=alloc_memory(mem_blks);
|
||||
num_used_entries++;
|
||||
}
|
||||
|
||||
void* malloc(uint32_t size) {
|
||||
uint32_t num_4b_grps=(uint32_t)ceilf((float)size/4);
|
||||
num_4b_grps+=3;
|
||||
int blk_indx=-1;
|
||||
uint32_t bmap_index;
|
||||
heap_block entry;
|
||||
for (int i=0;i<num_used_entries;i++) {
|
||||
uint32_t remaining_blks;
|
||||
entry=entries[i];
|
||||
if (entry.avail_data_size>=size) {
|
||||
char* bmap=entry.bitmap;
|
||||
uint32_t bmap_byt_sz=entry.bitmap_byt_size;
|
||||
for(int i=0;i<bmap_byt_sz;i++) {
|
||||
if (bmap[i]!=0xFF) {
|
||||
char got_0=0;
|
||||
remaining_blks=num_4b_grps;
|
||||
uint32_t old_j;
|
||||
for (uint32_t j=i*8;;j++) {
|
||||
char bit=get_bmap_bit(bmap,j);
|
||||
if (got_0) {
|
||||
if (bit) {
|
||||
if (remaining_blks==0) {
|
||||
bmap_index=old_j;
|
||||
break;
|
||||
} else {
|
||||
i+=j/8;
|
||||
i--;
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
remaining_blks--;
|
||||
}
|
||||
} else {
|
||||
if (!bit) {
|
||||
got_0=1;
|
||||
old_j=j;
|
||||
remaining_blks--;
|
||||
}
|
||||
}
|
||||
if (remaining_blks==0) {
|
||||
bmap_index=old_j;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (remaining_blks==0) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (remaining_blks==0) {
|
||||
blk_indx=i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (blk_indx==-1) {
|
||||
// reserve_block((uint32_t)ceilf((double)size/BLK_SZ));
|
||||
reserve_block(256);
|
||||
return malloc(size);
|
||||
}
|
||||
for (int i=0;i<num_4b_grps;i++) {
|
||||
set_bmap_bit(entry.bitmap,bmap_index+i);
|
||||
}
|
||||
uint32_t data_offset=(bmap_index*8)+12;
|
||||
uint32_t* info=(void*)(((uint32_t)entry.data_block)+data_offset-12);
|
||||
info[0]=num_4b_grps;
|
||||
info[1]=bmap_index;
|
||||
info[2]=blk_indx;
|
||||
entry.avail_data_size-=size+12;
|
||||
return (void*)(((uint32_t)entry.data_block)+data_offset);
|
||||
|
||||
}
|
||||
|
||||
void* realloc(void *mem, size_t new_sz) {
|
||||
void* ptr=malloc(new_sz);
|
||||
uint32_t num_4b_grps=*((uint32_t*)((uint32_t)mem-12));
|
||||
memcpy(ptr,mem,num_4b_grps*4);
|
||||
free(mem);
|
||||
mem=ptr;
|
||||
return ptr;
|
||||
}
|
||||
|
||||
void free(void* mem) {
|
||||
uint32_t* info=(uint32_t*)((uint32_t)mem-12);
|
||||
uint32_t num_4b_grps=info[0];
|
||||
uint32_t bmap_index=info[1];
|
||||
uint32_t blk_indx=info[2];
|
||||
heap_block entry=entries[blk_indx];
|
||||
for (int i=0;i<num_4b_grps;i++) {
|
||||
clear_bmap_bit(entry.bitmap,bmap_index+i);
|
||||
}
|
||||
entry.avail_data_size+=(num_4b_grps*4)+12;
|
||||
}
|
12
libc/stdlib.h
Normal file
12
libc/stdlib.h
Normal file
@ -0,0 +1,12 @@
|
||||
#ifndef STDLIB_H
|
||||
#define STDLIB_H
|
||||
|
||||
#include <stddef.h>
|
||||
#define EXIT_SUCCESS 0
|
||||
#define EXIT_FAILURE 1
|
||||
|
||||
void* malloc(size_t size);
|
||||
void* realloc(void *mem, size_t new_sz);
|
||||
void free(void* mem);
|
||||
|
||||
#endif
|
137
libc/string.c
Normal file
137
libc/string.c
Normal file
@ -0,0 +1,137 @@
|
||||
#include "string.h"
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
#include "stdlib.h"
|
||||
|
||||
void* memcpy(void* dest_ptr,const void* source_ptr,size_t len) {
|
||||
char* source=(char*)source_ptr;
|
||||
char* dest=(char*)dest_ptr;
|
||||
for(size_t i=0;i<len;i++) {
|
||||
dest[i]=source[i];
|
||||
}
|
||||
return dest_ptr;
|
||||
}
|
||||
|
||||
void* memset(void *dest_ptr,int val,size_t len) {
|
||||
char* dest=(char*)dest_ptr;
|
||||
for (size_t i=0;i<len;i++){
|
||||
dest[i]=(char)val;
|
||||
}
|
||||
return dest_ptr;
|
||||
}
|
||||
|
||||
int strcmp(const char* s1,const char* s2) {
|
||||
int i;
|
||||
for (i = 0; s1[i] == s2[i]; i++) {
|
||||
if (s1[i] == '\0') return 0;
|
||||
}
|
||||
return s1[i] - s2[i];
|
||||
}
|
||||
|
||||
size_t strlen(const char* str) {
|
||||
size_t i;
|
||||
for (i=0;str[i]!='\0';i++);
|
||||
return i;
|
||||
}
|
||||
|
||||
char* strcpy(char* dest,const char* src) {
|
||||
int i;
|
||||
for (i=0;i<strlen(src);i++) {
|
||||
dest[i]=src[i];
|
||||
}
|
||||
dest[i]='\0';
|
||||
return dest;
|
||||
}
|
||||
|
||||
char* strrev(char* str) {
|
||||
char chr;
|
||||
int j;
|
||||
for (int i=0,j=strlen(str)-1;i<j;i++,j--) {
|
||||
chr=str[i];
|
||||
str[i]=str[j];
|
||||
str[j]=chr;
|
||||
}
|
||||
return str;
|
||||
}
|
||||
|
||||
void int_to_ascii(int n,char* str) {
|
||||
int i;
|
||||
int sign;
|
||||
if ((sign = n)<0) {
|
||||
n=-n;
|
||||
}
|
||||
i=0;
|
||||
do {
|
||||
str[i++]=n%10+'0';
|
||||
} while ((n /= 10) > 0);
|
||||
if (sign < 0) {
|
||||
str[i++] = '-';
|
||||
}
|
||||
str[i]='\0';
|
||||
strrev(str);
|
||||
}
|
||||
|
||||
void hex_to_ascii(int n, char* str) {
|
||||
append(str, '0');
|
||||
append(str, 'x');
|
||||
char zeros = 0;
|
||||
|
||||
unsigned int tmp;
|
||||
int i;
|
||||
for (i = 28; i > 0; i -= 4) {
|
||||
tmp = (n >> i) & 0xF;
|
||||
if (tmp == 0 && zeros == 0) continue;
|
||||
zeros = 1;
|
||||
if (tmp > 0xA) append(str, tmp - 0xA + 'a');
|
||||
else append(str, tmp + '0');
|
||||
}
|
||||
|
||||
tmp = n & 0xF;
|
||||
if (tmp >= 0xA) append(str, tmp - 0xA + 'a');
|
||||
else append(str, tmp + '0');
|
||||
}
|
||||
|
||||
void append(char* s, char n) {
|
||||
int len = strlen(s);
|
||||
s[len] = n;
|
||||
s[len+1] = '\0';
|
||||
}
|
||||
|
||||
void backspace(char* s) {
|
||||
int len = strlen(s);
|
||||
s[len-1] = '\0';
|
||||
}
|
||||
|
||||
char* strtok_str=NULL;
|
||||
size_t strtok_index;
|
||||
|
||||
char strtok_delim_check(char* delim) {
|
||||
for (int i=0;i<strlen(delim);i++) {
|
||||
if (strtok_str[strtok_index]==delim[i]||strtok_str[strtok_index]=='\0') {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
char* strtok(char* str, const char* delim) {
|
||||
if (str!=NULL) {
|
||||
strtok_str=str;
|
||||
strtok_index=0;
|
||||
}
|
||||
if (!strtok_str || strtok_index>strlen(strtok_str)) {
|
||||
return NULL;
|
||||
}
|
||||
char* tok=malloc(sizeof(char)*32);
|
||||
tok[0]='\0';
|
||||
size_t max_len=32;
|
||||
for (;strtok_delim_check(delim);strtok_index++) {
|
||||
if (strlen(tok)+1==max_len) {
|
||||
tok=realloc(tok,sizeof(char)*(max_len+32));
|
||||
max_len+=32;
|
||||
}
|
||||
append(tok,strtok_str[strtok_index]);
|
||||
}
|
||||
strtok_index++;
|
||||
return tok;
|
||||
}
|
17
libc/string.h
Normal file
17
libc/string.h
Normal file
@ -0,0 +1,17 @@
|
||||
#ifndef STRING_H
|
||||
#define STRING_H
|
||||
#include <stddef.h>
|
||||
|
||||
void* memcpy(void* dest,const void* src,size_t len);
|
||||
void* memset(void* dest,int val,size_t len);
|
||||
int strcmp(const char* s1,const char* s2);
|
||||
size_t strlen(const char* str);
|
||||
char* strcpy(char* dest,const char* src);
|
||||
char* strtok(char* str, const char* delim);
|
||||
|
||||
char* strrev(char *str);
|
||||
void int_to_ascii(int n,char* str);
|
||||
void hex_to_ascii(int n, char* str);
|
||||
void append(char* s, char n);
|
||||
void backspace(char* s);
|
||||
#endif
|
32
linker.ld
Normal file
32
linker.ld
Normal file
@ -0,0 +1,32 @@
|
||||
ENTRY (_start)
|
||||
|
||||
SECTIONS
|
||||
{
|
||||
/* The kernel will live at 3GB + 1MB in the virtual address space, */
|
||||
/* which will be mapped to 1MB in the physical address space. */
|
||||
/* Note that we page-align the sections. */
|
||||
. = 0xC0100000;
|
||||
/* Add a symbol that indicates the start address of the kernel. */
|
||||
_kernel_start = .;
|
||||
.text ALIGN (4K) : AT (ADDR (.text) - 0xC0000000)
|
||||
{
|
||||
*(.multiboot)
|
||||
*(.text)
|
||||
}
|
||||
.rodata ALIGN (4K) : AT (ADDR (.rodata) - 0xC0000000)
|
||||
{
|
||||
*(.rodata)
|
||||
}
|
||||
.data ALIGN (4K) : AT (ADDR (.data) - 0xC0000000)
|
||||
{
|
||||
*(.data)
|
||||
}
|
||||
.bss ALIGN (4K) : AT (ADDR (.bss) - 0xC0000000)
|
||||
{
|
||||
*(COMMON)
|
||||
*(.bss)
|
||||
*(.bootstrap_stack)
|
||||
}
|
||||
/* Add a symbol that indicates the end address of the kernel. */
|
||||
_kernel_end = .;
|
||||
}
|
33
log
Normal file
33
log
Normal file
@ -0,0 +1,33 @@
|
||||
[INFO] First PS/2 port OK
|
||||
[INFO] Keyboard on PS/2 port 1
|
||||
[INFO] Registered keyboard driver on PS/2 port 1
|
||||
[INFO] Finished initializing PS/2 driver
|
||||
[INFO] Scanning for serial ports
|
||||
[INFO] Found COM1
|
||||
[INFO] Found COM2
|
||||
[INFO] Scanning for parallel ports
|
||||
[INFO] Found LPT1
|
||||
[INFO] Found PCI device. Class code:0x6, Subclass:0x0 Prog IF:0x0
|
||||
[INFO] Found PCI device. Class code:0x6, Subclass:0x1 Prog IF:0x0
|
||||
[INFO] Found PCI device. Class code:0x1, Subclass:0x1 Prog IF:0x80
|
||||
[INFO] Found PCI device. Class code:0x6, Subclass:0x80 Prog IF:0x0
|
||||
[INFO] Found PCI device. Class code:0x3, Subclass:0x0 Prog IF:0x0
|
||||
[INFO] Found PCI device. Class code:0x2, Subclass:0x0 Prog IF:0x0
|
||||
[INFO] Found network controller, detecting type
|
||||
[INFO] Unknown network card
|
||||
>pci list (Shows PCI devices and types)
|
||||
PCI device 0:
|
||||
Main class:Bridge
|
||||
PCI device 1:
|
||||
Main class:Bridge
|
||||
PCI device 2:
|
||||
Main class:Storage
|
||||
PCI device 3:
|
||||
Main class:Bridge
|
||||
PCI device 4:
|
||||
Main class:Display
|
||||
PCI device 5:
|
||||
Main class:Network
|
||||
>cat /hi.txt (Outputs contents of file)
|
||||
Hello!
|
||||
This is hi.txt!
|
14
makeinitrd.rb
Normal file
14
makeinitrd.rb
Normal file
@ -0,0 +1,14 @@
|
||||
folder=ARGV[0]
|
||||
output=ARGV[1]
|
||||
outf=File.open(output,"w")
|
||||
for name in Dir.glob("#{folder}/*")
|
||||
name=File.basename(name)
|
||||
contents=File.read("#{folder}/#{name}")
|
||||
outf.print [name.length].pack("L")
|
||||
outf.print name
|
||||
outf.print "\0"
|
||||
outf.print [contents.length].pack("L")
|
||||
outf.print contents
|
||||
end
|
||||
outf.print [0].pack("L")
|
||||
outf.close
|
65
network.rb
Normal file
65
network.rb
Normal file
@ -0,0 +1,65 @@
|
||||
require "socket"
|
||||
s=TCPServer.new("localhost",3000)
|
||||
c=s.accept
|
||||
udpsocks=[]
|
||||
tcpsocks=[]
|
||||
next_sock=0
|
||||
puts "Connection established"
|
||||
while true
|
||||
ch=c.getc
|
||||
if ch==nil
|
||||
next
|
||||
end
|
||||
cmd=ch.ord
|
||||
if cmd==0
|
||||
c.print [192,168,0,10].pack("CCCC")
|
||||
end
|
||||
if cmd==1
|
||||
sock=UDPSocket.new()
|
||||
sock.bind("10.0.0.180",0)
|
||||
c.print [next_sock,sock.addr[1]].pack("L<L<")
|
||||
udpsocks[next_sock]=sock
|
||||
next_sock+=1;
|
||||
end
|
||||
if cmd==4
|
||||
info=c.read(12).unpack("L<CCCCS<S<")
|
||||
msg=c.read(info[6])
|
||||
udpsocks[info[0]].send(msg,0,"#{info[1]}.#{info[2]}.#{info[3]}.#{info[4]}",info[5])
|
||||
end
|
||||
if cmd==5
|
||||
id=c.read(4).unpack("L<")[0]
|
||||
msg=udpsocks[id].recv(65536)
|
||||
if msg==""
|
||||
c.print [0].pack("L<")
|
||||
else
|
||||
c.print [msg.length].pack("L<")
|
||||
c.print msg
|
||||
end
|
||||
end
|
||||
if cmd==6
|
||||
id=c.read(4).unpack("L<")[0]
|
||||
udpsocks[id]=nil
|
||||
end
|
||||
if cmd==7
|
||||
info=c.read(6).unpack("CCCCS<")
|
||||
sock=TCPSocket.new("#{info[0]}.#{info[1]}.#{info[2]}.#{info[3]}",info[4])
|
||||
c.print [next_sock].pack("L<")
|
||||
tcpsocks[next_sock]=sock
|
||||
next_sock+=1;
|
||||
end
|
||||
if cmd==8
|
||||
info=c.read(6).unpack("L<S<")
|
||||
msg=c.read(info[1])
|
||||
tcpsocks[info[0]].print msg
|
||||
end
|
||||
if cmd==9
|
||||
id=c.read(4).unpack("L<")[0]
|
||||
if !tcpsocks[id].ready? and tcpsocks[id].closed?
|
||||
c.print [0].pack("L<")
|
||||
else
|
||||
msg=tcpsocks[id].gets
|
||||
c.print [msg.length].pack("L<")
|
||||
c.print msg
|
||||
end
|
||||
end
|
||||
end
|
1
psinfo/i386/cc.txt
Normal file
1
psinfo/i386/cc.txt
Normal file
@ -0,0 +1 @@
|
||||
i386-elf-gcc
|
1
psinfo/i386/gdb.txt
Normal file
1
psinfo/i386/gdb.txt
Normal file
@ -0,0 +1 @@
|
||||
i386-elf-gdb
|
2
psinfo/i386/o.txt
Normal file
2
psinfo/i386/o.txt
Normal file
@ -0,0 +1,2 @@
|
||||
cpu/i386/paging_helpers.o
|
||||
kernel/boot.o
|
56
qemu.log
Normal file
56
qemu.log
Normal file
@ -0,0 +1,56 @@
|
||||
CPU Reset (CPU 0)
|
||||
EAX=00000000 EBX=00000000 ECX=00000000 EDX=00000000
|
||||
ESI=00000000 EDI=00000000 EBP=00000000 ESP=00000000
|
||||
EIP=00000000 EFL=00000000 [-------] CPL=0 II=0 A20=0 SMM=0 HLT=0
|
||||
ES =0000 00000000 00000000 00000000
|
||||
CS =0000 00000000 00000000 00000000
|
||||
SS =0000 00000000 00000000 00000000
|
||||
DS =0000 00000000 00000000 00000000
|
||||
FS =0000 00000000 00000000 00000000
|
||||
GS =0000 00000000 00000000 00000000
|
||||
LDT=0000 00000000 00000000 00000000
|
||||
TR =0000 00000000 00000000 00000000
|
||||
GDT= 00000000 00000000
|
||||
IDT= 00000000 00000000
|
||||
CR0=00000000 CR2=00000000 CR3=00000000 CR4=00000000
|
||||
DR0=00000000 DR1=00000000 DR2=00000000 DR3=00000000
|
||||
DR6=00000000 DR7=00000000
|
||||
CCS=00000000 CCD=00000000 CCO=DYNAMIC
|
||||
EFER=0000000000000000
|
||||
FCW=0000 FSW=0000 [ST=0] FTW=ff MXCSR=00000000
|
||||
FPR0=0000000000000000 0000 FPR1=0000000000000000 0000
|
||||
FPR2=0000000000000000 0000 FPR3=0000000000000000 0000
|
||||
FPR4=0000000000000000 0000 FPR5=0000000000000000 0000
|
||||
FPR6=0000000000000000 0000 FPR7=0000000000000000 0000
|
||||
XMM00=00000000000000000000000000000000 XMM01=00000000000000000000000000000000
|
||||
XMM02=00000000000000000000000000000000 XMM03=00000000000000000000000000000000
|
||||
XMM04=00000000000000000000000000000000 XMM05=00000000000000000000000000000000
|
||||
XMM06=00000000000000000000000000000000 XMM07=00000000000000000000000000000000
|
||||
CPU Reset (CPU 0)
|
||||
EAX=00000000 EBX=00000000 ECX=00000000 EDX=00000663
|
||||
ESI=00000000 EDI=00000000 EBP=00000000 ESP=00000000
|
||||
EIP=0000fff0 EFL=00000002 [-------] CPL=0 II=0 A20=1 SMM=0 HLT=0
|
||||
ES =0000 00000000 0000ffff 00009300
|
||||
CS =f000 ffff0000 0000ffff 00009b00
|
||||
SS =0000 00000000 0000ffff 00009300
|
||||
DS =0000 00000000 0000ffff 00009300
|
||||
FS =0000 00000000 0000ffff 00009300
|
||||
GS =0000 00000000 0000ffff 00009300
|
||||
LDT=0000 00000000 0000ffff 00008200
|
||||
TR =0000 00000000 0000ffff 00008b00
|
||||
GDT= 00000000 0000ffff
|
||||
IDT= 00000000 0000ffff
|
||||
CR0=60000010 CR2=00000000 CR3=00000000 CR4=00000000
|
||||
DR0=00000000 DR1=00000000 DR2=00000000 DR3=00000000
|
||||
DR6=ffff0ff0 DR7=00000400
|
||||
CCS=00000000 CCD=00000000 CCO=DYNAMIC
|
||||
EFER=0000000000000000
|
||||
FCW=037f FSW=0000 [ST=0] FTW=00 MXCSR=00001f80
|
||||
FPR0=0000000000000000 0000 FPR1=0000000000000000 0000
|
||||
FPR2=0000000000000000 0000 FPR3=0000000000000000 0000
|
||||
FPR4=0000000000000000 0000 FPR5=0000000000000000 0000
|
||||
FPR6=0000000000000000 0000 FPR7=0000000000000000 0000
|
||||
XMM00=00000000000000000000000000000000 XMM01=00000000000000000000000000000000
|
||||
XMM02=00000000000000000000000000000000 XMM03=00000000000000000000000000000000
|
||||
XMM04=00000000000000000000000000000000 XMM05=00000000000000000000000000000000
|
||||
XMM06=00000000000000000000000000000000 XMM07=00000000000000000000000000000000
|
Loading…
Reference in New Issue
Block a user