Skip to content
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

310551034 lab5 & 6 & 7 #183

Open
wants to merge 2 commits into
base: 310551034
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 15 additions & 1 deletion bootloader/main.c
Original file line number Diff line number Diff line change
@@ -1,9 +1,23 @@
#include "uart.h"

extern char _kernel_start[]; // 0x80000
char* _dtb;

// little endian to unsigned int (4 bytes)
unsigned int LE_to_uint(char *s) {
unsigned int res = 0;
res += (unsigned int)(s[0] & 0xff);
res += (unsigned int)((s[1] & 0xff) << 8);
res += (unsigned int)((s[2] & 0xff) << 16);
res += (unsigned int)((s[3] & 0xff) << 24);
return res;
}

void load_kernel() {
char size_buf[5] = {0};
unsigned int size = 0;
uart_read(&size, 4); // read kernel8.img size
uart_read(size_buf, 4); // read kernel8.img size
size = LE_to_uint(size_buf);
uart_write_string("[+] Get kernel8.img size : 0x");
uart_write_hex(size);
uart_write_string("\r\n");
Expand Down
2 changes: 1 addition & 1 deletion bootloader/makefile
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
CROSS = aarch64-unknown-linux-gnu
CROSS = aarch64-linux-gnu
CC = $(CROSS)-gcc
CFLAGS = -Wall -O2 -ffreestanding -nostdinc -nostdlib -nostartfiles
LD = $(CROSS)-ld
Expand Down
2 changes: 1 addition & 1 deletion config.txt
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
kernel=bootloader.img
arm_64bit=1
initramfs initramfs.cpio 0x2000000
initramfs initramfs.cpio 0x20000000
12 changes: 11 additions & 1 deletion include/cpio.h
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
#ifndef CPIO_H
#define CPIO_H
#include "sched.h"
#include "simple_alloc.h"

// #define INITRD_ADDR (0x8000000) // QEMU: 0x8000000, Rpi3: 0x20000000
// QEMU: 0x8000000, Rpi3: 0x20000000
extern void* INITRD_ADDR;

typedef struct cpio_newc_header {
Expand Down Expand Up @@ -35,4 +36,13 @@ void cpio_ls_callback(char* param, cpio_newc_header* header, char* file_name, un
void cpio_cat_callback(char* param, cpio_newc_header* header, char* file_name, unsigned int name_size, char* file_data, unsigned int data_size);
void cpio_prog_callback(char* param, cpio_newc_header* header, char* file_name, unsigned int name_size, char* file_data, unsigned int data_size);

extern char *syscall_file_start_addr;
extern unsigned int syscall_file_size;
void cpio_get_file_start_callback(char* param, cpio_newc_header* header, char* file_name, unsigned int name_size, char* file_data, unsigned int data_size);
void cpio_get_file_size_callback(char* param, cpio_newc_header* header, char* file_name, unsigned int name_size, char* file_data, unsigned int data_size);
char* get_file_start(char* path);
unsigned int get_file_size(char* path);

void cpio_exec_callback(char* param, cpio_newc_header* header, char* file_name, unsigned int name_size, char* file_data, unsigned int data_size);

#endif
3 changes: 3 additions & 0 deletions include/dtb.h
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
#ifndef DTB_H
#define DTB_H
#include "uart.h"
#include "string.h"

extern char* DTB_ADDRESS;
extern void* INITRD_ADDR;
extern void* INITRD_END;

Expand Down
10 changes: 10 additions & 0 deletions include/esr.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
#ifndef ESR_H
#define ESR_H

typedef struct {
unsigned int iss : 25, // Instruction specific syndrome
il : 1, // Instruction length bit
ec : 6; // Exception class
} esr_el1_t;

#endif
25 changes: 19 additions & 6 deletions include/exception.h
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
#ifndef EXCEPTION_H
#define EXCEPTION_H
#include "timer.h"
#include "tpf.h"
#include "uart.h"
#include "task.h"
#include "timer.h"
#include "sched.h"
#include "syscall.h"

// https://github.com/Tekki/raspberrypi-documentation/blob/master/hardware/raspberrypi/bcm2836/QA7_rev3.4.pdf (p.16)
#define CORE0_INTERRUPT_SOURCE ((volatile unsigned int*)(0x40000060))
Expand All @@ -27,10 +31,19 @@ pending base' register different from the other 'base' interrupt registers
#define DISABLE_BASIC_IRQS ((volatile unsigned int*)(PBASE+0x0000B224))
#define IRQ_PENDING_1_AUX_INT (1<<29)

void sync_64_router(unsigned long long x0);
void irq_router(unsigned long long x0);
void sync_64_router(trapframe_t *tpf);
void irq_router(trapframe_t *tpf);
void invalid_exception_router(unsigned long long x0);
void enable_interrupt();
void disable_interrupt();

#endif
static inline void enable_interrupt() {
asm volatile("msr daifclr, 0xf");
}
static inline void disable_interrupt() {
asm volatile("msr daifset, 0xf");
}

unsigned long long is_disable_interrupt();
void lock();
void unlock();

#endif
3 changes: 3 additions & 0 deletions include/malloc.h
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ void sc_init();
void *sc_alloc(int size);
int sc_free(void *sc);

void *kmalloc(int size);
void kfree(void *ptr);

void sc_test();

#endif
63 changes: 63 additions & 0 deletions include/mmu.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
#ifndef MMU_H
#define MMU_H
#include "esr.h"
#include "uart.h"
#include "list.h"
#include "sched.h"
#include "string.h"
#include "malloc.h"
#include "exception.h"

#define TCR_CONFIG_REGION_48bit (((64 - 48) << 0) | ((64 - 48) << 16))
#define TCR_CONFIG_4KB ((0b00 << 14) | (0b10 << 30))
#define TCR_CONFIG_DEFAULT (TCR_CONFIG_REGION_48bit | TCR_CONFIG_4KB)

#define MAIR_DEVICE_nGnRnE 0b00000000
#define MAIR_NORMAL_NOCACHE 0b01000100
#define MAIR_IDX_DEVICE_nGnRnE 0
#define MAIR_IDX_NORMAL_NOCACHE 1
#define MAIR_CONFIG_DEFAULT ((MAIR_DEVICE_nGnRnE << (MAIR_IDX_DEVICE_nGnRnE * 8)) | (MAIR_NORMAL_NOCACHE << (MAIR_IDX_NORMAL_NOCACHE * 8)))

#define PD_TABLE 0b11L
#define PD_BLOCK 0b01L
#define PD_UNX (1L << 54)
#define PD_KNX (1L << 53)
#define PD_ACCESS (1L << 10)
#define PD_UK_ACCESS (1L << 6)
#define PD_RDONLY (1L << 7)
#define BOOT_PGD_ATTR PD_TABLE
#define BOOT_PUD_ATTR (PD_ACCESS | (MAIR_IDX_DEVICE_nGnRnE << 2) | PD_BLOCK)

#define PHYS_TO_VIRT(x) (x + 0xffff000000000000)
#define VIRT_TO_PHYS(x) (x - 0xffff000000000000)
#define ENTRY_ADDR_MASK 0xfffffffff000L

#define kernel_pgd_addr 0x1000
#define kernel_pud_addr 0x2000

#define DATA_ABORT_LOWER 0b100100
#define INS_ABORT_LOWER 0b100000

#define TF_LEVEL0 0b000100
#define TF_LEVEL1 0b000101
#define TF_LEVEL2 0b000110
#define TF_LEVEL3 0b000111

void *set_2M_kernel_mmu(void *x0);
void map_one_page(unsigned long *pgd_p, unsigned long va, unsigned long pa, unsigned long flag);
void add_vma(struct thread *t, unsigned long va, unsigned long size, unsigned long pa, unsigned long rwx, int is_alloced);
void free_page_tables(unsigned long *page_table, int level);
void handle_abort(esr_el1_t* esr_el1);
void map_one_page_rwx(unsigned long *pgd_p, unsigned long va, unsigned long pa, unsigned long rwxflag);
void seg_fault();

typedef struct vm_area_struct {
list_head_t listhead;
unsigned long virt_addr;
unsigned long phys_addr;
unsigned long area_size;
unsigned long rwx; // r = 1, w = 2, x = 4
int is_alloced;
} vm_area_struct_t;

#endif
9 changes: 9 additions & 0 deletions include/node.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
#ifndef NODE_H
#define NODE_H

enum node_type {
dir_t,
file_t
};

#endif
17 changes: 3 additions & 14 deletions include/reset.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,19 +5,8 @@
#define PM_RSTC 0x3f10001c
#define PM_WDOG 0x3f100024

void set(long addr, unsigned int value) {
volatile unsigned int* point = (unsigned int*)addr;
*point = value;
}

void reset(int tick) { // reboot after watchdog timer expire
set(PM_RSTC, PM_PASSWORD | 0x20); // full reset
set(PM_WDOG, PM_PASSWORD | tick); // number of watchdog tick
}

void cancel_reset() {
set(PM_RSTC, PM_PASSWORD | 0); // full reset
set(PM_WDOG, PM_PASSWORD | 0); // number of watchdog tick
}
void set(long addr, unsigned int value);
void reset(int tick);
void cancel_reset();

#endif
60 changes: 60 additions & 0 deletions include/sched.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
#ifndef SCHED_H
#define SCHED_H
#include "vfs.h"
#include "list.h"
#include "buddy.h"
#include "signal.h"
#include "malloc.h"
#include "syscall.h"
#include "exception.h"
#include "simple_alloc.h"

#define PIDMAX 4096
#define USTACK_SIZE 0x10000
#define KSTACK_SIZE 0x10000
#define SIGNAL_MAX 16

extern void switch_to(void *curr_context, void *next_context);
extern void store_context(void *curr_context);
extern void load_context(void *curr_context);
extern void *get_current();

typedef struct thread_context {
unsigned long x19, x20, x21, x22, x23, x24, x25, x26, x27, x28;
unsigned long fp, lr, sp;
} thread_context_t;

typedef struct thread {
list_head_t listhead;
thread_context_t context;
char *data;
unsigned int datasize;
int iszombie;
int pid;
int isused;
char* stack_alloced_ptr;
char* kernel_stack_alloced_ptr;
void (*singal_handler[SIGNAL_MAX+1])();
int sigcount[SIGNAL_MAX + 1];
void (*curr_signal_handler)();
int signal_is_checking;
thread_context_t signal_saved_context;
char curr_working_dir[256];
struct file* file_descriptors_table[16];
} thread_t;

extern thread_t *curr_thread;
extern list_head_t *run_queue;
extern list_head_t *wait_queue;
extern thread_t threads[PIDMAX + 1];

void init_thread_sched();
void idle();
void schedule();
void kill_zombies();
thread_t *thread_create(void *start);
void thread_exit();
int exec_thread(char *data, unsigned int filesize);
void schedule_timer(char *notuse);

#endif
22 changes: 3 additions & 19 deletions include/shell.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#include "mbox.h"
#include "reset.h"
#include "string.h"
#include "sched.h"
#include "timer.h"
#include "buddy.h"
#include "malloc.h"
Expand Down Expand Up @@ -34,28 +35,11 @@ void cmd_async();
void cmd_prog();
void cmd_sec2();
void cmd_setTimeout(char* param);
void cmd_foo();
void cmd_preempt();
void cmd_pageTest();
void cmd_chunkTest();
void cmd_exec(char* param);
void cmd_unknown();

struct cmd cmd_list[] = {
{"help", cmd_help, "print this help menu"},
{"hello", cmd_hello, "print Hello World!"},
// {"reboot", cmd_reboot, "reboot the device"},
{"revision", cmd_revision, "print board revision"},
{"memory", cmd_memory, "print ARM memory base address and size"},
{"ls", cmd_ls, "list directory contents"},
{"cat", cmd_cat, "print file content"},
{"dtb", cmd_dtb, "show device tree"},
{"initramfs", cmd_initramfs, "show initramfs address"},
// {"async", cmd_async, "test async print"},
{"prog", cmd_prog, "load a user program in the initramfs, and jump to it"},
{"sec2", cmd_sec2, "print the seconds after booting and set the next timeout to 2 seconds later."},
{"setTimeout",cmd_setTimeout,"prints message after seconds"},
// {"preempt", cmd_preempt, "test preemption"},
{"pageTest", cmd_pageTest, "test page frame allocator"},
{"chunkTest", cmd_chunkTest, "test small chunk allocator"},
};

#endif
14 changes: 14 additions & 0 deletions include/signal.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
#ifndef SIGNAL_H
#define SIGNAL_H
#include "tpf.h"
#include "sched.h"
#include "buddy.h"
#include "syscall.h"
#include "exception.h"

void check_signal(trapframe_t *tpf);
void run_signal(trapframe_t* tpf, int signal);
void signal_handler_wrapper();
void signal_default_handler();

#endif
1 change: 1 addition & 0 deletions include/simple_alloc.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#ifndef SIMPLE_ALLOC_H
#define SIMPLE_ALLOC_H
#include "uart.h"

// from linker.ld
extern char _simple_alloc_start;
Expand Down
Loading