From 34f7cf32bdafe88fecdc57fd338a28d1d7deff04 Mon Sep 17 00:00:00 2001 From: maxbarsukov Date: Thu, 24 Apr 2025 18:58:06 +0300 Subject: [PATCH] feat(io): :sparkles: start lab#1 --- 6 свв/лабораторные/lab1/.gitignore | 6 +++ 6 свв/лабораторные/lab1/io.c | 12 +++++ 6 свв/лабораторные/lab1/io.h | 9 ++++ 6 свв/лабораторные/lab1/kernel.c | 72 ++++++++++++++++++++++++++++++ 6 свв/лабораторные/lab1/kernel.h | 19 ++++++++ 6 свв/лабораторные/lab1/kernel.ld | 28 ++++++++++++ 6 свв/лабораторные/lab1/run.sh | 14 ++++++ 7 files changed, 160 insertions(+) create mode 100644 6 свв/лабораторные/lab1/.gitignore create mode 100644 6 свв/лабораторные/lab1/io.c create mode 100644 6 свв/лабораторные/lab1/io.h create mode 100644 6 свв/лабораторные/lab1/kernel.c create mode 100644 6 свв/лабораторные/lab1/kernel.h create mode 100644 6 свв/лабораторные/lab1/kernel.ld create mode 100755 6 свв/лабораторные/lab1/run.sh diff --git a/6 свв/лабораторные/lab1/.gitignore b/6 свв/лабораторные/lab1/.gitignore new file mode 100644 index 0000000..701bf15 --- /dev/null +++ b/6 свв/лабораторные/lab1/.gitignore @@ -0,0 +1,6 @@ +# Building +*.elf +*.map + +# IDEs +.vscode/ diff --git a/6 свв/лабораторные/lab1/io.c b/6 свв/лабораторные/lab1/io.c new file mode 100644 index 0000000..e6da03c --- /dev/null +++ b/6 свв/лабораторные/lab1/io.c @@ -0,0 +1,12 @@ +#include "io.h" + +void putchar(char ch); + +void +puts(const char *s) +{ + while (*s) + { + putchar(*s++); + } +} diff --git a/6 свв/лабораторные/lab1/io.h b/6 свв/лабораторные/lab1/io.h new file mode 100644 index 0000000..a241177 --- /dev/null +++ b/6 свв/лабораторные/lab1/io.h @@ -0,0 +1,9 @@ +#pragma once + +#define va_list __builtin_va_list +#define va_start __builtin_va_start +#define va_end __builtin_va_end +#define va_arg __builtin_va_arg + +extern void puts(const char *s); +extern void printf(const char *fmt, ...); diff --git a/6 свв/лабораторные/lab1/kernel.c b/6 свв/лабораторные/lab1/kernel.c new file mode 100644 index 0000000..94754e3 --- /dev/null +++ b/6 свв/лабораторные/lab1/kernel.c @@ -0,0 +1,72 @@ +#include "kernel.h" +#include "io.h" + +extern char __bss[], __bss_end[], __stack_top[]; + +struct sbiret +sbi_call(long arg0, long arg1, long arg2, long arg3, long arg4, long arg5, long fid, long eid) +{ + register long a0 __asm__("a0") = arg0; + register long a1 __asm__("a1") = arg1; + register long a2 __asm__("a2") = arg2; + register long a3 __asm__("a3") = arg3; + register long a4 __asm__("a4") = arg4; + register long a5 __asm__("a5") = arg5; + register long a6 __asm__("a6") = fid; + register long a7 __asm__("a7") = eid; + + __asm__ __volatile__("ecall" + : "=r"(a0), "=r"(a1) + : "r"(a0), "r"(a1), "r"(a2), "r"(a3), "r"(a4), "r"(a5), "r"(a6), "r"(a7) + : "memory"); + return (struct sbiret) {.error = a0, .value = a1}; +} + +void +putchar(char ch) +{ + sbi_call(ch, 0, 0, 0, 0, 0, 0, SBI_ECALL_0_1_PUTCHAR); +} + +int +getchar(void) +{ + struct sbiret ret; + + do + { + ret = sbi_call(0, 0, 0, 0, 0, 0, 0, SBI_ECALL_0_1_GETCHAR); + } while (ret.error == SBI_ERR_FAILED); + + return (int) ret.error; +} + +// TODO +void +kernel_main(void) +{ + for(char *p = __bss; p < __bss_end; p++) + { + *p = 0; + } + + puts("Hello World!"); + + for(;;) + { + __asm__ __volatile__("wfi"); + } +} + +__attribute__((section(".text.boot"))) +__attribute__((naked)) +void +boot(void) +{ + __asm__ __volatile__( + "mv sp, %[stack_top]\n" + "j kernel_main\n" + : + : [stack_top] "r" (__stack_top) + ); +} diff --git a/6 свв/лабораторные/lab1/kernel.h b/6 свв/лабораторные/lab1/kernel.h new file mode 100644 index 0000000..656ccd1 --- /dev/null +++ b/6 свв/лабораторные/lab1/kernel.h @@ -0,0 +1,19 @@ +#pragma once + +struct sbiret { + long error; + long value; +}; + +#define SBI_SUCCESS 0 +#define SBI_ERR_FAILED -1 +#define SBI_ECALL_0_1_PUTCHAR 0x01 +#define SBI_ECALL_0_1_GETCHAR 0x02 +#define SBI_EXT_BASE 0x10 +#define SBI_EXT_VER 0x00 +#define SBI_EXT_PMU 0x504D55 +#define SBI_EXT_CTR_NUM 0x00 +#define SBI_EXT_CTR_DTLS 0x01 +#define SBI_EXT_HSM 0x48534D +#define SBI_EXT_SRST 0x53525354 +#define SBI_EXT_SHUTDOWN 0x00 diff --git a/6 свв/лабораторные/lab1/kernel.ld b/6 свв/лабораторные/lab1/kernel.ld new file mode 100644 index 0000000..90bab70 --- /dev/null +++ b/6 свв/лабораторные/lab1/kernel.ld @@ -0,0 +1,28 @@ +ENTRY(boot) + +SECTIONS { + . = 0x80200000; + + .text :{ + KEEP(*(.text.boot)); + *(.text .text.*); + } + + .rodata : ALIGN(4) { + *(.rodata .rodata.*); + } + + .data : ALIGN(4) { + *(.data .data.*); + } + + .bss : ALIGN(4) { + __bss = .; + *(.bss .bss.* .sbss .sbss.*); + __bss_end = .; + } + + . = ALIGN(4); + . += 128 * 1024; + __stack_top = .; +} diff --git a/6 свв/лабораторные/lab1/run.sh b/6 свв/лабораторные/lab1/run.sh new file mode 100755 index 0000000..21258ca --- /dev/null +++ b/6 свв/лабораторные/lab1/run.sh @@ -0,0 +1,14 @@ +#!/bin/bash + +set -xue + +QEMU=qemu-system-riscv32 + +CC=clang +CFLAGS="-std=c11 -O2 -g3 -Wall -Wextra --target=riscv32 -ffreestanding -nostdlib" + +$CC $CFLAGS -Wl,-Tkernel.ld -Wl,-Map=kernel.map -o kernel.elf \ + kernel.c io.c + +$QEMU -machine virt -bios default -nographic -serial mon:stdio --no-reboot \ + -kernel kernel.elf