Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
45 commits
Select commit Hold shift + click to select a range
fdf90a3
add cross-platform check to cmake
f1ammable Oct 31, 2025
7489254
wip support for function calls
f1ammable Nov 3, 2025
5708bb6
Working function calling prototype
f1ammable Nov 11, 2025
beaa18e
define functions in environment instead of scanner
f1ammable Dec 15, 2025
58f49ec
add support for multiple arguments
f1ammable Dec 17, 2025
75b3146
remove need for semicolon at end
f1ammable Dec 17, 2025
73ffaa4
avoid defining stdlib functions more than once
f1ammable Dec 19, 2025
90c4a96
add pre-commit hook for clang-format
f1ammable Dec 19, 2025
caa506c
split command-line functionality and core functionality into libraries
f1ammable Dec 21, 2025
1606f85
add test coverage, add catch2 dependency
f1ammable Dec 21, 2025
14b3346
add scanner tests, fix uncaught scanner exceptions
f1ammable Dec 21, 2025
8c4cda2
remove print statement; remove synchronisation on errors
f1ammable Dec 30, 2025
817608e
produce only one statement whilst parsing
f1ammable Dec 30, 2025
e7bd6f4
move test helpers to separate file
f1ammable Dec 30, 2025
bd9bab7
add tests for parser
f1ammable Dec 30, 2025
340ace4
remove use of exceptions
f1ammable Dec 30, 2025
9be6882
adjust tests to remove exception checks
f1ammable Dec 30, 2025
6180dbf
Merge pull request #1 from f1ammable/remove-exceptions
f1ammable Dec 30, 2025
b3da518
improve equality operator correctness for object type
f1ammable Dec 31, 2025
c67c2c4
add first test case for `Object` type
f1ammable Dec 31, 2025
2876c96
add comparison, equality and binary operator tests
f1ammable Jan 1, 2026
6bbc15d
omit printing out null values
f1ammable Jan 2, 2026
b521683
add tests for `Object` operators
f1ammable Jan 2, 2026
687d37a
add `Environment` tests
f1ammable Jan 3, 2026
2d4b08c
fix variables getting treated as function calls
f1ammable Jan 3, 2026
d0654c8
add tests for `Interpreter`
f1ammable Jan 3, 2026
3448220
remove unneeded test files
f1ammable Jan 3, 2026
bac0904
enable running of tests via `ctest`
f1ammable Jan 3, 2026
191cc80
remove ast printer, add clang-tidy config
f1ammable Jan 3, 2026
89904a1
remove certain clang-tidy checks
f1ammable Jan 3, 2026
4ff77f4
remove unused `Process` class
f1ammable Jan 3, 2026
096e730
lint whole project lol
f1ammable Jan 3, 2026
4b319db
pass coverage flags to test executable
f1ammable Jan 4, 2026
eba7a9c
remove pre-commit and set up github actions ci
f1ammable Jan 4, 2026
f657233
checkout with submodules for `vcpkg`
f1ammable Jan 4, 2026
b01aeb3
remove `test_errors.cpp`
f1ammable Jan 4, 2026
9fe7f1e
recreate build folder when downloading artifacts
f1ammable Jan 4, 2026
feb3adb
ignore function macro warning from `clang-tidy`
f1ammable Jan 4, 2026
79a568c
add `+x` to test executable so it can run
f1ammable Jan 4, 2026
06ad50b
make `clang-tidy` fail on warnings
f1ammable Jan 4, 2026
014ac52
ensure llvm test tools match compiler version
f1ammable Jan 4, 2026
86ba40f
correct job name
f1ammable Jan 4, 2026
d64d907
integrate test job into build because llvm
f1ammable Jan 4, 2026
f36288d
use full path for llvm tools
f1ammable Jan 4, 2026
c8ac414
add permissions for comments
f1ammable Jan 4, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
92 changes: 92 additions & 0 deletions .clang-tidy
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
Checks: >
-*,
bugprone-*,
-bugprone-easily-swappable-parameters,
-bugprone-exception-escape,
cert-*,
-cert-err58-cpp,
clang-analyzer-*,
concurrency-*,
cppcoreguidelines-*,
-cppcoreguidelines-avoid-magic-numbers,
-cppcoreguidelines-avoid-const-or-ref-data-members,
-cppcoreguidelines-pro-bounds-array-to-pointer-decay,
-cppcoreguidelines-pro-bounds-pointer-arithmetic,
-cppcoreguidelines-pro-type-reinterpret-cast,
-cppcoreguidelines-pro-type-vararg,
-cppcoreguidelines-owning-memory,
-cppcoreguidelines-avoid-do-while,
google-*,
-google-readability-todo,
-google-runtime-references,
misc-*,
-misc-non-private-member-variables-in-classes,
-misc-no-recursion,
modernize-*,
-modernize-use-trailing-return-type,
-modernize-avoid-c-arrays,
performance-*,
readability-*,
-readability-identifier-length,
-readability-magic-numbers,
-readability-function-cognitive-complexity,
-readability-uppercase-literal-suffix,
-readability-else-after-return,
-readability-braces-around-statements,
-google-readability-braces-around-statements,
-misc-include-cleaner

