aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/README9
-rw-r--r--include/kpl.h39
-rw-r--r--include/kpl/code.h25
-rw-r--r--include/kpl/color.h119
-rw-r--r--include/kpl/io.h25
-rw-r--r--include/kpl/macro.h15
-rw-r--r--include/kpl/process.h39
-rw-r--r--include/kpl/queue.h53
-rw-r--r--include/kpl/system.h21
-rw-r--r--include/kpl/type.h53
-rw-r--r--include/kpl_test.h45
-rw-r--r--source/README17
-rw-r--r--source/config.c242
-rw-r--r--source/kpl.c20
-rw-r--r--source/queue.c91
-rw-r--r--test/README62
-rw-r--r--test/config.c51
-rw-r--r--test/queue.c96
-rw-r--r--test/test.c151
19 files changed, 0 insertions, 1173 deletions
diff --git a/include/README b/include/README
deleted file mode 100644
index b182099..0000000
--- a/include/README
+++ /dev/null
@@ -1,9 +0,0 @@
-Headers
-
----
-
-Complier Flags:
-
-KPL_COLOR_OFF # Turn off colored pretty printing
-
----
diff --git a/include/kpl.h b/include/kpl.h
deleted file mode 100644
index 833c18b..0000000
--- a/include/kpl.h
+++ /dev/null
@@ -1,39 +0,0 @@
-
-#pragma once
-
-#define KPL_VERSION "0.0.0"
-
-// All headers in one file for including
-
-#include "kpl/queue.h"
-#include "kpl/io.h"
-#include "kpl/process.h"
-#include "kpl/code.h"
-
-typedef enum : uint32_t {
- KPL_CONFIG_FLAG_EVAL = 1 << 0,
- KPL_CONFIG_FLAG_REPL = 1 << 1
-} kpl_config_flags;
-
-typedef struct {
- uint32_t flags;
- int32_t argc, main_module_arg_index;
- const char **argv, *module_extension, *version;
- kpl_config_io io;
- kpl_config_thread thread;
- kpl_config_code code;
-} kpl_config;
-
-void kpl_config_init(kpl_config *config);
-
-bool kpl_config_valid_module_exension(kpl_config *config, const char *module_name);
-
-int32_t kpl_config_parse_args(kpl_config *config, const int32_t argc, const char *argv[]);
-
-typedef struct _kpl_env {
- kpl_config config;
- _Atomic ssize_t total_priority;
- kpl_io io;
- kpl_process process;
- kpl_code code;
-} kpl_env;
diff --git a/include/kpl/code.h b/include/kpl/code.h
deleted file mode 100644
index 1902c42..0000000
--- a/include/kpl/code.h
+++ /dev/null
@@ -1,25 +0,0 @@
-
-#pragma once
-
-// Queues and trees for code life cycle
-
-#include "kpl/queue.h"
-
-typedef enum : int8_t {
- KPL_CONFIG_CODE_QUEUE_POW2_MIN = 4,
- KPL_CONFIG_CODE_QUEUE_POW2_DEFAULT = 7,
- KPL_CONFIG_CODE_QUEUE_POW2_MAX = 10,
-} kpl_config_code_queue_pow;
-
-typedef struct {
- int8_t queue_pow2;
-} kpl_config_code;
-
-// TODO namespace tree
-
-// TODO module tree
-
-typedef struct {
- kpl_config_code *config_code;
- kpl_ring_queue code_queue;
-} kpl_code;
diff --git a/include/kpl/color.h b/include/kpl/color.h
deleted file mode 100644
index 1f77dcb..0000000
--- a/include/kpl/color.h
+++ /dev/null
@@ -1,119 +0,0 @@
-
-#pragma once
-
-// C string pretty printing macros
-
-#define KPL_COLOR_CONCAT(COLOR) KPL_COLOR_ ## COLOR
-
-#ifndef KPL_COLOR_OFF
-
-#define KPL_COLOR(A) "\e[" KPL_COLOR_CONCAT(A) "m"
-#define KPL_COLOR2(A, B) "\e[" KPL_COLOR_CONCAT(A) ";" KPL_COLOR_CONCAT(B) "m"
-#define KPL_COLOR3(A, B, C) "\e[" KPL_COLOR_CONCAT(A) ";" KPL_COLOR_CONCAT(B) ";" KPL_COLOR_CONCAT(C) "m"
-
-#define KPL_COLOR_RESET "0"
-#define KPL_COLOR_BOLD "1"
-#define KPL_COLOR_FAINT "2"
-#define KPL_COLOR_ITALIC "3"
-#define KPL_COLOR_UNDERLINE "4"
-#define KPL_COLOR_BLINK "5"
-#define KPL_COLOR_REVERSE "7"
-#define KPL_COLOR_HIDDEN "8"
-#define KPL_COLOR_RESET_BOLD "21"
-#define KPL_COLOR_RESET_FAINT "22"
-#define KPL_COLOR_RESET_ITALIC "23"
-#define KPL_COLOR_RESET_UNDERLINE "24"
-#define KPL_COLOR_RESET_BLINK "25"
-#define KPL_COLOR_RESET_REVERSE "27"
-#define KPL_COLOR_RESET_HIDDEN "28"
-#define KPL_COLOR_BLACK "30"
-#define KPL_COLOR_RED "31"
-#define KPL_COLOR_GREEN "32"
-#define KPL_COLOR_YELLOW "33"
-#define KPL_COLOR_BLUE "34"
-#define KPL_COLOR_MAGENTA "35"
-#define KPL_COLOR_CYAN "36"
-#define KPL_COLOR_GREY "37"
-#define KPL_COLOR_DEFAULT "39"
-#define KPL_COLOR_BG_BLACK "30"
-#define KPL_COLOR_BG_RED "41"
-#define KPL_COLOR_BG_GREEN "42"
-#define KPL_COLOR_BG_YELLOW "43"
-#define KPL_COLOR_BG_BLUE "44"
-#define KPL_COLOR_BG_MAGENTA "45"
-#define KPL_COLOR_BG_CYAN "46"
-#define KPL_COLOR_BG_GREY "47"
-#define KPL_COLOR_DARK_GREY "90"
-#define KPL_COLOR_LIGHT_RED "91"
-#define KPL_COLOR_LIGHT_GREEN "92"
-#define KPL_COLOR_LIGHT_YELLOW "93"
-#define KPL_COLOR_LIGHT_BLUE "94"
-#define KPL_COLOR_LIGHT_MAGENTA "95"
-#define KPL_COLOR_LIGHT_CYAN "96"
-#define KPL_COLOR_WHITE "97"
-#define KPL_COLOR_BG_DARK_GREY "100"
-#define KPL_COLOR_BG_LIGHT_RED "101"
-#define KPL_COLOR_BG_LIGHT_GREEN "102"
-#define KPL_COLOR_BG_LIGHT_YELLOW "103"
-#define KPL_COLOR_BG_LIGHT_BLUE "104"
-#define KPL_COLOR_BG_LIGHT_MAGENTA "105"
-#define KPL_COLOR_BG_LIGHT_CYAN "106"
-#define KPL_COLOR_BG_WHITE "107"
-
-#else
-
-#define KPL_COLOR(A) KPL_COLOR_CONCAT(A)
-#define KPL_COLOR2(A, B) KPL_COLOR_CONCAT(A) KPL_COLOR_CONCAT(B)
-#define KPL_COLOR3(A, B, C) KPL_COLOR_CONCAT(A) KPL_COLOR_CONCAT(B) KPL_COLOR_CONCAT(C)
-
-
-#define KPL_COLOR_RESET ""
-#define KPL_COLOR_BOLD ""
-#define KPL_COLOR_FAINT ""
-#define KPL_COLOR_ITALIC ""
-#define KPL_COLOR_UNDERLINE ""
-#define KPL_COLOR_BLINK ""
-#define KPL_COLOR_REVERSE ""
-#define KPL_COLOR_HIDDEN ""
-#define KPL_COLOR_RESET_BOLD ""
-#define KPL_COLOR_RESET_FAINT ""
-#define KPL_COLOR_RESET_ITALIC ""
-#define KPL_COLOR_RESET_UNDERLINE ""
-#define KPL_COLOR_RESET_BLINK ""
-#define KPL_COLOR_RESET_REVERSE ""
-#define KPL_COLOR_RESET_HIDDEN ""
-#define KPL_COLOR_BLACK ""
-#define KPL_COLOR_RED ""
-#define KPL_COLOR_GREEN ""
-#define KPL_COLOR_YELLOW ""
-#define KPL_COLOR_BLUE ""
-#define KPL_COLOR_MAGENTA ""
-#define KPL_COLOR_CYAN ""
-#define KPL_COLOR_GREY ""
-#define KPL_COLOR_DEFAULT ""
-#define KPL_COLOR_BG_BLACK ""
-#define KPL_COLOR_BG_RED ""
-#define KPL_COLOR_BG_GREEN ""
-#define KPL_COLOR_BG_YELLOW ""
-#define KPL_COLOR_BG_BLUE ""
-#define KPL_COLOR_BG_MAGENTA ""
-#define KPL_COLOR_BG_CYAN ""
-#define KPL_COLOR_BG_GREY ""
-#define KPL_COLOR_DARK_GREY ""
-#define KPL_COLOR_LIGHT_RED ""
-#define KPL_COLOR_LIGHT_GREEN ""
-#define KPL_COLOR_LIGHT_YELLOW ""
-#define KPL_COLOR_LIGHT_BLUE ""
-#define KPL_COLOR_LIGHT_MAGENTA ""
-#define KPL_COLOR_LIGHT_CYAN ""
-#define KPL_COLOR_WHITE ""
-#define KPL_COLOR_BG_DARK_GREY ""
-#define KPL_COLOR_BG_LIGHT_RED ""
-#define KPL_COLOR_BG_LIGHT_GREEN ""
-#define KPL_COLOR_BG_LIGHT_YELLOW ""
-#define KPL_COLOR_BG_LIGHT_BLUE ""
-#define KPL_COLOR_BG_LIGHT_MAGENTA ""
-#define KPL_COLOR_BG_LIGHT_CYAN ""
-#define KPL_COLOR_BG_WHITE ""
-
-#endif
diff --git a/include/kpl/io.h b/include/kpl/io.h
deleted file mode 100644
index a1b4b3f..0000000
--- a/include/kpl/io.h
+++ /dev/null
@@ -1,25 +0,0 @@
-
-#pragma once
-
-// Io through io_uring
-
-#include "kpl/macro.h"
-
-typedef enum : int8_t {
- KPL_CONFIG_IO_QUEUE_POW2_MIN = 4,
- KPL_CONFIG_IO_QUEUE_POW2_DEFAULT = 10,
- KPL_CONFIG_IO_QUEUE_POW2_MAX = 16
-} kpl_io_queue_pow_options;
-
-typedef struct {
- int8_t queue_pow2;
-} kpl_config_io;
-
-typedef struct {
- kpl_config_io *config_io;
- // TODO
-} kpl_io;
-
-bool kpl_io_init(kpl_io *io);
-
-void kpl_io_free(kpl_io *io);
diff --git a/include/kpl/macro.h b/include/kpl/macro.h
deleted file mode 100644
index e0b59e5..0000000
--- a/include/kpl/macro.h
+++ /dev/null
@@ -1,15 +0,0 @@
-
-#pragma once
-
-// KPL specific macros
-
-#include "color.h"
-#include "type.h"
-
-#define _KPL_PRINT_(MESSAGE_COLOR, MESSAGE) printf(KPL_COLOR2(BOLD, MESSAGE_COLOR) "TODO " KPL_COLOR(RESET) KPL_COLOR(BOLD) "%s" KPL_COLOR(RESET) ":" KPL_COLOR(LIGHT_BLUE) "%s" KPL_COLOR(RESET) ":" KPL_COLOR(LIGHT_MAGENTA) "%d" KPL_COLOR(RESET) "::" KPL_COLOR(MESSAGE_COLOR) "%s\n" KPL_COLOR(RESET), __FILE__, __FUNCTION__, __LINE__, MESSAGE)
-
-#define KPL_PRINT_TODO(MESSAGE) _KPL_PRINT_(LIGHT_YELLOW, MESSAGE)
-
-#define KPL_PRINT_ERROR(MESSAGE) _KPL_PRINT_(LIGHT_RED, MESSAGE)
-
-#define KPL_PAGE_SIZE_ROUND(SIZE) ((SIZE + (getpagesize() - 1)) & ~(getpagesize() - 1))
diff --git a/include/kpl/process.h b/include/kpl/process.h
deleted file mode 100644
index 528365a..0000000
--- a/include/kpl/process.h
+++ /dev/null
@@ -1,39 +0,0 @@
-
-#pragma once
-
-// Kpl threads, allocators, atomic queues and garbage collection
-
-#include "kpl/queue.h"
-
-typedef enum : int8_t {
- KPL_CONFIG_THREAD_COUNT_AFFINITY = -1,
- KPL_CONFIG_THREAD_COUNT_MAX = 127
-} kpl_config_thread_count;
-
-typedef enum : uint8_t {
- KPL_CONFIG_THREAD_RING_POOL_COUNT = 28,
- KPL_CONFIG_THREAD_RING_POOL_MIN_OBJECT_SIZE_POW2 = 5,
- KPL_CONFIG_THREAD_RING_POOL_MAX_OBJECT_SIZE_POW2 = 27,
- KPL_CONFIG_THREAD_RING_POOL_MIN_RING_SIZE_POW2 = 6,
- KPL_CONFIG_THREAD_RING_POOL_MAX_RING_SIZE_POW2 = 20
-} kpl_config_thread_ring_pool;
-
-typedef struct {
- int8_t count, ring_pool_entries_pow2[KPL_CONFIG_THREAD_RING_POOL_COUNT];
-} kpl_config_thread;
-
-typedef struct {
- int32_t thread_id;
- _Atomic ssize_t priority;
- kpl_env *env;
- kpl_task_queue task_queue;
- // TODO
- sem_t sem;
- pthread_t pthread;
-} kpl_thread;
-
-typedef struct {
- kpl_config_thread *config_thread;
- kpl_thread *threads;
- kpl_ring_queue memory_pool[KPL_CONFIG_THREAD_RING_POOL_COUNT];
-} kpl_process;
diff --git a/include/kpl/queue.h b/include/kpl/queue.h
deleted file mode 100644
index 0107434..0000000
--- a/include/kpl/queue.h
+++ /dev/null
@@ -1,53 +0,0 @@
-
-#pragma once
-
-// KPL atomic queues
-
-#include "kpl/macro.h"
-
-typedef struct {
- kpl_task *_Atomic head, *tail;
- struct {
- kpl_task *_Atomic next;
- } dummy;
-} kpl_task_queue;
-
-inline void kpl_task_queue_init(kpl_task_queue *task_queue) {
- __atomic_store_n(&task_queue->dummy.next, NULL, __ATOMIC_RELAXED);
- __atomic_store_n(&task_queue->head, &task_queue->dummy, __ATOMIC_RELAXED);
- task_queue->tail = (kpl_task*) &task_queue->dummy;
-}
-
-inline void kpl_task_queue_add(kpl_task_queue *task_queue, kpl_task *task) {
- __atomic_store_n(&task->next, NULL, __ATOMIC_RELAXED);
- kpl_task *head = __atomic_exchange_n(&task_queue->head, task, __ATOMIC_SEQ_CST);
- __atomic_store_n(&head->next, task, __ATOMIC_RELEASE);
-}
-
-kpl_task *kpl_task_queue_next(kpl_task_queue *task_queue);
-
-typedef enum : int8_t {
- KPL_RING_QUEUE_MIN_POW2 = 4,
- KPL_RING_QUEUE_MAX_POW2 = 30
-} kpl_ring_queue_pow2_sizes;
-
-typedef struct {
- _Atomic ssize_t index;
- void *data;
-} kpl_ring_queue_item;
-
-typedef struct {
- size_t mmap_size, items_mask;
- _Atomic ssize_t head_index, tail_index;
- kpl_ring_queue_item *items;
-} kpl_ring_queue;
-
-bool kpl_ring_queue_init(kpl_ring_queue *ring_queue, int8_t size_pow2);
-
-inline void kpl_ring_queue_free(kpl_ring_queue *ring_queue) {
- munmap(ring_queue->items, ring_queue->mmap_size);
-}
-
-bool kpl_ring_queue_add(kpl_ring_queue *ring_queue, void *data);
-
-void *kpl_ring_queue_next(kpl_ring_queue *ring_queue);
diff --git a/include/kpl/system.h b/include/kpl/system.h
deleted file mode 100644
index 2d1ec48..0000000
--- a/include/kpl/system.h
+++ /dev/null
@@ -1,21 +0,0 @@
-
-#pragma once
-
-// System headers
-
-#include <stdlib.h>
-#include <stdio.h>
-#include <stdint.h>
-#include <stdbool.h>
-#include <string.h>
-#include <ctype.h>
-#include <pthread.h>
-#include <semaphore.h>
-#include <fcntl.h>
-#include <unistd.h>
-#include <sys/stat.h>
-#include <sys/ioctl.h>
-#include <sys/mman.h>
-#include <sys/uio.h>
-#include <linux/fs.h>
-#include <linux/io_uring.h>
diff --git a/include/kpl/type.h b/include/kpl/type.h
deleted file mode 100644
index 5003cf0..0000000
--- a/include/kpl/type.h
+++ /dev/null
@@ -1,53 +0,0 @@
-
-#pragma once
-
-// KPL specific types
-
-#include "system.h"
-
-typedef enum : int32_t {
- KPL_EXIT_CODE_SUCCESS = 0,
- KPL_EXIT_CODE_ERROR = 1,
- KPL_EXIT_CODE_HELP = 2
-} kpl_exit_code;
-
-typedef uint8_t kpl_utf8[4];
-
-typedef union {
- uint8_t u8;
- int8_t i8;
- uint16_t u16;
- int16_t i16;
- uint32_t u32;
- int32_t i32;
- uint64_t u64;
- int64_t i64;
- kpl_utf8 utf8;
- float f32;
- double f64;
- void *ptr;
-} kpl_value;
-
-typedef struct {
- kpl_value value;
- int64_t tag;
-} kpl_result;
-
-typedef struct _kpl_task kpl_task;
-
-typedef struct _kpl_env kpl_env;
-
-typedef void kpl_task_fn(kpl_task *task, kpl_env *env);
-
-typedef struct _kpl_task {
- struct _kpl_task *_Atomic next, *join;
- kpl_task_fn *task_fn;
- int32_t io_res;
- uint32_t io_flags;
- int32_t thread_id;
- _Atomic bool canceled __attribute__((aligned(4))), join_ready __attribute__((aligned(8)));
- kpl_result result;
- // TODO TASK ARGUMENTS
-} kpl_task;
-
-
diff --git a/include/kpl_test.h b/include/kpl_test.h
deleted file mode 100644
index c1645e2..0000000
--- a/include/kpl_test.h
+++ /dev/null
@@ -1,45 +0,0 @@
-
-#pragma once
-
-// KPL testing framework
-
-#include "kpl.h"
-
-typedef struct _kpl_test kpl_test;
-
-typedef void kpl_test_function(__attribute__((unused)) kpl_test *_test);
-
-typedef struct _kpl_test {
- int32_t error_line_number; // -1 for no error
- char *file_name, *test_name, *error_message;
- kpl_test_function *test_function;
- struct _kpl_test *next_test;
-} kpl_test;
-
-void kpl_test_add(kpl_test *_test);
-
-#define _KPL_TEST_FN_NAME(NAME) _kpl_test_function_ ## NAME
-
-#define _KPL_TEST_FN(NAME) static void _KPL_TEST_FN_NAME(NAME)(__attribute__((unused)) kpl_test *_test)
-
-#define KPL_TEST(NAME) _KPL_TEST_FN(NAME); \
-static void __attribute__((constructor)) _kpl_test_constructor_ ## NAME(void) { \
- static kpl_test _test = { \
- .error_line_number = -1, \
- .file_name = __FILE__, .test_name = #NAME, .error_message = NULL, \
- .test_function = _KPL_TEST_FN_NAME(NAME), \
- .next_test = NULL \
- }; \
- kpl_test_add(&_test); \
-} \
-_KPL_TEST_FN(NAME)
-
-#define KPL_FAIL(MESSAGE) do { \
- _test->error_line_number = __LINE__; \
- _test->error_message = MESSAGE; \
-} while (0)
-
-#define KPL_ASSERT(CONDITION, MESSAGE) do { \
- if (!(CONDITION)) \
- KPL_FAIL(#CONDITION "; " MESSAGE); \
-} while (0)
diff --git a/source/README b/source/README
deleted file mode 100644
index 0ec82e2..0000000
--- a/source/README
+++ /dev/null
@@ -1,17 +0,0 @@
-Source
-
----
-
-Includes:
-
-#include "kpl.h"
-
-This is the only header for any C file in the source folder
-
----
-
-Complier Flags:
-
-KPL_MAIN # For standalone exec, off for testing or including in other code
-
----
diff --git a/source/config.c b/source/config.c
deleted file mode 100644
index 31de7d4..0000000
--- a/source/config.c
+++ /dev/null
@@ -1,242 +0,0 @@
-
-#include "kpl.h"
-
-static const kpl_config default_config = {
- .argc = -1, .main_module_arg_index = -1, .version = KPL_VERSION,
- .argv = NULL, .module_extension = ".kpl",
- .flags = 0,
- .io = {
- .queue_pow2 = KPL_CONFIG_IO_QUEUE_POW2_DEFAULT
- },
- .thread = {
- .count = KPL_CONFIG_THREAD_COUNT_AFFINITY,
- .ring_pool_entries_pow2 = {
- [0] = 0, [1] = 0, [2] = 0, [3] = 0, [4] = 0, [5] = 13,
- [6] = 13, [7] = 13, [8] = 13, [9] = 13, [10] = 13, [11] = 13,
- [12] = 13, [13] = 13, [14] = 13, [15] = 13, [16] = 13, [17] = 13,
- [18] = 13, [19] = 13, [20] = 13, [21] = 13, [22] = 13, [23] = 13,
- [24] = 13, [25] = 13, [26] = 13, [27] = 13
- }
- },
- .code = {
- .queue_pow2 = KPL_CONFIG_CODE_QUEUE_POW2_DEFAULT
- }
-};
-
-void kpl_config_init(kpl_config *config) {
- memcpy(config, &default_config, sizeof(kpl_config));
-}
-
-typedef int32_t kpl_arg_match_fn(const char *match_str, const int32_t match_str_index, kpl_config *config);
-
-typedef struct {
- const char *match_str, *help_message;
- kpl_arg_match_fn *arg_match_fn;
-} kpl_arg_match;
-
-
-static int32_t kpl_arg_match_module_extension(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- config->module_extension = match_str + match_str_index;
- return KPL_EXIT_CODE_SUCCESS;
-}
-
-static int32_t kpl_arg_match_io_queue_pow2(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- int32_t queue_pow2 = atoi(match_str + match_str_index);
- if (queue_pow2 < KPL_CONFIG_IO_QUEUE_POW2_MIN || queue_pow2 > KPL_CONFIG_IO_QUEUE_POW2_MAX)
- return KPL_EXIT_CODE_ERROR;
- config->io.queue_pow2 = queue_pow2;
- return KPL_EXIT_CODE_SUCCESS;
-}
-
-static int32_t kpl_arg_match_thread_count(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- int32_t thread_count = atoi(match_str + match_str_index);
- if (thread_count <= 0 || thread_count > KPL_CONFIG_THREAD_COUNT_MAX)
- return KPL_EXIT_CODE_ERROR;
- config->thread.count = thread_count;
- return KPL_EXIT_CODE_SUCCESS;
-}
-
-static int32_t kpl_arg_match_memory_pool_pow2(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- char *endptr;
- int32_t object_size_pow2 = strtol(match_str + match_str_index, &endptr, 10);
- if (object_size_pow2 < KPL_CONFIG_THREAD_RING_POOL_MIN_OBJECT_SIZE_POW2 ||
- object_size_pow2 > KPL_CONFIG_THREAD_RING_POOL_MAX_OBJECT_SIZE_POW2)
- return KPL_EXIT_CODE_ERROR;
- while (*endptr && !isdigit(*endptr))
- endptr++;
- int32_t entry_size_pow2 = strtol(endptr, NULL, 10);
- if (entry_size_pow2 < KPL_CONFIG_THREAD_RING_POOL_MIN_RING_SIZE_POW2 ||
- entry_size_pow2 > KPL_CONFIG_THREAD_RING_POOL_MAX_RING_SIZE_POW2)
- return KPL_EXIT_CODE_ERROR;
- config->thread.ring_pool_entries_pow2[object_size_pow2] = entry_size_pow2;
- return KPL_EXIT_CODE_SUCCESS;
-}
-
-static int32_t kpl_arg_match_code_queue_pow2(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- int32_t queue_pow2 = atoi(match_str + match_str_index);
- if (queue_pow2 < KPL_CONFIG_CODE_QUEUE_POW2_MIN || queue_pow2 > KPL_CONFIG_CODE_QUEUE_POW2_MAX)
- return KPL_EXIT_CODE_ERROR;
- config->code.queue_pow2 = queue_pow2;
- return KPL_EXIT_CODE_SUCCESS;
-}
-
-static int32_t kpl_arg_match_eval(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- (void) match_str;
- (void) match_str_index;
- config->flags |= KPL_CONFIG_FLAG_EVAL;
- return KPL_EXIT_CODE_SUCCESS;
-}
-
-static int32_t kpl_arg_match_repl(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- (void) match_str;
- (void) match_str_index;
- config->flags |= KPL_CONFIG_FLAG_REPL;
- return KPL_EXIT_CODE_SUCCESS;
-}
-
-static int32_t kpl_arg_match_version(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- (void) match_str_index;
- printf("\nKevin's Programming Language (" KPL_COLOR(LIGHT_BLUE) "KPL" KPL_COLOR(RESET)
- "), Version: " KPL_COLOR(LIGHT_GREEN) "%s\n" KPL_COLOR(RESET),
- config->version);
- if (match_str)
- putchar('\n');
- return KPL_EXIT_CODE_HELP;
-}
-
-static int32_t kpl_arg_match_help(const char *match_str, const int32_t match_str_index, kpl_config *config);
-
-static kpl_arg_match arg_match_array[] = {
- {
- .match_str = "--module-extension=",
- .help_message="[WORD]; Change the module extension for imports (default .kpl)",
- .arg_match_fn = kpl_arg_match_module_extension
- },
- {
- .match_str = "--io-queue-pow2=",
- .help_message = "[NUMBER]; Power of 2 for calculating the size of the io_uring queue",
- .arg_match_fn = kpl_arg_match_io_queue_pow2
- },
- {
- .match_str = "--thread-count=",
- .help_message = "[NUMBER]; Number of running threads, minimum is 1",
- .arg_match_fn = kpl_arg_match_thread_count
- },
- {
- .match_str = "--memory-pool-pow2=",
- .help_message = "[NUMBER1],[NUMBER2]; Set the memory pool [NUMBER1] to have 2 ** [NUMBER2] entires",
- .arg_match_fn = kpl_arg_match_memory_pool_pow2
- },
- {
- .match_str = "--code-queue-pow2=",
- .help_message = "[NUMBER]; Power of 2 for calculating the size of the code queue",
- .arg_match_fn = kpl_arg_match_code_queue_pow2
- },
- {
- .match_str = "--eval",
- .help_message = " [STRING...]; Evaluate next argument(s) as modules",
- .arg_match_fn = kpl_arg_match_eval
- },
- {
- .match_str = "--repl",
- .help_message = "; Start (R)ead, (E)valuate, (P)rint, (L)oop",
- .arg_match_fn = kpl_arg_match_repl
- },
- {
- .match_str = "--version",
- .help_message = "; Show version",
- .arg_match_fn = kpl_arg_match_version
- },
- {
- .match_str = "--help",
- .help_message = "; Show help",
- .arg_match_fn = kpl_arg_match_help
- },
- { .match_str = NULL, .help_message = NULL, .arg_match_fn = NULL }
-};
-
-static int32_t kpl_arg_match_help(const char *match_str, const int32_t match_str_index, kpl_config *config) {
- (void) match_str;
- (void) match_str_index;
- kpl_arg_match_version(NULL, 0, config);
- printf("\nUsage " KPL_COLOR(BOLD) "%s" KPL_COLOR(RESET) KPL_COLOR(WHITE) " [OPTIONS] [MODULE]" KPL_COLOR(RESET)
- KPL_COLOR(BOLD) "%s\n\n" KPL_COLOR(RESET), config->argv[0], config->module_extension);
- printf("Where " KPL_COLOR(WHITE) "[OPTIONS]" KPL_COLOR(RESET) " are:\n");
- const kpl_arg_match *match_array = arg_match_array;
- while (match_array->match_str) {
- printf(KPL_COLOR(LIGHT_YELLOW) "\t%s" KPL_COLOR(RESET) "%s\n",
- match_array->match_str, match_array->help_message);
- match_array++;
- }
- putchar('\n');
- return KPL_EXIT_CODE_HELP;
-}
-
-static bool kpl_valid_match_str_index(const char *match_str_array, const char *match_str_arg, int32_t match_str_index) {
- return match_str_array[match_str_index] &&
- match_str_array[match_str_index] == match_str_arg[match_str_index];
-}
-
-static bool kpl_valid_match_str(const char *match_str_array, const char *match_str_arg, int32_t match_str_index) {
- return !match_str_array[match_str_index] && (!match_str_arg[match_str_index] ||
- (match_str_arg[match_str_index] && match_str_array[match_str_index - 1] == '='));
-}
-
-bool kpl_config_valid_module_exension(kpl_config *config, const char *module_name) {
- size_t name_length = strlen(module_name), module_extension_length = strlen(config->module_extension);
- return name_length > module_extension_length &&
- strcmp(module_name + name_length - module_extension_length, config->module_extension) == 0;
-}
-
-int32_t kpl_config_parse_args(kpl_config *config, const int32_t argc, const char *argv[]) {
- config->argc = argc;
- config->argv = argv;
- if (argc == 1) {
- printf(KPL_COLOR(LIGHT_RED) "\nNo Module Specified\n" KPL_COLOR(RESET));
- return kpl_arg_match_help(NULL, 0, config);
- }
- int32_t arg_index = 1;
- while (arg_index < argc && !config->flags) {
- int32_t match_str_index = 0;
- const char *match_str_arg = argv[arg_index];
- const kpl_arg_match *match_array = arg_match_array;
- while (match_array->match_str) {
- while (kpl_valid_match_str_index(match_array->match_str, match_str_arg, match_str_index))
- match_str_index++;
- if (kpl_valid_match_str(match_array->match_str, match_str_arg, match_str_index)) {
- int32_t exit_status = match_array->arg_match_fn(match_str_arg, match_str_index, config);
- if (exit_status != KPL_EXIT_CODE_SUCCESS) {
- if (exit_status == KPL_EXIT_CODE_ERROR)
- printf(KPL_COLOR(LIGHT_RED) "\nInvalid Option: " KPL_COLOR(BOLD) "%s\n" KPL_COLOR(RESET),
- match_str_arg);
- return exit_status;
- }
- break;
- }
- match_str_index = 0;
- match_array++;
- }
- if (!match_array->match_str)
- break;
- arg_index++;
- }
- config->main_module_arg_index = arg_index;
- if (config->flags) {
- if ((config->flags & KPL_CONFIG_FLAG_EVAL) && argc - arg_index < 1) {
- printf(KPL_COLOR(LIGHT_RED) "\nInvalid EVAL\n" KPL_COLOR(RESET));
- return kpl_arg_match_help(NULL, 0, config);
- }
- if ((config->flags & KPL_CONFIG_FLAG_REPL) && argc != arg_index) {
- printf(KPL_COLOR(LIGHT_RED) "\nInvalid REPL\n" KPL_COLOR(RESET));
- return kpl_arg_match_help(NULL, 0, config);
- }
- return KPL_EXIT_CODE_SUCCESS;
- }
- if (!kpl_config_valid_module_exension(config, argv[arg_index])) {
- printf(KPL_COLOR(LIGHT_RED) "\nInvalid " KPL_COLOR(RESET)
- KPL_COLOR(WHITE) "[OPTION]/[MODULE]: " KPL_COLOR(RESET)
- KPL_COLOR2(BOLD, LIGHT_RED) "%s\n" KPL_COLOR(RESET), argv[arg_index]);
- return kpl_arg_match_help(NULL, 0, config);
- }
- return KPL_EXIT_CODE_SUCCESS;
-}
diff --git a/source/kpl.c b/source/kpl.c
deleted file mode 100644
index cc98b4b..0000000
--- a/source/kpl.c
+++ /dev/null
@@ -1,20 +0,0 @@
-
-#include "kpl.h"
-
-#ifdef KPL_MAIN
-int32_t main(const int32_t argc, const char *argv[]) {
- int32_t exit_status = KPL_EXIT_CODE_SUCCESS;
- kpl_env env;
- kpl_config_init(&env.config);
- if ((exit_status = kpl_config_parse_args(&env.config, argc, argv)))
- return exit_status;
- KPL_PRINT_TODO("INIT KPL");
- if (env.config.flags & KPL_CONFIG_FLAG_EVAL)
- KPL_PRINT_TODO("RUN EVAL");
- else if (env.config.flags & KPL_CONFIG_FLAG_REPL)
- KPL_PRINT_TODO("RUN REPL");
- else
- KPL_PRINT_TODO("RUN MODULE");
- return exit_status;
-}
-#endif
diff --git a/source/queue.c b/source/queue.c
deleted file mode 100644
index 350c4e2..0000000
--- a/source/queue.c
+++ /dev/null
@@ -1,91 +0,0 @@
-
-#include "kpl.h"
-
-extern inline void kpl_task_queue_init(kpl_task_queue *task_queue);
-
-extern inline void kpl_task_queue_add(kpl_task_queue *task_queue, kpl_task *task);
-
-kpl_task *kpl_task_queue_next(kpl_task_queue *task_queue) {
- kpl_task *task = NULL;
- for (;;) {
- kpl_task *tail = task_queue->tail, *next = __atomic_load_n(&tail->next, __ATOMIC_ACQUIRE);
- if (tail == (kpl_task*) &task_queue->dummy) {
- if (!next)
- break;
- tail = task_queue->tail = next;
- next = __atomic_load_n(&tail->next, __ATOMIC_ACQUIRE);
- }
- if (!next) {
- kpl_task *head = __atomic_load_n(&task_queue->head, __ATOMIC_ACQUIRE);
- if (tail != head)
- continue;
- kpl_task_queue_add(task_queue, (kpl_task*) &task_queue->dummy);
- next = __atomic_load_n(&tail->next, __ATOMIC_ACQUIRE);
- }
- if (next) {
- task_queue->tail = next;
- task = tail;
- break;
- }
- }
- if (task)
- __atomic_store_n(&task->next, NULL, __ATOMIC_RELAXED);
- return task;
-}
-
-bool kpl_ring_queue_init(kpl_ring_queue *ring_queue, int8_t size_pow2) {
- if (size_pow2 < KPL_RING_QUEUE_MIN_POW2 || size_pow2 > KPL_RING_QUEUE_MAX_POW2)
- return false;
- size_t size = 1L << size_pow2;
- ring_queue->mmap_size = KPL_PAGE_SIZE_ROUND(sizeof(kpl_ring_queue_item) * size);
- ring_queue->items = mmap(NULL, ring_queue->mmap_size,
- PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
- ring_queue->items_mask = size - 1;
- __atomic_store_n(&ring_queue->head_index, 0, __ATOMIC_RELAXED);
- __atomic_store_n(&ring_queue->tail_index, 0, __ATOMIC_RELAXED);
- for (size_t index = 0; index < size; index++)
- __atomic_store_n(&ring_queue->items[index].index, index, __ATOMIC_RELAXED);
- return true;
-}
-
-extern inline void kpl_ring_queue_free(kpl_ring_queue *ring_queue);
-
-bool kpl_ring_queue_add(kpl_ring_queue *ring_queue, void *data) {
- for (;;) {
- ssize_t tail_index = __atomic_load_n(&ring_queue->tail_index, __ATOMIC_RELAXED);
- kpl_ring_queue_item *item = &ring_queue->items[tail_index & ring_queue->items_mask];
- ssize_t item_index = __atomic_load_n(&item->index, __ATOMIC_ACQUIRE), diff = item_index - tail_index;
- if (diff > 0)
- continue;
- if (diff < 0)
- break;
- if (!__atomic_compare_exchange_n(&ring_queue->tail_index, &tail_index, tail_index + 1, true,
- __ATOMIC_RELAXED, __ATOMIC_RELAXED))
- continue;
- item->data = data;
- __atomic_store_n(&item->index, tail_index + 1, __ATOMIC_RELEASE);
- return true;
- }
- return false;
-}
-
-void *kpl_ring_queue_next(kpl_ring_queue *ring_queue) {
- for (;;) {
- ssize_t head_index = __atomic_load_n(&ring_queue->head_index, __ATOMIC_RELAXED);
- kpl_ring_queue_item *item = &ring_queue->items[head_index & ring_queue->items_mask];
- ssize_t item_index = __atomic_load_n(&item->index, __ATOMIC_ACQUIRE),
- diff = item_index - (head_index + 1);
- if (diff > 0)
- continue;
- if (diff < 0)
- break;
- if (!__atomic_compare_exchange_n(&ring_queue->head_index, &head_index, head_index + 1, true,
- __ATOMIC_RELAXED, __ATOMIC_RELAXED))
- continue;
- void *data = item->data;
- item->data = NULL;
- __atomic_store_n(&item->index, head_index + ring_queue->items_mask + 1, __ATOMIC_RELEASE);
- return data;
- }
- return NULL;
-}
diff --git a/test/README b/test/README
deleted file mode 100644
index f1c86df..0000000
--- a/test/README
+++ /dev/null
@@ -1,62 +0,0 @@
-Testing
-
----
-
-File Layout:
-
-The test files mirror the src files, so a function in src/file.c would have a test in test/file.c
-
----
-
-Includes:
-
-#include "kpl_test.h"
-
-This is the only include a .c file in the test folder needs
-
----
-
-Writing Tests:
-
-KPL_TEST(test_name) {
- // TEST CODE
-}
-
-Tests pass by default
-
----
-
-Asserting:
-
-KPL_ASSERT(CONDITION, FAIL_MESSAGE);
-
----
-
-Failing:
-
-KPL_FAIL(FAIL_MESSAGE);
-
----
-
-Building:
-
-make kpl_test # build test exec
-make kpl_test_memory # build test exec with address, leak and undefined sanitizer
-make kpl_test_thread # build test exec with thread sanitizer
-
-All objects need to be built with the same sanitizer and do not run valgrind when sanitizers are added
-
----
-
-Running:
-
-./kpl_test # Run all tests
-./kpl_test NAME # Run test named NAME
-./kpl_test NAME1 NAME2 ... # Run selected tests named NAM1 NAME2 ...
-./kpl_test -h # Show help
-
----
-
-Compiler Flags:
-
----
diff --git a/test/config.c b/test/config.c
deleted file mode 100644
index 978e003..0000000
--- a/test/config.c
+++ /dev/null
@@ -1,51 +0,0 @@
-
-#include "kpl_test.h"
-
-KPL_TEST(show_help) {
- kpl_config config;
- const int32_t argc = 2;
- const char *argv[] = { "./kpl", "--help", "not_used" };
- kpl_config_init(&config);
- int32_t code = kpl_config_parse_args(&config, argc, argv);
- KPL_ASSERT(code == KPL_EXIT_CODE_HELP, "Invalid help exit code");
-}
-
-KPL_TEST(change_module_extension) {
- kpl_config config;
- const int32_t argc = 3;
- const char *argv[] = { "./kpl", "--module-extension=.l", "./file.l" };
- kpl_config_init(&config);
- int32_t code = kpl_config_parse_args(&config, argc, argv);
- KPL_ASSERT(code == KPL_EXIT_CODE_SUCCESS, "Invalid exit code");
- KPL_ASSERT(strcmp(config.module_extension, ".l") == 0, "Invalid new module extension");
-}
-
-KPL_TEST(io_queue_pow2) {
- kpl_config config;
- const int32_t argc = 3;
- const char *argv[] = { "./kpl", "--io-queue-pow2=14", "./file.kpl" };
- kpl_config_init(&config);
- int32_t code = kpl_config_parse_args(&config, argc, argv);
- KPL_ASSERT(code == KPL_EXIT_CODE_SUCCESS, "Invalid exit code");
- KPL_ASSERT(config.io.queue_pow2 == 14, "Invalid io queue power of two");
-}
-
-KPL_TEST(thread_count) {
- kpl_config config;
- const int32_t argc = 3;
- const char *argv[] = { "./kpl", "--thread-count=1", "./file.kpl" };
- kpl_config_init(&config);
- int32_t code = kpl_config_parse_args(&config, argc, argv);
- KPL_ASSERT(code == KPL_EXIT_CODE_SUCCESS, "Invalid exit code");
- KPL_ASSERT(config.thread.count == 1, "Invalid thread count");
-}
-
-KPL_TEST(memory_pool_pow2) {
- kpl_config config;
- const int32_t argc = 3;
- const char *argv[] = { "./kpl", "--memory-pool-pow2=6,7", "./file.kpl" };
- kpl_config_init(&config);
- int32_t code = kpl_config_parse_args(&config, argc, argv);
- KPL_ASSERT(code == KPL_EXIT_CODE_SUCCESS, "Invalid exit code");
- KPL_ASSERT(config.thread.ring_pool_entries_pow2[6] == 7, "Invalid entries pow2");
-}
diff --git a/test/queue.c b/test/queue.c
deleted file mode 100644
index 0f63322..0000000
--- a/test/queue.c
+++ /dev/null
@@ -1,96 +0,0 @@
-
-#include "kpl_test.h"
-
-typedef struct {
- _Atomic int32_t increments;
- bool pop_error;
- kpl_task_queue task_queue;
- pthread_t pthread;
-} kpl_task_queue_thread_test;
-
-#define TASK_QUEUE_THREAD_COUNT 3
-
-#define TASK_QUEUE_PER_THREAD_INCREMENTS 10
-
-static const int32_t kpl_task_queue_total_increments = TASK_QUEUE_THREAD_COUNT * TASK_QUEUE_PER_THREAD_INCREMENTS;
-
-static kpl_task_queue_thread_test task_queue_threads[TASK_QUEUE_THREAD_COUNT] = {};
-
-static void *task_queue_thread_fn(void *arg) {
- const int32_t thread_id = (int32_t) (intptr_t) arg;
- for (int32_t round = 0; round < TASK_QUEUE_PER_THREAD_INCREMENTS; round++) {
- for (int32_t id = 0; id < TASK_QUEUE_THREAD_COUNT; id++) {
- kpl_task *task = calloc(1, sizeof(kpl_task));
- kpl_task_queue_add(&task_queue_threads[id].task_queue, task);
- }
- kpl_task *task = kpl_task_queue_next(&task_queue_threads[thread_id].task_queue);
- if (task) {
- task_queue_threads[thread_id].increments++;
- free(task);
- } else {
- task_queue_threads[thread_id].pop_error = true;
- break;
- }
- }
- return NULL;
-}
-
-KPL_TEST(task_queue_threads) {
- for (int32_t id = 0; id < TASK_QUEUE_THREAD_COUNT; id++)
- kpl_task_queue_init(&task_queue_threads[id].task_queue);
- for (int32_t id = 0; id < TASK_QUEUE_THREAD_COUNT; id++)
- pthread_create(&task_queue_threads[id].pthread, NULL, task_queue_thread_fn, (void*) (intptr_t) id);
- for (int32_t id = 0; id < TASK_QUEUE_THREAD_COUNT; id++)
- pthread_join(task_queue_threads[id].pthread, NULL);
- for (int32_t id = 0; id < TASK_QUEUE_THREAD_COUNT; id++) {
- kpl_task *task = NULL;
- while ((task = kpl_task_queue_next(&task_queue_threads[id].task_queue))) {
- task_queue_threads[id].increments++;
- free(task);
- }
- KPL_ASSERT(!task_queue_threads[id].pop_error, "Task queue pop failed");
- KPL_ASSERT(task_queue_threads[id].increments == kpl_task_queue_total_increments,
- "Invalid number of increments");
- }
-}
-
-#define RING_QUEUE_THREAD_COUNT 3
-
-#define RING_QUEUE_SLOTS_PER_THREAD 1000
-
-#define RING_QUEUE_SLOT_LENGTH (RING_QUEUE_THREAD_COUNT * RING_QUEUE_SLOTS_PER_THREAD)
-
-static pthread_t ring_queue_threads[RING_QUEUE_THREAD_COUNT] = {};
-
-static bool ring_queue_test_slots[RING_QUEUE_SLOT_LENGTH] = {};
-
-static kpl_ring_queue ring_queue;
-
-static void *ring_queue_thread_fn(void *arg) {
- const int32_t thread_id = (int32_t) (intptr_t) arg;
- int32_t slot_index;
- for (int32_t round = 1; round < RING_QUEUE_SLOTS_PER_THREAD; round++) {
- slot_index = thread_id * RING_QUEUE_SLOTS_PER_THREAD + round;
- if (!kpl_ring_queue_add(&ring_queue, (void*) (intptr_t) slot_index))
- break;
- if ((slot_index = (int32_t) (intptr_t) kpl_ring_queue_next(&ring_queue)))
- ring_queue_test_slots[slot_index] = true;
- }
- while ((slot_index = (int32_t) (intptr_t) kpl_ring_queue_next(&ring_queue)))
- ring_queue_test_slots[slot_index] = true;
- return NULL;
-}
-
-KPL_TEST(ring_queue_threads) {
- for (int32_t skip_round = 0; skip_round < RING_QUEUE_THREAD_COUNT; skip_round++)
- ring_queue_test_slots[skip_round * RING_QUEUE_SLOTS_PER_THREAD] = true;
- KPL_ASSERT(kpl_ring_queue_init(&ring_queue, 12), "Ring queue should init");
- for (int32_t id = 0; id < RING_QUEUE_THREAD_COUNT; id++)
- pthread_create(&ring_queue_threads[id], NULL, ring_queue_thread_fn, (void*) (intptr_t) id);
- for (int32_t id = 0; id < RING_QUEUE_THREAD_COUNT; id++)
- pthread_join(ring_queue_threads[id], NULL);
- for (int32_t slot_index = 0; slot_index < RING_QUEUE_SLOT_LENGTH; slot_index++) {
- KPL_ASSERT(ring_queue_test_slots[slot_index], "Slot should have been set");
- }
- kpl_ring_queue_free(&ring_queue);
-}
diff --git a/test/test.c b/test/test.c
deleted file mode 100644
index 04cade6..0000000
--- a/test/test.c
+++ /dev/null
@@ -1,151 +0,0 @@
-
-#include "kpl_test.h"
-
-static kpl_test *_kpl_test_head = NULL, *_kpl_test_tail = NULL, *_kpl_error_head = NULL, *_kpl_error_tail = NULL;
-
-static int32_t _kpl_test_count = 0, _kpl_test_error_count = 0;
-
-void kpl_test_add(kpl_test *_test) {
- _kpl_test_count++;
- if (_kpl_test_head)
- _kpl_test_tail = _kpl_test_tail->next_test = _test;
- else
- _kpl_test_head = _kpl_test_tail = _test;
-}
-
-static void kpl_test_report(kpl_test *_test) {
- printf(KPL_COLOR(BOLD) "%s" KPL_COLOR(RESET) ":" KPL_COLOR(LIGHT_CYAN) "%s" KPL_COLOR(RESET),
- _test->file_name, _test->test_name);
-}
-
-static void kpl_test_report_success(kpl_test *_test) {
- printf(KPL_COLOR2(BOLD, LIGHT_GREEN) "PASSED " KPL_COLOR(RESET));
- kpl_test_report(_test);
- putchar('\n');
-}
-
-static void kpl_test_report_error(kpl_test *_test, bool failed_status) {
- if (failed_status)
- printf(KPL_COLOR2(BOLD, LIGHT_RED) "FAILED " KPL_COLOR(RESET));
- kpl_test_report(_test);
- printf(":" KPL_COLOR(LIGHT_MAGENTA) "%d" KPL_COLOR(RESET) "::"
- KPL_COLOR(LIGHT_RED) "%s\n" KPL_COLOR(RESET), _test->error_line_number, _test->error_message);
-}
-
-static int32_t kpl_test_error_list(void) {
- if (!_kpl_test_error_count) {
- printf(KPL_COLOR2(BOLD, LIGHT_GREEN) "ALL TESTS PASSED\n" KPL_COLOR(RESET));
- return KPL_EXIT_CODE_SUCCESS;
- }
- printf(KPL_COLOR2(BOLD, LIGHT_RED) "FAILED TEST COUNT:" KPL_COLOR(RESET)
- KPL_COLOR(WHITE) " %d\n\n" KPL_COLOR(RESET), _kpl_test_error_count);
- while (_kpl_error_head) {
- kpl_test_report_error(_kpl_error_head, false);
- putchar('\n');
- _kpl_error_head = _kpl_error_head->next_test;
- }
- return KPL_EXIT_CODE_ERROR;
-}
-
-static void kpl_test_run(kpl_test *_test) {
- _test->test_function(_test);
- if (_test->error_line_number == -1) {
- kpl_test_report_success(_test);
- return;
- }
- _kpl_test_error_count++;
- kpl_test_report_error(_test, true);
- if (_kpl_error_head)
- _kpl_error_tail = _kpl_error_tail->next_test = _test;
- else
- _kpl_error_head = _kpl_error_tail = _test;
-}
-
-static kpl_test *kpl_test_next(void) {
- if (!_kpl_test_head)
- return NULL;
- kpl_test *_test = _kpl_test_head;
- _kpl_test_head = _kpl_test_head->next_test;
- _test->next_test = NULL;
- return _test;
-}
-
-static int32_t kpl_test_run_all(void) {
- kpl_test *_test = NULL;
- while ((_test = kpl_test_next()))
- kpl_test_run(_test);
- return kpl_test_error_list();
-}
-
-static int32_t kpl_test_help(const char *argv0) {
- printf("\nUsage: " KPL_COLOR(BOLD) "%s " KPL_COLOR(RESET)
- KPL_COLOR(WHITE) "[OPTIONS] [TEST NAMES]\n\n" KPL_COLOR(RESET), argv0);
- printf("Where " KPL_COLOR(WHITE) "[OPTIONS]" KPL_COLOR(RESET) " are:\n");
- printf(KPL_COLOR(LIGHT_YELLOW) "\t-a " KPL_COLOR(RESET) "Run All Tests\n");
- printf(KPL_COLOR(LIGHT_YELLOW) "\t-h " KPL_COLOR(RESET) "Show Help\n");
- printf(KPL_COLOR(LIGHT_YELLOW) "\t-l " KPL_COLOR(RESET) "List Test Names\n");
- putchar('\n');
- return KPL_EXIT_CODE_HELP;
-}
-
-static int32_t kpl_test_list(void) {
- printf("\nTest Count: " KPL_COLOR(WHITE) "%d\n\n"
- KPL_COLOR(RESET) KPL_COLOR(LIGHT_CYAN), _kpl_test_count);
- while (_kpl_test_head) {
- printf("%s ", _kpl_test_head->test_name);
- _kpl_test_head = _kpl_test_head->next_test;
- }
- printf(KPL_COLOR(RESET) "\n\n");
- return KPL_EXIT_CODE_HELP;
-}
-
-static int32_t kpl_test_run_by_name(const int32_t argc, const char *argv[], const int32_t named_arg_index) {
- if (named_arg_index == argc) {
- printf(KPL_COLOR(LIGHT_RED) "\nNo Tests Specified\n" KPL_COLOR(RESET));
- return kpl_test_help(argv[0]);
- }
- int32_t tests_ran = 0;
- kpl_test *_test = NULL;
- while ((_test = kpl_test_next()))
- for (int32_t test_name_index = named_arg_index; test_name_index < argc; test_name_index++)
- if (strcmp(argv[test_name_index], _test->test_name) == 0) {
- kpl_test_run(_test);
- tests_ran++;
- }
- if (!tests_ran) {
- printf(KPL_COLOR(LIGHT_RED) "\nNo Matching Tests Found, for help run: " KPL_COLOR(RESET)
- KPL_COLOR(BOLD) "%s -h\n\n" KPL_COLOR(RESET), argv[0]);
- return KPL_EXIT_CODE_ERROR;
- }
- return kpl_test_error_list();
-}
-
-int32_t main(const int32_t argc, const char *argv[]) {
- int32_t arg_index = 1;
- while (arg_index < argc) {
- if (argv[arg_index][0] != '-' || !argv[arg_index][1] || argv[arg_index][2])
- break;
- switch (argv[arg_index][1]) {
- case 'a':
- return kpl_test_run_all();
- case 'h':
- return kpl_test_help(argv[0]);
- case 'l':
- return kpl_test_list();
- default:
- return kpl_test_run_by_name(argc, argv, arg_index);
- }
- arg_index++;
- }
- return kpl_test_run_by_name(argc, argv, arg_index);
-}
-
-KPL_TEST(pass_by_default) {
- // Pass by default
- // Uncomment below to f ail
- // KPL_FAIL("Failure message");
-}
-
-KPL_TEST(counting) {
- KPL_ASSERT(_kpl_test_count > 0, "Test counter not incrementing");
-}