Initial commit

This commit is contained in:
2026-06-06 18:15:42 -05:00
commit 7c1b0ab290
24 changed files with 1954 additions and 0 deletions
+152
View File
@@ -0,0 +1,152 @@
# Compiler Flags
CC := gcc
CFLAGS := -g -Wall -Wextra -Werror -pedantic -fno-omit-frame-pointer
DEPFLAGS = -MMD -MP
# Directory Variables
LIBDIR := lib
OBJ := obj
INC := include
SRC := src
TEST := tests
# Install Paths (override with: make install PREFIX=/usr/local)
PREFIX ?= /usr/local
INSTALL_LIB = $(PREFIX)/lib
INSTALL_INC = $(PREFIX)/include
# Platform Detection and Library Linking
ifeq ($(OS), Windows_NT)
PLATFORM := win32
PLATFORM_SRCS := $(wildcard $(SRC)/win32_*.c)
PLATFORM_OBJS := $(patsubst $(SRC)/%.c, $(OBJ)/%.o, $(PLATFORM_SRCS))
PLATFORM_FLAGS := -D WIN32
PLATFORM_LIBS := -mwindows
else
UNAME_S := $(shell uname -s)
ifeq ($(UNAME_S), Linux)
PLATFORM := linux
PLATFORM_SRCS := $(wildcard $(SRC)/linux_*.c)
PLATFORM_OBJS := $(patsubst $(SRC)/%.c, $(OBJ)/%.o, $(PLATFORM_SRCS))
PLATFORM_FLAGS := -D LINUX
PLATFORM_LIBS := -lX11
else ifeq ($(UNAME_S), Darwin)
PLATFORM := mac
PLATFORM_SRCS := $(wildcard $(SRC)/mac_*.c)
PLATFORM_OBJS := $(patsubst $(SRC)/%.c, $(OBJ)/%.o, $(PLATFORM_SRCS))
PLATFORM_FLAGS := -D MACOS
PLATFORM_LIBS :=
else
$(error Unsupported platform: $(UNAME_S))
endif
endif
# Add platform flags
CFLAGS += $(PLATFORM_FLAGS)
# Filepath Pattern Matching
LIB := $(LIBDIR)/lib.a
# Filter out ALL platform-prefixed files, then add back the correct platform's
SRCS := $(filter-out \
$(wildcard $(SRC)/win32_*.c) \
$(wildcard $(SRC)/linux_*.c) \
$(wildcard $(SRC)/macos_*.c), \
$(wildcard $(SRC)/*.c)) \
$(PLATFORM_SRCS)
OBJS := $(patsubst $(SRC)/%.c, $(OBJ)/%.o, $(SRCS))
TESTS := $(wildcard $(TEST)/*.c)
TESTBINS := $(patsubst $(TEST)/%.c, $(TEST)/bin/%, $(TESTS))
# Commands must be labeled PHONY
.PHONY: all release clean test install uninstall
# Compiler Release Flags (no sanitizers — those belong in CI/debug builds)
release: CFLAGS := -Wall -Wextra -Werror -pedantic -fno-omit-frame-pointer -O2 -DNDEBUG $(PLATFORM_FLAGS)
release: clean $(LIB)
@echo "\nRelease build complete for platform: $(PLATFORM)\n"
# Target for compilation
all: $(LIB)
@echo "\nBuilt for platform: $(PLATFORM)\n"
# Target / Dependencies
$(LIB): $(OBJS) | $(LIBDIR)
ar -cvrs $@ $^
# Compile with automatic dependency tracking
$(OBJ)/%.o: $(SRC)/%.c $(SRC)/%.h | $(OBJ)
$(CC) $(CFLAGS) $(DEPFLAGS) -c $< -o $@
$(OBJ)/%.o: $(SRC)/%.c | $(OBJ)
$(CC) $(CFLAGS) $(DEPFLAGS) -c $< -o $@
$(TEST)/bin/%: $(TEST)/%.c $(LIB) | $(TEST)/bin
$(CC) $(CFLAGS) $< $(LIB) $(PLATFORM_LIBS) -o $@
# Make directories if none
$(LIBDIR):
mkdir $@
$(OBJ):
mkdir $@
$(TEST)/bin:
mkdir -p $@
# Run the tests in the bin folder and track results
# Uses perl for nanosecond timing — portable across Linux and macOS
test: $(LIB) $(TESTBINS)
@SUCCESS=0; FAILURE=0; \
RED='\033[0;31m'; GREEN='\033[0;32m'; YELLOW='\033[1;33m'; NC='\033[0m'; \
for t in $(TESTBINS); do \
NAME=$$(basename $$t); \
START=$$(perl -MTime::HiRes=time -e 'printf "%d\n", time()*1000'); \
if $$t; then \
RET=0; \
else \
RET=$$?; \
fi; \
END=$$(perl -MTime::HiRes=time -e 'printf "%d\n", time()*1000'); \
ELAPSED_MS=$$((END - START)); \
if [ $$RET -eq 0 ]; then \
printf "%-20s %bPASS%b (%b%4d ms%b)\n" "$$NAME" "$$GREEN" "$$NC" "$$YELLOW" "$$ELAPSED_MS" "$$NC"; \
SUCCESS=$$((SUCCESS + 1)); \
else \
printf "%-20s %bFAIL%b (%b%4d ms%b)\n" "$$NAME" "$$RED" "$$NC" "$$YELLOW" "$$ELAPSED_MS" "$$NC"; \
FAILURE=$$((FAILURE + 1)); \
fi; \
done; \
printf "\nTests completed\n"; \
printf "SUCCESS: %b%d%b\n" "$$GREEN" "$$SUCCESS" "$$NC"; \
printf "FAILURE: %b%d%b\n" "$$RED" "$$FAILURE" "$$NC"; \
test $$FAILURE -eq 0
# Install library and public headers
install: $(LIB)
@echo "Installing to $(PREFIX)..."
install -d $(INSTALL_LIB)
install -d $(INSTALL_INC)
install -m 644 $(LIB) $(INSTALL_LIB)/
@if [ -d $(INC) ]; then \
install -m 644 $(INC)/*.h $(INSTALL_INC)/; \
echo "Installed headers from $(INC)/"; \
else \
echo "Warning: no $(INC)/ directory found — skipping header install"; \
fi
@echo "Install complete: lib -> $(INSTALL_LIB) headers -> $(INSTALL_INC)"
uninstall:
@echo "Removing installed files from $(PREFIX)..."
$(RM) $(INSTALL_LIB)/lib.a
@if [ -d $(INC) ]; then \
for h in $(INC)/*.h; do \
$(RM) $(INSTALL_INC)/$$(basename $$h); \
done; \
fi
@echo "Uninstall complete"
clean:
$(RM) -r $(LIBDIR) $(OBJ) $(TEST)/bin/
# Pull in generated dependency files (silently ignored if absent)
-include $(DEPS)
+58
View File
@@ -0,0 +1,58 @@
# ci2
## Description
Inspired by all in the acknowledgments, this is my own personal C codebase.
## Table of Contents
* [Features](#features)
* [Todos](#todos)
* [Usage](#usage)
* [Acknowledgments](#acknowledgments)
* [License](#license)
## Features
## Todos
## Usage
```bash
# Example installation
git clone https://myrepos.dev/Randy-Jordan/ci2.git
# Navigate into the directory
cd ci2
# Build the project
make
# Build and run tests.
make test
```
## Acknowledgments
[C Interfaces and Implementations](https://github.com/drh/cii)<br>
[Unix Networking Programming Sockets Networking API](https://www.amazon.com/Unix-Network-Programming-Sockets-Networking/dp/0131411551)<br>
[Advanced Programming in the UNIX Environment](https://www.amazon.com/Advanced-Programming-UNIX-Environment-3rd/dp/0321637739/146-5615695-5426958)<br>
[stsaz - ffsys](https://github.com/stsaz/ffsys)<br>
[nothings - stb](https://github.com/nothings/stb)<br>
[Sean Barret - Advice for writing small programs](https://youtu.be/eAhWIO1Ra6M)<br>
[Eskil Steenberg - How I program C](https://www.youtube.com/watch?v=443UNeGrFoM)<br>
[Ginger Bill](https://www.gingerbill.org/)<br>
[GingerGill gb](https://github.com/gingerBill/gb)<br>
[Chris Wellons](https://nullprogram.com/)<br>
[Skeeto - W64devkit](https://github.com/skeeto/w64devkit)<br>
[Mongoose Webserver](https://github.com/cesanta/mongoose)<br>
[Tsoding Daily](https://www.youtube.com/c/TsodingDaily)<br>
[Jacob Sorber](https://www.youtube.com/@JacobSorber)<br>
[Crafting Interpreters](https://craftinginterpreters.com/)<br>
## License
This project is licensed under the MIT License - see the [MIT License](LICENSE) file for details.
+32
View File
@@ -0,0 +1,32 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_H
#define CI2_H
#include "./platform/ci2_platform.h"
#include "./platform/error/ci2_exception.h"
#include "./platform/mem/ci2_mem.h"
#include "./platform/mem/ci2_arena.h"
#endif // ci2.h
+126
View File
@@ -0,0 +1,126 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_ASSERT_H
#define CI2_ASSERT_H
#include <stdio.h>
/* Force Inline */
#if defined(_MSC_VER) || defined(__INTEL__LLVM_COMPILER)
#define CI2_INLINE __forceinline
#elif defined(__GNUC__) || defined(__clang__)
#define CI2_INLINE __attribute__((always_inline)) inline
#else
#define CI2_INLINE inline
#endif
/* Use __has_builtin if available (Clang and newer GCC). */
#if defined(__has_builtin)
/* Check builtins in preferred order */
#if __has_builtin(__builtin_debugtrap)
#define CI2_DEBUG_TRAP() __builtin_debugtrap()
#elif __has_builtin(__builtin_trap)
#define CI2_DEBUG_TRAP() __builtin_trap()
#elif __has_builtin(__builtin_break)
#define CI2_DEBUG_TRAP() __builtin_break()
#endif
#elif defined(_MSC_VER) || defined(__INTEL__LLVM_COMPILER)
#define CI2_DEBUG_TRAP() __debugbreak()
#else
#define CI2_DEBUG_TRAP() (*(volatile int*)0 = 0)
#endif
/* Static Asserts */
#if defined(__STDC_VERSION__) && (__STDC_VERSION__ >= 201112L)
/* C11 */
#define CI2_STATIC_ASSERT(expr) _Static_assert((expr), #expr)
#else
/* Abuse a typedef of a negative-size array */
#define CI2_STATIC_ASSERT(expr) typedef char _static_assert_[(expr) ? 1 : -1]
#endif
/* Current __func__ */
#if defined(__FUNC__)
#define CI2_FUNC __FUNCTION__
#else
#define CI2_FUNC __func__
#endif
/* Assert Fail */
static CI2_INLINE void
ci2_assert_fail(const char* expr,
const char* msg, /* may be NULL */
const char* file,
int line,
const char* func)
{
if (msg)
fprintf(stderr,
"\n[ASSERT FAILED]\n"
" Expression : %s\n"
" Message : %s\n"
" Location : %s:%d\n"
" Function : %s\n\n",
expr,
msg,
file,
line,
func);
else
fprintf(stderr,
"\n[ASSERT FAILED]\n"
" Expression : %s\n"
" Location : %s:%d\n"
" Function : %s\n\n",
expr,
file,
line,
func);
/* Flush so the message is visible before we halt */
fflush(stderr);
CI2_DEBUG_TRAP();
}
#ifndef NDEBUG
#define CI2_ASSERT(expr) \
do { \
if (!(expr)) { \
ci2_assert_fail(#expr, NULL, __FILE__, __LINE__, CI2_FUNC); \
} \
} while (0)
#define CI2_ASSERT_MSG(expr, msg) \
do { \
if (!(expr)) { \
ci2_assert_fail(#expr, (msg), __FILE__, __LINE__, CI2_FUNC); \
} \
} while (0)
#else /* NDEBUG — strip all runtime checks */
#define ASSERT(expr) ((void)(expr))
#define ASSERT_MSG(expr, msg) ((void)(expr))
#endif /* NDEBUG */
#endif // ci2_assert.h
+49
View File
@@ -0,0 +1,49 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_BASE_H
#define CI2_BASE_H
#include "ci2_assert.h"
#include "ci2_compiler.h"
#include "ci2_os.h"
#include "ci2_thread.h"
#include "ci2_win_env.h"
#include "ci2_macros.h"
#include "ci2_syntax.h"
/* Here is where we abstract away the differnces between Operating Systems */
#if defined CI2_UNIX
#define CI2_INVALID_FD -1
typedef int ci2_fd;
typedef char ci2_sys_char;
#else // Windows:
#define CI2_INVALID_FD NULL
typedef HANDLE ci2_fd;
typedef wchar_t ci2_sys_char;
#endif
#endif // ci2_base.h
+38
View File
@@ -0,0 +1,38 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_COMPILER_H
#define CI2_COMPILER_H
#if defined(__INTEL_LLVM_COMPILER)
#define CI2_INTEL_ICX
#elif defined(__GNUC__) && !defined(__clang__)
#define CI2_GCC
#elif defined(__clang__)
#define CI2_CLANG
#elif define(_MSC_VER) && !defined(__clang__)
#define CI2_MSVC
#else
#error "Compiler is unkown and unsupported."
#endif
#endif // ci2_compiler.h
+101
View File
@@ -0,0 +1,101 @@
/* - | Copyright |
-------------------------------------------------------------- Copyright (c)
2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_MACROS_H
#define CI2_MACROS_H
#define UNUSED(x) (void)(x)
#define STR2(s) #s
#define STR(s) STR2(s)
#define U8_MIN 0u
#define U8_MAX 0xffu
#define I8_MIN (-0x7f - 1)
#define I8_MAX 0x7f
#define U16_MIN 0u
#define U16_MAX 0xffffu
#define I16_MIN (-0x7fff - 1)
#define I16_MAX 0x7fff
#define U32_MIN 0u
#define U32_MAX 0xffffffffu
#define I32_MIN (-0x7fffffff - 1)
#define I32_MAX 0x7fffffff
#define U64_MIN 0ull
#define U64_MAX 0xffffffffffffffffull
#define I64_MIN (-0x7fffffffffffffffll - 1)
#define I64_MAX 0x7fffffffffffffffll
#define F32_MIN 1.17549435e-38f
#define F32_MAX 3.40282347e+38f
#define F64_MIN 2.2250738585072014e-308
#define F64_MAX 1.7976931348623157e+308
#define PI 3.14159265
#define RAD2DEG(x) ((x) / PI * 180)
#define DEG2RAD(x) ((x) * PI / 180)
#define ALIGNB(x, align) (((x) + ((align) - 1)) & ~((align) - 1))
#define ALIGN(x, align) ((((x) + ((align) - 1)) / (align)) * (align))
#define FLOORB(x, align) ((x) & ~((align) - 1))
#define FLOOR(x, align) (((x) / (align)) * (align))
#define CEILB(x, align) ALIGNB(x, align)
#define CEIL(x, align) ALIGN(x, align)
#define CLIP(x, min, max) \
(((x) < (min)) ? (min) : (((x) > (max)) ? (max) : (x)))
#define UCLIP(x, max) (((x) > (max)) ? (max) : (x))
#define LCLIP(x, min) (((x) < (min)) ? (min) : (x))
#define MIN(x, y) (((x) < (y)) ? (x) : (y))
#define MAX(x, y) (((x) > (y)) ? (x) : (y))
#define ABS(x) (((x) < 0) ? -(x) : (x))
#define DIFF(a, b) ABS((a) - (b))
#define IS_NAN(x) ((x) != (x))
#define IMPLIES(x, y) (!(x) || (y))
#define COMPARE(x, y) (((x) > (y)) - ((x) < (y)))
#define SIGN(x) COMPARE(x, 0)
#define IS_ODD(num) ((num) & 1)
#define IS_EVEN(num) (!IS_ODD((num)))
#define IS_BETWEEN(n, L, H) ((unsigned char)((n) >= (L) && (n) <= (H)))
#define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0]))
#define SET(d, n, v) \
do { \
size_t i_, n_; \
for (n_ = (n), i_ = 0; n_ > 0; --n_, ++i_) \
(d)[i_] = (v); \
} while (0)
#define ZERO(d, n) SET(d, n, 0)
#define SWAP(a, b) \
do { \
a ^= b; \
b ^= a; \
a ^= b; \
} while (0)
#define SORT(a, b) \
do { \
if ((a) > (b)) \
SWAP((a), (b)); \
} while (0)
#endif // ci2_macros.h
+81
View File
@@ -0,0 +1,81 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_OS_H
#define CI2_OS_H
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__NT__)
/* Entire windows platform */
#define CI2_WIN_APIVER 0x0600 // Vista
#define NOMINMAX // Don't define min/max macros
#define _CRT_SECURE_NO_WARNINGS // No unsafe C warnings
#define _CRT_RAND_S // TODO
#define OEMRESOURCE // GUI must be before windows.h
#include <windows.h> // haha
#define CI2_WINDOWS
#ifdef _WIN64
/* Windows (64-bit only) */
#define CI2_WINDOWS_64
#else
/* Windows (32-bit only) */
#define CI2_WINDOWS_32
#endif
#elif __APPLE__
#define CI2_UNIX
#define CI2_APPLE
#include <TargetConditionals.h>
#if TARGET_IPHONE_SIMULATOR
// iOS, tvOS, or watchOS Simulator
#define CI2_IOS
#elif TARGET_OS_MACCATALYST
// Mac's Catalyst (ports iOS API into Mac, like UIKit).
#define CI2_IOS
#elif TARGET_OS_IPHONE
// iOS, tvOS, or watchOS device
#define CI2_IOS
#elif TARGET_OS_MAC
// Other kinds of Apple platforms
#define CI2_OSX
#else
#error "Unknown Apple platform"
#endif
#elif __ANDROID__
#define CI2_UNIX
#define CI2_ANDROID
#elif __linux__
#define CI2_UNIX
#elif __unix__ // TODO BSD Variants
#define CI2_UNIX
#elif defined(_POSIX_VERSION)
#define CI2_POSIX
#else
#error "Unknown and unsupported operating system."
#endif
#endif // ci2_os.h
+68
View File
@@ -0,0 +1,68 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_SYNTAX_H
#define CI2_SYNTAX_H
/* Floating Points */
typedef float ci2_f32; // IEEE 754
typedef double ci2_f64; // IEE 754
/* Characters */
typedef signed char ci2_char; // [127, +127]
typedef unsigned char ci2_uchar; // [0, 255]
typedef unsigned char ci2_byte; // [0, 255]
typedef unsigned char* ci2_bytes; // Pointer
/* Integers */
typedef signed short ci2_short; // [32,767, 32,767]
typedef unsigned short ci2_ushort; // [0, 65,535]
typedef signed int ci2_int; // [32,767, 32,767]
typedef unsigned int ci2_uint; // [0, 65,535]
typedef signed long int ci2_long; // [2,147,483,647, 2,147,483,647]
typedef unsigned long int ci2_ulong; // [0, 4,294,967,295]
#if defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L
#include <inttypes.h>
#include <stddef.h>
#include <stdint.h>
// 9223372036854775807
typedef unsigned long long int ci2_ull; // +9223372036854775807 range.
typedef signed long long int ci2_ll; //[0, 18446744073709551615] range.
typedef int8_t i8;
typedef int16_t i16;
typedef int32_t i32;
typedef int64_t i64;
typedef uint8_t u8;
typedef uint16_t u16;
typedef uint32_t u32;
typedef uint64_t u64;
typedef uintptr_t uptr;
typedef ptrdiff_t size;
typedef size_t usize;
#endif
#endif // ci2_syntax.h
+37
View File
@@ -0,0 +1,37 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_THREAD_H
#define CI2_THREAD_H
#if !defined(ci2_thread_local)
#if defined(_MSC_VER) && _MSC_VER >= 1300
#define ci2_thread_local __declspec(thread)
#elif defined(__GNUC__)
#define ci2_thread_local __thread
#else
#define ci2_thread_local thread_local
#endif
#endif
#endif // ci2_thread.h
+37
View File
@@ -0,0 +1,37 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_WIN_ENV_H
#define CI2_WIN_ENV_H
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__NT__)
#if defined __MINGW32__ || defined __MINGW64__
#define CI2_WIN_ENV
#define CI2_MINGW
#elif defined __CYGWIN__
#define CI2_WIN_ENV
#define CI2_CYGWIN
#endif
#endif
#endif // ci2_win_env.h
+94
View File
@@ -0,0 +1,94 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_PLATFORM_H
#define CI2_PLATFORM_H
#include "./base/ci2_base.h"
/* No name mangling for declarations---------------------------------------- */
#ifdef __cplusplus
extern "C"
{
#endif
/* CI2_EXTERN: plain extern with C++ aware linkage token for macros if needed */
#if defined(__cplusplus)
#define CI2_EXTERN extern "C"
#else
#define CI2_EXTERN extern
#endif
/* CI2_API: platform/compiler-aware import/export/visibility */
#if defined(_WIN32) || defined(__CYGWIN__)
#if defined(CI2_BUILD_DLL)
#define CI2_API CI2_EXTERN __declspec(dllexport)
#elif defined(CI2_USE_DLL)
#define CI2_API CI2_EXTERN __declspec(dllimport)
#else
#define CI2_API CI2_EXTERN
#endif
#else
/* Non-Windows: use visibility if supported */
#if defined(__GNUC__) || defined(__clang__) || defined(__INTEL_LLVM_COMPILER)
#if defined(CI2_BUILD_DLL)
#define CI2_API CI2_EXTERN __attribute__((visibility("default")))
#else
#define CI2_API CI2_EXTERN
#endif
#else
#define CI2_API CI2_EXTERN
#endif
#endif
/* CI2_DEF: internal vs external linkage */
#ifndef CI2_DEF
#ifdef CI2_STATIC
#define CI2_DEF static
#else
#define CI2_DEF CI2_API
#endif
#endif
#define CI2_SUCCESS 0
#define CI2_FAILURE -1
#define CI2_TRUE 1
#define CI2_FALSE 0
#define CI2_SIZE(x) (ptrdiff_t)sizeof(x)
#define CI2_COUNT(a) (sizeof(a) / sizeof(*(a)))
#define CI2_LEN(s) (countof(s) - 1)
#define CI2_KB(x) ((x) * (size_t)(1024))
#define CI2_MB(x) (CI2_KB(x) * (size_t)(1024))
#define CI2_GB(x) (CI2_MB(x) * (size_t)(1024))
#define CI2_TB(x) (CI2_GB(x) * (size_t)(1024))
CI2_API ci2_thread_local int ci2_errno;
CI2_API int* ci2_errno_location(void);
/*---------------------------------------------------------------------------*/
#ifdef __cplusplus
}
#endif // c++
#endif // ci2_platform.h
+188
View File
@@ -0,0 +1,188 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_EXCEPTION_H
#define CI2_EXCEPTION_H
#include "../ci2_platform.h"
#include <setjmp.h>
struct Exception
{
const char* msg;
};
typedef struct Exception Exception;
struct Exception_Frame
{
struct Exception_Frame* prev;
jmp_buf env;
const char* file;
const char* func;
int line;
const struct Exception* exception;
};
typedef struct Exception_Frame Exception_Frame;
enum
{
EXCEPTION_ENTERED = 0,
EXCEPTION_RAISED,
EXCEPTION_HANDLED,
EXCEPTION_FINALIZED
};
CI2_API const struct Exception assertion_failed;
CI2_API void
ci2_try_assert(int cond);
CI2_API void
ci2_raise_exception(const struct Exception* e,
const char* file,
const char* func,
int line);
#if defined(CI2_WINDOWS)
CI2_DEF DWORD exception_stack;
CI2_DEF void
ci2_exception_init(void);
CI2_DEF void
ci2_exception_push(struct Exception_Frame* fp);
CI2_DEF void
ci2_exception_pop(void);
#define CI2_RAISE(e) ci2_raise_exception(&(e), __FILE__, CI2_FUNC, __LINE__)
#define CI2_RERAISE \
ci2_raise_exception(exception_frame.exception, \
exception_frame.file, \
exception_frame.func, \
exception_frame.line)
#define CI2_RETURN \
switch (ci2_exception_pop(), 0) \
default: \
return
#define CI2_TRY \
do { \
volatile int exception_flag; \
Exception_Frame exception_frame; \
if (exception_stack == TLS_OUT_OF_INDEXES) \
ci2_exception_init(); \
ci2_exception_push(&exception_frame); \
exception_flag = setjmp(exception_frame.env); \
if (exception_flag == EXCEPTION_ENTERED) {
#define CI2_EXCEPT(e) \
if (exception_flag == EXCEPTION_ENTERED) \
ci2_exception_pop(); \
} \
else if (exception_frame.exception == &(e)) \
{ \
exception_flag = EXCEPTION_HANDLED;
#define CI2_ELSE \
if (exception_flag == EXCEPTION_ENTERED) \
ci2_exception_pop(); \
} \
else \
{ \
exception_flag = EXCEPTION_HANDLED;
#define CI2_FINALLY \
if (exception_flag == EXCEPTION_ENTERED) \
ci2_exception_pop(); \
} \
{ \
if (exception_flag == EXCEPTION_ENTERED) \
exception_flag = EXCEPTION_FINALIZED;
#define CI2_END_TRY \
if (exception_flag == EXCEPTION_ENTERED) \
ci2_exception_pop(); \
} \
if (exception_flag == EXCEPTION_RAISED) \
CI2_RERAISE; \
} \
while (0)
#else // UNIX
CI2_DEF struct Exception_Frame* exception_stack;
#define CI2_RAISE(e) ci2_raise_exception(&(e), __FILE__, CI2_FUNC, __LINE__)
#define CI2_RERAISE \
ci2_raise_exception(exception_frame.exception, \
exception_frame.file, \
exception_frame.func, \
exception_frame.line)
#define CI2_RETURN \
switch (exception_stack = exception_stack->prev, 0) \
default: \
return
#define CI2_TRY \
do { \
volatile int exception_flag; \
Exception_Frame exception_frame; \
exception_frame.prev = exception_stack; \
exception_stack = &exception_frame; \
exception_flag = setjmp(exception_frame.env); \
if (exception_flag == EXCEPTION_ENTERED) {
#define CI2_EXCEPT(e) \
if (exception_flag == EXCEPTION_ENTERED) \
exception_stack = exception_stack->prev; \
} \
else if (exception_frame.exception == &(e)) \
{ \
exception_flag = EXCEPTION_HANDLED;
#define CI2_ELSE \
if (exception_flag == EXCEPTION_ENTERED) \
exception_stack = exception_stack->prev; \
} \
else \
{ \
exception_flag = EXCEPTION_HANDLED;
#define CI2_FINALLY \
if (exception_flag == EXCEPTION_ENTERED) \
exception_stack = exception_stack->prev; \
} \
{ \
if (exception_flag == EXCEPTION_ENTERED) \
exception_flag = EXCEPTION_FINALIZED;
#define CI2_END_TRY \
if (exception_flag == EXCEPTION_ENTERED) \
exception_stack = exception_stack->prev; \
} \
if (exception_flag == EXCEPTION_RAISED) \
CI2_RERAISE; \
} \
while (0)
#endif
#endif // ci2_exception.h
+67
View File
@@ -0,0 +1,67 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_ARENA_H
#define CI2_ARENA_H
#include "../ci2_platform.h"
#include "../error/ci2_exception.h"
enum
{
DEFAULT = 0, /* default: fail-handler (throws) + zero */
SOFT_FAIL = 1u << 0, /* on failure return NULL */
HARD_FAIL = 1u << 1, /* on failure call abort() */
NO_ZERO = 1u << 2, /* do not zero memory on success */
};
struct Arena
{
char* beg;
char* end;
};
typedef struct Arena Arena;
/* Forward definition of an exception */
CI2_API struct Exception arena_oom;
/* Initialize an Arena from a buffer. */
CI2_API void
arena_init(struct Arena* a, void* buf, ptrdiff_t len);
/* Dynamically allocate an Arena */
CI2_API struct Arena
arena_new(ptrdiff_t cap);
/* Get the remaining capicity of an arena. */
CI2_API ptrdiff_t
arena_size(struct Arena a);
/* Make an allocation from an Arena. */
CI2_API void*
arena_alloc(struct Arena* a,
int flags,
ptrdiff_t size,
ptrdiff_t align,
ptrdiff_t count);
#endif // ci2_arena.h
+69
View File
@@ -0,0 +1,69 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#ifndef CI2_MEM_H
#define CI2_MEM_H
#include "../error/ci2_exception.h"
#include <stddef.h>
/* Out of memory exception forward declaration. */
CI2_API const struct Exception oom;
/* Allocate an object and do not zero. May throw exception. */
CI2_API void*
ci2_malloc(size_t nbytes, const char* file, const char* func, int line);
/* Allocate an object and zero ci2ory. May throw exception. */
CI2_API void*
ci2_calloc(size_t count,
size_t nbytes,
const char* file,
const char* func,
int line);
/* Free and null a pointer */
CI2_API void
ci2_free(void** ptr, const char* file, const char* func, int line);
/* Resize a non-null pointer */
CI2_API void*
ci2_resize(void* ptr,
size_t nbytes,
const char* file,
const char* func,
int line);
#define CI2_MALLOC(nbytes) ci2_malloc((nbytes), __FILE__, CI2_FUNC, __LINE__)
#define CI2_CALLOC(count, nbytes) \
ci2_calloc((count), (nbytes), __FILE__, CI2_FUNC, __LINE__)
#define CI2_NEW(p) ((p) = CI2_MALLOC((size_t)sizeof *(p)))
#define CI2_NEW0(p) ((p) = CI2_CALLOC(1, (size_t)sizeof *(p)))
#define CI2_FREE(ptr) \
((void)(ci2_free((ptr), __FILE__, CI2_FUNC, __LINE__), (ptr) = 0))
#define CI2_RESIZE(ptr, nbytes) \
((ptr) = ci2_resize((ptr), (nbytes), __FILE__, CI2_FUNC, __LINE__))
#endif // ci2_mem.h
+80
View File
@@ -0,0 +1,80 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#include "../include/platform/mem/ci2_arena.h"
#include <string.h>
#include <stdlib.h>
struct Exception arena_oom = {"Arena is out of memory!"};
/* Initialize an Arena from a buffer. */
void
arena_init(struct Arena* a, void* buf, ptrdiff_t len)
{
CI2_ASSERT(buf != NULL);
CI2_ASSERT(len > 0);
a->beg = (char*)buf;
a->end = (char*)buf + len;
}
/* Dynamically allocate an Arena */
struct Arena
arena_new(ptrdiff_t cap)
{
struct Arena a = { 0 };
a.beg = malloc(cap);
a.end = a.beg ? a.beg + cap : 0;
return a;
}
/* Get the remaining capicity of an arena. */
ptrdiff_t
arena_size(struct Arena a)
{
ptrdiff_t res = a.end - a.beg;
return res;
}
/* Make an allocation from an Arena. */
void*
arena_alloc(struct Arena* a,
int flags,
ptrdiff_t size,
ptrdiff_t align,
ptrdiff_t count)
{
ptrdiff_t padding = -(uintptr_t)a->beg & (align - 1);
ptrdiff_t available = a->end - a->beg - padding;
if (available < 0 || count > available / size) {
if (flags & SOFT_FAIL)
return 0;
if (flags & HARD_FAIL)
CI2_DEBUG_TRAP();
CI2_RAISE(arena_oom);
}
void* p = a->beg + padding;
ptrdiff_t total = padding + count * size;
a->beg += total;
return flags & NO_ZERO ? p : memset(p, 0, total);
}
+94
View File
@@ -0,0 +1,94 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#include "../include/platform/mem/ci2_mem.h"
#include <stdlib.h>
const struct Exception oom = { "Out of Memory!" };
void*
ci2_malloc(size_t nbytes, const char* file, const char* func, int line)
{
void* ptr;
ci2_try_assert(nbytes > 0);
ptr = malloc(nbytes);
if (ptr == NULL) {
if (file == NULL)
CI2_RAISE(oom);
else
ci2_raise_exception(&oom, file, func, line);
}
return ptr;
}
void*
ci2_calloc(size_t count,
size_t nbytes,
const char* file,
const char* func,
int line)
{
void* ptr;
ci2_try_assert(count > 0);
ci2_try_assert(nbytes > 0);
ptr = calloc(count, nbytes);
if (ptr == NULL) {
if (file == NULL)
CI2_RAISE(oom);
else
ci2_raise_exception(&oom, file, func, line);
}
return ptr;
}
void
ci2_free(void** ptr, const char* file, const char* func, int line)
{
UNUSED(file);
UNUSED(func);
UNUSED(line);
if (ptr && *ptr) {
free(*ptr);
*ptr = NULL;
}
}
void*
ci2_resize(void* ptr,
size_t nbytes,
const char* file,
const char* func,
int line)
{
ci2_try_assert(ptr != NULL);
ci2_try_assert(nbytes > 0);
void* temp = realloc(ptr, nbytes);
if (temp == NULL) {
if (file == NULL)
CI2_RAISE(oom);
else
ci2_raise_exception(&oom, file, func, line);
}
ptr = temp;
return ptr;
}
+66
View File
@@ -0,0 +1,66 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#include "../include/platform/error/ci2_exception.h"
struct Exception_Frame *exception_stack = NULL;
const struct Exception assertion_failed = {"CI2 Assertion Failed"};
void ci2_try_assert(int cond)
{
if(!cond){
CI2_RAISE(assertion_failed);
}
}
void ci2_raise_exception(
const struct Exception *e,
const char *file,
const char *func,
int line)
{
struct Exception_Frame *p = exception_stack;
ci2_try_assert(e != NULL);
if (p == NULL) {
fprintf(stderr, "Uncaught exception");
if (e->msg)
fprintf(stderr, " %s", e->msg);
else
fprintf(stderr, " at 0x%p", (void*)e);
if (file && line > 0)
fprintf(stderr, " raised at %s:%d", file, line);
if (func != NULL)
fprintf(stderr,":%s",func);
fprintf(stderr, "\ninitiating debug trap...\n");
fflush(stderr);
CI2_DEBUG_TRAP();
}
p->exception = e;
p->file = file;
p->func = func;
p->line = line;
exception_stack = exception_stack->prev;
longjmp(p->env, EXCEPTION_RAISED);
}
+94
View File
@@ -0,0 +1,94 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#include "../include/platform/error/ci2_exception.h"
DWORD exception_stack = -1;
const struct Exception assertion_failed = {"CI2 Assertion Failed"};
void ci2_try_assert(int cond)
{
if(!cond){
CI2_RAISE(assertion_failed);
}
}
void ci2_raise_exception(
const struct Exception *e,
const char *file,
const char *func,
int line)
{
struct Exception_Frame *p;
if (exception_stack == TLS_OUT_OF_INDEXES)
ci2_exception_init();
p = TlsGetValue(exception_stack);
ci2_try_assert(e != NULL);
if (p == NULL) {
fprintf(stderr, "Uncaught exception");
if (e->msg)
fprintf(stderr, " %s", e->msg);
else
fprintf(stderr, " at 0x%p", (void *)e);
if (file && line > 0)
fprintf(stderr, " raised at %s:%d", file, line);
if(func != NULL)
fprintf(stderr,":%s",func);
fprintf(stderr, "\nInitiating debug trap/break...\n");
fflush(stderr);
CI2_DEBUG_TRAP();
}
p->exception = e;
p->file = file;
p->func = func;
p->line = line;
ci2_exception_pop();
longjmp(p->env, EXCEPTION_RAISED);
}
void ci2_exception_init(void) {
BOOL cond;
exception_stack = TlsAlloc();
ci2_try_assert(exception_stack != TLS_OUT_OF_INDEXES);
cond = TlsSetValue(exception_stack, NULL);
ci2_try_assert(cond == TRUE);
}
void ci2_exception_push(struct Exception_Frame *fp) {
BOOL cond;
fp->prev = TlsGetValue(exception_stack);
cond = TlsSetValue(exception_stack, fp);
ci2_try_assert(cond == TRUE);
}
void ci2_exception_pop(void) {
BOOL cond;
struct Exception_Frame *tos = TlsGetValue(exception_stack);
cond = TlsSetValue(exception_stack, tos->prev);
ci2_try_assert(cond == TRUE);
}
+60
View File
@@ -0,0 +1,60 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#define DEBUG
#include "../include/ci2.h"
#include <stdio.h>
#include <stdlib.h>
#include <limits.h> /* INT_MAX, CHAR_BIT — C standard */
#include <float.h> /* FLT_MANT_DIG — C standard */
int main(int argc, char *argv[]){
(void) argc;
(void) argv;
/* Fundamental type sizes that almost all C code silently assumes. */
CI2_STATIC_ASSERT(CHAR_BIT == 8);
CI2_STATIC_ASSERT(sizeof(char) == 1);
CI2_STATIC_ASSERT(sizeof(short) == 2);
CI2_STATIC_ASSERT(sizeof(int) == 4);
CI2_STATIC_ASSERT(sizeof(float) == 4);
CI2_STATIC_ASSERT(sizeof(double) == 8);
/* Pointer and size_t width — catches ILP64 oddities. */
CI2_STATIC_ASSERT(sizeof(void *) == sizeof(size_t));
/* Fixed-width types from <stdint.h> */
CI2_STATIC_ASSERT(sizeof(uint8_t) == 1);
CI2_STATIC_ASSERT(sizeof(uint16_t) == 2);
CI2_STATIC_ASSERT(sizeof(uint32_t) == 4);
CI2_STATIC_ASSERT(sizeof(uint64_t) == 8);
CI2_STATIC_ASSERT(sizeof(int8_t) == 1);
CI2_STATIC_ASSERT(sizeof(int16_t) == 2);
CI2_STATIC_ASSERT(sizeof(int32_t) == 4);
CI2_STATIC_ASSERT(sizeof(int64_t) == 8);
/* IEEE-754 single precision: 24 significand bits. */
CI2_STATIC_ASSERT(FLT_MANT_DIG == 24);
return EXIT_SUCCESS;
}
+107
View File
@@ -0,0 +1,107 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#define DEBUG
#include "../include/ci2.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/* Platform-specific verification headers */
#if defined(CI2_WINDOWS)
#include <windows.h> /* GetSystemInfo, SYSTEM_INFO */
#elif defined(CI2_UNIX)
#include <sys/utsname.h>/* uname() — POSIX */
#include <unistd.h> /* sysconf, _SC_* constants — POSIX */
#endif
int
main(int argc, char* argv[])
{
(void)argc;
(void)argv;
#if defined(CI2_WINDOWS)
printf(" Detected platform : Windows\n");
/*
* GetSystemInfo() is a Win32 API that fills SYSTEM_INFO.
* If _WIN32 were wrong this wouldn't compile or link.
*/
SYSTEM_INFO si;
GetSystemInfo(&si);
printf(" Page size : %lu bytes\n", (unsigned long)si.dwPageSize);
printf(" Processor count : %lu\n", (unsigned long)si.dwNumberOfProcessors);
printf(" Processor arch : %u\n", (unsigned)si.wProcessorArchitecture);
CI2_ASSERT(si.dwPageSize > 0);
CI2_ASSERT(si.dwNumberOfProcessors > 0);
#elif defined(CI2_UNIX)
/*
* uname() fills a struct utsname with kernel name, release, machine, etc.
* This is a POSIX function — available on Linux, macOS, and all BSDs.
* It won't compile on Windows, proving our platform guard is correct.
*/
struct utsname uts;
int ret = uname(&uts);
CI2_ASSERT(ret == 0);
printf(" Detected platform : Unix-like\n");
printf(" OS / sysname : %s\n", uts.sysname);
printf(" Kernel release : %s\n", uts.release);
printf(" Machine arch : %s\n", uts.machine);
printf(" Node name : %s\n", uts.nodename);
/*
* sysconf() is another POSIX function.
* _SC_PAGESIZE and _SC_NPROCESSORS_ONLN are available on Linux & macOS.
*/
long page_size = sysconf(_SC_PAGESIZE);
long n_cpus = sysconf(_SC_NPROCESSORS_ONLN);
printf(" Page size : %ld bytes\n", page_size);
printf(" CPUs online : %ld\n", n_cpus);
CI2_ASSERT(page_size > 0);
CI2_ASSERT(n_cpus > 0);
/* Sanity: page size is always a power of two */
CI2_ASSERT((page_size & (page_size - 1)) == 0);
#if defined(CI2_LINUX)
printf(" Sub-platform : Linux\n");
CI2_ASSERT(strlen(uts.sysname) > 0);
#elif defined(CI2_MACOS)
printf(" Sub-platform : macOS\n");
CI2_ASSERT(strlen(uts.sysname) > 0);
#endif
#else
printf(" [FAIL] No platform macro was defined!\n");
return EXIT_FAILURE;
#endif
return EXIT_SUCCESS;
}
+57
View File
@@ -0,0 +1,57 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#define DEBUG
#include "../include/ci2.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char *argv[]){
(void) argc;
(void) argv;
#if defined(CI2_INTEL_ICX)
printf(" Detected compiler : INTEL-IXC\n");
printf(" __INTEL_LLVM_COMPILER VER: %d\n", __INTEL_LLVM_COMPILER);
CI2_ASSERT(__INTEL_LLVM_COMPILER > 0);
#elif defined(CI2_GCC)
printf(" Detected compiler : GCC\n");
printf(" GCC __VERSION__: %s\n", __VERSION__);
CI2_ASSERT(strlen(__VERSION__) > 0);
#elif defined(CI2_CLANG)
printf(" Detected compiler : CLANG\n");
printf(" __clang_version__: %s\n", __clang_version__);
CI2_ASSERT(strlen(__clang_version__) > 0);
#elif defined(CI2_MSVC)
printf(" Detected compiler : MSVC\n");
printf(" _MSC_VER : %d\n", _MSC_VER);
CI2_ASSERT(_MSC_VER > 0);
#else
printf(" [FAIL] No compiler macro was defined!\n");
return EXIT_FAILURE;
#endif
return EXIT_SUCCESS;
}
+109
View File
@@ -0,0 +1,109 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#define DEBUG
#include "../include/ci2.h"
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h> /* bool, true, false — C99 */
#include <string.h> /* strcmp — C standard */
static void test_assert_passing(void){
/* Basic truthy values */
CI2_ASSERT(1);
CI2_ASSERT(1 == 1);
/* Pointer non-null */
const char *str = "hello";
CI2_ASSERT(str != NULL);
/* Arithmetic */
int x = 42;
CI2_ASSERT(x > 0);
CI2_ASSERT(x * 2 == 84);
/* CI2_ASSERT_MSG variants */
CI2_ASSERT_MSG(x == 42, "x must be 42");
CI2_ASSERT_MSG(sizeof(int) == 4, "int must be 4 bytes on this platform");
/* Boolean */
bool flag = true;
CI2_ASSERT(flag);
}
static void test_assert_failing(void){
printf(" Triggering CI2_ASSERT(0) failure now...\n");
fflush(stdout);
CI2_ASSERT(0); /* <-- should break/trap here */
/* Should never reach here */
printf(" [FAIL] Execution continued past a failing CI2_ASSERT!\n");
}
static void test_assert_msg_failing(void){
printf("CI2_ASSERT_MSG — Deliberate Failure (triggering a debug break...)\n");
fflush(stdout);
CI2_ASSERT_MSG(0, "This failure is intentional — testing the message path");
printf(" [FAIL] Execution continued past a failing CI2_ASSERT_MSG!\n");
}
static void test_ndebug_status(void){
printf("NDEBUG / Release Mode");
#ifdef NDEBUG
printf(" NDEBUG is DEFINED — asserts are compiled out.\n");
CI2_ASSERT(0); /* harmless in release */
printf(" Confirmed: CI2_ASSERT(0) was a no-op.\n");
#else
printf(" NDEBUG is NOT defined — asserts are active (debug build).\n");
#endif
}
int main(int argc, char *argv[]){
(void) argc;
(void) argv;
/* Determine whether the user wants to trigger a deliberate failure */
bool run_fail = false;
bool run_fail_msg = false;
for (int i = 1; i < argc; i++) {
if (strcmp(argv[i], "--fail") == 0) run_fail = true;
if (strcmp(argv[i], "--fail-msg") == 0) run_fail_msg = true;
}
/* --- Run the safe tests --- */
test_assert_passing();
test_ndebug_status();
/* --- Optional deliberate-failure tests --- */
if (run_fail) test_assert_failing();
if (run_fail_msg) test_assert_msg_failing();
if (!run_fail && !run_fail_msg) {
printf("Tip: run with --fail or --fail-msg to test the");
printf(" debug-break path (attach a debugger first).\n");
}
return EXIT_SUCCESS;
}
+90
View File
@@ -0,0 +1,90 @@
/* - | Copyright | ------------------------------------------------------------
Copyright (c) 2026 Randy Jordan
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, and to permit persons to whom the Software is furnished to do
so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
* --------------------------------------------------------------------------*/
#define DEBUG
#include "../include/ci2.h"
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h> /* bool, true, false — C99 */
#include <string.h> /* strcmp — C standard */
static void test_assert_passing(void){
/* Basic truthy values */
ci2_try_assert(1);
ci2_try_assert(1 == 1);
/* Pointer non-null */
const char *str = "hello";
ci2_try_assert(str != NULL);
/* Arithmetic */
int x = 42;
ci2_try_assert(x > 0);
ci2_try_assert(x * 2 == 84);
/* Boolean */
bool flag = true;
ci2_try_assert(flag);
}
static void test_assert_failing(void){
printf(" Triggering ci2_try_assert(0) failure now...\n");
fflush(stdout);
ci2_try_assert(0); /* <-- should break/trap here */
/* Should never reach here */
printf(" [FAIL] Execution continued past a failing ci2_try_assert!\n");
}
static void test_ndebug_status(void){
printf("NDEBUG / Release Mode");
#ifdef NDEBUG
printf(" NDEBUG is DEFINED — asserts are compiled out.\n");
ci2_try_assert(0); /* harmless in release */
printf(" Confirmed: ci2_try_assert(0) was a no-op.\n");
#else
printf(" NDEBUG is NOT defined — asserts are active (debug build).\n");
#endif
}
int main(int argc, char *argv[]){
(void) argc;
(void) argv;
/* Determine whether the user wants to trigger a deliberate failure */
bool run_fail = false;
for (int i = 1; i < argc; i++) {
if (strcmp(argv[i], "--fail") == 0) run_fail = true;
}
/* --- Run the safe tests --- */
test_assert_passing();
test_ndebug_status();
/* --- Optional deliberate-failure tests --- */
if (run_fail) test_assert_failing();
if (!run_fail) {
printf("Tip: run with --fail to test the exceptions");
}
return EXIT_SUCCESS;
}