WarningsAsErrors: ''

CheckOptions:
# Naming conventions
- key: readability-identifier-naming.NamespaceCase
value: lower_case
- key: readability-identifier-naming.ClassCase
value: CamelCase
- key: readability-identifier-naming.StructCase
value: CamelCase
- key: readability-identifier-naming.EnumCase
value: CamelCase
- key: readability-identifier-naming.FunctionCase
value: camelBack
- key: readability-identifier-naming.VariableCase
value: camelBack
- key: readability-identifier-naming.ParameterCase
value: camelBack
- key: readability-identifier-naming.MemberCase
value: lower_case
- key: readability-identifier-naming.MemberCase.Prefix
value: m_
- key: readability-identifier-naming.ConstantMemberCase
value: camelBack
- key: readability-identifier-naming.ConstantMemberPrefix
value: m_
- key: readability-identifier-naming.ConstantCase
value: camelBack
- key: readability-identifier-naming.EnumConstantCase
value: UPPER_CASE
- key: readability-identifier-naming.GlobalConstantCase
value: UPPER_CASE
- key: readability-identifier-naming.StaticConstantCase
value: CamelCase

# Line length
- key: readability-function-size.LineThreshold
value: 200
- key: readability-function-size.StatementThreshold
value: 200

# Misc settings
- key: modernize-use-nullptr.NullMacros
value: 'NULL'
- key: performance-move-const-arg.CheckTriviallyCopyableMove
value: true
- key: cppcoreguidelines-special-member-functions.AllowSoleDefaultDtor
value: true

# Exclude third-party code and build artifacts
HeaderFilterRegex: '^.*/(src|test)/.*\.(h|hpp)$'

# Suppress warnings from system headers
SystemHeaders: false
26 changes: 26 additions & 0 deletions .github/scripts/check-format.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
#!/bin/bash
set -euo pipefail

echo "Finding changed C++ files against base branch: main"
CHANGED_FILES=$(git diff --name-only --diff-filter=AM "origin/main...HEAD" | \
grep -E '\.(cpp|hpp|h)$' || true)

# Filter to only files that exist (not deleted)
EXISTING_FILES=""
for file in $CHANGED_FILES; do
if [ -f "$file" ]; then
EXISTING_FILES="$EXISTING_FILES $file"
fi
done

if [ -z "$EXISTING_FILES" ]; then
echo "No C++ files changed, skipping format check"
exit 0
fi

echo "Checking formatting for: $EXISTING_FILES"

# shellcheck disable=SC2086
clang-format --dry-run --Werror $EXISTING_FILES

echo "All files are properly formatted!"
44 changes: 44 additions & 0 deletions .github/scripts/generate-coverage.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
#!/bin/bash
set -euo pipefail

cd build

echo "Running tests with coverage instrumentation..."
export LLVM_PROFILE_FILE="caesar-%p.profraw"
./caesar_test

echo "Checking for profraw files..."
if ! ls caesar-*.profraw 1> /dev/null 2>&1; then
echo "ERROR: No .profraw files found!"
exit 1
fi

echo "Merging profile data..."
/usr/bin/llvm-profdata-21 merge -sparse caesar-*.profraw -o caesar.profdata

echo "Generating coverage report (text summary)..."
/usr/bin/llvm-cov-21 report ./caesar_test \
-instr-profile=caesar.profdata \
-ignore-filename-regex='test/.*' \
-ignore-filename-regex='.*/Catch2/.*'

echo "Generating detailed HTML report..."
/usr/bin/llvm-cov-21 show ./caesar_test \
-instr-profile=caesar.profdata \
-format=html \
-output-dir=coverage-report \
-ignore-filename-regex='test/.*' \
-ignore-filename-regex='.*/Catch2/.*' \
-show-line-counts-or-regions \
-show-instantiations

echo "Generating per-file coverage summary..."
echo "### Per-File Coverage Summary" > coverage-summary.txt
/usr/bin/llvm-cov-21 report ./caesar_test \
-instr-profile=caesar.profdata \
-ignore-filename-regex='test/.*' \
-ignore-filename-regex='.*/Catch2/.*' \
>> coverage-summary.txt

echo "Coverage report generated successfully"
cat coverage-summary.txt
29 changes: 29 additions & 0 deletions .github/scripts/run-clang-tidy.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
#!/bin/bash
set -euo pipefail

echo "Finding changed C++ files against base branch: main"
CHANGED_FILES=$(git diff --name-only --diff-filter=AM "origin/main...HEAD" | \
grep -E '\.(cpp)$' | \
grep -v '^test/' || true)

