This repository has no description
0

Configure Feed

Select the types of activity you want to include in your feed.

Write to real screen for the first time!

Ivan Ilak (Apr 10, 2023, 6:17 PM +0200) 83f184cc 3d615e8d

+1015 -103
+3 -1
CMakeLists.txt
··· 1 1 cmake_minimum_required (VERSION 3.17) 2 2 3 3 include(cmake/target.cmake) 4 - setup("MODEL_0" ${CMAKE_CURRENT_SOURCE_DIR}) 4 + setup("MODEL_1" ${CMAKE_CURRENT_SOURCE_DIR}) 5 + message("Build Info:\n\t - Arch:\t${ARCH}\n\t - Model:\t${MODEL}") 6 + 5 7 6 8 set(CMAKE_DEPENDS_USE_COMPILER ON) 7 9
+3
README.md
··· 7 7 8 8 [[_TOC_]] 9 9 10 + ## ToDo 11 + [ ] Revist memory management... I think the code is a bit to simplisic (want to add virtual memory management.) 12 + 10 13 ## Notes 11 14 Since I don't belive there is one perfect source for the relevant topics, I spend a lot of time reading code from others. 12 15 * [armOS (*Thanos Koutroubas*)](https://github.com/thanoskoutr/armOS): This project is pretty much where I want to be at the end (I guess), and its nice to see what will be necessary for this...
+19 -1
cmake/target.cmake
··· 1 1 macro(setup model path) 2 2 set(BUILD_DIR ${path}/build/bin) 3 3 4 - if(${model} STREQUAL "MODEL_0") 4 + if(${model} STREQUAL "MODEL_0" 5 + OR ${model} STREQUAL "MODEL_1") 5 6 set(CPU arm1176jzf-s) 6 7 set(ARCH_DIR ${path}/arch/armv6) 7 8 elseif(${model} STREQUAL "MODEL_2") ··· 16 17 endif() 17 18 18 19 if(${model} STREQUAL "MODEL_0" 20 + OR ${model} STREQUAL "MODEL_1" 19 21 OR ${model} STREQUAL "MODEL_2") 20 22 setup_arch("32") 21 23 else() ··· 23 25 endif() 24 26 25 27 set(MODEL ${model}) 28 + 29 + if(${ARCH} STREQUAL "AARCH_32") 30 + if(${MODEL} STREQUAL "MODEL_0") 31 + add_compile_definitions(MODEL_0 AARCH_32) 32 + elseif(${MODEL} STREQUAL "MODEL_1") 33 + add_compile_definitions(MODEL_1 AARCH_32) 34 + elseif(${MODEL} STREQUAL "MODEL_2") 35 + add_compile_definitions(MODEL_2 AARCH_32) 36 + endif() 37 + elseif(${ARCH} STREQUAL "AARCH_64") 38 + if(${MODEL} STREQUAL "MODEL_3") 39 + add_compile_definitions(MODEL_3 AARCH_64) 40 + elseif(${MODEL} STREQUAL "MODEL_4") 41 + add_compile_definitions(MODEL_4 AARCH_64) 42 + endif() 43 + endif() 26 44 27 45 endmacro() 28 46
+4 -14
os/CMakeLists.txt
··· 8 8 set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -T ${ARCH_DIR}/linker.ld") 9 9 10 10 set(SOURCES 11 + src/kernel/kerio.c 12 + src/kernel/gpu.c 13 + src/kernel/mailbox.c 14 + src/kernel/framebuffer.c 11 15 src/kernel/memory.c 12 16 src/kernel/atag.c 13 17 src/kernel/uart.c ··· 18 22 19 23 # Create minimal ELF binary from sources. 20 24 add_executable(${KERNEL}.elf ${SOURCES}) 21 - 22 - if(${ARCH} STREQUAL "AARCH_32") 23 - if(${MODEL} STREQUAL "MODEL_0") 24 - target_compile_definitions(${KERNEL}.elf PUBLIC MODEL_0 AARCH_32) 25 - elseif(${MODEL} STREQUAL "MODEL_2") 26 - target_compile_definitions(${KERNEL}.elf PUBLIC MODEL_2 AARCH_32) 27 - endif() 28 - elseif(${ARCH} STREQUAL "AARCH_64") 29 - if(${MODEL} STREQUAL "MODEL_3") 30 - target_compile_definitions(${KERNEL}.elf PUBLIC MODEL_3 AARCH_64) 31 - elseif(${MODEL} STREQUAL "MODEL_4") 32 - target_compile_definitions(${KERNEL}.elf PUBLIC MODEL_4 AARCH_64) 33 - endif() 34 - endif() 35 25 36 26 # The compiler must make no assumptions about the build. 37 27 set_target_properties(${KERNEL}.elf PROPERTIES LINK_FLAGS "-nostdlib -nostartfiles")
+16 -14
os/include/common/stdlib.h
··· 3 3 * @brief Implement basic functionality of the stdint-C-library. 4 4 */ 5 5 6 + #include <stddef.h> // defines NULL and size_t 7 + #include <stdint.h> 6 8 #ifndef STDLIB_H 7 9 #define STDLIB_H 8 10 9 - #include <stddef.h> // defines NULL and size_t 11 + #define MIN(x,y) ((x < y ? x : y)) 12 + #define MAX(x,y) ((x < y ? y : x)) 13 + 14 + typedef struct divmod_result { 15 + uint32_t div; 16 + uint32_t mod; 17 + } divmod_t; 18 + 19 + divmod_t divmod(uint32_t dividend, uint32_t divisor); 20 + uint32_t div(uint32_t dividend, uint32_t divisor); 10 21 11 22 /** 12 23 * @brief Fills the first @a n bytes of the memory area pointed to by @a s with the constant byte @a c. 13 24 * @return A pointer to the memory area s. 14 25 */ 15 - void* memset(void* s, int c, size_t n); 26 + void* memset(void * dest, int c, unsigned int bytes); 16 27 17 28 /** 18 29 * @brief Copies @a n bytes from memory area @a src to memory area @a dest. The memory areas must not overlap. 19 30 * @return A pointer to dest. 20 31 */ 21 - void* memcpy(void* dest, const void* src, size_t n); 32 + void* memcpy(void * dest, const void * src, unsigned int bytes); 22 33 23 34 /** 24 35 * @brief int -> str(int) ··· 28 39 * @param value Value to be converted to a string. 29 40 * @return A pointer to the resulting null-terminated string. 30 41 */ 31 - char* itoa(int value); 42 + char* itoa(int value, int base); 32 43 33 - /* 34 - * Converts an int to a null-terminated string using the specified base. 35 - * @param value Value to be converted to a string. 36 - * @param base Numerical base used to represent the value as a string. 37 - * Where 10 means decimal base, 16 hexadecimal, 8 octal, and 2 binary. 38 - * (Only base 10 supported for now) 39 - * @return A pointer to the resulting null-terminated string. 40 - */ 41 - // char *itoa(int value, int base); 42 44 43 45 /** 44 46 * @brief str -> int ··· 48 50 * @return The converted integral number as an int value. 49 51 * If no valid conversion could be performed, it returns zero. 50 52 */ 51 - int atoi(const char* str); 53 + int atoi(char* str); 52 54 53 55 54 56 /**
+1 -1
os/include/common/string.h
··· 3 3 * @brief Some basic functions to manipulate strings. 4 4 */ 5 5 6 + #include <stddef.h> // defines NULL and size_t 6 7 #ifndef STRING_H 7 8 #define STRING_H 8 9 9 - #include <stddef.h> // defines NULL and size_t 10 10 11 11 /** 12 12 * @brief Calculates the length of the string pointed to by @a s, excluding the terminating null byte ('\0').
+2 -3
os/include/kernel/atag.h
··· 1 + #include <stdint.h> 2 + 1 3 #ifndef ATAG_H 2 4 #define ATAG_H 3 - 4 - #include <stdint.h> 5 - 6 5 7 6 typedef enum { 8 7 NONE = 0x00000000,
+138
os/include/kernel/chars_pixels.h
··· 1 + #include <stdint.h> 2 + #ifndef CHAR_BMPS_H 3 + #define CHAR_BMPS_H 4 + /* From https://github.com/dhepper/font8x8/blob/master/font8x8_block.h */ 5 + const uint8_t * font(int c) { 6 + static const char f[128][8] = { 7 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0000 (nul) 8 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0001 9 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0002 10 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0003 11 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0004 12 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0005 13 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0006 14 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0007 15 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0008 16 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0009 17 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+000A 18 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+000B 19 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+000C 20 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+000D 21 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+000E 22 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+000F 23 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0010 24 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0011 25 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0012 26 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0013 27 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0014 28 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0015 29 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0016 30 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0017 31 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0018 32 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0019 33 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+001A 34 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+001B 35 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+001C 36 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+001D 37 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+001E 38 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+001F 39 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0020 (space) 40 + { 0x18, 0x3C, 0x3C, 0x18, 0x18, 0x00, 0x18, 0x00}, // U+0021 (!) 41 + { 0x36, 0x36, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0022 (") 42 + { 0x36, 0x36, 0x7F, 0x36, 0x7F, 0x36, 0x36, 0x00}, // U+0023 (#) 43 + { 0x0C, 0x3E, 0x03, 0x1E, 0x30, 0x1F, 0x0C, 0x00}, // U+0024 ($) 44 + { 0x00, 0x63, 0x33, 0x18, 0x0C, 0x66, 0x63, 0x00}, // U+0025 (%) 45 + { 0x1C, 0x36, 0x1C, 0x6E, 0x3B, 0x33, 0x6E, 0x00}, // U+0026 (&) 46 + { 0x06, 0x06, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0027 (') 47 + { 0x18, 0x0C, 0x06, 0x06, 0x06, 0x0C, 0x18, 0x00}, // U+0028 (() 48 + { 0x06, 0x0C, 0x18, 0x18, 0x18, 0x0C, 0x06, 0x00}, // U+0029 ()) 49 + { 0x00, 0x66, 0x3C, 0xFF, 0x3C, 0x66, 0x00, 0x00}, // U+002A (*) 50 + { 0x00, 0x0C, 0x0C, 0x3F, 0x0C, 0x0C, 0x00, 0x00}, // U+002B (+) 51 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x0C, 0x0C, 0x06}, // U+002C (,) 52 + { 0x00, 0x00, 0x00, 0x3F, 0x00, 0x00, 0x00, 0x00}, // U+002D (-) 53 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x0C, 0x0C, 0x00}, // U+002E (.) 54 + { 0x60, 0x30, 0x18, 0x0C, 0x06, 0x03, 0x01, 0x00}, // U+002F (/) 55 + { 0x3E, 0x63, 0x73, 0x7B, 0x6F, 0x67, 0x3E, 0x00}, // U+0030 (0) 56 + { 0x0C, 0x0E, 0x0C, 0x0C, 0x0C, 0x0C, 0x3F, 0x00}, // U+0031 (1) 57 + { 0x1E, 0x33, 0x30, 0x1C, 0x06, 0x33, 0x3F, 0x00}, // U+0032 (2) 58 + { 0x1E, 0x33, 0x30, 0x1C, 0x30, 0x33, 0x1E, 0x00}, // U+0033 (3) 59 + { 0x38, 0x3C, 0x36, 0x33, 0x7F, 0x30, 0x78, 0x00}, // U+0034 (4) 60 + { 0x3F, 0x03, 0x1F, 0x30, 0x30, 0x33, 0x1E, 0x00}, // U+0035 (5) 61 + { 0x1C, 0x06, 0x03, 0x1F, 0x33, 0x33, 0x1E, 0x00}, // U+0036 (6) 62 + { 0x3F, 0x33, 0x30, 0x18, 0x0C, 0x0C, 0x0C, 0x00}, // U+0037 (7) 63 + { 0x1E, 0x33, 0x33, 0x1E, 0x33, 0x33, 0x1E, 0x00}, // U+0038 (8) 64 + { 0x1E, 0x33, 0x33, 0x3E, 0x30, 0x18, 0x0E, 0x00}, // U+0039 (9) 65 + { 0x00, 0x0C, 0x0C, 0x00, 0x00, 0x0C, 0x0C, 0x00}, // U+003A (:) 66 + { 0x00, 0x0C, 0x0C, 0x00, 0x00, 0x0C, 0x0C, 0x06}, // U+003B (//) 67 + { 0x18, 0x0C, 0x06, 0x03, 0x06, 0x0C, 0x18, 0x00}, // U+003C (<) 68 + { 0x00, 0x00, 0x3F, 0x00, 0x00, 0x3F, 0x00, 0x00}, // U+003D (=) 69 + { 0x06, 0x0C, 0x18, 0x30, 0x18, 0x0C, 0x06, 0x00}, // U+003E (>) 70 + { 0x1E, 0x33, 0x30, 0x18, 0x0C, 0x00, 0x0C, 0x00}, // U+003F (?) 71 + { 0x3E, 0x63, 0x7B, 0x7B, 0x7B, 0x03, 0x1E, 0x00}, // U+0040 (@) 72 + { 0x0C, 0x1E, 0x33, 0x33, 0x3F, 0x33, 0x33, 0x00}, // U+0041 (A) 73 + { 0x3F, 0x66, 0x66, 0x3E, 0x66, 0x66, 0x3F, 0x00}, // U+0042 (B) 74 + { 0x3C, 0x66, 0x03, 0x03, 0x03, 0x66, 0x3C, 0x00}, // U+0043 (C) 75 + { 0x1F, 0x36, 0x66, 0x66, 0x66, 0x36, 0x1F, 0x00}, // U+0044 (D) 76 + { 0x7F, 0x46, 0x16, 0x1E, 0x16, 0x46, 0x7F, 0x00}, // U+0045 (E) 77 + { 0x7F, 0x46, 0x16, 0x1E, 0x16, 0x06, 0x0F, 0x00}, // U+0046 (F) 78 + { 0x3C, 0x66, 0x03, 0x03, 0x73, 0x66, 0x7C, 0x00}, // U+0047 (G) 79 + { 0x33, 0x33, 0x33, 0x3F, 0x33, 0x33, 0x33, 0x00}, // U+0048 (H) 80 + { 0x1E, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x1E, 0x00}, // U+0049 (I) 81 + { 0x78, 0x30, 0x30, 0x30, 0x33, 0x33, 0x1E, 0x00}, // U+004A (J) 82 + { 0x67, 0x66, 0x36, 0x1E, 0x36, 0x66, 0x67, 0x00}, // U+004B (K) 83 + { 0x0F, 0x06, 0x06, 0x06, 0x46, 0x66, 0x7F, 0x00}, // U+004C (L) 84 + { 0x63, 0x77, 0x7F, 0x7F, 0x6B, 0x63, 0x63, 0x00}, // U+004D (M) 85 + { 0x63, 0x67, 0x6F, 0x7B, 0x73, 0x63, 0x63, 0x00}, // U+004E (N) 86 + { 0x1C, 0x36, 0x63, 0x63, 0x63, 0x36, 0x1C, 0x00}, // U+004F (O) 87 + { 0x3F, 0x66, 0x66, 0x3E, 0x06, 0x06, 0x0F, 0x00}, // U+0050 (P) 88 + { 0x1E, 0x33, 0x33, 0x33, 0x3B, 0x1E, 0x38, 0x00}, // U+0051 (Q) 89 + { 0x3F, 0x66, 0x66, 0x3E, 0x36, 0x66, 0x67, 0x00}, // U+0052 (R) 90 + { 0x1E, 0x33, 0x07, 0x0E, 0x38, 0x33, 0x1E, 0x00}, // U+0053 (S) 91 + { 0x3F, 0x2D, 0x0C, 0x0C, 0x0C, 0x0C, 0x1E, 0x00}, // U+0054 (T) 92 + { 0x33, 0x33, 0x33, 0x33, 0x33, 0x33, 0x3F, 0x00}, // U+0055 (U) 93 + { 0x33, 0x33, 0x33, 0x33, 0x33, 0x1E, 0x0C, 0x00}, // U+0056 (V) 94 + { 0x63, 0x63, 0x63, 0x6B, 0x7F, 0x77, 0x63, 0x00}, // U+0057 (W) 95 + { 0x63, 0x63, 0x36, 0x1C, 0x1C, 0x36, 0x63, 0x00}, // U+0058 (X) 96 + { 0x33, 0x33, 0x33, 0x1E, 0x0C, 0x0C, 0x1E, 0x00}, // U+0059 (Y) 97 + { 0x7F, 0x63, 0x31, 0x18, 0x4C, 0x66, 0x7F, 0x00}, // U+005A (Z) 98 + { 0x1E, 0x06, 0x06, 0x06, 0x06, 0x06, 0x1E, 0x00}, // U+005B ([) 99 + { 0x03, 0x06, 0x0C, 0x18, 0x30, 0x60, 0x40, 0x00}, // U+005C (\) 100 + { 0x1E, 0x18, 0x18, 0x18, 0x18, 0x18, 0x1E, 0x00}, // U+005D (]) 101 + { 0x08, 0x1C, 0x36, 0x63, 0x00, 0x00, 0x00, 0x00}, // U+005E (^) 102 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF}, // U+005F (_) 103 + { 0x0C, 0x0C, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+0060 (`) 104 + { 0x00, 0x00, 0x1E, 0x30, 0x3E, 0x33, 0x6E, 0x00}, // U+0061 (a) 105 + { 0x07, 0x06, 0x06, 0x3E, 0x66, 0x66, 0x3B, 0x00}, // U+0062 (b) 106 + { 0x00, 0x00, 0x1E, 0x33, 0x03, 0x33, 0x1E, 0x00}, // U+0063 (c) 107 + { 0x38, 0x30, 0x30, 0x3e, 0x33, 0x33, 0x6E, 0x00}, // U+0064 (d) 108 + { 0x00, 0x00, 0x1E, 0x33, 0x3f, 0x03, 0x1E, 0x00}, // U+0065 (e) 109 + { 0x1C, 0x36, 0x06, 0x0f, 0x06, 0x06, 0x0F, 0x00}, // U+0066 (f) 110 + { 0x00, 0x00, 0x6E, 0x33, 0x33, 0x3E, 0x30, 0x1F}, // U+0067 (g) 111 + { 0x07, 0x06, 0x36, 0x6E, 0x66, 0x66, 0x67, 0x00}, // U+0068 (h) 112 + { 0x0C, 0x00, 0x0E, 0x0C, 0x0C, 0x0C, 0x1E, 0x00}, // U+0069 (i) 113 + { 0x30, 0x00, 0x30, 0x30, 0x30, 0x33, 0x33, 0x1E}, // U+006A (j) 114 + { 0x07, 0x06, 0x66, 0x36, 0x1E, 0x36, 0x67, 0x00}, // U+006B (k) 115 + { 0x0E, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x1E, 0x00}, // U+006C (l) 116 + { 0x00, 0x00, 0x33, 0x7F, 0x7F, 0x6B, 0x63, 0x00}, // U+006D (m) 117 + { 0x00, 0x00, 0x1F, 0x33, 0x33, 0x33, 0x33, 0x00}, // U+006E (n) 118 + { 0x00, 0x00, 0x1E, 0x33, 0x33, 0x33, 0x1E, 0x00}, // U+006F (o) 119 + { 0x00, 0x00, 0x3B, 0x66, 0x66, 0x3E, 0x06, 0x0F}, // U+0070 (p) 120 + { 0x00, 0x00, 0x6E, 0x33, 0x33, 0x3E, 0x30, 0x78}, // U+0071 (q) 121 + { 0x00, 0x00, 0x3B, 0x6E, 0x66, 0x06, 0x0F, 0x00}, // U+0072 (r) 122 + { 0x00, 0x00, 0x3E, 0x03, 0x1E, 0x30, 0x1F, 0x00}, // U+0073 (s) 123 + { 0x08, 0x0C, 0x3E, 0x0C, 0x0C, 0x2C, 0x18, 0x00}, // U+0074 (t) 124 + { 0x00, 0x00, 0x33, 0x33, 0x33, 0x33, 0x6E, 0x00}, // U+0075 (u) 125 + { 0x00, 0x00, 0x33, 0x33, 0x33, 0x1E, 0x0C, 0x00}, // U+0076 (v) 126 + { 0x00, 0x00, 0x63, 0x6B, 0x7F, 0x7F, 0x36, 0x00}, // U+0077 (w) 127 + { 0x00, 0x00, 0x63, 0x36, 0x1C, 0x36, 0x63, 0x00}, // U+0078 (x) 128 + { 0x00, 0x00, 0x33, 0x33, 0x33, 0x3E, 0x30, 0x1F}, // U+0079 (y) 129 + { 0x00, 0x00, 0x3F, 0x19, 0x0C, 0x26, 0x3F, 0x00}, // U+007A (z) 130 + { 0x38, 0x0C, 0x0C, 0x07, 0x0C, 0x0C, 0x38, 0x00}, // U+007B ({) 131 + { 0x18, 0x18, 0x18, 0x00, 0x18, 0x18, 0x18, 0x00}, // U+007C (|) 132 + { 0x07, 0x0C, 0x0C, 0x38, 0x0C, 0x0C, 0x07, 0x00}, // U+007D (}) 133 + { 0x6E, 0x3B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, // U+007E (~) 134 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00} // U+007F 135 + }; 136 + return (uint8_t *)f[c]; 137 + } 138 + #endif
+24
os/include/kernel/framebuffer.h
··· 1 + #include <stdint.h> 2 + #ifndef FRAMEBUFFER_H 3 + #define FRAMEBUFFER_H 4 + 5 + #define COLORDEPTH 24 6 + #define BYTES_PER_PIXEL COLORDEPTH/8 7 + 8 + typedef struct framebuffer_info { 9 + uint32_t width; 10 + uint32_t height; 11 + uint32_t pitch; 12 + void * buf; 13 + uint32_t buf_size; 14 + uint32_t chars_width; 15 + uint32_t chars_height; 16 + uint32_t chars_x; 17 + uint32_t chars_y; 18 + } framebuffer_info_t; 19 + 20 + extern framebuffer_info_t fbinfo; 21 + 22 + int framebuffer_init(void); 23 + 24 + #endif // FRAMEBUFFER_H
+20
os/include/kernel/gpu.h
··· 1 + #include <stdint.h> 2 + #ifndef GPU_H 3 + #define GPU_H 4 + 5 + #define CHAR_WIDTH 8 6 + #define CHAR_HEIGHT 8 7 + 8 + typedef struct pixel { 9 + uint8_t red; 10 + uint8_t green; 11 + uint8_t blue; 12 + } pixel_t; 13 + 14 + void gpu_init(void); 15 + 16 + void write_pixel(uint32_t x, uint32_t y, const pixel_t * pixel); 17 + 18 + void gpu_putc(char c); 19 + 20 + #endif
+15
os/include/kernel/kerio.h
··· 1 + #ifndef STDIO_H 2 + #define STDIO_H 3 + 4 + char getc(void); 5 + void putc(char c); 6 + 7 + void puts(const char * s); 8 + 9 + // This version of gets copies until newline, replacing newline with null char, or until buflen. 10 + // whichever comes first 11 + void gets(char * buf, int buflen); 12 + 13 + void printf(const char * fmt, ...); 14 + 15 + #endif
+108
os/include/kernel/mailbox.h
··· 1 + #include <stdint.h> 2 + #include "peripherals/base.h" 3 + #ifndef MAILBOX_H 4 + #define MAILBOX_H 5 + 6 + #define MAILBOX_OFFSET 0xB880 7 + 8 + #define MAILBOX_BASE MMIO_BASE + MAILBOX_OFFSET 9 + #define MAIL0_READ (((mail_message_t *)(0x00 + MAILBOX_BASE))) 10 + #define MAIL0_STATUS (((mail_status_t *)(0x18 + MAILBOX_BASE))) 11 + #define MAIL0_WRITE (((mail_message_t *)(0x20 + MAILBOX_BASE))) 12 + #define PROPERTY_CHANNEL 8 13 + #define FRAMEBUFFER_CHANNEL 1 14 + 15 + typedef struct { 16 + uint8_t channel: 4; 17 + uint32_t data: 28; 18 + } mail_message_t; 19 + 20 + typedef struct { 21 + uint32_t reserved: 30; 22 + uint8_t empty: 1; 23 + uint8_t full:1; 24 + } mail_status_t; 25 + 26 + mail_message_t mailbox_read(int channel); 27 + void mailbox_send(mail_message_t msg, int channel); 28 + 29 + /** 30 + * A property message can either be a request, or a response, and a response can be successfull or an error 31 + */ 32 + typedef enum { 33 + REQUEST = 0x00000000, 34 + RESPONSE_SUCCESS = 0x80000000, 35 + RESPONSE_ERROR = 0x80000001 36 + } buffer_req_res_code_t; 37 + 38 + 39 + /* 40 + * A buffer that holds many property messages. 41 + * The last tag must be a 4 byte zero, and then padding to make the whole thing 4 byte aligned 42 + */ 43 + typedef struct { 44 + uint32_t size; // Size includes the size itself 45 + buffer_req_res_code_t req_res_code; 46 + uint32_t tags[1]; // A concatenated sequence of tags. will use overrun to make large enough 47 + } property_message_buffer_t; 48 + 49 + 50 + /** 51 + * A message is identified by a tag. These are some of the possible tags 52 + */ 53 + typedef enum { 54 + NULL_TAG = 0, 55 + FB_ALLOCATE_BUFFER = 0x00040001, 56 + FB_RELESE_BUFFER = 0x00048001, 57 + FB_GET_PHYSICAL_DIMENSIONS = 0x00040003, 58 + FB_SET_PHYSICAL_DIMENSIONS = 0x00048003, 59 + FB_GET_VIRTUAL_DIMENSIONS = 0x00040004, 60 + FB_SET_VIRTUAL_DIMENSIONS = 0x00048004, 61 + FB_GET_BITS_PER_PIXEL = 0x00040005, 62 + FB_SET_BITS_PER_PIXEL = 0x00048005, 63 + FB_GET_BYTES_PER_ROW = 0x00040008 64 + } property_tag_t; 65 + 66 + /** 67 + * For each possible tag, we create a struct corresponding to the request value buffer, and the response value buffer 68 + */ 69 + 70 + typedef struct { 71 + void * fb_addr; 72 + uint32_t fb_size; 73 + } fb_allocate_res_t; 74 + 75 + typedef struct { 76 + uint32_t width; 77 + uint32_t height; 78 + } fb_screen_size_t; 79 + 80 + 81 + /* 82 + * The value buffer can be any one of these types 83 + */ 84 + typedef union { 85 + uint32_t fb_allocate_align; 86 + fb_allocate_res_t fb_allocate_res; 87 + fb_screen_size_t fb_screen_size; 88 + uint32_t fb_bits_per_pixel; 89 + uint32_t fb_bytes_per_row; 90 + } value_buffer_t; 91 + 92 + /* 93 + * A message_buffer can contain any number of these 94 + */ 95 + typedef struct { 96 + property_tag_t proptag; 97 + value_buffer_t value_buffer; 98 + } property_message_tag_t; 99 + 100 + 101 + /** 102 + * given an array of tags, will send all of the tags given, and will populate that array with the responses. 103 + * the given array should end with a "null tag" with the proptag field set to 0. 104 + * returns 0 on success 105 + */ 106 + int send_messages(property_message_tag_t * tags); 107 + 108 + #endif // MAILBOX_H
+2 -3
os/include/kernel/memory.h
··· 1 - #ifndef MEMORY_H 2 - #define MEMORY_H 3 - 4 1 #include <stdint.h> 5 2 #include "atag.h" 6 3 #include "list.h" 4 + #ifndef MEMORY_H 5 + #define MEMORY_H 7 6 8 7 #define PAGE_SIZE 4096 9 8 #define KERNEL_HEAP_SIZE (1024*1024)
-1
os/include/kernel/mmio.h
··· 4 4 * 5 5 * Reading and writing from/to Memory Mapped IO. 6 6 */ 7 - 8 7 #include <stdint.h> 9 8 10 9 #ifndef MMIO_H
+1 -2
os/include/peripherals/aux.h
··· 6 6 * > Also all three are controlled by the auxiliary enable register. 7 7 */ 8 8 9 + #include "gpio.h" 9 10 #ifndef AUX_H 10 11 #define AUX_H 11 - 12 - #include "gpio.h" 13 12 14 13 /** 15 14 * @brief Enum containg all the relevant addresses. The offset is again the same for all RPi's, but the base address is not.
+1 -1
os/include/peripherals/base.h
··· 17 17 * 18 18 */ 19 19 enum { 20 - #ifdef MODEL_0 20 + #if MODEL_0 || MODEL_1 21 21 /** For raspi 0,1 */ 22 22 MMIO_BASE = 0x20000000 23 23 #elif MODEL_2 || MODEL_3
+2 -3
os/include/peripherals/gpio.h
··· 3 3 * @brief GIPO addresses for the different RPi's 4 4 */ 5 5 6 + #include "base.h" 6 7 #ifndef GPIO_H 7 8 #define GPIO_H 8 - 9 - #include "base.h" 10 9 11 10 /** 12 11 * GPIO Pins available functionalities: 5 Alternative Functions, Input, Output. ··· 69 68 GPAFEN0 = (GPIO_BASE + 0x88), /**< GPIO Pin Async. Falling Edge Detect 0 */ 70 69 GPAFEN1 = (GPIO_BASE + 0x8C), /**< GPIO Pin Async. Falling Edge Detect 1 */ 71 70 72 - #if defined(MODEL_0) || defined(MODEL_2) || defined(MODEL_3) 71 + #if defined(MODEL_0) || defined(MODEL_1) || defined(MODEL_2) || defined(MODEL_3) 73 72 /** 74 73 * GPIO Pin Pull-up/down Enable 75 74 * Controls actuation of pull up/down to ALL GPIO pins
+17
os/include/peripherals/mailbox.h
··· 1 + #include "base.h" 2 + #ifndef P_MBOX_H 3 + #define P_MBOX_H 4 + 5 + /** 6 + * \ingroup peripherals 7 + * The offsets for Mailbox registers (For raspi 3,4). 8 + */ 9 + enum 10 + { 11 + MBOX_BASE = (MMIO_BASE + 0xB880), /**< The base address for Mailbox registers */ 12 + MBOX_READ = (MBOX_BASE + 0x00), /**< Reads messages from the GPU */ 13 + MBOX_STATUS = (MBOX_BASE + 0x18), /**< Status for READ and WRITE registers */ 14 + MBOX_WRITE = (MBOX_BASE + 0x20) /**< Writes messages to the GPU */ 15 + }; 16 + 17 + #endif
+124 -51
os/src/common/stdlib.c
··· 1 1 #include "common/stdlib.h" 2 2 #include "common/string.h" 3 3 4 - char* itoa(int value) 5 - { 6 - int i, sign; 4 + #include <stdint.h> 7 5 8 - /* Declare as static in order to return it */ 9 - static char s[21]; // Biggest int, 10 digits long 6 + // raspi model 1 does not have division instruction, so we need to define our own 7 + __inline__ uint32_t div(uint32_t dividend, uint32_t divisor) { 8 + #ifdef MODEL_1 9 + // Use long division, but in binary. Copied from Stack overflow... 10 + uint32_t denom=divisor; 11 + uint32_t current = 1; 12 + uint32_t answer=0; 10 13 11 - sign = value; 12 - if (value < 0) 13 - value = -value; 14 - 15 - i = 0; 14 + if ( denom > dividend) 15 + return 0; 16 16 17 - // digits are in reverse order 18 - do 19 - { 20 - s[i] = value % 10 + '0'; // (int)'0'==48; 21 - i++; 22 - value/=10; 23 - } while (value > 0); 17 + if ( denom == dividend) 18 + return 1; 24 19 25 - if (sign < 0) { 26 - s[i] = '-'; 27 - i++; 28 - } 29 - s[i] = '\0'; 20 + while (denom <= dividend) { 21 + denom <<= 1; 22 + current <<= 1; 23 + } 30 24 31 - strrev(s); 25 + denom >>= 1; 26 + current >>= 1; 32 27 33 - return s; 28 + while (current!=0) { 29 + if ( dividend >= denom) { 30 + dividend -= denom; 31 + answer |= current; 32 + } 33 + current >>= 1; 34 + denom >>= 1; 35 + } 36 + return answer; 37 + #else 38 + return dividend / divisor; 39 + #endif 34 40 } 35 41 36 - int atoi(const char* str) 37 - { 38 - int num = 0; 39 - 40 - while ((*str != '\0') && (*str >= '0' && *str <= '9')) { 41 - num = num * 10 + (*str - '0'); 42 - str++; 43 - } 42 + __inline__ divmod_t divmod(uint32_t dividend, uint32_t divisor) { 43 + divmod_t res; 44 + #ifdef MODEL_1 45 + res.div = div(dividend, divisor); 46 + res.mod = dividend - res.div*divisor; 47 + #else 48 + res.div = dividend / divisor; 49 + res.mod = dividend % divisor; 50 + #endif 51 + return res; 52 + } 44 53 45 - return num; 54 + void* memcpy(void * dest, const void * src, unsigned int bytes) { 55 + char * d = dest; 56 + const char * s = src; 57 + while (bytes--) { 58 + *d++ = *s++; 59 + } 60 + return dest; 46 61 } 47 62 48 63 void bzero(void * dest, int bytes) { 49 64 memset(dest, 0, bytes); 50 65 } 51 66 52 - void* memset(void* s, int c, size_t n) 53 - { 54 - unsigned char* dst = s; 67 + void* memset(void * dest, int c, unsigned int bytes) { 68 + uint8_t * d = dest; 69 + while (bytes--) { 70 + *d++ = c; 71 + } 72 + return dest; 73 + } 74 + 75 + char * itoa(int num, int base) { 76 + static char intbuf[33]; 77 + uint32_t j = 0, isneg = 0, i; 78 + divmod_t divmod_res; 55 79 56 - while(n>0) 57 - { 58 - *dst = (unsigned char) c; 59 - dst++; 60 - n--; 80 + if (num == 0) { 81 + intbuf[0] = '0'; 82 + intbuf[1] = '\0'; 83 + return intbuf; 84 + } 85 + 86 + if (base == 10 && num < 0) { 87 + isneg = 1; 88 + num = -num; 89 + } 90 + 91 + i = (uint32_t) num; 92 + 93 + while (i != 0) { 94 + divmod_res = divmod(i,base); 95 + intbuf[j++] = (divmod_res.mod) < 10 ? '0' + (divmod_res.mod) : 'a' + (divmod_res.mod) - 10; 96 + i = divmod_res.div; 97 + } 98 + 99 + if (isneg) 100 + intbuf[j++] = '-'; 101 + 102 + if (base == 16) { 103 + intbuf[j++] = 'x'; 104 + intbuf[j++] = '0'; 105 + } else if(base == 8) { 106 + intbuf[j++] = '0'; 107 + } else if(base == 2) { 108 + intbuf[j++] = 'b'; 109 + intbuf[j++] = '0'; 110 + } 111 + 112 + intbuf[j] = '\0'; 113 + j--; 114 + i = 0; 115 + while (i < j) { 116 + isneg = intbuf[i]; 117 + intbuf[i] = intbuf[j]; 118 + intbuf[j] = isneg; 119 + i++; 120 + j--; 61 121 } 62 - return s; 122 + 123 + return intbuf; 63 124 } 64 125 65 - void* memcpy(void* dest, const void* src, size_t n) 66 - { 67 - char* d = (char *) dest; 68 - const char *s = (const char*) src; 126 + int atoi(char * num) { 127 + int res = 0, power = 0, digit, i; 128 + char * start = num; 129 + 130 + // Find the end 131 + while (*num >= '0' && *num <= '9') { 132 + num++; 133 + } 134 + 135 + num--; 136 + 137 + while (num != start) { 138 + digit = *num - '0'; 139 + for (i = 0; i < power; i++) { 140 + digit *= 10; 141 + } 142 + res += digit; 143 + power++; 144 + num--; 145 + } 69 146 70 - while (n > 0) { 71 - *(d++) = *(s++); 72 - n--; 73 - } 74 - return dest; 147 + return res; 75 148 }
+1 -1
os/src/kernel/atag.c
··· 7 7 } 8 8 tag = (atag_t *)((uint32_t *)tag + tag->tag_size); // Cast back to avoid compiler warning 9 9 } 10 - return 1024*1024*512; 10 + return 0; 11 11 }
+229
os/src/kernel/framebuffer.c
··· 1 + #include "kernel/framebuffer.h" 2 + 3 + #include "kernel/mailbox.h" 4 + #include "kernel/gpu.h" 5 + #include "kernel/memory.h" 6 + 7 + framebuffer_info_t fbinfo; 8 + 9 + #if MODEL_0 || MODEL_1 10 + typedef struct { 11 + uint32_t width; 12 + uint32_t height; 13 + uint32_t vwidth; 14 + uint32_t vheight; 15 + uint32_t bytes; 16 + uint32_t depth; 17 + uint32_t ignorex; 18 + uint32_t ignorey; 19 + void * pointer; 20 + uint32_t size; 21 + } fb_init_t; 22 + 23 + fb_init_t fbinit __attribute__((aligned(16))); 24 + 25 + int framebuffer_init(void) { 26 + mail_message_t msg; 27 + 28 + fbinit.width = 640; 29 + fbinit.height = 480; 30 + fbinit.vwidth = fbinit.width; 31 + fbinit.vheight = fbinit.height; 32 + fbinit.depth = COLORDEPTH; 33 + 34 + msg.data = ((uint32_t)&fbinit + 0x40000000) >> 4; 35 + 36 + mailbox_send(msg, FRAMEBUFFER_CHANNEL); 37 + msg = mailbox_read(FRAMEBUFFER_CHANNEL); 38 + 39 + if (!msg.data) 40 + return -1; 41 + 42 + fbinfo.width = fbinit.width; 43 + fbinfo.height = fbinit.height; 44 + fbinfo.chars_width = fbinfo.width / CHAR_WIDTH; 45 + fbinfo.chars_height = fbinfo.height / CHAR_HEIGHT; 46 + fbinfo.chars_x = 0; 47 + fbinfo.chars_y = 0; 48 + fbinfo.pitch = fbinit.bytes; 49 + fbinfo.buf = fbinit.pointer; 50 + fbinfo.buf_size = fbinit.size; 51 + 52 + return 0; 53 + } 54 + 55 + #elif MODEL_2 || MODEL_3 || MODEL_4 56 + 57 + typedef enum { 58 + NULL_TAG = 0, 59 + FB_ALLOCATE_BUFFER = 0x00040001, 60 + FB_RELESE_BUFFER = 0x00048001, 61 + FB_GET_PHYSICAL_DIMENSIONS = 0x00040003, 62 + FB_SET_PHYSICAL_DIMENSIONS = 0x00048003, 63 + FB_GET_VIRTUAL_DIMENSIONS = 0x00040004, 64 + FB_SET_VIRTUAL_DIMENSIONS = 0x00048004, 65 + FB_GET_BITS_PER_PIXEL = 0x00040005, 66 + FB_SET_BITS_PER_PIXEL = 0x00048005, 67 + FB_GET_BYTES_PER_ROW = 0x00040008 68 + } property_tag_t; 69 + 70 + typedef struct { 71 + void * fb_addr; 72 + uint32_t fb_size; 73 + } fb_allocate_res_t; 74 + 75 + typedef struct { 76 + uint32_t width; 77 + uint32_t height; 78 + } fb_screen_size_t; 79 + 80 + /* 81 + * The value buffer can be any one of these types 82 + */ 83 + typedef union { 84 + uint32_t fb_allocate_align; 85 + fb_allocate_res_t fb_allocate_res; 86 + fb_screen_size_t fb_screen_size; 87 + uint32_t fb_bits_per_pixel; 88 + uint32_t fb_bytes_per_row; 89 + } value_buffer_t; 90 + 91 + /* 92 + * A message_buffer can contain any number of these 93 + */ 94 + typedef struct { 95 + property_tag_t proptag; 96 + value_buffer_t value_buffer; 97 + } property_message_tag_t; 98 + 99 + static uint32_t get_value_buffer_len(property_message_tag_t * tag) { 100 + switch(tag->proptag) { 101 + case FB_ALLOCATE_BUFFER: 102 + case FB_GET_PHYSICAL_DIMENSIONS: 103 + case FB_SET_PHYSICAL_DIMENSIONS: 104 + case FB_GET_VIRTUAL_DIMENSIONS: 105 + case FB_SET_VIRTUAL_DIMENSIONS: 106 + return 8; 107 + case FB_GET_BITS_PER_PIXEL: 108 + case FB_SET_BITS_PER_PIXEL: 109 + case FB_GET_BYTES_PER_ROW: 110 + return 4; 111 + case FB_RELESE_BUFFER: 112 + default: 113 + return 0; 114 + } 115 + } 116 + 117 + int send_messages(property_message_tag_t * tags) { 118 + property_message_buffer_t * msg; 119 + mail_message_t mail; 120 + uint32_t bufsize = 0, i, len, bufpos; 121 + 122 + // Calculate the sizes of each tag 123 + for (i = 0; tags[i].proptag != NULL_TAG; i++) { 124 + bufsize += get_value_buffer_len(&tags[i]) + 3*sizeof(uint32_t); 125 + } 126 + 127 + // Add the buffer size, buffer request/response code and buffer end tag sizes 128 + bufsize += 3*sizeof(uint32_t); 129 + 130 + // buffer size must be 16 byte aligned 131 + bufsize += (bufsize % 16) ? 16 - (bufsize % 16) : 0; 132 + 133 + // kmalloc returns a 16 byte aligned address 134 + msg = kmalloc(bufsize); 135 + if (!msg) 136 + return -1; 137 + 138 + msg->size = bufsize; 139 + msg->req_res_code = REQUEST; 140 + 141 + // Copy the messages into the buffer 142 + for (i = 0, bufpos = 0; tags[i].proptag != NULL_TAG; i++) { 143 + len = get_value_buffer_len(&tags[i]); 144 + msg->tags[bufpos++] = tags[i].proptag; 145 + msg->tags[bufpos++] = len; 146 + msg->tags[bufpos++] = 0; 147 + memcpy(msg->tags+bufpos, &tags[i].value_buffer, len); 148 + bufpos += len/4; 149 + } 150 + 151 + msg->tags[bufpos] = 0; 152 + 153 + // Send the message 154 + mail.data = ((uint32_t)msg) >>4; 155 + 156 + mailbox_send(mail, PROPERTY_CHANNEL); 157 + mail = mailbox_read(PROPERTY_CHANNEL); 158 + 159 + 160 + if (msg->req_res_code == REQUEST) { 161 + kfree(msg); 162 + return 1; 163 + } 164 + // Check the response code 165 + if (msg->req_res_code == RESPONSE_ERROR) { 166 + kfree(msg); 167 + return 2; 168 + } 169 + 170 + 171 + // Copy the tags back into the array 172 + for (i = 0, bufpos = 0; tags[i].proptag != NULL_TAG; i++) { 173 + len = get_value_buffer_len(&tags[i]); 174 + bufpos += 3; //skip over the tag bookkepping info 175 + memcpy(&tags[i].value_buffer, msg->tags+bufpos,len); 176 + bufpos += len/4; 177 + } 178 + 179 + kfree(msg); 180 + return 0; 181 + } 182 + 183 + int framebuffer_init(void) { 184 + property_message_tag_t tags[5]; 185 + 186 + 187 + tags[0].proptag = FB_SET_PHYSICAL_DIMENSIONS; 188 + tags[0].value_buffer.fb_screen_size.width = 640; 189 + tags[0].value_buffer.fb_screen_size.height = 480; 190 + tags[1].proptag = FB_SET_VIRTUAL_DIMENSIONS; 191 + tags[1].value_buffer.fb_screen_size.width = 640; 192 + tags[1].value_buffer.fb_screen_size.height = 480; 193 + tags[2].proptag = FB_SET_BITS_PER_PIXEL; 194 + tags[2].value_buffer.fb_bits_per_pixel = COLORDEPTH; 195 + tags[3].proptag = NULL_TAG; 196 + 197 + 198 + // Send over the initialization 199 + if (send_messages(tags) != 0) { 200 + return -1; 201 + } 202 + 203 + fbinfo.width = tags[0].value_buffer.fb_screen_size.width; 204 + fbinfo.height = tags[0].value_buffer.fb_screen_size.height; 205 + fbinfo.chars_width = fbinfo.width / CHAR_WIDTH; 206 + fbinfo.chars_height = fbinfo.height / CHAR_HEIGHT; 207 + fbinfo.chars_x = 0; 208 + fbinfo.chars_y = 0; 209 + fbinfo.pitch = fbinfo.width*BYTES_PER_PIXEL; 210 + 211 + // request a framebuffer 212 + tags[0].proptag = FB_ALLOCATE_BUFFER; 213 + tags[0].value_buffer.fb_screen_size.width = 0; 214 + tags[0].value_buffer.fb_screen_size.height = 0; 215 + tags[0].value_buffer.fb_allocate_align = 16; 216 + tags[1].proptag = NULL_TAG; 217 + 218 + 219 + if (send_messages(tags) != 0) { 220 + return -1; 221 + } 222 + 223 + fbinfo.buf = tags[0].value_buffer.fb_allocate_res.fb_addr; 224 + fbinfo.buf_size = tags[0].value_buffer.fb_allocate_res.fb_size; 225 + 226 + return 0; 227 + } 228 + 229 + #endif
+67
os/src/kernel/gpu.c
··· 1 + #include "kernel/framebuffer.h" 2 + #include "kernel/gpu.h" 3 + #include "kernel/memory.h" 4 + #include "kernel/kerio.h" 5 + #include "kernel/mailbox.h" 6 + #include "kernel/chars_pixels.h" 7 + #include "common/stdlib.h" 8 + 9 + 10 + void write_pixel(uint32_t x, uint32_t y, const pixel_t * pix) { 11 + uint8_t * location = fbinfo.buf + y*fbinfo.pitch + x*BYTES_PER_PIXEL; 12 + memcpy(location, pix, BYTES_PER_PIXEL); 13 + } 14 + 15 + void gpu_putc(char c) { 16 + static const pixel_t WHITE = {0xff, 0xff, 0xff}; 17 + static const pixel_t BLACK = {0x00, 0x00, 0x00}; 18 + uint8_t w,h; 19 + uint8_t mask; 20 + const uint8_t * bmp = font(c); 21 + uint32_t i, num_rows = fbinfo.height/CHAR_HEIGHT; 22 + 23 + // shift everything up one row 24 + if (fbinfo.chars_y >= num_rows) { 25 + // Copy a whole character row into the one above it 26 + for (i = 0; i < num_rows-1; i++) 27 + memcpy(fbinfo.buf + fbinfo.pitch*i*CHAR_HEIGHT, fbinfo.buf + fbinfo.pitch*(i+1)*CHAR_HEIGHT, fbinfo.pitch * CHAR_HEIGHT); 28 + // zero out the last row 29 + bzero(fbinfo.buf + fbinfo.pitch*i*CHAR_HEIGHT,fbinfo.pitch * CHAR_HEIGHT); 30 + fbinfo.chars_y--; 31 + } 32 + 33 + if (c == '\n') { 34 + fbinfo.chars_x = 0; 35 + fbinfo.chars_y++; 36 + return; 37 + } 38 + 39 + for(w = 0; w < CHAR_WIDTH; w++) { 40 + for(h = 0; h < CHAR_HEIGHT; h++) { 41 + mask = 1 << (w); 42 + if (bmp[h] & mask) 43 + write_pixel(fbinfo.chars_x*CHAR_WIDTH + w, fbinfo.chars_y*CHAR_HEIGHT + h, &WHITE); 44 + else 45 + write_pixel(fbinfo.chars_x*CHAR_WIDTH + w, fbinfo.chars_y*CHAR_HEIGHT + h, &BLACK); 46 + } 47 + } 48 + 49 + fbinfo.chars_x++; 50 + if (fbinfo.chars_x > fbinfo.chars_width) { 51 + fbinfo.chars_x = 0; 52 + fbinfo.chars_y++; 53 + } 54 + } 55 + 56 + void gpu_init(void) { 57 + static const pixel_t BLACK = {0x00, 0x00, 0x00}; 58 + // Aparantly, this sometimes does not work, so try in a loop 59 + while(framebuffer_init()); 60 + 61 + // clear screen 62 + for (uint32_t j = 0; j < fbinfo.height; j++) { 63 + for (uint32_t i = 0; i < fbinfo.width; i++) { 64 + write_pixel(i,j,&BLACK); 65 + } 66 + } 67 + }
+63
os/src/kernel/kerio.c
··· 1 + #include "kernel/kerio.h" 2 + 3 + #include "kernel/uart.h" 4 + #include "kernel/gpu.h" 5 + #include "common/stdlib.h" 6 + #include <stdarg.h> 7 + 8 + char getc(void) { 9 + return uart_getc(); 10 + } 11 + 12 + void putc(char c) { 13 + gpu_putc(c); 14 + } 15 + 16 + void puts(const char * str) { 17 + int i; 18 + for (i = 0; str[i] != '\0'; i ++) 19 + putc(str[i]); 20 + } 21 + 22 + void gets(char * buf, int buflen) { 23 + int i; 24 + char c; 25 + // Leave a spot for null char in buffer 26 + for (i = 0; (c = getc()) != '\r' && buflen > 1; i++, buflen--) { 27 + putc(c); 28 + buf[i] = c; 29 + } 30 + 31 + putc('\n'); 32 + if (c == '\n') { 33 + buf[i] = '\0'; 34 + } 35 + else 36 + buf[buflen-1] = '\0'; 37 + } 38 + 39 + void printf(const char * fmt, ...) { 40 + va_list args; 41 + va_start(args, fmt); 42 + 43 + for (; *fmt != '\0'; fmt++) { 44 + if (*fmt == '%') { 45 + switch (*(++fmt)) { 46 + case '%': 47 + putc('%'); 48 + break; 49 + case 'd': 50 + puts(itoa(va_arg(args, int), 10)); 51 + break; 52 + case 'x': 53 + puts(itoa(va_arg(args, int), 16)); 54 + break; 55 + case 's': 56 + puts(va_arg(args, char *)); 57 + break; 58 + } 59 + } else putc(*fmt); 60 + } 61 + 62 + va_end(args); 63 + }
+9 -5
os/src/kernel/kernel.c
··· 4 4 #include "common/string.h" 5 5 6 6 #include "kernel/memory.h" 7 - #include "kernel/uart.h" 7 + #include "kernel/kerio.h" 8 8 #include "kernel/atag.h" 9 + #include "kernel/gpu.h" 10 + #include "kernel/uart.h" 9 11 10 12 /*! 11 13 * @brief Entry point for the kernel ··· 21 23 { 22 24 23 25 mem_init((atag_t *)atags); 24 - uart_init(); 26 + gpu_init(); 25 27 26 - uart_puts("Welcome to piOS!\n"); 28 + puts("Welcome to piOS!\n\n"); 27 29 28 30 uint32_t mem_size = get_mem_size((atag_t *)atags); 29 - uart_puts(strcat("RAM size: ", itoa(mem_size/1024/1024))); 31 + printf("RAM size: %d\n", mem_size/1024/1024); 32 + 33 + puts("I han d Lea gern!"); 30 34 31 35 while(1) { 32 - uart_putc(uart_getc()); 36 + putc(getc()); 33 37 } 34 38 }
+121
os/src/kernel/mailbox.c
··· 1 + #include "kernel/mailbox.h" 2 + #include "common/stdlib.h" 3 + #include "kernel/memory.h" 4 + 5 + mail_message_t mailbox_read(int channel) { 6 + mail_status_t stat; 7 + mail_message_t res; 8 + 9 + // Make sure that the message is from the right channel 10 + do { 11 + // Make sure there is mail to recieve 12 + do { 13 + stat = *MAIL0_STATUS; 14 + } while (stat.empty); 15 + 16 + // Get the message 17 + res = *MAIL0_READ; 18 + } while (res.channel != channel); 19 + 20 + return res; 21 + } 22 + 23 + void mailbox_send(mail_message_t msg, int channel) { 24 + mail_status_t stat; 25 + msg.channel = channel; 26 + 27 + 28 + // Make sure you can send mail 29 + do { 30 + stat = *MAIL0_STATUS; 31 + } while (stat.full); 32 + 33 + // send the message 34 + *MAIL0_WRITE = msg; 35 + } 36 + 37 + /** 38 + * returns the max of the size of the request and result buffer for each tag 39 + */ 40 + static uint32_t get_value_buffer_len(property_message_tag_t * tag) { 41 + switch(tag->proptag) { 42 + case FB_ALLOCATE_BUFFER: 43 + case FB_GET_PHYSICAL_DIMENSIONS: 44 + case FB_SET_PHYSICAL_DIMENSIONS: 45 + case FB_GET_VIRTUAL_DIMENSIONS: 46 + case FB_SET_VIRTUAL_DIMENSIONS: 47 + return 8; 48 + case FB_GET_BITS_PER_PIXEL: 49 + case FB_SET_BITS_PER_PIXEL: 50 + case FB_GET_BYTES_PER_ROW: 51 + return 4; 52 + case FB_RELESE_BUFFER: 53 + default: 54 + return 0; 55 + } 56 + } 57 + 58 + int send_messages(property_message_tag_t * tags) { 59 + property_message_buffer_t * msg; 60 + mail_message_t mail; 61 + uint32_t bufsize = 0, i, len, bufpos; 62 + 63 + // Calculate the sizes of each tag 64 + for (i = 0; tags[i].proptag != NULL_TAG; i++) { 65 + bufsize += get_value_buffer_len(&tags[i]) + 3*sizeof(uint32_t); 66 + } 67 + 68 + // Add the buffer size, buffer request/response code and buffer end tag sizes 69 + bufsize += 3*sizeof(uint32_t); 70 + 71 + // buffer size must be 16 byte aligned 72 + bufsize += (bufsize % 16) ? 16 - (bufsize % 16) : 0; 73 + 74 + msg = kmalloc(bufsize); 75 + if (!msg) 76 + return -1; 77 + 78 + msg->size = bufsize; 79 + msg->req_res_code = REQUEST; 80 + 81 + // Copy the messages into the buffer 82 + for (i = 0, bufpos = 0; tags[i].proptag != NULL_TAG; i++) { 83 + len = get_value_buffer_len(&tags[i]); 84 + msg->tags[bufpos++] = tags[i].proptag; 85 + msg->tags[bufpos++] = len; 86 + msg->tags[bufpos++] = 0; 87 + memcpy(msg->tags+bufpos, &tags[i].value_buffer, len); 88 + bufpos += len/4; 89 + } 90 + 91 + msg->tags[bufpos] = 0; 92 + 93 + // Send the message 94 + mail.data = ((uint32_t)msg) >>4; 95 + 96 + mailbox_send(mail, PROPERTY_CHANNEL); 97 + mail = mailbox_read(PROPERTY_CHANNEL); 98 + 99 + 100 + if (msg->req_res_code == REQUEST) { 101 + kfree(msg); 102 + return 1; 103 + } 104 + // Check the response code 105 + if (msg->req_res_code == RESPONSE_ERROR) { 106 + kfree(msg); 107 + return 2; 108 + } 109 + 110 + 111 + // Copy the tags back into the array 112 + for (i = 0, bufpos = 0; tags[i].proptag != NULL_TAG; i++) { 113 + len = get_value_buffer_len(&tags[i]); 114 + bufpos += 3; //skip over the tag bookkepping info 115 + memcpy(&tags[i].value_buffer, msg->tags+bufpos,len); 116 + bufpos += len/4; 117 + } 118 + 119 + kfree(msg); 120 + return 0; 121 + }
+2 -2
os/src/kernel/uart.c
··· 31 31 /* 32 32 * Disable pull up/down for pin 14 && 15 33 33 */ 34 - #if defined(MODEL_0) || defined(MODEL_2) || defined(MODEL_3) 34 + #if defined(MODEL_0) || defined(MODEL_1) || defined(MODEL_2) || defined(MODEL_3) 35 35 /* Disable pull up/down for all GPIO pins & delay for 150 cycles */ 36 36 mmio_write(GPPUD, 0x00000000); 37 37 delay(150); ··· 77 77 mmio_write(AUX_MU_MCR_REG, 0); 78 78 79 79 /* Set baud rate to 115200 */ 80 - #if defined(MODEL_0) || defined(MODEL_2) || defined(MODEL_3) 80 + #if defined(MODEL_0) || defined(MODEL_1) || defined(MODEL_2) || defined(MODEL_3) 81 81 /* System_Clock_Freq = 250 MHz */ 82 82 /* (( System_Clock_Freq / baudrate_reg) / 8 ) - 1 */ 83 83 /* ((250,000,000 / 115200) / 8) - 1 = 270 */
+7
tests/CMakeLists.txt
··· 1 + set(CMAKE_C_COMPILER "clang") 2 + 3 + add_executable(test test.c) 4 + 5 + target_link_libraries(test PRIVATE cmocka) 6 + target_link_directories(test PRIVATE "/opt/homebrew/Cellar/cmocka/1.1.7/lib") 7 + target_include_directories(test PRIVATE "/opt/homebrew/Cellar/cmocka/1.1.7/include")
+16
tests/test.c
··· 1 + #include <stdarg.h> 2 + #include <stddef.h> 3 + #include <setjmp.h> 4 + #include <cmocka.h> 5 + 6 + static void test_integers(void** state) { 7 + assert_int_equal(1,1); 8 + } 9 + 10 + int main(int argc, char* argv[]) { 11 + const struct CMUnitTest tests[] = { 12 + cmocka_unit_test(test_integers), 13 + }; 14 + 15 + return cmocka_run_group_tests(tests, NULL, NULL); 16 + }