From 4d0c664b88cd38aa7631a73a8782aa617f4f5761 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Tue, 13 Jun 2017 02:24:24 +0900 Subject: [PATCH 01/29] Add asm/processor.h --- src/arch/x86_64/c/include/asm/processor.h | 108 ++++++++++++++++++++++ 1 file changed, 108 insertions(+) create mode 100644 src/arch/x86_64/c/include/asm/processor.h diff --git a/src/arch/x86_64/c/include/asm/processor.h b/src/arch/x86_64/c/include/asm/processor.h new file mode 100644 index 0000000..84b59ee --- /dev/null +++ b/src/arch/x86_64/c/include/asm/processor.h @@ -0,0 +1,108 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/arch/x86/include/asm/processor.h + +#ifndef ASM_PROCESSOR_H +#define ASM_PROCESSOR_H + +#include + +// rdtsc (Read-time stamp counter) +// return the 64-bit time stamp value +inline static uint64_t +rdtsc(void) +{ + uint64_t lo, hi; + asm volatile("rdtsc" : "=a"(lo), "=d"(hi)); + return (hi << 32 | lo); +} + +// wbinvd asm instruction(Write back and invalidate cache) +inline static void +flush_cache(void) +{ + asm volatile("wbinvd" ::: "memory"); +} + +// invd asm instruction (Invalidate internal caches - without writing back) +inline static void +invalid_cache(void) +{ + asm volatile("invd"); +} + +// NOTE: mb, rmb, wmb will be moved to arch/x86_64/c/processor.c +// and used via extern func_memory_barrier (mb|rmb|wmb) + +// mb (Memory barrier) +// mfence asm instruction (Memory Fence - Serializes load and store operations) +inline static void +mb(void) +{ + asm volatile("mfence" ::: "memory"); +} + +// rmb (Read memory barrier) +// lfence asm instruction (Load Fence - Serializes load operations) +inline static void +rmb(void) +{ + asm volatile("lfence" ::: "memory"); +} + +// wmb (Write memory barrier) +// sfence asm instruction (Store Fence - Serializes store operations) +inline static void +wmb(void) +{ + asm volatile("sfence" ::: "memory"); +} + +// search the most significant bit +// bsr (Bit Scan Reverse) asm instruction +static inline size_t +msb(size_t i) +{ + size_t ret; + + if (!i) { + return (sizeof(size_t) * 8); + } + asm volatile("bsr %1, %0" : "=r"(ret) : "r"(i) : "cc"); + + return ret; +} + +// search the least significant bit +// bsf (Bit Scan Forward) asm instruction +static inline size_t +lsb(size_t i) +{ + size_t ret; + + if (!i) { + return (sizeof(size_t) * 8); + } + asm volatile("bsf %1, %0" : "=r"(ret) : "r"(i) : "cc"); + + return ret; +} + +// A one-instruction-do-nothing +#define NOP1 asm volatile("nop") +// A two-instruction-do-nothing +#define NOP2 asm volatile("nop;nop") +// A four-instruction-do-nothing +#define NOP4 asm volatile("nop;nop;nop;nop") +// A eight-instruction-do-nothing +#define NOP8 asm volatile("nop;nop;nop;nop;nop;nop;nop;nop") + +#endif /* end of include guard: ASM_PROCESSOR_H */ From a984c2dae1763891b16894ccc3a55975033eda10 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Thu, 15 Jun 2017 14:09:18 +0900 Subject: [PATCH 02/29] asm/stddef.h: Fix include guard to avoid conflict --- src/arch/x86_64/c/include/asm/stddef.h | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/arch/x86_64/c/include/asm/stddef.h b/src/arch/x86_64/c/include/asm/stddef.h index e40209e..c7d0918 100644 --- a/src/arch/x86_64/c/include/asm/stddef.h +++ b/src/arch/x86_64/c/include/asm/stddef.h @@ -10,8 +10,8 @@ // The part of this file was taken from: // https://github.com/RWTH-OS/eduOS/blob/master/arch/x86/include/asm/stddef.h -#ifndef STDDEF_H -#define STDDEF_H +#ifndef ASM_STDDEF_H +#define ASM_STDDEF_H // Unsigned 64 bit integer typedef unsigned long long uint64_t; @@ -34,7 +34,8 @@ typedef char int8_t; typedef unsigned long long size_t; // This defines what the stack looks like after the task context is saved. -struct state { +struct state +{ // R15 register uint64_t r15; // R14 register @@ -80,4 +81,4 @@ struct state { uint64_t ss; }; -#endif /* end of include guard: STDDEF_H */ +#endif /* end of include guard: ASM_STDDEF_H */ From bc7f7c24ec023717a7e97d7ec58c0b05f11100be Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Thu, 15 Jun 2017 14:14:46 +0900 Subject: [PATCH 03/29] Add c_kernel/include/stddef.h some macros must be moved to config.h later --- src/c_kernel/include/stddef.h | 33 +++++++++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 src/c_kernel/include/stddef.h diff --git a/src/c_kernel/include/stddef.h b/src/c_kernel/include/stddef.h new file mode 100644 index 0000000..0855e0c --- /dev/null +++ b/src/c_kernel/include/stddef.h @@ -0,0 +1,33 @@ +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/include/eduos/tasks.h + +#ifndef STDDEF_H +#define STDDEF_H + +// #include +#include + +#define VIDEO_MEM_ADDR 0xb8000 +#define CACHE_LINE 64 + +#define NORETURN __attribute__((noreturn)) +#define STDCALL __attribute__((stdcall)) + +#define NULL ((void*) 0) + +// represents a task identifier +typedef unsigned int tid_t; + +struct task; + +// pointer to the current (running) task +// NOTE: defined in tasks.c +extern struct task* current_task; + +#endif /* end of include guard: STDDEF_H */ \ No newline at end of file From e69f6f75700552ca4985daa4a612b16a54c3740b Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Thu, 15 Jun 2017 14:19:32 +0900 Subject: [PATCH 04/29] Add c_kernel/include/tasks_types.h it has PCB and queue --- src/c_kernel/include/tasks_types.h | 75 ++++++++++++++++++++++++++++++ 1 file changed, 75 insertions(+) create mode 100644 src/c_kernel/include/tasks_types.h diff --git a/src/c_kernel/include/tasks_types.h b/src/c_kernel/include/tasks_types.h new file mode 100644 index 0000000..f4c79fd --- /dev/null +++ b/src/c_kernel/include/tasks_types.h @@ -0,0 +1,75 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/include/eduos/tasks_types.h + +#ifndef TASKS_TYPES_H +#define TASKS_TYPES_H + +#include +// #include + +#define TASK_INVALID 0 +#define TASK_READY 1 +#define TASK_RUNNING 2 +#define TASK_BLOCKED 3 +#define TASK_FINISHED 4 +#define TASK_IDLE 5 + +#define MAX_PRIO 31 +#define REALTIME_PRIO 31 +#define HIGH_PRIO 16 +#define NORMAL_PRIO 8 +#define LOW_PRIO 1 +#define IDLE_PRIO 0 + +typedef int (*entry_point_t)(void*); + +// Represents the Process Control Block +typedef struct task +{ + // task id = position in the task table + tid_t id __attribute__((aligned(CACHE_LINE))); + // task status + uint32_t status; + // copy of the stack pointer before a context switch + size_t* last_stack_pointer; + // starting address of the stack + void* stack; + // task priority + uint8_t prio; + // next task in the queue + struct task* next; + // previous task in the queue + struct task* prev; +} task_t; + +typedef struct +{ + task_t* first; + task_t* last; +} task_list_t; + +// Represents a queue for all runnable tasks +typedef struct +{ + // idle task + task_t* idle __attribute__((aligned(CACHE_LINE))); + // previous task + task_t* old_task; + // total number of tasks in the queue + uint32_t nr_tasks; + // indicates the used priority queues + uint32_t prio_bitmap; + // a queue for each priority + task_list_t queue[MAX_PRIO - 1]; +} readyqueues_t; + +#endif /* end of include guard: TASKS_TYPES_H */ \ No newline at end of file From 58735032652846677831e14822c0ef4a0a7f2d80 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Thu, 15 Jun 2017 14:23:25 +0900 Subject: [PATCH 05/29] Add c_kernel/include/tasks.h --- src/c_kernel/include/tasks.h | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100644 src/c_kernel/include/tasks.h diff --git a/src/c_kernel/include/tasks.h b/src/c_kernel/include/tasks.h new file mode 100644 index 0000000..1635f4f --- /dev/null +++ b/src/c_kernel/include/tasks.h @@ -0,0 +1,28 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/include/eduos/tasks.h + +#ifndef TASKS_H +#define TASKS_H + +#include +#include +// #include + +int multitasking_init(void); + +int create_kernel_task(tid_t* id, entry_point_t ep, void* args, uint8_t prio); + +void reschedule(void); + +void NORETURN leave_kernel_task(void); + +#endif /* end of include guard: TASKS_H */ \ No newline at end of file From 69e28479da46ea0293421a85af149b86c5bd5f8b Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Thu, 15 Jun 2017 15:04:20 +0900 Subject: [PATCH 06/29] c_kernel/include: Move macros from stddef.h to config.h --- src/c_kernel/include/config.h | 23 +++++++++++++++++++++++ src/c_kernel/include/stddef.h | 8 +------- 2 files changed, 24 insertions(+), 7 deletions(-) create mode 100644 src/c_kernel/include/config.h diff --git a/src/c_kernel/include/config.h b/src/c_kernel/include/config.h new file mode 100644 index 0000000..4d9cd00 --- /dev/null +++ b/src/c_kernel/include/config.h @@ -0,0 +1,23 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/include/eduos/config.h.example + +#ifndef CONFIG_H +#define CONFIG_H + +#define MAX_TASKS 16 +#define VIDEO_MEM_ADDR 0xb8000 +#define CACHE_LINE 64 + +#define NORETURN __attribute__((noreturn)) +#define STDCALL __attribute__((stdcall)) + +#endif /* end of include guard: CONFIG_H */ \ No newline at end of file diff --git a/src/c_kernel/include/stddef.h b/src/c_kernel/include/stddef.h index 0855e0c..d3a3e5c 100644 --- a/src/c_kernel/include/stddef.h +++ b/src/c_kernel/include/stddef.h @@ -10,15 +10,9 @@ #ifndef STDDEF_H #define STDDEF_H -// #include +#include #include -#define VIDEO_MEM_ADDR 0xb8000 -#define CACHE_LINE 64 - -#define NORETURN __attribute__((noreturn)) -#define STDCALL __attribute__((stdcall)) - #define NULL ((void*) 0) // represents a task identifier From cbf2bd4baac7478ce32a1d4c7e3b7bd396fa043b Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 01:50:38 +0900 Subject: [PATCH 07/29] c_kernel/include/config.h: Implement BUILTIN_EXPECT(exp, b) macro --- src/c_kernel/include/config.h | 1 + 1 file changed, 1 insertion(+) diff --git a/src/c_kernel/include/config.h b/src/c_kernel/include/config.h index 4d9cd00..dfc1fb9 100644 --- a/src/c_kernel/include/config.h +++ b/src/c_kernel/include/config.h @@ -17,6 +17,7 @@ #define VIDEO_MEM_ADDR 0xb8000 #define CACHE_LINE 64 +#define BUILTIN_EXPECT(exp, b) __builtin_expect((exp), (b)) #define NORETURN __attribute__((noreturn)) #define STDCALL __attribute__((stdcall)) From 3a5a4eaaf1ea94b4c8bf659f58bcc15b933fb393 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 01:51:09 +0900 Subject: [PATCH 08/29] Makefile: Add -O2 option to CFLAGS --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index 0f124f2..8469193 100644 --- a/Makefile +++ b/Makefile @@ -16,7 +16,7 @@ kernel := build/kernel-$(arch).bin iso := build/utero-$(arch).iso top_dir := $(shell pwd) INCLUDE := -I$(top_dir)/src/c_kernel/include -I$(top_dir)/src/arch/x86_64/c/include -CFLAGS := -ffreestanding -nostdinc -Wno-implicit +CFLAGS := -O2 -ffreestanding -nostdinc -Wno-implicit libcr := src/musl/lib/libcr.a libu := build/arch/$(arch)/c/libu.a From 166af59c35bf6cb732661fc699bb0ee65c9d59fb Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 01:52:53 +0900 Subject: [PATCH 09/29] c_kernel/include/tasks_types.h: Include asm/tasks_types.h --- src/arch/x86_64/c/include/asm/tasks_types.h | 16 ++++++++++++++++ src/c_kernel/include/tasks_types.h | 2 +- 2 files changed, 17 insertions(+), 1 deletion(-) create mode 100644 src/arch/x86_64/c/include/asm/tasks_types.h diff --git a/src/arch/x86_64/c/include/asm/tasks_types.h b/src/arch/x86_64/c/include/asm/tasks_types.h new file mode 100644 index 0000000..e754cbc --- /dev/null +++ b/src/arch/x86_64/c/include/asm/tasks_types.h @@ -0,0 +1,16 @@ +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/arch/x86/include/asm/tasks_types.h + +#ifndef ASM_TASKS_TYPES_H +#define ASM_TASKS_TYPES_H + +#include +#include + +#endif /* end of include guard: ASM_TASKS_TYPES_H */ \ No newline at end of file diff --git a/src/c_kernel/include/tasks_types.h b/src/c_kernel/include/tasks_types.h index f4c79fd..fa27fef 100644 --- a/src/c_kernel/include/tasks_types.h +++ b/src/c_kernel/include/tasks_types.h @@ -14,7 +14,7 @@ #define TASKS_TYPES_H #include -// #include +#include #define TASK_INVALID 0 #define TASK_READY 1 From a157ff5a3bbfcbcc2c3c366eca01f1a5b72044a1 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 01:55:27 +0900 Subject: [PATCH 10/29] add c_kernel/include/errno.h based on musl/arch/mips64/bits/errno.h, depends on architecture --- src/c_kernel/include/errno.h | 151 +++++++++++++++++++++++++++++++++++ 1 file changed, 151 insertions(+) create mode 100644 src/c_kernel/include/errno.h diff --git a/src/c_kernel/include/errno.h b/src/c_kernel/include/errno.h new file mode 100644 index 0000000..1c838f7 --- /dev/null +++ b/src/c_kernel/include/errno.h @@ -0,0 +1,151 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// This is taken from: +// src/musl/arch/mips64/bits/errno.h + +#ifndef ERRNO_H +#define ERRNO_H + +#define EPERM 1 +#define ENOENT 2 +#define ESRCH 3 +#define EINTR 4 +#define EIO 5 +#define ENXIO 6 +#define E2BIG 7 +#define ENOEXEC 8 +#define EBADF 9 +#define ECHILD 10 +#define EAGAIN 11 +#define ENOMEM 12 +#define EACCES 13 +#define EFAULT 14 +#define ENOTBLK 15 +#define EBUSY 16 +#define EEXIST 17 +#define EXDEV 18 +#define ENODEV 19 +#define ENOTDIR 20 +#define EISDIR 21 +#define EINVAL 22 +#define ENFILE 23 +#define EMFILE 24 +#define ENOTTY 25 +#define ETXTBSY 26 +#define EFBIG 27 +#define ENOSPC 28 +#define ESPIPE 29 +#define EROFS 30 +#define EMLINK 31 +#define EPIPE 32 +#define EDOM 33 +#define ERANGE 34 +#define ENOMSG 35 +#define EIDRM 36 +#define ECHRNG 37 +#define EL2NSYNC 38 +#define EL3HLT 39 +#define EL3RST 40 +#define ELNRNG 41 +#define EUNATCH 42 +#define ENOCSI 43 +#define EL2HLT 44 +#define EDEADLK 45 +#define ENOLCK 46 +#define EBADE 50 +#define EBADR 51 +#define EXFULL 52 +#define ENOANO 53 +#define EBADRQC 54 +#define EBADSLT 55 +#define EDEADLOCK 56 +#define EBFONT 59 +#define ENOSTR 60 +#define ENODATA 61 +#define ETIME 62 +#define ENOSR 63 +#define ENONET 64 +#define ENOPKG 65 +#define EREMOTE 66 +#define ENOLINK 67 +#define EADV 68 +#define ESRMNT 69 +#define ECOMM 70 +#define EPROTO 71 +#define EDOTDOT 73 +#define EMULTIHOP 74 +#define EBADMSG 77 +#define ENAMETOOLONG 78 +#define EOVERFLOW 79 +#define ENOTUNIQ 80 +#define EBADFD 81 +#define EREMCHG 82 +#define ELIBACC 83 +#define ELIBBAD 84 +#define ELIBSCN 85 +#define ELIBMAX 86 +#define ELIBEXEC 87 +#define EILSEQ 88 +#define ENOSYS 89 +#define ELOOP 90 +#define ERESTART 91 +#define ESTRPIPE 92 +#define ENOTEMPTY 93 +#define EUSERS 94 +#define ENOTSOCK 95 +#define EDESTADDRREQ 96 +#define EMSGSIZE 97 +#define EPROTOTYPE 98 +#define ENOPROTOOPT 99 +#define EPROTONOSUPPORT 120 +#define ESOCKTNOSUPPORT 121 +#define EOPNOTSUPP 122 +#define ENOTSUP EOPNOTSUPP +#define EPFNOSUPPORT 123 +#define EAFNOSUPPORT 124 +#define EADDRINUSE 125 +#define EADDRNOTAVAIL 126 +#define ENETDOWN 127 +#define ENETUNREACH 128 +#define ENETRESET 129 +#define ECONNABORTED 130 +#define ECONNRESET 131 +#define ENOBUFS 132 +#define EISCONN 133 +#define ENOTCONN 134 +#define EUCLEAN 135 +#define ENOTNAM 137 +#define ENAVAIL 138 +#define EISNAM 139 +#define EREMOTEIO 140 +#define ESHUTDOWN 143 +#define ETOOMANYREFS 144 +#define ETIMEDOUT 145 +#define ECONNREFUSED 146 +#define EHOSTDOWN 147 +#define EHOSTUNREACH 148 +#define EWOULDBLOCK EAGAIN +#define EALREADY 149 +#define EINPROGRESS 150 +#define ESTALE 151 +#define ECANCELED 158 +#define ENOMEDIUM 159 +#define EMEDIUMTYPE 160 +#define ENOKEY 161 +#define EKEYEXPIRED 162 +#define EKEYREVOKED 163 +#define EKEYREJECTED 164 +#define EOWNERDEAD 165 +#define ENOTRECOVERABLE 166 +#define ERFKILL 167 +#define EHWPOISON 168 +#define EDQUOT 1133 + +#endif /* end of include guard: ERRNO_H */ From 567cda177fe66381cd5474061cae418ac8a4f587 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 01:56:26 +0900 Subject: [PATCH 11/29] Add c_kernel/include/stdlib.h --- src/c_kernel/include/stdlib.h | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 src/c_kernel/include/stdlib.h diff --git a/src/c_kernel/include/stdlib.h b/src/c_kernel/include/stdlib.h new file mode 100644 index 0000000..705fbc9 --- /dev/null +++ b/src/c_kernel/include/stdlib.h @@ -0,0 +1,21 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/include/eduos/stdlib.h + +#ifndef STDLIB_H +#define STDLIB_H + +#include +#include + +void* create_stack(tid_t id); + +#endif /* end of include guard: STDLIB_H */ \ No newline at end of file From 3c80c08d8e6cc5e0791d4498c6f47861a32e41ee Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 19:43:51 +0900 Subject: [PATCH 12/29] x86_64/c/isrs.c: Format the code --- src/arch/x86_64/c/isrs.c | 188 ++++++++++++++++++++++++++------------- 1 file changed, 124 insertions(+), 64 deletions(-) diff --git a/src/arch/x86_64/c/isrs.c b/src/arch/x86_64/c/isrs.c index 8a3fe56..594b1dc 100644 --- a/src/arch/x86_64/c/isrs.c +++ b/src/arch/x86_64/c/isrs.c @@ -11,8 +11,8 @@ // https://github.com/RWTH-OS/eduOS/blob/master/arch/x86/kernel/isrs.c #include -#include #include +#include #include /* @@ -52,10 +52,10 @@ extern void isr28(void); extern void isr29(void); extern void isr30(void); extern void isr31(void); -extern int eputs(const char *); -extern int eprint(const char *); +extern int eputs(const char*); +extern int eprint(const char*); -void fault_handler(struct state *s); +void fault_handler(struct state* s); // static void fault_handler(struct state *s); // fqu_handler @@ -70,74 +70,107 @@ void fault_handler(struct state *s); * set to the required '14', which is represented by 'E' in * hex. */ -void isrs_install(void) +void +isrs_install(void) { int i; idt_set_gate(0, (size_t)isr0, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(1, (size_t)isr1, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(2, (size_t)isr2, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(3, (size_t)isr3, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(4, (size_t)isr4, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(5, (size_t)isr5, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(6, (size_t)isr6, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(7, (size_t)isr7, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(8, (size_t)isr8, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(9, (size_t)isr9, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(10, (size_t)isr10, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(11, (size_t)isr11, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(12, (size_t)isr12, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(13, (size_t)isr13, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(14, (size_t)isr14, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(15, (size_t)isr15, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(16, (size_t)isr16, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(17, (size_t)isr17, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(18, (size_t)isr18, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(19, (size_t)isr19, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(20, (size_t)isr20, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(21, (size_t)isr21, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(22, (size_t)isr22, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(23, (size_t)isr23, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(24, (size_t)isr24, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(25, (size_t)isr25, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(26, (size_t)isr26, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(27, (size_t)isr27, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(28, (size_t)isr28, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(29, (size_t)isr29, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(30, (size_t)isr30, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); idt_set_gate(31, (size_t)isr31, KERNEL_CODE_SELECTOR, - IDT_FLAG_PRESENT|IDT_FLAG_RING0|IDT_FLAG_32BIT|IDT_FLAG_INTTRAP); + IDT_FLAG_PRESENT | IDT_FLAG_RING0 | IDT_FLAG_32BIT | + IDT_FLAG_INTTRAP); // install the default handler @@ -151,39 +184,66 @@ void isrs_install(void) * message by accessing it like this: * exception_message[interrupt_number] */ -static const char *exception_messages[] = { - "Division By Zero", "Debug", "Non Maskable Interrupt", - "Breakpoint", "Into Detected Overflow", "Out of Bounds", "Invalid Opcode", - "No Coprocessor", "Double Fault", "Coprocessor Segment Overrun", "Bad TSS", - "Segment Not Present", "Stack Fault", "General Protection Fault", "Page Fault", - "Unknown Interrupt", "Coprocessor Fault", "Alignment Check", "Machine Check", - "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", - "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", - "Reserved", "Reserved" }; +static const char* exception_messages[] = { "Division By Zero", + "Debug", + "Non Maskable Interrupt", + "Breakpoint", + "Into Detected Overflow", + "Out of Bounds", + "Invalid Opcode", + "No Coprocessor", + "Double Fault", + "Coprocessor Segment Overrun", + "Bad TSS", + "Segment Not Present", + "Stack Fault", + "General Protection Fault", + "Page Fault", + "Unknown Interrupt", + "Coprocessor Fault", + "Alignment Check", + "Machine Check", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved", + "Reserved" }; - /* - * All of our Exception handling Interrupt Service Routines will - * point to this function. This will tell us what exception has - * occured! Right now, we simply abort the current task. - * All ISRs disable interrupts while they are being - * serviced as a 'locking' mechanism to prevent an IRQ from - * happening and messing up kernel data structures - */ +/* + * All of our Exception handling Interrupt Service Routines will + * point to this function. This will tell us what exception has + * occured! Right now, we simply abort the current task. + * All ISRs disable interrupts while they are being + * serviced as a 'locking' mechanism to prevent an IRQ from + * happening and messing up kernel data structures + */ #define N 256 -void fault_handler(struct state *s) +void +fault_handler(struct state* s) // static void fault_handler(struct state *s) { - char message[N] = {'\0'}; + char message[N] = { '\0' }; if (s->int_no < 32) { - sprintf(message, " Exception (%llu) at 0x%llx:0x%llx, error code 0x%llx, rflags 0x%llx\n", - s->int_no, s->cs, s->rip, s->error, s->rflags); - eputs(exception_messages[s->int_no]); - eprint(message); + sprintf( + message, + " Exception (%llu) at 0x%llx:0x%llx, error code 0x%llx, rflags 0x%llx\n", + s->int_no, s->cs, s->rip, s->error, s->rflags); + eputs(exception_messages[s->int_no]); + eprint(message); - outb(0x20, 0x20); + outb(0x20, 0x20); - // irq_enable(); - // abort(); - for (;;); + // irq_enable(); + // abort(); + for (;;) + ; } } From f96faebe47c9ed1f3c5898a84effb1f598228890 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 20:25:35 +0900 Subject: [PATCH 13/29] Add c_kernel/memory.c note that memory.c should move to mm directory later --- src/c_kernel/include/config.h | 2 ++ src/c_kernel/include/stdlib.h | 1 + src/c_kernel/memory.c | 31 +++++++++++++++++++++++++++++++ 3 files changed, 34 insertions(+) create mode 100644 src/c_kernel/memory.c diff --git a/src/c_kernel/include/config.h b/src/c_kernel/include/config.h index dfc1fb9..509d8ff 100644 --- a/src/c_kernel/include/config.h +++ b/src/c_kernel/include/config.h @@ -16,6 +16,8 @@ #define MAX_TASKS 16 #define VIDEO_MEM_ADDR 0xb8000 #define CACHE_LINE 64 +#define KERNEL_STACK_SIZE (8 << 10) /* 8 KiB */ +#define DEFAULT_STACK_SIZE (16 * 1024) /* 16 KiB */ #define BUILTIN_EXPECT(exp, b) __builtin_expect((exp), (b)) #define NORETURN __attribute__((noreturn)) diff --git a/src/c_kernel/include/stdlib.h b/src/c_kernel/include/stdlib.h index 705fbc9..85faf37 100644 --- a/src/c_kernel/include/stdlib.h +++ b/src/c_kernel/include/stdlib.h @@ -16,6 +16,7 @@ #include #include +// Implemented in memory.c void* create_stack(tid_t id); #endif /* end of include guard: STDLIB_H */ \ No newline at end of file diff --git a/src/c_kernel/memory.c b/src/c_kernel/memory.c new file mode 100644 index 0000000..ea2a4bf --- /dev/null +++ b/src/c_kernel/memory.c @@ -0,0 +1,31 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/mm/memory.c + +#include +#include + +static char stack[MAX_TASKS - 1][KERNEL_STACK_SIZE]; + +void* +create_stack(tid_t id) +{ + // Idle task uses stack + if (BUILTIN_EXPECT(!id, 0)) { + return NULL; + } + // Do we have a valid task id? + if (BUILTIN_EXPECT(id >= MAX_TASKS, 0)) { + return NULL; + } + + return (void*)stack[id - 1]; +} From 27a1784f80e59c53263f67188ec657aee93e43ad Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 20:50:43 +0900 Subject: [PATCH 14/29] Fix source url --- src/c_kernel/include/stddef.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/c_kernel/include/stddef.h b/src/c_kernel/include/stddef.h index d3a3e5c..eeec58a 100644 --- a/src/c_kernel/include/stddef.h +++ b/src/c_kernel/include/stddef.h @@ -5,7 +5,7 @@ // except according to those terms. // // The part of this file was taken from: -// https://github.com/RWTH-OS/eduOS/blob/master/include/eduos/tasks.h +// https://github.com/RWTH-OS/eduOS/blob/master/include/eduos/stddef.h #ifndef STDDEF_H #define STDDEF_H From d70c15bc4871cf38bf1744a36ed442ead8dc11bd Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 21:48:21 +0900 Subject: [PATCH 15/29] c_kernel/include/stdlib.h: Fix including from asm/stddef.h to stddef.h because tid_t is defined in stddef.h --- src/c_kernel/include/stdlib.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/c_kernel/include/stdlib.h b/src/c_kernel/include/stdlib.h index 85faf37..bec7406 100644 --- a/src/c_kernel/include/stdlib.h +++ b/src/c_kernel/include/stdlib.h @@ -13,7 +13,7 @@ #ifndef STDLIB_H #define STDLIB_H -#include +#include #include // Implemented in memory.c From 12847a7c782b014ce1bdd2a90e744d47d96581e3 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Wed, 21 Jun 2017 21:55:42 +0900 Subject: [PATCH 16/29] Enable to use create_default_frame --- src/arch/x86_64/c/include/asm/tasks.h | 31 +++++++++++ src/arch/x86_64/c/tasks.c | 75 +++++++++++++++++++++++++++ src/c_kernel/include/processor.h | 21 ++++++++ src/c_kernel/include/tasks.h | 2 +- 4 files changed, 128 insertions(+), 1 deletion(-) create mode 100644 src/arch/x86_64/c/include/asm/tasks.h create mode 100644 src/arch/x86_64/c/tasks.c create mode 100644 src/c_kernel/include/processor.h diff --git a/src/arch/x86_64/c/include/asm/tasks.h b/src/arch/x86_64/c/include/asm/tasks.h new file mode 100644 index 0000000..d373c3e --- /dev/null +++ b/src/arch/x86_64/c/include/asm/tasks.h @@ -0,0 +1,31 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/arch/x86/include/asm/tasks.h + +#ifndef ASM_TASKS_H +#define ASM_TASKS_H + +#include + +// Switch the current task +// stack: Pointer to the old stack pointer +void switch_context(size_t** stack); + +// Setup a default frame for a new task +// task: Pointer to the task structure +// ep: The entry point for code execution +// arg: Arguments list pointer for the task's stack +// return +// - 0 on success +// - -EINVAL (-22) on failure +int create_default_frame(task_t* task, entry_point_t ep, void* arg); + +#endif /* end of include guard: ASM_TASKS_H */ \ No newline at end of file diff --git a/src/arch/x86_64/c/tasks.c b/src/arch/x86_64/c/tasks.c new file mode 100644 index 0000000..f275cec --- /dev/null +++ b/src/arch/x86_64/c/tasks.c @@ -0,0 +1,75 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/arch/x86/kernel/tasks.c + +#include +#include +// #include +#include +#include +#include + +size_t* +get_current_stack(void) +{ + task_t* curr_task = current_task; + + return curr_task->last_stack_pointer; +} + +int +create_default_frame(task_t* task, entry_point_t ep, void* arg) +{ + size_t* stack; + struct state* stptr; + size_t state_size; + + if (BUILTIN_EXPECT(!task, 0)) { + return -EINVAL; + } + + if (BUILTIN_EXPECT(!task->stack, 0)) { + return -EINVAL; + } + + memset(task->stack, 0xcd, KERNEL_STACK_SIZE); + // => stack is 16byte aligned + stack = (size_t*)(task->stack + KERNEL_STACK_SIZE - 16); + // Only marker for debugging purposes, ... + *stack-- = 0xdeadbeef; + // and the "caller" we shall return to + // This procedure cleans the task after exit + *stack = (size_t)leave_kernel_task; + // Next bunch on the stack is the initial register state + // The stack must look like the stack of a task + // which was scheduled away previously + state_size = sizeof(struct state); + stack = (size_t*)((size_t)stack - state_size); + stptr = (struct state*)stack; + memset(stptr, 0x00, state_size); + stptr->rsp = (size_t)stack + state_size; + // The first-function-to-be-called's arguments, ... + stptr->rdi = (size_t)arg; + stptr->int_no = 0xb16b00b5; + stptr->error = 0xc03db4b3; + // The instruction pointer shall be set on the first function + // to be called after IRETing + stptr->rip = (size_t)ep; + stptr->cs = 0x08; + stptr->ss = 0x10; + stptr->rflags = 0x1002; + stptr->userrsp = stptr->rsp; + // Set the task's stack pointer entry to the stack + // we have crafted right now + task->last_stack_pointer = (size_t*)stack; + + return 0; +} diff --git a/src/c_kernel/include/processor.h b/src/c_kernel/include/processor.h new file mode 100644 index 0000000..79ade15 --- /dev/null +++ b/src/c_kernel/include/processor.h @@ -0,0 +1,21 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/include/eduos/processor.h + +#ifndef PROCESSOR_H +#define PROCESSOR_H + +// This is no needed because of being included in stddef.h +// #include +#include +#include + +#endif /* end of include guard: PROCESSOR_H */ diff --git a/src/c_kernel/include/tasks.h b/src/c_kernel/include/tasks.h index 1635f4f..22617c0 100644 --- a/src/c_kernel/include/tasks.h +++ b/src/c_kernel/include/tasks.h @@ -15,7 +15,7 @@ #include #include -// #include +#include int multitasking_init(void); From 4484d68b67d04a71e29bfdd853978d40afc96d8d Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Thu, 22 Jun 2017 23:19:42 +0900 Subject: [PATCH 17/29] Implement c_kernel/tasks.c --- src/c_kernel/tasks.c | 309 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 309 insertions(+) create mode 100644 src/c_kernel/tasks.c diff --git a/src/c_kernel/tasks.c b/src/c_kernel/tasks.c new file mode 100644 index 0000000..67ebaa8 --- /dev/null +++ b/src/c_kernel/tasks.c @@ -0,0 +1,309 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// The part of this file was taken from: +// https://github.com/RWTH-OS/eduOS/blob/master/kernel/tasks.c + +#include +#include +#include +#include +#include +#include +extern void* stack_top; // defined in boot.asm +extern int eputs(const char*); +extern int eprint(const char*); + +// Array of task structures (PCB) +// A task's id will be its position in this array +static task_t task_table[MAX_TASKS] = + {[0] = { 0, TASK_IDLE, NULL, NULL, 0, NULL, NULL }, + [1 ... MAX_TASKS - 1] = { 0, TASK_INVALID, NULL, NULL, 0, NULL, NULL } }; +// readyqueues +// Task list is a queue for priority, total number is 30 +static readyqueues_t readyqueues = { task_table+0, NULL, 0, 0, {[0 ... MAX_PRIO-2] = {NULL, NULL}}}; + +task_t* current_task = task_table+0; + +// Return pointer to the task_t structure of current task +task_t * +get_current_task(void) +{ + return current_task; +} + +int multitasking_init(void) +{ + // if the first task status isn't idle (it's unlikely) + // puts message task 0 is not an idle task + if (BUILTIN_EXPECT(task_table[0].status != TASK_IDLE, 0)) { + // Equivalent to kputs("Task 0 is not an idle task\n"); + eputs("Task 0 is not an idle task"); + return -ENOMEM; + } + // At the first task_table + // Set prio to zero + task_table[0].prio = IDLE_PRIO; + // Set stack_top - 8192 to stack + task_table[0].stack = stack_top - 8192; + return 0; +} + +void +finish_task_switch(void) +{ + // pointer to old task and prio + task_t* old; + uint8_t prio; + // Old(previous) task in the ready queue is NOT NULL + if ((old = readyqueues.old_task) != NULL) { + // If old task's status is TASK_INVALID + if (old->status == TASK_INVALID) { + // Set old task's stack to NULL + old->stack = NULL; + // Set old task's last_stack_pointer to NULL + old->last_stack_pointer = NULL; + // Set old task in the queue to NULL + readyqueues.old_task = NULL; + + } else { // else if old task's status is valid + // Set old task's prio to (current) prio + prio = old->prio; + if (!readyqueues.queue[prio - 1].first) { // if a queue for current prio is not the first + // Set next and previous tasks against old task to NULL + old->next = old->prev = NULL; + // Set old task to the first and the last in task list + readyqueues.queue[prio - 1].first = readyqueues.queue[prio - 1].last = old; + + } else { // else if a queue for prio is the first + // Set next task against old to NULL + old->next = NULL; + // Set previous task against old to the last in task list + old->prev = readyqueues.queue[prio - 1].last; + // Set old to the next task of the last task in list + readyqueues.queue[prio - 1].last->next = old; + // Set old to the last task in list + readyqueues.queue[prio - 1].last = old; + } + // The previous task in ready queues is NULL; + readyqueues.old_task = NULL; + // Using |= operator, if there's prio_bitmap, assign itself + // but when no prio_bitmap, assign 1 << prio + readyqueues.prio_bitmap |= (1 << prio); + } + } +} + +#define N 256 // For message +// Procedures which are called by exiting tasks +static void NORETURN +do_exit(int arg) +{ + task_t* curr_task = current_task; + // Equivalent to kprintf("Terminate task: %u, return value %d\n", curr_task->id, arg); + char message[N] = { '\0' }; + sprintf(message, "Terminate task: %u, return value %d\n", curr_task->id, arg); + eprint(message); + + curr_task->status = TASK_FINISHED; + reschedule(); + // Equivalent to kprintf("Kernel panic: scheduler found no valid task\n"); + eputs("Kernel panic: scheduler found no valid task"); + while (1) + { + NOP8; + } +} + +// A procedure to be called by kernel tasks +void NORETURN +leave_kernel_task(void) +{ + int result; + result = 0; // get_return_value(); + do_exit(result); +} + +// Create a task with a specific entry point +// id: Pointer to a tid_t struct where the id shall be set +// ep: Pointer to the function the task shall start with +// arg: Arguments list +// prio: Desired priority of the new task +static int +create_task(tid_t* id, entry_point_t ep, void* arg, uint8_t prio) +{ + int ret = -ENOMEM; + uint32_t i; + + // entry pointer is null + if (BUILTIN_EXPECT(!ep, 0)) { + return -EINVAL; + } + // the given prio equals IDLE_PRIO(0) + if (BUILTIN_EXPECT(prio == IDLE_PRIO, 0)) { + return -EINVAL; + } + // the given prio is higher than MAX_PRIO(31) + if (BUILTIN_EXPECT(prio > MAX_PRIO, 0)) { + return -EINVAL; + } + // Loop 0~15 + for(i=0; i < MAX_TASKS; i++) { + // Turn invalid-status task into ready-status + if (task_table[i].status == TASK_INVALID) { + // set i to id + task_table[i].id = i; + // set status to TASK_READY; + task_table[i].status == TASK_READY; + // last_stack_pointer = NULL; + task_table[i].last_stack_pointer = NULL; + task_table[i].stack = create_stack(i); + // Set the given prio to prio + task_table[i].prio = prio; + + if (id) { + // set i to id's pointer + *id = i; + } + + ret = create_default_frame(task_table+i, ep, arg); + // Add task in the readyqueues + readyqueues.prio_bitmap |= (1 << prio); + readyqueues.nr_tasks++; + // if there's no first one of queue + if (!readyqueues.queue[prio-1].first) { + // next and prev of task_table[i] = NULL; + task_table[i].next = task_table[i].prev = NULL; + // set task_table+i (address of task_table+i?) to first + readyqueues.queue[prio - 1].first = task_table + i; + // set task_table+i (address of task_table+i?) to last + readyqueues.queue[prio - 1].last = task_table + i; + } else { // else there's the first of queue + // set queue[prio-1].last to previous task in task_table + task_table[i].prev = readyqueues.queue[prio - 1].last; + // set NULL to next task in task_table + task_table[i].next = NULL; + // set task_table+i to the last of the queue to next task + readyqueues.queue[prio - 1].last->next = task_table + i; + // set task_table+i to the last of the queue + readyqueues.queue[prio - 1].last = task_table + i; + } + break; + } + } + + return ret; +} + +int +create_kernel_task(tid_t* id, entry_point_t ep, void* args, uint8_t prio) +{ + // given prio is higher than MAX_PRIO(31) + if (prio > MAX_PRIO) { + // Set NORMAL_PRIO to prio + prio = NORMAL_PRIO; + } + return create_task(id, ep, args, prio); +} + +size_t** +scheduler(void) +{ + task_t* orig_task; + uint32_t prio; + + orig_task = current_task; + // signalizes that this task could be reused + // current_task is task_table+0 when initialized + if (current_task->status == TASK_FINISHED) { + current_task->status = TASK_INVALID; + readyqueues.old_task = current_task; + } else { // current_task is NOT FINISHED + // Reset old task + readyqueues.old_task = NULL; + } + // Determines highest priority (at this point) + prio = msb(readyqueues.prio_bitmap); + // if current highest prio is higher than MAX_PRIO + if (prio > MAX_PRIO) { + // Get task out + if ((current_task->status == TASK_RUNNING) || + (current_task->status == TASK_IDLE)) { + goto get_task_out; + } + // set readyqueues.idle (idle task) to current_task + current_task = readyqueues.idle; + + } else { // current highest prio is lower than MAX_PRIO + // Does the current task have an higher priority? => no task switch + // if current_task's prio is higher than current highest prio AND + // current_task's status is TASK_RUNNING + if ((current_task->prio > prio) && (current_task->status == TASK_RUNNING)) { + goto get_task_out; + } + // if current_task's status is equals to TASK_RUNNING + if (current_task->status == TASK_RUNNING) { + // Set current_task's status to TASK_READY + current_task->status = TASK_READY; + // Set current_task to readyqueues.old_task + readyqueues.old_task = current_task; + } + // Set readyqueues's queue[current prio].first to current_task + current_task = readyqueues.queue[prio - 1].first; + // if current_task's status equals to TASK_INVALID (unlikely) + if (BUILTIN_EXPECT(current_task->status == TASK_INVALID, 0)) { + // Equivalent to kprintf("Upps!!!!!! Got invalid task %d, orig task %d\n", + // current_task->id, orig_task->id); + char message[N] = { '\0' }; + sprintf(message, "Upps!!!!!! Got invalid task %d, orig task %d\n", + current_task->id, orig_task->id); + eprint(message); + } + // Set current_task's status to TASK_RUNNING + current_task->status = TASK_RUNNING; + // Remove new task from queue + // By the way, priority 0 is only used by the idle task and doesn't need own + // queue + readyqueues.queue[prio - 1].first = current_task->next; + // if there's no next task in the queue + if (!current_task->next) { + readyqueues.queue[prio - 1].last = NULL; + // ~ is Binary Ones Complement Operator has the effect of 'flipping' bits + // &= is bitwise AND operator which turns (1 AND 0) or (0 AND 0) into 0 + readyqueues.prio_bitmap &= ~(1 << prio); + } + // Set the next and the previous tasks against current_task to NULL + current_task->next = current_task->prev = NULL; + } + +get_task_out: + if (current_task != orig_task) { // current_task is not orig_task + // Equivalent to kprintf("schedule from %u to %u with prio %u\n", + // orig_task->id, + // current_task->id, (uint32_t)current_task->prio); + char message[N] = { '\0' }; + sprintf(message, "schedule from %u to %u with prio %u\n", orig_task->id, + current_task->id, (uint32_t)current_task->prio); + eprint(message); + // Returns the address of last_stack_pointer in orig_task + return (size_t**)&(orig_task->last_stack_pointer); + } + + return NULL; +} + +void +reschedule(void) +{ + // pointer to pointer of address of stack + size_t** stack; + if ((stack = scheduler())) { + switch_context(stack); + } +} From 837d27e3500a1d3a077d1a7060fd691b3794d226 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Thu, 22 Jun 2017 23:35:48 +0900 Subject: [PATCH 18/29] main.cr: Comment out Division by zero --- src/kernel/main.cr | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/kernel/main.cr b/src/kernel/main.cr index f6152e8..8f3e822 100644 --- a/src/kernel/main.cr +++ b/src/kernel/main.cr @@ -28,8 +28,8 @@ print "\b"; puts puts "33: Current directory is #{__DIR__}" print "34: "; cprint(LibU.hello_from_c) cprint(LibU.dummy_exception) -# Division By Zero -42 / 0 +# For testing: Division By Zero +# 42 / 0 # clear # puts "---------strlen------------" From 4da9b28bafd38a76060bace584dec624422b5490 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Thu, 22 Jun 2017 23:36:28 +0900 Subject: [PATCH 19/29] Implement LibU.multitasking_init --- src/kernel/prelude.cr | 1 + src/kernel/tasks.cr | 14 ++++++++++++++ src/kernel/utero_init.cr | 1 + 3 files changed, 16 insertions(+) create mode 100644 src/kernel/tasks.cr diff --git a/src/kernel/prelude.cr b/src/kernel/prelude.cr index eb5e88a..5023bfe 100644 --- a/src/kernel/prelude.cr +++ b/src/kernel/prelude.cr @@ -12,3 +12,4 @@ require "./lib_u" require "./lib_u/**" # Alpha-sorted list +require "./tasks" diff --git a/src/kernel/tasks.cr b/src/kernel/tasks.cr new file mode 100644 index 0000000..692d4d9 --- /dev/null +++ b/src/kernel/tasks.cr @@ -0,0 +1,14 @@ +# Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +# file at the top-level directory of this distribution. +# +# Licensed under the Apache License, Version 2.0 or the MIT license +# , at your +# option. This file may not be copied, modified, or distributed +# except according to those terms. +require "./lib_u" + +# tasks.c +lib LibU + fun multitasking_init : Int +end diff --git a/src/kernel/utero_init.cr b/src/kernel/utero_init.cr index 8e115d3..0d5f315 100644 --- a/src/kernel/utero_init.cr +++ b/src/kernel/utero_init.cr @@ -19,3 +19,4 @@ end cprint LibU.make_kernel_info LibU.idt_install LibU.isrs_install +LibU.multitasking_init From 9c54c1c3adb40b371811b93a5122fd32d464e5f0 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 02:43:46 +0900 Subject: [PATCH 20/29] x86_64/c/tasks.c: Fix rflags --- src/arch/x86_64/c/tasks.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/arch/x86_64/c/tasks.c b/src/arch/x86_64/c/tasks.c index f275cec..b23186a 100644 --- a/src/arch/x86_64/c/tasks.c +++ b/src/arch/x86_64/c/tasks.c @@ -65,7 +65,7 @@ create_default_frame(task_t* task, entry_point_t ep, void* arg) stptr->rip = (size_t)ep; stptr->cs = 0x08; stptr->ss = 0x10; - stptr->rflags = 0x1002; + stptr->rflags = 0x1202; stptr->userrsp = stptr->rsp; // Set the task's stack pointer entry to the stack // we have crafted right now From 54760f47e013fc819998f7f8ceb685ef3e0197f8 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 02:46:45 +0900 Subject: [PATCH 21/29] Add string.h which includes memset --- src/arch/x86_64/c/tasks.c | 2 +- src/c_kernel/include/string.h | 19 +++++++++++++++++++ 2 files changed, 20 insertions(+), 1 deletion(-) create mode 100644 src/c_kernel/include/string.h diff --git a/src/arch/x86_64/c/tasks.c b/src/arch/x86_64/c/tasks.c index b23186a..170f072 100644 --- a/src/arch/x86_64/c/tasks.c +++ b/src/arch/x86_64/c/tasks.c @@ -12,7 +12,7 @@ #include #include -// #include +#include #include #include #include diff --git a/src/c_kernel/include/string.h b/src/c_kernel/include/string.h new file mode 100644 index 0000000..ad0959b --- /dev/null +++ b/src/c_kernel/include/string.h @@ -0,0 +1,19 @@ +// Copyright (c) 2016-2017 Utero OS Developers. See the COPYRIGHT +// file at the top-level directory of this distribution. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. +// +// Functions are taken from musl/include/string.h + +#ifndef STRING_H +#define STRING_H + +#include "bits/alltypes.h" + +void* memset(void*, int, size_t); + +#endif /* end of include guard: STRING_H */ From 22b2d121791dc6c9b52d8c9ff35423dfeec2209f Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 02:48:39 +0900 Subject: [PATCH 22/29] long_mode_init: Call get_current_stack and finish_task_switch --- src/arch/x86_64/long_mode_init.asm | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/arch/x86_64/long_mode_init.asm b/src/arch/x86_64/long_mode_init.asm index 3e4b9d8..25a91b4 100644 --- a/src/arch/x86_64/long_mode_init.asm +++ b/src/arch/x86_64/long_mode_init.asm @@ -116,6 +116,8 @@ isrstub_pseudo_error 9 extern fault_handler ; extern irq_handler +extern get_current_stack +extern finish_task_switch global switch_context ALIGN 8 @@ -175,14 +177,13 @@ common_stub: call fault_handler ; call irq_handler - ; cmp rax, 0 - ; je no_context_switch - jmp no_context_switch + cmp rax, 0 + je no_context_switch + ; jmp no_context_switch common_switch: mov [rax], rsp ; store old rsp - ; TODO: It seems to be defined in arch/x86/kernel/tasks.c - ; call get_current_stack ; get new rsp + call get_current_stack ; get new rsp xchg rax, rsp ; set task switched flag @@ -196,8 +197,7 @@ common_switch: ; call set_kernel_stack ; call cleanup code - ; TODO: It seems to be defined in kernel/tasks.c - ; call finish_task_switch + call finish_task_switch no_context_switch: pop r15 From c967ac42e10193909dcdd513d5bc60af8524701f Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 02:51:36 +0900 Subject: [PATCH 23/29] Implement create_foo function for multitasking and fun for calling from Crystal-land ...but it fails --- src/c_kernel/utero_init.c | 37 ++++++++++++++++++++++++++++++++++++- src/kernel/main.cr | 1 + src/kernel/utero_init.cr | 1 + 3 files changed, 38 insertions(+), 1 deletion(-) diff --git a/src/c_kernel/utero_init.c b/src/c_kernel/utero_init.c index e7de537..00f1ef5 100644 --- a/src/c_kernel/utero_init.c +++ b/src/c_kernel/utero_init.c @@ -1,6 +1,9 @@ #include "make_string.h" #include -// #include "stdint.h" +#include +#include +#include +#include #define N 256 // Parameters passed from assembly or linker @@ -8,6 +11,8 @@ extern const void * kernel_start; extern const void * kernel_end; extern const void * bss_start; extern const void * bss_end; +extern int eputs(const char*); +extern int eprint(const char*); // int early_info(unsigned int ks, unsigned int ke) // { @@ -35,3 +40,33 @@ multiboot info at: %p\n"; &mb_info); return *str; } + +static int +foo(void* arg) +{ + int i = 0; + + + for (i = 0; i < 5; i++) { + char *message; + sprintf(message, "hello from %s\n", (char*)arg); + eprint(message); + reschedule(); + } + + return 0; +} + +int create_foo(void) +{ + tid_t id1; + tid_t id2; + create_kernel_task(&id1, foo, "foo1", NORMAL_PRIO); + create_kernel_task(&id2, foo, "foo2", NORMAL_PRIO); + reschedule(); + + while (1) { + NOP8; + } + return 0; +} diff --git a/src/kernel/main.cr b/src/kernel/main.cr index 8f3e822..2feb8ce 100644 --- a/src/kernel/main.cr +++ b/src/kernel/main.cr @@ -31,6 +31,7 @@ cprint(LibU.dummy_exception) # For testing: Division By Zero # 42 / 0 # clear +# LibU.create_foo # puts "---------strlen------------" # ab = "abc" diff --git a/src/kernel/utero_init.cr b/src/kernel/utero_init.cr index 0d5f315..4714441 100644 --- a/src/kernel/utero_init.cr +++ b/src/kernel/utero_init.cr @@ -3,6 +3,7 @@ require "./scrn" lib LibU fun make_kernel_info : LibU::Char* + fun create_foo : LibU::Int end # A same named function in C, and call that from assembly before call main From db46ccf7835ec8e7a672389b9dfd0f6e55ef8117 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 02:54:48 +0900 Subject: [PATCH 24/29] Implement C binding for multitasking...but it fails(OMG) --- src/kernel/lib_u.cr | 4 ++++ src/kernel/tasks.cr | 4 +++- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/src/kernel/lib_u.cr b/src/kernel/lib_u.cr index 820ad33..cd64d84 100644 --- a/src/kernel/lib_u.cr +++ b/src/kernel/lib_u.cr @@ -32,5 +32,9 @@ lib LibU alias Float = Float32 alias Double = Float64 + # typedef unsigned int tid_t; + alias Tid_t = Int + alias UInt8_t = UChar + $environ : Char** end diff --git a/src/kernel/tasks.cr b/src/kernel/tasks.cr index 692d4d9..bcd4a74 100644 --- a/src/kernel/tasks.cr +++ b/src/kernel/tasks.cr @@ -10,5 +10,7 @@ require "./lib_u" # tasks.c lib LibU - fun multitasking_init : Int + fun multitasking_init : LibU::Int + fun reschedule : Void + fun create_kernel_task(id : LibU::Tid_t*, ep : Void* -> LibU::Int, args : Void*, prio : LibU::UInt8_t) : Int end From d6463935f7a5682d446df5b13272165b8e2acf54 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 02:56:14 +0900 Subject: [PATCH 25/29] Add box.cr --- src/core/box.cr | 28 ++++++++++++++++++++++++++++ src/core/prelude.cr | 1 + 2 files changed, 29 insertions(+) create mode 100644 src/core/box.cr diff --git a/src/core/box.cr b/src/core/box.cr new file mode 100644 index 0000000..7416335 --- /dev/null +++ b/src/core/box.cr @@ -0,0 +1,28 @@ +# A Box allows turning any object to a `Void*` and back. +# +# A Box's purpose is passing data to C as a `Void*` and then converting that +# back to the original data type. +# +# For an example usage, see `Proc`'s explanation about sending Procs to C. +class Box(T) + # Returns the original object + # getter object : T + + # Creates a `Box` with the given object. + # + # This method isn't usually used directly. Instead, `Box.box` is used. + def initialize(@object : T) + end + + # Creates a Box for an object and returns it as a `Void*`. + def self.box(object) : Void* + new(object).as(Void*) + end + + # Unboxes a `Void*` into an object of type `T`. Note that for this you must + # specify T: `Box(T).unbox(data)`. + def self.unbox(pointer : Void*) : T + pointer.as(self).as(T) + # pointer.as(self).object + end +end diff --git a/src/core/prelude.cr b/src/core/prelude.cr index 6db23a5..fc9608a 100644 --- a/src/core/prelude.cr +++ b/src/core/prelude.cr @@ -13,6 +13,7 @@ require "./lib_cr/**" require "./string" # Alpha-sorted list +require "./box" require "./int" require "./number" require "./pointer" From 9c3fffd50a60677a0d2fae1f05ea0461eb22c8fd Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 02:56:55 +0900 Subject: [PATCH 26/29] Add stdlib.cr for LibCR --- src/core/lib_cr/x86_64-linux-musl/c/stdlib.cr | 24 +++++++++++++++++++ 1 file changed, 24 insertions(+) create mode 100644 src/core/lib_cr/x86_64-linux-musl/c/stdlib.cr diff --git a/src/core/lib_cr/x86_64-linux-musl/c/stdlib.cr b/src/core/lib_cr/x86_64-linux-musl/c/stdlib.cr new file mode 100644 index 0000000..3b3e119 --- /dev/null +++ b/src/core/lib_cr/x86_64-linux-musl/c/stdlib.cr @@ -0,0 +1,24 @@ +require "./stddef" +# require "./sys/wait" + +lib LibCR + # struct DivT + # quot : Int + # rem : Int + # end + + # fun atof(x0 : Char*) : Double + # fun div(x0 : Int, x1 : Int) : DivT + fun exit(x0 : Int) : NoReturn + fun free(x0 : Void*) : Void + fun getenv(x0 : Char*) : Char* + fun malloc(x0 : SizeT) : Void* + fun mkstemp(x0 : Char*) : Int + fun putenv(x0 : Char*) : Int + fun realloc(x0 : Void*, x1 : SizeT) : Void* + fun realpath(x0 : Char*, x1 : Char*) : Char* + fun setenv(x0 : Char*, x1 : Char*, x2 : Int) : Int + fun strtof(x0 : Char*, x1 : Char**) : Float + # fun strtod(x0 : Char*, x1 : Char**) : Double + fun unsetenv(x0 : Char*) : Int +end From cd612de254f73f045fb1e6d693f3240de0988b7d Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 21:07:37 +0900 Subject: [PATCH 27/29] main.cr: Comment out on invoking LibU.create_foo --- src/kernel/main.cr | 1 + 1 file changed, 1 insertion(+) diff --git a/src/kernel/main.cr b/src/kernel/main.cr index 2feb8ce..50cbbac 100644 --- a/src/kernel/main.cr +++ b/src/kernel/main.cr @@ -31,6 +31,7 @@ cprint(LibU.dummy_exception) # For testing: Division By Zero # 42 / 0 # clear +# This would fail... # LibU.create_foo # puts "---------strlen------------" From ff8bee9792287911cf88eb34ac830c07ea178359 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 21:08:17 +0900 Subject: [PATCH 28/29] Makefile: Add -monitor stdio to qemu --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index 8469193..7d48f5e 100644 --- a/Makefile +++ b/Makefile @@ -61,7 +61,7 @@ cleanobjs: @rm -rf target/ run: $(iso) - @qemu-system-$(arch) -cdrom $(iso) + @qemu-system-$(arch) -cdrom $(iso) -monitor stdio iso: $(iso) From fd26c29f9946682ef3b63a6c7f663ddd58ec17c3 Mon Sep 17 00:00:00 2001 From: noriyotcp Date: Fri, 30 Jun 2017 21:13:06 +0900 Subject: [PATCH 29/29] README: Bump up Crystal version to 0.23.0 --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index f428bb2..255967e 100644 --- a/README.md +++ b/README.md @@ -7,7 +7,7 @@ This is the *work in progress*. ## Requirements -* Crystal 0.22.0 +* Crystal 0.23.0 * llvm * Please see [All required libraries](https://github.com/crystal-lang/crystal/wiki/All-required-libraries) * nasm