# Filter to only files that exist (not deleted)
EXISTING_FILES=""
for file in $CHANGED_FILES; do
if [ -f "$file" ]; then
EXISTING_FILES="$EXISTING_FILES $file"
fi
done

if [ -z "$EXISTING_FILES" ]; then
echo "No C++ files changed, skipping clang-tidy"
exit 0
fi

echo "Changed C++ files: $EXISTING_FILES"
echo "Running clang-tidy..."

# Run clang-tidy on changed files
# shellcheck disable=SC2086
clang-tidy -p build --warnings-as-errors='*' $EXISTING_FILES

echo "clang-tidy completed successfully"
137 changes: 137 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,137 @@
name: CI

on:
pull_request:
branches: [ main ]

permissions:
contents: read
pull-requests: write

env:
VCPKG_ROOT: ${{ github.workspace }}/vcpkg
VCPKG_COMMIT: 'b1e15efef6758eaa0beb0a8732cfa66f6a68a81d'

jobs:
build:
name: Build and test
runs-on: ubuntu-latest

steps:
- uses: actions/checkout@v4
with:
submodules: true

- name: Install system dependencies
run: |
sudo apt-get update
sudo apt-get install -y cmake ninja-build ccache
wget https://apt.llvm.org/llvm.sh
chmod +x llvm.sh
sudo ./llvm.sh 21 all
sudo update-alternatives --install /usr/bin/clang clang /usr/bin/clang-21 100
sudo update-alternatives --install /usr/bin/clang++ clang++ /usr/bin/clang++-21 100
sudo update-alternatives --install /usr/bin/clang-scan-deps clang-scan-deps /usr/bin/clang-scan-deps-21 100
sudo update-alternatives --install /usr/bin/llvm-profdata llvm-profdata /usr/bin/llvm-profdata-21 100
sudo update-alternatives --install /usr/bin/llvm-cov llvm-cov /usr/bin/llvm-cov-21 100

- name: Setup ccache
uses: hendrikmuhs/ccache-action@v1.2
with:
key: ${{ runner.os }}-ccache-${{ github.sha }}
restore-keys: |
${{ runner.os }}-ccache-

- name: Setup vcpkg
uses: lukka/run-vcpkg@v11
with:
vcpkgDirectory: ${{ env.VCPKG_ROOT }}
vcpkgGitCommitId: ${{ env.VCPKG_COMMIT }}

- name: Configure CMake
run: cmake -B build --preset debug -DENABLE_COVERAGE=ON
env:
CC: /usr/bin/clang-21
CXX: /usr/bin/clang++-21
CMAKE_CXX_COMPILER_LAUNCHER: ccache

- name: Build
run: cmake --build build

- name: Run tests and generate coverage
run: .github/scripts/generate-coverage.sh

- name: Upload coverage report
uses: actions/upload-artifact@v4
with:
name: coverage-report
path: |
build/coverage-report/
build/coverage-summary.txt
retention-days: 30

- name: Upload build artifacts
uses: actions/upload-artifact@v4
with:
name: build-artifacts
path: |
build/
!build/vcpkg_installed/
retention-days: 1

lint:
name: Lint
runs-on: ubuntu-latest
needs: build

steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0

- name: Install system dependencies
run: |
sudo apt-get update
sudo apt-get install -y cmake ninja-build
wget https://apt.llvm.org/llvm.sh
chmod +x llvm.sh
sudo ./llvm.sh 21 all
sudo update-alternatives --install /usr/bin/clang-tidy clang-tidy /usr/bin/clang-tidy-21 100
sudo update-alternatives --install /usr/bin/clang-format clang-format /usr/bin/clang-format-21 100

- name: Download build artifacts
uses: actions/download-artifact@v4
with:
name: build-artifacts
path: build

- name: Check formatting on changed files
run: .github/scripts/check-format.sh

- name: Run clang-tidy on changed files
run: .github/scripts/run-clang-tidy.sh

coverage-comment:
name: Post Coverage Comment
runs-on: ubuntu-latest
needs: build

steps:
- name: Download coverage report
uses: actions/download-artifact@v4
with:
name: coverage-report

- name: Comment coverage summary on PR
uses: actions/github-script@v7
with:
script: |
const fs = require('fs');
const summary = fs.readFileSync('coverage-summary.txt', 'utf8');

github.rest.issues.createComment({
issue_number: context.issue.number,
owner: context.repo.owner,
repo: context.repo.repo,
body: '## Code Coverage Report\n\n```\n' + summary + '\n```\n\nDetailed HTML report available in artifacts.'
});
11 changes: 11 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,13 @@
.cache
build/
vcpkg-manifest-install.log
vcpkg_installed

# Coverage
coverage/
*.profraw
*.profdata
*.gcda
*.gcno
*.gcov
*.info
Loading
Loading