Compare commits
79 commits
03d915a96c
...
751dd61da9
| Author | SHA1 | Date | |
|---|---|---|---|
| 751dd61da9 | |||
| a5de8b167a | |||
| 0d6685abcd | |||
| 3a838ae3d5 | |||
| 9d70f29379 | |||
| abd0f5c0d6 | |||
| 91f4fa3c07 | |||
| 92bb5d4471 | |||
| c3ccab9492 | |||
| cc03c915fc | |||
| 303e48d37e | |||
| fdaed27527 | |||
| abfb302c52 | |||
| 76a6103721 | |||
| 604c415c0c | |||
| 9698074279 | |||
| 1016ebab51 | |||
| be590414af | |||
| 4825007b97 | |||
| 7fd6445cd2 | |||
| 872eaf3ab3 | |||
| 892fa3cfbf | |||
| 4309ec2a52 | |||
| 4e69a3ce63 | |||
| 24c54fba41 | |||
| 570407688c | |||
| d13d217ef2 | |||
| 3be01f35e6 | |||
| d452c9c6bc | |||
| 7372365961 | |||
| 8e895dafcc | |||
| d96976c6a9 | |||
| 57dda41bf3 | |||
| 23c6d4e869 | |||
| be5f2b1981 | |||
| 40999fe7db | |||
| c7438ca109 | |||
| 43ce9f83af | |||
| 9bba1e34ec | |||
| 3bcdc83e30 | |||
| c68244d6f6 | |||
| 28545fa8d4 | |||
| 060005543c | |||
| 1415b7fc9d | |||
| d17c89f552 | |||
| 42d323a4a0 | |||
| 6f6cf78a30 | |||
| 925a0f95f9 | |||
| 5eb5cd7348 | |||
| 587bb76108 | |||
| 0b6c0e9a61 | |||
| b598521704 | |||
| 4d5e63080b | |||
| 061f2418a9 | |||
| e2cbc7be63 | |||
| 0b838dfd30 | |||
| d2f673bf24 | |||
| d8540a33eb | |||
| bb704a3778 | |||
| 529acb77b1 | |||
| 6084e15368 | |||
| e0f7d793f3 | |||
| f90a24e799 | |||
| 01d50e9253 | |||
| cda661f263 | |||
| 40a4800195 | |||
| 63545ed918 | |||
| a47660edc7 | |||
| 7b79cf9032 | |||
| 02f0c07bce | |||
| e7e1343a83 | |||
| 567fa73796 | |||
| 8f2847abfb | |||
| 4bf1acd1f4 | |||
| 744972b364 | |||
| 4f8beb70b9 | |||
| 71576be449 | |||
| bebe6dfda0 | |||
| 5c57391e5d |
544 changed files with 17061 additions and 6400 deletions
18
.clang-format
Normal file
18
.clang-format
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
BasedOnStyle: LLVM
|
||||
IndentWidth: 2
|
||||
TabWidth: 2
|
||||
UseTab: Never
|
||||
ContinuationIndentWidth: 2
|
||||
AccessModifierOffset: -2
|
||||
BraceWrapping:
|
||||
AfterControlStatement: false
|
||||
AfterEnum: false
|
||||
AfterFunction: false
|
||||
AfterNamespace: false
|
||||
AfterStruct: false
|
||||
BeforeElse: false
|
||||
IndentBraces: false
|
||||
ColumnLimit: 0
|
||||
AllowShortIfStatementsOnASingleLine: true
|
||||
AllowShortFunctionsOnASingleLine: Inline
|
||||
PenaltyExcessCharacter: 50
|
||||
7
.clang-tidy
Normal file
7
.clang-tidy
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
Checks: >
|
||||
clang-analyzer-*,
|
||||
bugprone-*,
|
||||
performance-*
|
||||
WarningsAsErrors: ""
|
||||
HeaderFilterRegex: ".*"
|
||||
FormatStyle: none
|
||||
53
.github/workflows/cmake-ubuntu-latest.yml
vendored
53
.github/workflows/cmake-ubuntu-latest.yml
vendored
|
|
@ -24,7 +24,7 @@ jobs:
|
|||
# run: sudo apt upgrade -y
|
||||
|
||||
- name: Install dependencies
|
||||
run: sudo apt install cmake libjson-c-dev libssl-dev -y
|
||||
run: sudo apt install cmake doxygen graphviz libjson-c-dev libssl-dev -y
|
||||
|
||||
- name: Configure CMake
|
||||
run: cmake -S . -B build -DCMAKE_BUILD_TYPE=${{env.BUILD_TYPE}} -DFUN_DEBUG=OFF -DFUN_WITH_REPL=ON -DFUN_WITH_PCSC=OFF -DFUN_WITH_LIBSQL=OFF -DFUN_WITH_SQLITE=OFF -DFUN_WITH_CURL=OFF -DFUN_WITH_PCRE2=OFF -DFUN_WITH_XML2=OFF -DFUN_WITH_JSON=ON -DFUN_WITH_TCLTK=OFF -DFUN_WITH_INI=OFF -DFUN_WITH_NOTCURSES=OFF -DFUN_WITH_CPP=ON -DFUN_WITH_OPENSSL=ON -DFUN_WITH_LIBRESSL=OFF -DFUN_WITH_YAML=OFF -DFUN_USE_MUSL=OFF -DFUN_WITH_RUST=OFF
|
||||
|
|
@ -36,6 +36,9 @@ jobs:
|
|||
working-directory: ${{github.workspace}}/build
|
||||
run: ctest -C ${{env.BUILD_TYPE}}
|
||||
|
||||
- name: Run Opcode include checks.
|
||||
run: ./scripts/check_op_includes.py
|
||||
|
||||
- name: Run Examples
|
||||
run: ./scripts/run_examples.sh
|
||||
|
||||
|
|
@ -54,41 +57,41 @@ jobs:
|
|||
- name: Run Examples (crypto)
|
||||
run: ./scripts/run_examples.sh crypto
|
||||
|
||||
#- name: Run Examples (external/curl)
|
||||
# run: ./scripts/run_examples.sh external/curl
|
||||
#- name: Run Examples (extensions/curl)
|
||||
# run: ./scripts/run_examples.sh extensions/curl
|
||||
|
||||
#- name: Run Examples (external/ini)
|
||||
# run: ./scripts/run_examples.sh external/ini
|
||||
#- name: Run Examples (extensions/ini)
|
||||
# run: ./scripts/run_examples.sh extensions/ini
|
||||
|
||||
- name: Run Examples (external/json)
|
||||
run: ./scripts/run_examples.sh external/json
|
||||
- name: Run Examples (extensions/json)
|
||||
run: ./scripts/run_examples.sh extensions/json
|
||||
|
||||
#- name: Run Examples (external/libressl)
|
||||
# run: ./scripts/run_examples.sh external/libressl
|
||||
#- name: Run Examples (extensions/libressl)
|
||||
# run: ./scripts/run_examples.sh extensions/libressl
|
||||
|
||||
#- name: Run Examples (external/libsql)
|
||||
# run: ./scripts/run_examples.sh external/libsql
|
||||
#- name: Run Examples (extensions/libsql)
|
||||
# run: ./scripts/run_examples.sh extensions/libsql
|
||||
|
||||
#- name: Run Examples (external/notcurses)
|
||||
# run: ./scripts/run_examples.sh external/notcurses
|
||||
#- name: Run Examples (extensions/notcurses)
|
||||
# run: ./scripts/run_examples.sh extensions/notcurses
|
||||
|
||||
- name: Run Examples (external/openssl)
|
||||
run: ./scripts/run_examples.sh external/openssl
|
||||
- name: Run Examples (extensions/openssl)
|
||||
run: ./scripts/run_examples.sh extensions/openssl
|
||||
|
||||
#- name: Run Examples (external/pcre2)
|
||||
# run: ./scripts/run_examples.sh external/pcre2
|
||||
#- name: Run Examples (extensions/pcre2)
|
||||
# run: ./scripts/run_examples.sh extensions/pcre2
|
||||
|
||||
#- name: Run Examples (external/pcsc)
|
||||
# run: ./scripts/run_examples.sh external/pcsc
|
||||
#- name: Run Examples (extensions/pcsc)
|
||||
# run: ./scripts/run_examples.sh extensions/pcsc
|
||||
|
||||
#- name: Run Examples (external/sqlite)
|
||||
# run: ./scripts/run_examples.sh external/sqlite
|
||||
#- name: Run Examples (extensions/sqlite)
|
||||
# run: ./scripts/run_examples.sh extensions/sqlite
|
||||
|
||||
#- name: Run Examples (external/tcltk)
|
||||
# run: ./scripts/run_examples.sh external/tcltk
|
||||
#- name: Run Examples (extensions/tcltk)
|
||||
# run: ./scripts/run_examples.sh extensions/tcltk
|
||||
|
||||
#- name: Run Examples (external/xml2)
|
||||
# run: ./scripts/run_examples.sh external/xml2
|
||||
#- name: Run Examples (extensions/xml2)
|
||||
# run: ./scripts/run_examples.sh extensions/xml2
|
||||
|
||||
- name: Run Examples (functions)
|
||||
run: ./scripts/run_examples.sh functions
|
||||
|
|
|
|||
15
.gitignore
vendored
15
.gitignore
vendored
|
|
@ -1,12 +1,22 @@
|
|||
CMakeCache.txt
|
||||
Doxygen.in
|
||||
.*
|
||||
!.clang-format
|
||||
!.clang-tidy
|
||||
!.editorconfig
|
||||
!.gitignore
|
||||
!.github
|
||||
!.gitkeep
|
||||
!api/.gitkeep
|
||||
.venv
|
||||
build*
|
||||
api/
|
||||
build/*
|
||||
build_debug/*
|
||||
build_release/*
|
||||
cmake_install.cmake
|
||||
compile_commands.json
|
||||
database.sqlite
|
||||
defines.txt
|
||||
demo_*
|
||||
dist/
|
||||
downloaded.png
|
||||
|
|
@ -18,3 +28,6 @@ src/rust/Cargo.lock
|
|||
src/rust/target
|
||||
*.swp
|
||||
tmp*
|
||||
web/_cache/*
|
||||
web/_site/*
|
||||
web/Gemfile.lock
|
||||
|
|
|
|||
117
CHANGELOG.md
Normal file
117
CHANGELOG.md
Normal file
|
|
@ -0,0 +1,117 @@
|
|||
# Changelog
|
||||
|
||||
All notable changes to this project will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html) (during 0.x.y development phase).
|
||||
|
||||
## [0.41.15] - 2026-05-26
|
||||
### Changed
|
||||
- More internal optimizations.
|
||||
|
||||
## [0.41.14] - 2026-05-26
|
||||
### Changed
|
||||
- Internal optimizations and helper improvements.
|
||||
|
||||
## [0.41.13] - 2026-05-26
|
||||
### Added
|
||||
- Basic interactive IRC client example (experimental; known issues remain).
|
||||
|
||||
## [0.41.12] - 2026-05-26
|
||||
### Fixed
|
||||
- Minor fixes and adjustments for the new IRC library.
|
||||
|
||||
## [0.41.11] - 2026-05-26
|
||||
### Added
|
||||
- Basic IRC library fully written in Fun (see lib/net/irc.fun) and initial examples.
|
||||
|
||||
## [0.41.10] - 2026-05-09
|
||||
### Added
|
||||
- Doxygen documentation for kcgi opcodes via inline comments. No code changes.
|
||||
- Blog post and various content updates. No code changes.
|
||||
### Changed
|
||||
- CMake output messages tweaked. No code changes.
|
||||
- Various content/doc cleanups. No code changes.
|
||||
### Fixed
|
||||
- kcgi-related check in scripts/check_op_includes.py.
|
||||
|
||||
## [0.41.9] - 2026-05-09
|
||||
### Added
|
||||
- Basic CGI support using kcgi.
|
||||
- New “features” section on the website and navigation entry (web/). No code changes.
|
||||
### Changed
|
||||
- Content updates across the website and docs. No code changes.
|
||||
|
||||
## [0.41.8] - 2026-05-07
|
||||
### Fixed
|
||||
- Bug in the PCSC extension.
|
||||
### Added
|
||||
- More Doxygen documentation across extensions. No code changes.
|
||||
|
||||
## [0.41.7] - 2026-05-07
|
||||
### Changed
|
||||
- Refactored the PCRE2 extension.
|
||||
### Added
|
||||
- New regex examples demonstrating the PCRE2 extension.
|
||||
|
||||
## [0.41.6] - 2026-05-07
|
||||
### Changed
|
||||
- Refactoring and cleanups in VM code.
|
||||
|
||||
## [0.41.5] - 2026-05-01
|
||||
### Added
|
||||
- Doxygen configuration (Doxyfile) and initial documentation scaffolding (Doxygen.in).
|
||||
- Optional docs build flag (-DFUN_BUILD_DOCS=ON). No code changes.
|
||||
- .clang-format and .clang-tidy configurations. No code changes.
|
||||
### Changed
|
||||
- Doxygen-related code comments cleaned up. No code changes.
|
||||
- GitHub CI updates to build Doxygen docs. No code changes.
|
||||
- Removed sudo from make install dependency.
|
||||
|
||||
## [0.41.4] - 2026-04-27
|
||||
### Changed
|
||||
- scripts/play.fun now behaves more like scripts/run_examples.sh. No internal logic changes.
|
||||
|
||||
## [0.41.3] - 2026-04-27
|
||||
### Changed
|
||||
- Opcode cleanup.
|
||||
- GitHub workflow now checks opcode includes. No code changes.
|
||||
|
||||
## [0.41.2] - 2026-04-27
|
||||
### Fixed
|
||||
- Threading on Alpine Linux.
|
||||
|
||||
## [0.41.1] - 2026-04-27
|
||||
### Fixed
|
||||
- Threading on Alpine Linux.
|
||||
|
||||
## [0.41.0] - 2026-04-27
|
||||
### Changed
|
||||
- Parser: default variable scope in functions is now local (fixes scoping issues).
|
||||
|
||||
## [0.40.5] - 2026-04-10
|
||||
### Removed
|
||||
- All `libsql` support.
|
||||
- All `tcltk` support.
|
||||
|
||||
## [0.40.0] - 2026-03-25
|
||||
### Added
|
||||
- Nested functions support in the Fun parser.
|
||||
- Higher-order function patterns enabled by nesting.
|
||||
|
||||
## [0.39.15] - 2026-03-10
|
||||
### Added
|
||||
- Initial GitHub Actions CI workflow.
|
||||
- Automated execution of examples in CI.
|
||||
### Changed
|
||||
- Refactored examples directory structure.
|
||||
### Fixed
|
||||
- Line number reporting in error messages.
|
||||
|
||||
## [0.30.0] - 2025-11-15
|
||||
### Added
|
||||
- `libcurl` (cURL) support for networking.
|
||||
- `CRC32` and `CRC32C` classes in stdlib.
|
||||
|
||||
---
|
||||
*Note: Dates for older versions are approximate based on repository history.*
|
||||
|
|
@ -1,5 +1,5 @@
|
|||
cmake_minimum_required(VERSION 3.10)
|
||||
project(fun VERSION 0.40.5 LANGUAGES C)
|
||||
project(fun VERSION 0.41.15 LANGUAGES C)
|
||||
|
||||
set(CMAKE_C_STANDARD 99)
|
||||
set(CMAKE_C_STANDARD_REQUIRED ON)
|
||||
|
|
@ -37,12 +37,19 @@ else()
|
|||
set(_FUN_WITH_RUST_STATE "DISABLED")
|
||||
endif()
|
||||
|
||||
message(STATUS "==== Fun build options ====")
|
||||
#if(FUN_BUILD_DOCS)
|
||||
# set(_FUN_BUILD_DOCS "ENABLED")
|
||||
#else()
|
||||
# set(_FUN_BUILD_DOCS "DISABLED")
|
||||
#endif()
|
||||
|
||||
message(STATUS "---- Fun build options ---------")
|
||||
message(STATUS " FUN_DEBUG: ${_FUN_DEBUG_STATE}")
|
||||
message(STATUS " FUN_USE_MUSL: ${_FUN_USE_MUSL_STATE}")
|
||||
message(STATUS " FUN_WITH_CPP: ${_FUN_WITH_CPP_STATE}")
|
||||
message(STATUS " FUN_WITH_RUST: ${_FUN_WITH_RUST_STATE}")
|
||||
message(STATUS "===========================")
|
||||
#message(STATUS " FUN_BUILD_DOCS: ${_FUN_BUILD_DOCS}")
|
||||
message(STATUS "--------------------------------")
|
||||
|
||||
# Convenience aggregate target (like 'build' in Makefile)
|
||||
add_custom_target(build
|
||||
|
|
@ -423,6 +430,75 @@ if(BUILD_TESTING)
|
|||
else()
|
||||
message(WARNING "include_line_mapping_test.fun not found; skipping include_line_mapping CTest")
|
||||
endif()
|
||||
|
||||
# KCGI example smoke test (only when the KCGI extension is enabled)
|
||||
# We run the CGI example with minimal environment to avoid RFC warnings
|
||||
# and assert the body contains the expected greeting.
|
||||
if(FUN_WITH_KCGI)
|
||||
set(_kcgi_example "${CMAKE_SOURCE_DIR}/examples/cgi/hello_kcgi.fun")
|
||||
if(EXISTS "${_kcgi_example}")
|
||||
add_test(NAME kcgi_hello
|
||||
COMMAND $<TARGET_FILE:fun> "${_kcgi_example}"
|
||||
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
|
||||
)
|
||||
# Provide standard library path and minimal CGI environment
|
||||
set_tests_properties(kcgi_hello PROPERTIES
|
||||
ENVIRONMENT "FUN_LIB_DIR=${CMAKE_SOURCE_DIR}/lib;REQUEST_METHOD=GET;QUERY_STRING=name=Fun;SERVER_NAME=localhost;SERVER_PORT=80;SCRIPT_NAME=/hello_kcgi.fun;REMOTE_ADDR=127.0.0.1"
|
||||
PASS_REGULAR_EXPRESSION "Hello, Fun!"
|
||||
)
|
||||
else()
|
||||
message(WARNING "KCGI example not found: ${_kcgi_example}; skipping kcgi_hello CTest")
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# --- Doxygen docs target (optional) ---
|
||||
# Generate API documentation for everything under src/ into <build>/docs/html.
|
||||
# Disabled by default; enable with -DFUN_BUILD_DOCS=ON
|
||||
option(FUN_BUILD_DOCS "Enable Doxygen documentation target 'fun_docs'" OFF)
|
||||
|
||||
if(FUN_BUILD_DOCS)
|
||||
find_package(Doxygen REQUIRED dot)
|
||||
|
||||
# Provide a boolean for HAVE_DOT in the Doxyfile
|
||||
set(HAVE_DOT NO)
|
||||
if (DOXYGEN_DOT_FOUND)
|
||||
set(HAVE_DOT YES)
|
||||
endif()
|
||||
|
||||
# Determine documentation version: prefer `git describe`, fallback to project version
|
||||
set(FUN_DOCS_VERSION "${PROJECT_VERSION}")
|
||||
find_package(Git QUIET)
|
||||
if(GIT_FOUND)
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} describe --tags --dirty --always
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
OUTPUT_VARIABLE _git_desc
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
ERROR_QUIET
|
||||
)
|
||||
if(_git_desc)
|
||||
set(FUN_DOCS_VERSION "${_git_desc}")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# Optional logo (if present in the website assets)
|
||||
set(FUN_DOCS_LOGO "")
|
||||
set(_fun_logo_path "${CMAKE_SOURCE_DIR}/web/images/fun-square.png")
|
||||
if(EXISTS "${_fun_logo_path}")
|
||||
set(FUN_DOCS_LOGO "${_fun_logo_path}")
|
||||
endif()
|
||||
|
||||
set(DOXYGEN_IN ${CMAKE_SOURCE_DIR}/Doxygen.in)
|
||||
set(DOXYGEN_OUT ${CMAKE_CURRENT_BINARY_DIR}/Doxyfile)
|
||||
configure_file(${DOXYGEN_IN} ${DOXYGEN_OUT} @ONLY)
|
||||
|
||||
# Create a target to run Doxygen with the configured file
|
||||
add_custom_target(fun_docs
|
||||
COMMAND ${DOXYGEN_EXECUTABLE} ${DOXYGEN_OUT}
|
||||
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
|
||||
COMMENT "Generating API documentation with Doxygen"
|
||||
VERBATIM)
|
||||
endif()
|
||||
|
||||
# Install rules
|
||||
|
|
|
|||
45
README.md
45
README.md
|
|
@ -80,23 +80,25 @@ Fun may not change the world — but it will make programming a little more fun.
|
|||
- if/else if/else
|
||||
- try/catch/finally
|
||||
|
||||
And much more...! Look at the specs in [Spec](./spec/) for more detailed information.
|
||||
|
||||
### Lib (./lib/)
|
||||
|
||||
See [./lib/](https://git.xw3.org/fun/fun/src/branch/main/lib) for what the standard library provides.
|
||||
|
||||
### Optional extensions (build-time selectable / only testing this on Linux actually):
|
||||
|
||||
- [CGI](https://en.wikipedia.org/wiki/Common_Gateway_Interface) support builtin using [kcgi](https://kristaps.bsd.lv/kcgi/) (optional) ☐
|
||||
- [cURL (libcurl)](./docs/external/curl.md) (optional) ☑
|
||||
- [INI (iniparser)](./docs/external/ini.md) (optional) ☑
|
||||
- [JSON (json-c)](./docs/external/json.md) (optional) ☑
|
||||
- [PCRE2](./docs/external/pcre2.md) (optional) ☑
|
||||
- [PCSC (smart cards)](./docs/external/pcsc.md) (optional) ☑
|
||||
- [OpenSSL](./docs/external/openssl.md) (optional) ☑
|
||||
- [SQLite](./docs/external/sqlite.md) (optional) ☑
|
||||
- [XML (libxml2)](./docs/external/xml2.md) (optional) ☑
|
||||
- [CGI](https://en.wikipedia.org/wiki/Common_Gateway_Interface) support builtin using [kcgi](https://kristaps.bsd.lv/kcgi/) (optional) — see [docs](./web/documentation/extensions/kcgi/kcgi.md) ☑
|
||||
- [cURL (libcurl)](./web/documentation/extensions/curl/curl.md) (optional) ☑
|
||||
- [INI (iniparser)](./web/documentation/extensions/ini/ini.md) (optional) ☑
|
||||
- [JSON (json-c)](./web/documentation/extensions/json/json.md) (optional) ☑
|
||||
- [PCRE2](./web/documentation/extensions/pcre2/pcre2.md) (optional) ☑
|
||||
- [PCSC (smart cards)](./web/documentation/extensions/pcsc/pcsc.md) (optional) ☑
|
||||
- [OpenSSL](./web/documentation/extensions/openssl/openssl.md) (optional) ☑
|
||||
- [SQLite](./web/documentation/extensions/sqlite/sqlite.md) (optional) ☑
|
||||
- [XML (libxml2)](./web/documentation/extensions/xml2/xml2.md) (optional) ☑
|
||||
|
||||
☑ = Done / ☐ = Planned or in progress.
|
||||
☑ = Done (or basics implemented) / ☐ = Planned or in progress.
|
||||
|
||||
Note: Not all of the above features will be implemented. Those who are marked "Done" will probaly remain in Fun, but I don't know actually... ;)
|
||||
|
||||
|
|
@ -104,26 +106,27 @@ There are some libs written in Fun available in the [./lib/](https://git.xw3.org
|
|||
|
||||
### OpenSSL quickstart (MD5)
|
||||
|
||||
See the dedicated page: ./docs/external/openssl.md
|
||||
See the dedicated page: [./web/documentation/extensions/openssl/](./web/documentation/extensions/openssl/openssl.md)
|
||||
|
||||
## Documentation
|
||||
|
||||
Looking for docs? Start here:
|
||||
|
||||
- Local documentation index: [docs/README.md](./docs/README.md)
|
||||
- Handbook: [docs/handbook.md](./docs/handbook.md)
|
||||
- Types overview: [docs/types.md](./docs/types.md)
|
||||
- REPL guide: [docs/repl.md](./docs/repl.md)
|
||||
- Testing: [docs/testing.md](./docs/testing.md)
|
||||
- Troubleshooting: [docs/troubleshooting.md](./docs/troubleshooting.md)
|
||||
- Local documentation index: [./web/documentation/documenatation.md](./web/documentation/documentation.md)
|
||||
- Handbook: [./web/documentation/handbook/handbook.md](./web/documentation/handbook/handbook.md)
|
||||
- Types overview: [./web/documentation/types/types.md](./web/documentation/types/types.md)
|
||||
- REPL guide: [./web/documentation/repl/repl.md](./web/documentation/repl/repl.md)
|
||||
- Testing: [./web/documentation/testing/testing.md](./web/documentation/testing/testing.md)
|
||||
- Troubleshooting: [./web/documentation/troubleshooting/troubleshooting.md](./web/documentation/troubleshooting/troubleshooting.md)
|
||||
|
||||
Additional references:
|
||||
|
||||
- Specification: [spec/v0.3.md](./spec/v0.3.md) (work in progress)
|
||||
- Examples demonstrating most features: [examples/](./examples/)
|
||||
- Internals and VM opcodes live in [src/](./src/) (see [src/vm/](./src/vm) for opcode implementations)
|
||||
- Specification: [./web/documentation/spec/v0.4.md](./web/documentation/spec/v0.4.md) (work in progress)
|
||||
- Changelog: [CHANGELOG.md](./CHANGELOG.md)
|
||||
- Examples demonstrating most features: [./examples/](./examples/)
|
||||
- Internals and VM opcodes live in [./src/](./src/) (see [./src/vm/](./src/vm) for opcode implementations)
|
||||
|
||||
Note: The project is evolving; some documents may lag behind. The docs index in `./docs/README.md` is the most up‑to‑date entry point.
|
||||
Note: The project is evolving; some documents may lag behind. The docs index in [./web/documentation/documenatation.md](./web/documentation/documentation.md) is the most up‑to‑date entry point.
|
||||
|
||||
## Author
|
||||
|
||||
|
|
|
|||
0
api/.gitkeep
Normal file
0
api/.gitkeep
Normal file
|
|
@ -10,27 +10,28 @@ function(_fun_print_feature name flag)
|
|||
endif()
|
||||
endfunction()
|
||||
|
||||
# Include each extension module (Tcl/Tk removed)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/SQLITE.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/PCSC.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/JSON.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/INI.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/XML2.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/PCRE2.cmake)
|
||||
# Include each extension module
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/CURL.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/REPL.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/INI.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/JSON.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/KCGI.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/OPENSSL.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/PCRE2.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/PCSC.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/REPL.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/SQLITE.cmake)
|
||||
include(${CMAKE_SOURCE_DIR}/cmake/Extensions/XML2.cmake)
|
||||
|
||||
# Summary of extension toggles
|
||||
message(STATUS "---- Fun extension summary ----")
|
||||
_fun_print_feature("SQLite (FUN_WITH_SQLITE)" FUN_WITH_SQLITE)
|
||||
_fun_print_feature("PCSC (FUN_WITH_PCSC)" FUN_WITH_PCSC)
|
||||
_fun_print_feature("JSON-C (FUN_WITH_JSON)" FUN_WITH_JSON)
|
||||
_fun_print_feature("INI/iniparser (FUN_WITH_INI)" FUN_WITH_INI)
|
||||
_fun_print_feature("curl (FUN_WITH_CURL)" FUN_WITH_CURL)
|
||||
_fun_print_feature("iniparser (FUN_WITH_INI)" FUN_WITH_INI)
|
||||
_fun_print_feature("json-c (FUN_WITH_JSON)" FUN_WITH_JSON)
|
||||
_fun_print_feature("kcgi (FUN_WITH_KCGI)" FUN_WITH_KCGI)
|
||||
_fun_print_feature("libxml2 (FUN_WITH_XML2)" FUN_WITH_XML2)
|
||||
## libsql extension removed
|
||||
_fun_print_feature("PCRE2 (FUN_WITH_PCRE2)" FUN_WITH_PCRE2)
|
||||
_fun_print_feature("libcurl (FUN_WITH_CURL)" FUN_WITH_CURL)
|
||||
_fun_print_feature("REPL (FUN_WITH_REPL)" FUN_WITH_REPL)
|
||||
_fun_print_feature("OpenSSL (FUN_WITH_OPENSSL)" FUN_WITH_OPENSSL)
|
||||
_fun_print_feature("PCRE2 (FUN_WITH_PCRE2)" FUN_WITH_PCRE2)
|
||||
_fun_print_feature("PCSC-Lite (FUN_WITH_PCSC)" FUN_WITH_PCSC)
|
||||
_fun_print_feature("REPL (FUN_WITH_REPL)" FUN_WITH_REPL)
|
||||
_fun_print_feature("SQLite (FUN_WITH_SQLITE)" FUN_WITH_SQLITE)
|
||||
message(STATUS "--------------------------------")
|
||||
|
|
|
|||
19
cmake/Extensions/KCGI.cmake
Normal file
19
cmake/Extensions/KCGI.cmake
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
# KCGI (kcgi)
|
||||
option(FUN_WITH_KCGI "Enable kcgi support (CGI/FastCGI via kcgi)" OFF)
|
||||
set(KCGI_INCLUDE_DIRS "")
|
||||
set(KCGI_LINK_LIBS "")
|
||||
|
||||
if(FUN_WITH_KCGI)
|
||||
add_definitions(-DFUN_WITH_KCGI)
|
||||
find_package(PkgConfig QUIET)
|
||||
if(PKG_CONFIG_FOUND)
|
||||
pkg_check_modules(KCGI QUIET kcgi)
|
||||
endif()
|
||||
if(KCGI_FOUND)
|
||||
list(APPEND KCGI_INCLUDE_DIRS ${KCGI_INCLUDE_DIRS} ${KCGI_INCLUDE_DIRS})
|
||||
list(APPEND KCGI_LINK_LIBS ${KCGI_LINK_LIBS} ${KCGI_LIBRARIES})
|
||||
else()
|
||||
# Fallback libs commonly required for kcgi on Linux
|
||||
list(APPEND KCGI_LINK_LIBS kcgi z)
|
||||
endif()
|
||||
endif()
|
||||
|
|
@ -1,100 +0,0 @@
|
|||
## LibreSSL optional integration (MD5, etc.)
|
||||
|
||||
option(FUN_WITH_LIBRESSL "Enable LibreSSL-based features (e.g., md5)" OFF)
|
||||
|
||||
set(LIBRESSL_INCLUDE_DIRS "")
|
||||
set(LIBRESSL_LINK_LIBS "")
|
||||
|
||||
if(FUN_WITH_LIBRESSL)
|
||||
# We must NOT depend on OpenSSL being installed. Detect LibreSSL directly.
|
||||
# Strategy (in order):
|
||||
# 1) Prefer pkg-config 'libressl' if available (brings ssl+crypto and headers)
|
||||
# 2) Else, prefer explicit LibreSSL include prefix (/usr/include/libressl)
|
||||
# 3) Else, fall back to generic OpenSSL-compatible headers, but only if they
|
||||
# are provided by LibreSSL (detected heuristically via opensslv.h content)
|
||||
# 4) Link against libcrypto (from LibreSSL). No OpenSSL::Crypto usage.
|
||||
|
||||
include(CheckIncludeFile)
|
||||
include(FindPkgConfig)
|
||||
|
||||
set(_libressl_found FALSE)
|
||||
|
||||
# 1) Try pkg-config: libressl (meta) or libtls (often implies LibreSSL presence)
|
||||
if(PKG_CONFIG_FOUND)
|
||||
pkg_check_modules(LIBRESSL_PKG QUIET libressl)
|
||||
if(LIBRESSL_PKG_FOUND)
|
||||
list(APPEND LIBRESSL_INCLUDE_DIRS ${LIBRESSL_PKG_INCLUDE_DIRS})
|
||||
list(APPEND LIBRESSL_LINK_LIBS ${LIBRESSL_PKG_LIBRARIES})
|
||||
set(_libressl_found TRUE)
|
||||
else()
|
||||
# Some distros provide only crypto/ssl pc files from LibreSSL
|
||||
pkg_check_modules(LIBRESSL_CRYPTO QUIET libcrypto)
|
||||
pkg_check_modules(LIBRESSL_SSL QUIET libssl)
|
||||
if(LIBRESSL_CRYPTO_FOUND)
|
||||
list(APPEND LIBRESSL_INCLUDE_DIRS ${LIBRESSL_CRYPTO_INCLUDE_DIRS})
|
||||
list(APPEND LIBRESSL_LINK_LIBS ${LIBRESSL_CRYPTO_LIBRARIES})
|
||||
if(LIBRESSL_SSL_FOUND)
|
||||
list(APPEND LIBRESSL_INCLUDE_DIRS ${LIBRESSL_SSL_INCLUDE_DIRS})
|
||||
list(APPEND LIBRESSL_LINK_LIBS ${LIBRESSL_SSL_LIBRARIES})
|
||||
endif()
|
||||
set(_libressl_found TRUE)
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# 2) Prefer explicit LibreSSL include prefix if present
|
||||
if(EXISTS "/usr/include/libressl")
|
||||
list(PREPEND LIBRESSL_INCLUDE_DIRS "/usr/include/libressl")
|
||||
set(_libressl_found TRUE)
|
||||
endif()
|
||||
|
||||
# 3) Heuristic: check if the generic openssl headers are from LibreSSL
|
||||
if(NOT _libressl_found)
|
||||
# Try to find opensslv.h and see if it defines LIBRESSL_VERSION_NUMBER
|
||||
find_path(_GEN_OPENSSL_INCLUDE_DIR openssl/opensslv.h
|
||||
PATHS /usr/include /usr/local/include)
|
||||
if(_GEN_OPENSSL_INCLUDE_DIR)
|
||||
file(READ "${_GEN_OPENSSL_INCLUDE_DIR}/openssl/opensslv.h" _opensslv_h CONTENT_STRIP_TRAILING_WHITESPACE)
|
||||
string(FIND "${_opensslv_h}" "LIBRESSL_VERSION_NUMBER" _idx)
|
||||
if(NOT _idx EQUAL -1)
|
||||
list(APPEND LIBRESSL_INCLUDE_DIRS "${_GEN_OPENSSL_INCLUDE_DIR}")
|
||||
set(_libressl_found TRUE)
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# 4) Find the crypto library (from LibreSSL). Avoid CMake's OpenSSL package and target.
|
||||
if(NOT LIBRESSL_LINK_LIBS)
|
||||
# Try to locate libcrypto first
|
||||
find_library(LIBRESSL_CRYPTO_LIB NAMES crypto libcrypto PATHS
|
||||
/usr/lib /usr/local/lib /lib)
|
||||
if(LIBRESSL_CRYPTO_LIB)
|
||||
list(APPEND LIBRESSL_LINK_LIBS ${LIBRESSL_CRYPTO_LIB})
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(NOT _libressl_found OR NOT LIBRESSL_LINK_LIBS)
|
||||
message(FATAL_ERROR "FUN_WITH_LIBRESSL=ON but LibreSSL headers and/or libcrypto not found.\n"
|
||||
"Tried pkg-config (libressl/libcrypto), /usr/include/libressl, and generic openssl headers from LibreSSL.")
|
||||
endif()
|
||||
|
||||
# Ensure the compile definition is visible even if targets are created later
|
||||
add_compile_definitions(FUN_WITH_LIBRESSL=1)
|
||||
|
||||
# Propagate to main targets if they exist in this scope
|
||||
if(TARGET fun_core)
|
||||
target_link_libraries(fun_core PRIVATE ${LIBRESSL_LINK_LIBS})
|
||||
target_include_directories(fun_core PRIVATE ${LIBRESSL_INCLUDE_DIRS})
|
||||
target_compile_definitions(fun_core PRIVATE FUN_WITH_LIBRESSL=1)
|
||||
endif()
|
||||
if(TARGET fun)
|
||||
target_link_libraries(fun PRIVATE ${LIBRESSL_LINK_LIBS})
|
||||
target_include_directories(fun PRIVATE ${LIBRESSL_INCLUDE_DIRS})
|
||||
target_compile_definitions(fun PRIVATE FUN_WITH_LIBRESSL=1)
|
||||
endif()
|
||||
if(TARGET fun_test)
|
||||
target_link_libraries(fun_test PRIVATE ${LIBRESSL_LINK_LIBS})
|
||||
target_include_directories(fun_test PRIVATE ${LIBRESSL_INCLUDE_DIRS})
|
||||
target_compile_definitions(fun_test PRIVATE FUN_WITH_LIBRESSL=1)
|
||||
endif()
|
||||
endif()
|
||||
|
|
@ -1,27 +0,0 @@
|
|||
# libsql
|
||||
option(FUN_WITH_LIBSQL "Enable libsql (Turso) client support" OFF)
|
||||
set(LIBSQL_INCLUDE_DIRS "")
|
||||
set(LIBSQL_LINK_LIBS "")
|
||||
if(FUN_WITH_LIBSQL)
|
||||
add_definitions(-DFUN_WITH_LIBSQL)
|
||||
find_package(PkgConfig QUIET)
|
||||
if(PKG_CONFIG_FOUND)
|
||||
pkg_check_modules(LIBSQL QUIET libsql)
|
||||
if(NOT LIBSQL_FOUND)
|
||||
pkg_check_modules(LIBSQL_CLIENT QUIET libsql-client)
|
||||
if(LIBSQL_CLIENT_FOUND)
|
||||
set(LIBSQL_FOUND TRUE)
|
||||
set(LIBSQL_INCLUDE_DIRS ${LIBSQL_CLIENT_INCLUDE_DIRS})
|
||||
set(LIBSQL_LINK_LIBS ${LIBSQL_CLIENT_LIBRARIES})
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
if(NOT LIBSQL_FOUND)
|
||||
find_library(LIBSQL_LIB sqlite3)
|
||||
if(LIBSQL_LIB)
|
||||
list(APPEND LIBSQL_LINK_LIBS ${LIBSQL_LIB})
|
||||
else()
|
||||
message(FATAL_ERROR "libsql not found. Install libsql (or compatible sqlite3 client) or disable FUN_WITH_LIBSQL.")
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
|
@ -1,20 +0,0 @@
|
|||
# Notcurses
|
||||
option(FUN_WITH_NOTCURSES "Enable Notcurses TUI support" OFF)
|
||||
set(NOTCURSES_INCLUDE_DIRS "")
|
||||
set(NOTCURSES_LINK_LIBS "")
|
||||
if(FUN_WITH_NOTCURSES)
|
||||
add_definitions(-DFUN_WITH_NOTCURSES)
|
||||
find_package(PkgConfig QUIET)
|
||||
if(PkgConfig_FOUND)
|
||||
pkg_check_modules(NOTCURSES QUIET notcurses)
|
||||
if(NOT NOTCURSES_FOUND)
|
||||
pkg_check_modules(NOTCURSES QUIET notcurses-core)
|
||||
endif()
|
||||
endif()
|
||||
if(NOT NOTCURSES_FOUND)
|
||||
message(FATAL_ERROR "FUN_WITH_NOTCURSES=ON but notcurses was not found via pkg-config (tried notcurses and notcurses-core). Install notcurses or configure with -DFUN_WITH_NOTCURSES=OFF")
|
||||
else()
|
||||
list(APPEND NOTCURSES_INCLUDE_DIRS ${NOTCURSES_INCLUDE_DIRS} ${NOTCURSES_INCLUDE_DIRS})
|
||||
list(APPEND NOTCURSES_LINK_LIBS ${NOTCURSES_LINK_LIBS} ${NOTCURSES_LIBRARIES})
|
||||
endif()
|
||||
endif()
|
||||
|
|
@ -1,46 +0,0 @@
|
|||
# Tcl/Tk GUI support
|
||||
option(FUN_WITH_TCLTK "Enable Tcl/Tk GUI support" OFF)
|
||||
set(TCL_INCLUDE_DIRS "")
|
||||
set(TCL_LINK_LIBS "")
|
||||
if(FUN_WITH_TCLTK)
|
||||
add_definitions(-DFUN_WITH_TCLTK)
|
||||
find_package(PkgConfig QUIET)
|
||||
if(PKG_CONFIG_FOUND)
|
||||
pkg_check_modules(TCL QUIET tcl)
|
||||
pkg_check_modules(TK QUIET tk)
|
||||
endif()
|
||||
if(TCL_FOUND OR TK_FOUND)
|
||||
if(TCL_FOUND)
|
||||
list(APPEND TCL_INCLUDE_DIRS ${TCL_INCLUDE_DIRS} ${TCL_INCLUDE_DIRS})
|
||||
list(APPEND TCL_LINK_LIBS ${TCL_LINK_LIBS} ${TCL_LIBRARIES})
|
||||
endif()
|
||||
if(TK_FOUND)
|
||||
list(APPEND TCL_INCLUDE_DIRS ${TCL_INCLUDE_DIRS} ${TK_INCLUDE_DIRS})
|
||||
list(APPEND TCL_LINK_LIBS ${TCL_LINK_LIBS} ${TK_LIBRARIES})
|
||||
endif()
|
||||
else()
|
||||
find_path(TCL_INCLUDE_DIR tcl.h PATH_SUFFIXES tcl8.7 tcl8.6 include)
|
||||
find_library(TCL_LIB NAMES tcl8.7 tcl8.6 tcl)
|
||||
find_library(TK_LIB NAMES tk8.7 tk8.6 tk)
|
||||
if(TCL_INCLUDE_DIR)
|
||||
list(APPEND TCL_INCLUDE_DIRS ${TCL_INCLUDE_DIR})
|
||||
endif()
|
||||
if(TCL_LIB)
|
||||
list(APPEND TCL_LINK_LIBS ${TCL_LIB})
|
||||
endif()
|
||||
if(TK_LIB)
|
||||
list(APPEND TCL_LINK_LIBS ${TK_LIB})
|
||||
endif()
|
||||
if(APPLE)
|
||||
# macOS frameworks often unnecessary when using Homebrew tcl/tk
|
||||
elseif(WIN32)
|
||||
list(APPEND TCL_LINK_LIBS user32 gdi32 comctl32)
|
||||
else()
|
||||
find_package(X11 QUIET)
|
||||
if(X11_FOUND)
|
||||
list(APPEND TCL_INCLUDE_DIRS ${X11_INCLUDE_DIR})
|
||||
list(APPEND TCL_LINK_LIBS ${X11_LIBRARIES})
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
|
@ -33,3 +33,13 @@ endif()
|
|||
|
||||
# Debug option to enable verbose parser/VM logging
|
||||
option(FUN_DEBUG "Enable extra debug logging in Fun" OFF)
|
||||
|
||||
# Optional: VM trace and opcode counters (disabled by default)
|
||||
option(FUN_TRACE "Enable VM tracing and opcode execution counters" OFF)
|
||||
|
||||
# VM settings (configurable via -D...)
|
||||
set(MAX_FRAMES 128 CACHE STRING "Maximum depth of the call stack (frames)")
|
||||
set(MAX_FRAME_LOCALS 64 CACHE STRING "Maximum number of local variables per frame")
|
||||
set(MAX_GLOBALS 128 CACHE STRING "Maximum number of global variables")
|
||||
set(OUTPUT_SIZE 1024 CACHE STRING "Size of the VM output buffer (number of values)")
|
||||
set(STACK_SIZE 1024 CACHE STRING "Size of the VM evaluation stack")
|
||||
|
|
|
|||
|
|
@ -21,10 +21,22 @@ if(FUN_DEBUG)
|
|||
target_compile_definitions(fun_core PUBLIC FUN_DEBUG=1)
|
||||
endif()
|
||||
|
||||
# Enable VM tracing/counters when requested
|
||||
if(FUN_TRACE)
|
||||
target_compile_definitions(fun_core PUBLIC FUN_TRACE=1)
|
||||
endif()
|
||||
|
||||
# Provide default stdlib directory and version to the runtime
|
||||
target_compile_definitions(fun_core PUBLIC FUN_VERSION="${PROJECT_VERSION}")
|
||||
target_compile_definitions(fun_core PUBLIC DEFAULT_LIB_DIR="${DEFAULT_LIB_DIR}")
|
||||
|
||||
# VM configuration
|
||||
target_compile_definitions(fun_core PUBLIC MAX_FRAMES=${MAX_FRAMES})
|
||||
target_compile_definitions(fun_core PUBLIC MAX_FRAME_LOCALS=${MAX_FRAME_LOCALS})
|
||||
target_compile_definitions(fun_core PUBLIC MAX_GLOBALS=${MAX_GLOBALS})
|
||||
target_compile_definitions(fun_core PUBLIC OUTPUT_SIZE=${OUTPUT_SIZE})
|
||||
target_compile_definitions(fun_core PUBLIC STACK_SIZE=${STACK_SIZE})
|
||||
|
||||
# Apply extension include/link variables discovered in cmake/Extensions
|
||||
foreach(var_pair
|
||||
PCSC
|
||||
|
|
@ -35,7 +47,8 @@ foreach(var_pair
|
|||
INIPARSER
|
||||
LIBSQL
|
||||
LIBXML2
|
||||
OPENSSL)
|
||||
OPENSSL
|
||||
KCGI)
|
||||
if(${var_pair}_INCLUDE_DIRS)
|
||||
target_include_directories(fun_core PRIVATE ${${var_pair}_INCLUDE_DIRS})
|
||||
endif()
|
||||
|
|
@ -86,6 +99,10 @@ if(FUN_WITH_OPENSSL)
|
|||
target_compile_definitions(fun_core PUBLIC FUN_WITH_OPENSSL=1)
|
||||
endif()
|
||||
|
||||
if(FUN_WITH_KCGI)
|
||||
target_compile_definitions(fun_core PUBLIC FUN_WITH_KCGI=1)
|
||||
endif()
|
||||
|
||||
# LibreSSL toggle: ensure compile definitions are applied to fun_core so
|
||||
# the LibreSSL code paths are compiled, and linking vars are handled above.
|
||||
|
||||
|
|
|
|||
|
|
@ -1,57 +0,0 @@
|
|||
# Fun Documentation Index
|
||||
|
||||
This file serves as an index of the documents in this directory. Links are relative and can be opened directly on Git hosting or locally.
|
||||
|
||||
## Overview
|
||||
|
||||
- [handbook.md](./handbook.md) - Comprehensive handbook for the Fun language and VM: install/build, configuration flags, usage, and full feature overview.
|
||||
- [types.md](./types.md) - Core types (numbers, strings, arrays, maps, nil/bool), common operations, patterns, and interop notes.
|
||||
- [numbers.md](./numbers.md) - Working with integers and floats: arithmetic, conversions, clamping, bitwise ops, and patterns.
|
||||
- [strings.md](./strings.md) - Working with strings: literals/escaping, concatenation, substr/find, split, and conversions.
|
||||
- [arrays.md](./arrays.md) - Working with arrays: creation, indexing/slicing, iteration patterns, helpers, and idioms.
|
||||
- [maps.md](./maps.md) - Working with maps: construction, lookup/update, merging, iteration, and common patterns.
|
||||
- [includes.md](./includes.md) - Using local vs. system includes, FUN_LIB_DIR, DEFAULT_LIB_DIR, and namespaced includes with `as`.
|
||||
- [repl.md](./repl.md) - REPL guide: how to build/launch, editing and history, completions, REPL-on-error, and tips.
|
||||
- [opcodes.md](./opcodes.md) - VM opcodes overview grouped by domain with brief behavior/stack notes.
|
||||
- [internals.md](./internals.md) - Implementation details: bytecode format, VM architecture, stacks/frames, parser, and dispatch.
|
||||
- [rust.md](./rust.md) - Writing Rust-backed opcodes and wiring them into the C VM; build/setup notes.
|
||||
- [examples.md](./examples.md) - How to run the examples and the interactive showcase script, with environment tips.
|
||||
- [testing.md](./testing.md) - How to build and run tests/targets with CMake/CTest, and where to add new tests.
|
||||
- [troubleshooting.md](./troubleshooting.md) - Common issues and quick fixes for build, includes, and REPL usage.
|
||||
|
||||
## New and supplemental guides
|
||||
|
||||
- [build.md](./build.md) - How to build Fun with CMake, available targets, and build options (FUN_DEBUG, FUN_USE_MUSL, FUN_WITH_CPP, FUN_WITH_RUST, FUN_WITH_OPENSSL).
|
||||
- [cli.md](./cli.md) - Command-line usage of the `fun` executable: synopsis, options, exit codes, includes and library paths.
|
||||
- [fun.md](./fun.md) - Full usage guide for the `fun` executable: invocation patterns, REPL, env vars, include paths, examples, and install locations.
|
||||
- [asyncio.md](./asyncio.md) - Async I/O primitives and patterns: non-blocking sockets, fd polling, examples, and best practices.
|
||||
- [funstx.md](./funstx.md) - Syntax checker for .fun files with optional --fix auto-corrections; usage, exit codes, and limitations.
|
||||
- [contributing.md](./contributing.md) - How to contribute: project structure, coding style, running tests, and PR guidelines.
|
||||
- [style-guide.md](./style-guide.md) - Coding conventions for C and Fun (indentation, naming, idioms).
|
||||
- [stdlib.md](./stdlib.md) - Overview of the standard library modules under ./lib with one-line summaries.
|
||||
- [embedding.md](./embedding.md) - Embedding the VM from C/Rust, lifecycle, and host integration tips.
|
||||
- [errors-and-diagnostics.md](./errors-and-diagnostics.md) - Understanding parser/runtime errors and enabling diagnostics.
|
||||
- [performance.md](./performance.md) - Build/runtime tuning tips and patterns for better performance.
|
||||
- [security-and-sandboxing.md](./security-and-sandboxing.md) - Trust boundaries, I/O expectations, and capability restrictions.
|
||||
- [faq.md](./faq.md) - Frequently asked questions and quick answers.
|
||||
- [writing-tests.md](./writing-tests.md) - How to author new tests for Fun and opcode components.
|
||||
- [bytecode-format.md](./bytecode-format.md) - Reference for the bytecode format (split out from internals for convenience).
|
||||
- [roadmap.md](./roadmap.md) - High-level direction, planned features, and pointers to issues.
|
||||
|
||||
## Examples
|
||||
|
||||
- [examples/README.md](./examples/README.md) - Catalog of all example scripts under ./examples/: what each area contains, how to run them, required env vars, and extension requirements.
|
||||
|
||||
## External extensions
|
||||
|
||||
Documentation for optional, build-time selectable integrations lives in [external/](./external/):
|
||||
|
||||
- [Index of extensions](./external/README.md)
|
||||
- Highlights: [cURL](./external/curl.md), [INI](./external/ini.md), [JSON](./external/json.md), [XML (libxml2)](./external/xml2.md), [SQLite](./external/sqlite.md), [PCRE2](./external/pcre2.md), [PC/SC](./external/pcsc.md), [OpenSSL](./external/openssl.md)
|
||||
|
||||
## Tips
|
||||
|
||||
- When building from the repo without installing, set `FUN_LIB_DIR` to the local `./lib` directory so examples and the REPL can locate the stdlib.
|
||||
- For a broader project overview and quickstart, see the repository root [README.md](../README.md).
|
||||
- Crypto examples:
|
||||
- If built with `-DFUN_WITH_OPENSSL=ON`, try `examples/crypto/openssl_md5.fun`.
|
||||
|
|
@ -1,40 +0,0 @@
|
|||
# Contributing to Fun
|
||||
|
||||
Thanks for your interest in contributing! This guide covers the basics to get you productive quickly.
|
||||
|
||||
## Getting started
|
||||
- Clone the repo and build (see [build.md](./build.md)).
|
||||
- Run tests locally (see [testing.md](./testing.md)).
|
||||
- Explore examples (see [examples.md](./examples.md)).
|
||||
|
||||
## Project structure
|
||||
- `src/` - C core, VM, and opcode implementations ([src/vm](../src/vm/)).
|
||||
- `lib/` - Standard library written in Fun.
|
||||
- `examples/` - Example programs and showcases.
|
||||
- `docs/` - Documentation.
|
||||
- `spec/` - Language specification drafts.
|
||||
|
||||
## Code style
|
||||
- C: C99, two-space indent, no tabs. Keep functions short and focused.
|
||||
- Fun: two-space indent, snake_case for functions, PascalCase for classes/constructors.
|
||||
- Prefer clear names over abbreviations. See [style-guide.md](./style-guide.md).
|
||||
|
||||
## Development workflow
|
||||
1. Create a small, focused branch.
|
||||
2. Add/adjust tests for behavior changes (see [writing-tests.md](./writing-tests.md)).
|
||||
3. Update docs if user-visible behavior changes.
|
||||
4. Submit a PR with a clear description and rationale.
|
||||
|
||||
## Commit/PR guidelines
|
||||
- Keep commits atomic; include test updates with the change.
|
||||
- Reference related issues.
|
||||
- Include benchmarks only when meaningful and reproducible.
|
||||
|
||||
## Reporting bugs
|
||||
Please include:
|
||||
- Reproducer script (minimal), expected vs. actual behavior
|
||||
- Build options and platform
|
||||
- `fun --version` output
|
||||
|
||||
## Code of Conduct
|
||||
Be respectful and inclusive. See [CODE_OF_CONDUCT.md](../CODE_OF_CONDUCT.md) in the repository root.
|
||||
|
|
@ -1,29 +0,0 @@
|
|||
# Embedding Fun
|
||||
|
||||
This guide outlines how to embed the Fun VM in a host application and extend it from C/Rust.
|
||||
|
||||
## Overview
|
||||
- The VM is implemented in C (see [src/vm](../src/vm/)).
|
||||
- Optional Rust-based opcodes can be enabled via `FUN_WITH_RUST` (see [rust.md](./rust.md)).
|
||||
|
||||
## Embedding from C
|
||||
While the exact API surface may evolve, a typical embedding flow looks like:
|
||||
1. Initialize the VM/runtime and allocate a context.
|
||||
2. Load/compile Fun source or bytecode.
|
||||
3. Push arguments or set globals as needed.
|
||||
4. Execute entry function or script body.
|
||||
5. Retrieve results and clean up.
|
||||
|
||||
See [src/vm/core](../src/vm/core/) and related headers for public entry points and value types.
|
||||
|
||||
### Hosting considerations
|
||||
- Threading: share VM state cautiously or create one VM per thread.
|
||||
- Memory: clarify ownership of strings/buffers crossing the boundary.
|
||||
- Errors: propagate parse/runtime errors back to the host with useful messages.
|
||||
|
||||
## Extending with Rust
|
||||
When `FUN_WITH_RUST=ON`, a Rust static library from [`src/rust/`](../src/rust/) is built and linked. You can:
|
||||
- Implement new opcodes/functions in Rust.
|
||||
- Expose a C ABI for the VM to call into.
|
||||
|
||||
See [rust.md](./rust.md) for details and example code.
|
||||
|
|
@ -1,218 +0,0 @@
|
|||
# Examples catalog and how to run them
|
||||
|
||||
This page is a practical catalog of the example areas that ship with the Fun language. It explains what you’ll find in each folder under ./examples/, how to run the scripts, and where deeper walkthroughs live.
|
||||
|
||||
If you’re building/running from the repository without installing, set FUN_LIB_DIR to the local ./lib directory so examples can locate the stdlib:
|
||||
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- Then run an example: ./build_debug/fun examples/basics/hello_world.fun
|
||||
- Or, if installed: fun examples/basics/hello_world.fun
|
||||
|
||||
Notes
|
||||
- Most scripts are self‑documented with a short header comment at the top. Open them to see exact behavior and expected output.
|
||||
- Some examples depend on optional extensions (cURL, PCRE2, SQLite, Notcurses, Tk, PC/SC, OpenSSL/LibreSSL). See docs/external/ for enablement and availability.
|
||||
- Networking examples often bind to 127.0.0.1 on high ports; read the file header for the exact port.
|
||||
|
||||
Deep‑dives
|
||||
|
||||
## Top‑level examples (./examples)
|
||||
|
||||
Quick micro demos covering language features and tiny utilities.
|
||||
|
||||
Run pattern:
|
||||
- fun examples/<file>.fun
|
||||
|
||||
Highlights (selection):
|
||||
|
||||
- [builtins_extended.fun](./builtins_extended.md) — tour of core built‑ins beyond the basics
|
||||
- [byte_for_demo.fun](./byte_for_demo.md) — iterating bytes with for
|
||||
- [byte_overflow_try_catch.fun](./byte_overflow_try_catch.md) — error handling on overflow
|
||||
- [cast_demo.fun](./cast_demo.md) — conversions and casting helpers
|
||||
- [class_constructor.fun](./class_constructor.md) — basic constructor usage and init patterns
|
||||
- [class_test.fun](./class_test.md) — small class feature checks
|
||||
- [classes_demo.fun](classes_demo.md) — class basics and usage
|
||||
- [class_without_object.fun](./class_without_object.md) — class features without an instance helper
|
||||
- [cli_argv_dump.fun](./cli_argv_dump.md) — prints argv/argc handling
|
||||
- [conversions_showcase.fun](./conversions_showcase.md) — numbers, strings, bytes conversions
|
||||
- [cpp_add.fun](./cpp_add.md) — calling into the optional C++ extension (if enabled)
|
||||
- [datetime_basic.fun](./datetime_basic.md) — minimal date/time helpers
|
||||
- [datetime_extended.fun](./datetime_extended.md) — richer date/time operations
|
||||
- [datetime_timer.fun](datetime_timer.md) — time/date helpers
|
||||
- [echo_example.fun](./echo_example.md) — simple echo of input/args
|
||||
- [env_all.fun](./env_all.md) — enumerate environment variables
|
||||
- [os_env.fun](./os_env.md) — reading environment variables
|
||||
- [error_handling.fun](./error_handling.md) — try/catch and error objects
|
||||
- [try_catch_finally.fun](try_catch_finally.md) — error patterns
|
||||
- [expressions_test.fun](./expressions_test.md) — precedence and grouping
|
||||
- [features.fun](./features.md) — grab bag of language features
|
||||
- [file_print_for_file_line_by_line.fun](./file_print_for_file_line_by_line.md) — iterate file content
|
||||
- [floats.fun](./floats.md) — float ops and formatting
|
||||
- [for_range_test.fun](./for_range_test.md) — ranges and loops
|
||||
- [functions_test.fun](./functions_test.md) — functions, closures, returns
|
||||
- [have_fun.fun](./have_fun.md) — playful starter demo
|
||||
- [have_fun_function.fun](have_fun_function.md) — playful demos
|
||||
- [hex_example.fun](./hex_example.md) — hex encode/decode
|
||||
- [if_else_test.fun](./if_else_test.md) — conditional branching examples
|
||||
- [nested_loops.fun](./nested_loops.md) — loops inside loops
|
||||
- [loops_break_continue.fun](loops_break_continue.md) — control flow
|
||||
- [include_local.fun](./include_local.md) — include a local file/module
|
||||
- [include_lib.fun](./include_lib.md) — include from the stdlib path
|
||||
- [include_local_util.fun](include_local_util.md) — include mechanics
|
||||
- [inheritance_demo.fun](./inheritance_demo.md) — simple class inheritance
|
||||
- [maps.fun](./maps.md), [match.fun](match.md) — data structures and pattern matching
|
||||
- [namespaced_mod.fun](./namespaced_mod.md) — namespaced includes with as
|
||||
- [objects_basic.fun](./objects_basic.md) — simple objects and methods
|
||||
- [objects_more.fun](./objects_more.md) — OO basics
|
||||
- [process_example.fun](./process_example.md) — spawn and capture subprocess output
|
||||
- [progress.fun](./progress.md) — progress bar helper
|
||||
- [progress_inline.fun](./progress_inline.md) — simple progress displays
|
||||
- [random_demo.fun](./random_demo.md) — random helpers overview
|
||||
- [random_number_example.fun](random_number_example.md) — RNG usage
|
||||
- [regex_demo.fun](./regex_demo.md) — regex basics (PCRE2 when enabled)
|
||||
- [regex_procedural.fun](./regex_procedural.md) — regex helpers (PCRE2 when enabled)
|
||||
- [rust_hello.fun](./rust_hello.md), rust_hello_args*.fun — Rust opcodes (if FUN_WITH_RUST)
|
||||
- [serial_demo.fun](./serial_demo.md) — serial port usage
|
||||
- [test_serial.fun](./test_serial.md) — serial port (when available)
|
||||
- [short_circuit_test.fun](./short_circuit_test.md) — boolean evaluation order
|
||||
- [signed_ints.fun](./signed_ints.md) — signed integers overview
|
||||
- [uint_types.fun](./uint_types.md) — unsigned integers overview
|
||||
- [types_integers.fun](./types_integers.md) — integer families
|
||||
- [stdlib_showcase.fun](./stdlib_showcase.md) — sampler of common stdlib modules
|
||||
- [strings_test.fun](./strings_test.md) — string helpers and edge cases
|
||||
- [tcp_http_get.fun](./tcp_http_get.md) — simple HTTP GET over raw TCP
|
||||
- [tcp_http_get_class.fun](./tcp_http_get_class.md) — manual HTTP client over sockets
|
||||
- [test_bits.fun](./test_bits.md) — /rol/shl/xor/dec_to_hex/hex_to_dec bitwise utilities
|
||||
- [thread_class_example.fun](./thread_class_example.md) — define and run a thread class
|
||||
- [threads_demo.fun](./threads_demo.md) — threading building blocks
|
||||
- [typeof.fun](./typeof.md) — type inspection
|
||||
- [typeof_features.fun](./typeof_features.md) — type inspection of declared integer subtypes and runtime categories
|
||||
- [type_safety.fun](./type_safety.md) — static/dynamic type checks
|
||||
- [type_safety_fails.fun](./type_safety_fails.md) — static/dynamic type checks
|
||||
- [types_overview.fun](./types_overview.md) — language types tour
|
||||
- [unix_socket_echo.fun](./unix_socket_echo.md) — local domain socket echo demo
|
||||
- [version.fun](./version.md) — print VM/version info
|
||||
- [while_test.fun](./while_test.md) — simple while loop example
|
||||
|
||||
Tip: If a file name is listed above but not present on your build, it may depend on an extension you did not enable.
|
||||
|
||||
|
||||
## Algorithms (./examples/algos)
|
||||
- deduplicate.fun — removing duplicates from arrays/maps
|
||||
- sort_and_search.fun — sorting and lookup patterns
|
||||
- stack_queue.fun — basic stack and queue implementation
|
||||
|
||||
## Arrays (./examples/arrays)
|
||||
- arrays.fun — create, index, slice; typical idioms
|
||||
- arrays_iter.fun — iteration and enumeration
|
||||
- arrays_advanced.fun — copying, filtering, transformations
|
||||
|
||||
## Basics (./examples/basics)
|
||||
- boolean_decl.fun, booleans.fun — boolean values and operators
|
||||
- builtins_conversions.fun — core built‑ins, type conversions
|
||||
- collections.fun — arrays, maps, nested structures
|
||||
- fibonacci.fun, fizzbuzz.fun — classic exercises
|
||||
- hello_world.fun — the canonical first program
|
||||
|
||||
## CLI (./examples/cli)
|
||||
- args_parse.fun — arguments parsing patterns for small CLIs
|
||||
|
||||
## Compose (./examples/compose)
|
||||
Compositional patterns, small abstractions to combine behavior.
|
||||
|
||||
## Crypto (./examples/crypto)
|
||||
Hashing and cryptographic helpers. Availability depends on whether OpenSSL/LibreSSL is enabled.
|
||||
- openssl_md5.fun — MD5 via OpenSSL (if -DFUN_WITH_OPENSSL)
|
||||
- libressl_md5.fun — MD5 via LibreSSL (if -DFUN_WITH_LIBRESSL)
|
||||
- aes256.fun and hash samples if present on your build
|
||||
|
||||
## Data (./examples/data)
|
||||
Static assets for example servers; not meant to be run directly.
|
||||
- htdocs/ — files used by HTTP server examples (index.html, hello.fun, info.fun, form_post.fun, counter.fun, redirect.fun, json_like_api.fun)
|
||||
|
||||
## Error handling and diagnostics (./examples/error)
|
||||
- debug_reporting.fun — enabling debug output and reading traces
|
||||
- exit_example.fun — exit codes
|
||||
- fail.fun — triggering and observing failures
|
||||
- repl_on_error.fun — dropping into REPL on error
|
||||
- rust_vm_access.fun — Rust opcode errors (if enabled)
|
||||
- test_indent.fun — parser/indentation corner cases
|
||||
- try_catch_with_error.fun — capturing error objects
|
||||
|
||||
## Extra integrations (./examples/extra)
|
||||
These require optional external libraries. See docs/external/.
|
||||
- curl_* — cURL HTTP client examples (download, GET JSON, POST)
|
||||
- ini_* — parsing INI files (simple to complex)
|
||||
- json_showcase.fun — JSON helpers
|
||||
- libsql_example.fun — libSQL client usage
|
||||
- notcurses_* — rich TUI demos (if Notcurses enabled)
|
||||
- pcre2_* — PCRE2 regex engine demos
|
||||
- pcsc*.fun — smart card access via PC/SC
|
||||
- sqlite_example.fun — SQLite usage
|
||||
- tcp_echo_server*.fun — basic TCP echo server
|
||||
- tk_* — Tcl/Tk GUI examples
|
||||
- xml_* — XML parsing with libxml2
|
||||
|
||||
## Interactive (./examples/interactive)
|
||||
- console_prompt.fun — simple prompt loop
|
||||
- input_example.fun — reading user input
|
||||
- input_hidden_example.fun, input_hidden_pam_auth.fun — hidden input/passwords
|
||||
|
||||
## IO (./examples/io)
|
||||
- async_http_client.fun — non‑blocking HTTP client
|
||||
- await_http_client.fun — non‑blocking HTTP client using lib/async/scheduler.fun (await-style helpers)
|
||||
- csv_reader.fun — parse CSV files
|
||||
- file_io.fun, read_write_file.fun — file operations
|
||||
- word_count.fun — classic WC example
|
||||
|
||||
## Math (./examples/math)
|
||||
Small, focused math helpers and demonstrations:
|
||||
- math_ceil, math_floor, math_round, math_trunc, math_sign
|
||||
- math_cos, math_sin, math_tan
|
||||
- math_sqrt, math_isqrt
|
||||
- math_exp_log
|
||||
- math_fmin_fmax
|
||||
- math_gcd_lcm
|
||||
|
||||
## Networking (./examples/net)
|
||||
Servers and socket utilities. See docs/examples/net/httpserver.md for the HTTP family.
|
||||
- HTTP servers: [httpserver.md](./net/httpserver.md) — end‑to‑end walkthrough of all HTTP server variants in examples/net/
|
||||
- http_static_server.fun — minimal static server over sockets
|
||||
- http_server.fun — blocking static/CGI dispatcher using lib/net/http_server.fun
|
||||
- http_server_cgi.fun — blocking server with CGI via lib/net/http_cgi_server.fun
|
||||
- http_server_cgi_lib.fun — blocking server leveraging net/cgi.fun helpers
|
||||
- http_mt_server.fun — thread‑per‑connection static server
|
||||
- http_mt_server_cgi.fun — thread‑per‑connection with CGI support
|
||||
|
||||
## Patterns (./examples/patterns)
|
||||
Small idioms and reusable patterns.
|
||||
- assert_like.fun — assert‑style checks via language constructs
|
||||
|
||||
## Snippets (./examples/snippets)
|
||||
Miscellaneous one‑off code snippets demonstrating particular opcodes or tricks.
|
||||
|
||||
## SQLite daemon (./examples/sqlited)
|
||||
- Files related to running a small SQLite‑backed service (see source for details)
|
||||
|
||||
## Strings (./examples/strings)
|
||||
- base64_demo.fun — base64 encode/decode using encoding/base64
|
||||
- split_join_trim.fun — string splitting and trimming
|
||||
- templating_min.fun — bare‑bones templating
|
||||
- urlencode_decode.fun — percent‑encoding helpers
|
||||
|
||||
## Broken (./examples/broken)
|
||||
Historical or intentionally broken examples kept for reference/regression.
|
||||
- notcurses_* — experiments around Notcurses
|
||||
- ripemd160* — legacy or experimental hash routines
|
||||
|
||||
### Running examples reliably
|
||||
|
||||
Prefer the local build when running from the repository root:
|
||||
- ./build_debug/fun <path/to/example.fun>
|
||||
- or: ./build_release/fun <path/to/example.fun>
|
||||
|
||||
Set up env if needed:
|
||||
- export FUN_LIB_DIR="./lib" # to find stdlib
|
||||
- export FUN_EXEC="./build_debug/fun" # used by CGI examples
|
||||
- export FUN_HTDOCS="./examples/data/htdocs" # override docroot
|
||||
|
||||
When optional extensions are not enabled, their examples will not run; reconfigure the build with the required -D flags shown in docs/external/.
|
||||
|
|
@ -1,13 +0,0 @@
|
|||
# builtins_extended.fun — overview
|
||||
|
||||
What it shows
|
||||
- A tour of core built‑ins beyond the basics: printing, typing, math helpers, conversions, and utility functions commonly used in small scripts.
|
||||
|
||||
How to run
|
||||
- From repo root with local build:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/builtins_extended.fun
|
||||
- Or, if installed: fun examples/builtins_extended.fun
|
||||
|
||||
Notes
|
||||
- Exact behavior and outputs are documented inline at the top of the script; open the .fun file for details.
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# builtins_maps_and_more.fun — overview
|
||||
|
||||
What it shows
|
||||
- Exploring built‑ins while working with maps and related data structures.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/builtins_maps_and_more.fun
|
||||
- Or: fun examples/builtins_maps_and_more.fun
|
||||
|
||||
Notes
|
||||
- Open the .fun file to see the exact behaviors and printed output.
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# byte_for_demo.fun — overview
|
||||
|
||||
What it shows
|
||||
- Iterating bytes with a for-loop; indexing and printing byte values.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/byte_for_demo.fun
|
||||
- Or: fun examples/byte_for_demo.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# byte_overflow_try_catch.fun — overview
|
||||
|
||||
What it shows
|
||||
- Error handling around byte/integer overflow using try/catch.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/byte_overflow_try_catch.fun
|
||||
- Or: fun examples/byte_overflow_try_catch.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# cast_demo.fun — overview
|
||||
|
||||
What it shows
|
||||
- Conversions and casting helpers; demonstrates changing between numeric and string types safely.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/cast_demo.fun
|
||||
- Or: fun examples/cast_demo.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# class_constructor.fun — overview
|
||||
|
||||
What it shows
|
||||
- Class basics and constructor behavior; initializing fields and using methods.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/class_constructor.fun
|
||||
- Or: fun examples/class_constructor.fun
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# class_test.fun — overview
|
||||
|
||||
What it shows
|
||||
- Simple class usage and method invocation; small sanity checks around classes.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/class_test.fun
|
||||
- Or: fun examples/class_test.fun
|
||||
|
||||
Notes
|
||||
- Open the script to see the exact behavior and outputs.
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# class_without_object.fun — overview
|
||||
|
||||
What it shows
|
||||
- Class features that can be used without creating an instance (static-like usage patterns).
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/class_without_object.fun
|
||||
- Or: fun examples/class_without_object.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# classes_demo.fun — overview
|
||||
|
||||
What it shows
|
||||
- Class basics and usage: defining classes, instantiating objects, calling methods.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/classes_demo.fun
|
||||
- Or: fun examples/classes_demo.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# cli_argv_dump.fun — overview
|
||||
|
||||
What it shows
|
||||
- Prints argv/argc handling to demonstrate CLI arguments parsing at a low level.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/cli_argv_dump.fun --foo bar 123
|
||||
- Or: fun examples/cli_argv_dump.fun --foo bar 123
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# conversions_showcase.fun — overview
|
||||
|
||||
What it shows
|
||||
- Numbers, strings, and bytes conversions; typical idioms and edge cases.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/conversions_showcase.fun
|
||||
- Or: fun examples/conversions_showcase.fun
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# cpp_add.fun — overview
|
||||
|
||||
What it shows
|
||||
- Calling into the optional C++ extension from Fun.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/cpp_add.fun
|
||||
- Or: fun examples/cpp_add.fun
|
||||
|
||||
Notes
|
||||
- Requires the optional C++ extension to be enabled in your build; otherwise this example may be unavailable.
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
# counter.fun (CGI)
|
||||
|
||||
- Location: examples/data/htdocs/counter.fun
|
||||
- Category: CGI script used by HTTP server examples
|
||||
|
||||
Description
|
||||
- Simple stateful counter example for CGI; demonstrates reading and updating a value across requests (implementation details in script).
|
||||
|
||||
How to run
|
||||
- Through one of the HTTP server examples, e.g.:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun"
|
||||
- ./build_debug/fun examples/net/http_server_cgi.fun
|
||||
- Open: http://127.0.0.1:8080/counter.fun
|
||||
|
||||
See also
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
# form_post.fun (CGI)
|
||||
|
||||
- Location: examples/data/htdocs/form_post.fun
|
||||
- Category: CGI script used by HTTP server examples
|
||||
|
||||
Description
|
||||
- Demonstrates handling of POST form data via the CGI interface.
|
||||
|
||||
How to run
|
||||
- Through one of the HTTP server examples, e.g.:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun"
|
||||
- ./build_debug/fun examples/net/http_server_cgi.fun
|
||||
- Submit a form to: http://127.0.0.1:8080/form_post.fun
|
||||
|
||||
See also
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
# hello.fun (CGI)
|
||||
|
||||
- Location: examples/data/htdocs/hello.fun
|
||||
- Category: CGI script used by HTTP server examples
|
||||
|
||||
Description
|
||||
- Simple CGI .fun script that prints a greeting, optionally using query parameters (e.g., ?name=Fun).
|
||||
|
||||
How to run
|
||||
- Through one of the HTTP server examples, e.g.:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun"
|
||||
- ./build_debug/fun examples/net/http_server_cgi.fun
|
||||
- Open: http://127.0.0.1:8080/hello.fun?name=Fun
|
||||
|
||||
See also
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
# info.fun (CGI)
|
||||
|
||||
- Location: examples/data/htdocs/info.fun
|
||||
- Category: CGI script used by HTTP server examples
|
||||
|
||||
Description
|
||||
- CGI script that prints request/environment information, useful for debugging CGI variables.
|
||||
|
||||
How to run
|
||||
- Through one of the HTTP server examples, e.g.:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun"
|
||||
- ./build_debug/fun examples/net/http_server_cgi.fun
|
||||
- Open: http://127.0.0.1:8080/info.fun
|
||||
|
||||
See also
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
# json_like_api.fun (CGI)
|
||||
|
||||
- Location: examples/data/htdocs/json_like_api.fun
|
||||
- Category: CGI script used by HTTP server examples
|
||||
|
||||
Description
|
||||
- Demonstrates returning JSON-like output from a CGI endpoint.
|
||||
|
||||
How to run
|
||||
- Through one of the HTTP server examples, e.g.:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun"
|
||||
- ./build_debug/fun examples/net/http_server_cgi.fun
|
||||
- Open: http://127.0.0.1:8080/json_like_api.fun
|
||||
|
||||
See also
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
# redirect.fun (CGI)
|
||||
|
||||
- Location: examples/data/htdocs/redirect.fun
|
||||
- Category: CGI script used by HTTP server examples
|
||||
|
||||
Description
|
||||
- Demonstrates issuing HTTP redirects from a CGI script (setting Status and Location headers).
|
||||
|
||||
How to run
|
||||
- Through one of the HTTP server examples, e.g.:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun"
|
||||
- ./build_debug/fun examples/net/http_server_cgi.fun
|
||||
- Open: http://127.0.0.1:8080/redirect.fun
|
||||
|
||||
See also
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# datetime_basic.fun — overview
|
||||
|
||||
What it shows
|
||||
- Basic time/date helpers and formatting.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/datetime_basic.fun
|
||||
- Or: fun examples/datetime_basic.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# datetime_extended.fun — overview
|
||||
|
||||
What it shows
|
||||
- Extended datetime helpers: parsing, arithmetic, timers, and formatting variants.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/datetime_extended.fun
|
||||
- Or: fun examples/datetime_extended.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# datetime_timer.fun — overview
|
||||
|
||||
What it shows
|
||||
- Measuring elapsed time and simple timers using datetime helpers.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/datetime_timer.fun
|
||||
- Or: fun examples/datetime_timer.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# echo_example.fun — overview
|
||||
|
||||
What it shows
|
||||
- Simple echo of input/args; prints back what you type or pass as arguments.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/echo_example.fun hello world
|
||||
- Or: fun examples/echo_example.fun hello world
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# env_all.fun — overview
|
||||
|
||||
What it shows
|
||||
- Reading and listing environment variables.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/env_all.fun
|
||||
- Or: fun examples/env_all.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# error_handling.fun — overview
|
||||
|
||||
What it shows
|
||||
- Error patterns and handling strategies using try/catch/finally.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/error_handling.fun
|
||||
- Or: fun examples/error_handling.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# expressions_test.fun — overview
|
||||
|
||||
What it shows
|
||||
- Operator precedence and expression grouping tests/demonstrations.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/expressions_test.fun
|
||||
- Or: fun examples/expressions_test.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# features.fun — overview
|
||||
|
||||
What it shows
|
||||
- Grab bag of language features in a single script.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/features.fun
|
||||
- Or: fun examples/features.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# file_print_for_file_line_by_line.fun — overview
|
||||
|
||||
What it shows
|
||||
- Iterate a file line-by-line and print each line; basic file IO idioms.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/file_print_for_file_line_by_line.fun path/to/file.txt
|
||||
- Or: fun examples/file_print_for_file_line_by_line.fun path/to/file.txt
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# floats.fun — overview
|
||||
|
||||
What it shows
|
||||
- Floating point operations and formatting details.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/floats.fun
|
||||
- Or: fun examples/floats.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# for_range_test.fun — overview
|
||||
|
||||
What it shows
|
||||
- Ranges and loops; iterating numeric ranges and verifying bounds.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/for_range_test.fun
|
||||
- Or: fun examples/for_range_test.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# functions_test.fun — overview
|
||||
|
||||
What it shows
|
||||
- Functions, closures, and return behavior; call semantics basics.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/functions_test.fun
|
||||
- Or: fun examples/functions_test.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# have_fun.fun — overview
|
||||
|
||||
What it shows
|
||||
- Playful demo showing off small language tricks.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/have_fun.fun
|
||||
- Or: fun examples/have_fun.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# have_fun_function.fun — overview
|
||||
|
||||
What it shows
|
||||
- A playful function-centric demo; small utility behaviors.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/have_fun_function.fun
|
||||
- Or: fun examples/have_fun_function.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# hex_example.fun — overview
|
||||
|
||||
What it shows
|
||||
- Hex encode/decode helpers; working with hexadecimal representations.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/hex_example.fun
|
||||
- Or: fun examples/hex_example.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# if_else_test.fun — overview
|
||||
|
||||
What it shows
|
||||
- Control flow with if/else; branching and comparisons.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/if_else_test.fun
|
||||
- Or: fun examples/if_else_test.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# include_lib.fun — overview
|
||||
|
||||
What it shows
|
||||
- Including modules from the standard library path using #include <...>.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib" # ensure stdlib is discoverable
|
||||
- ./build_debug/fun examples/include_lib.fun
|
||||
- Or: fun examples/include_lib.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# include_local.fun — overview
|
||||
|
||||
What it shows
|
||||
- Including local files relative to the script and reusing helpers.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/include_local.fun
|
||||
- Or: fun examples/include_local.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# include_local_util.fun — overview
|
||||
|
||||
What it shows
|
||||
- Local include mechanics with a small utility module.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/include_local_util.fun
|
||||
- Or: fun examples/include_local_util.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# inheritance_demo.fun — overview
|
||||
|
||||
What it shows
|
||||
- Simple class inheritance and method overriding examples.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/inheritance_demo.fun
|
||||
- Or: fun examples/inheritance_demo.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# loops_break_continue.fun — overview
|
||||
|
||||
What it shows
|
||||
- Loop control: break and continue; demonstrating control flow within loops.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/loops_break_continue.fun
|
||||
- Or: fun examples/loops_break_continue.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# maps.fun — overview
|
||||
|
||||
What it shows
|
||||
- Working with maps: creation, indexing, iteration, and typical idioms.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/maps.fun
|
||||
- Or: fun examples/maps.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# match.fun — overview
|
||||
|
||||
What it shows
|
||||
- Pattern matching constructs and examples of branching by value/shape.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/match.fun
|
||||
- Or: fun examples/match.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# namespaced_mod.fun — overview
|
||||
|
||||
What it shows
|
||||
- Namespaced includes and using the "as" aliasing pattern for modules.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/namespaced_mod.fun
|
||||
- Or: fun examples/namespaced_mod.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# nested_loops.fun — overview
|
||||
|
||||
What it shows
|
||||
- Control flow with nested loops; inner/outer loop coordination.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/nested_loops.fun
|
||||
- Or: fun examples/nested_loops.fun
|
||||
|
|
@ -1,20 +0,0 @@
|
|||
# http_mt_server.fun
|
||||
|
||||
- Location: examples/net/http_mt_server.fun
|
||||
- Category: Networking / HTTP (multi-threaded)
|
||||
|
||||
Description
|
||||
- Thread-per-connection HTTP server built on io/socket.fun and io/thread.fun. For each accepted client, spawns a thread and returns a small HTML page.
|
||||
|
||||
How to run
|
||||
- From the repository root:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/net/http_mt_server.fun
|
||||
- Then open http://127.0.0.1:8080/ (or the port printed on start)
|
||||
|
||||
Requirements
|
||||
- Uses stdlib io/socket.fun and io/thread.fun. No external extensions required.
|
||||
|
||||
See also
|
||||
- docs/examples/README.md
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,22 +0,0 @@
|
|||
# http_mt_server_cgi.fun
|
||||
|
||||
- Location: examples/net/http_mt_server_cgi.fun
|
||||
- Category: Networking / HTTP with CGI (multi-threaded)
|
||||
|
||||
Description
|
||||
- Multi-threaded HTTP server (thread-per-connection) with CGI support. Serves static files from htdocs and executes .fun scripts as CGI using net/cgi.fun helpers.
|
||||
|
||||
How to run
|
||||
- From the repository root:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun" # optional; auto-detected if omitted
|
||||
- export FUN_HTDOCS="./examples/data/htdocs" # optional
|
||||
- ./build_debug/fun examples/net/http_mt_server_cgi.fun
|
||||
- Try: http://127.0.0.1:8080/ and /hello.fun?name=Fun, /info.fun
|
||||
|
||||
Requirements
|
||||
- Uses stdlib io/socket.fun, io/thread.fun, and net/cgi.fun. No external extensions required.
|
||||
|
||||
See also
|
||||
- docs/examples/README.md
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,24 +0,0 @@
|
|||
# http_server.fun
|
||||
|
||||
- Location: examples/net/http_server.fun
|
||||
- Category: Networking / HTTP (blocking)
|
||||
|
||||
Description
|
||||
- Blocking HTTP server that serves static files and executes .fun CGI scripts via lib/net/http_server.fun.
|
||||
|
||||
How to run
|
||||
- From the repository root:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/net/http_server.fun
|
||||
- Default docroot: ./examples/data/htdocs
|
||||
- Visit: http://127.0.0.1:8080/
|
||||
|
||||
Notes
|
||||
- For CGI .fun under htdocs, the server uses the Fun interpreter to execute them and forwards output as HTTP.
|
||||
|
||||
Requirements
|
||||
- Uses io/socket.fun and strings.fun; no external extensions required.
|
||||
|
||||
See also
|
||||
- docs/examples/README.md
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,22 +0,0 @@
|
|||
# http_server_cgi.fun
|
||||
|
||||
- Location: examples/net/http_server_cgi.fun
|
||||
- Category: Networking / HTTP with CGI (blocking)
|
||||
|
||||
Description
|
||||
- Minimal CGI-capable HTTP server (blocking) using lib/net/http_cgi_server.fun. Serves static files and executes .fun scripts as CGI.
|
||||
|
||||
How to run
|
||||
- From the repository root:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun" # optional; auto-detected if omitted
|
||||
- export FUN_HTDOCS="./examples/data/htdocs" # optional
|
||||
- ./build_debug/fun examples/net/http_server_cgi.fun
|
||||
- Try: http://127.0.0.1:8080/ and /hello.fun, /info.fun
|
||||
|
||||
Requirements
|
||||
- Uses stdlib io/socket.fun, strings.fun, and net/cgi.fun. No external extensions required.
|
||||
|
||||
See also
|
||||
- docs/examples/README.md
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,22 +0,0 @@
|
|||
# http_server_cgi_lib.fun
|
||||
|
||||
- Location: examples/net/http_server_cgi_lib.fun
|
||||
- Category: Networking / HTTP with CGI (blocking, stdlib helpers)
|
||||
|
||||
Description
|
||||
- Blocking HTTP server that serves static files and runs .fun as CGI using helpers from lib/net/http_cgi_lib_server.fun and net/cgi.fun.
|
||||
|
||||
How to run
|
||||
- From the repository root:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- export FUN_EXEC="./build_debug/fun" # optional; auto-detected if omitted
|
||||
- export FUN_HTDOCS="./examples/data/htdocs" # optional
|
||||
- ./build_debug/fun examples/net/http_server_cgi_lib.fun
|
||||
- Try: http://127.0.0.1:8080/ and /hello.fun, /info.fun
|
||||
|
||||
Requirements
|
||||
- Uses stdlib io/socket.fun, strings.fun, net/cgi.fun. No external extensions required.
|
||||
|
||||
See also
|
||||
- docs/examples/README.md
|
||||
- docs/examples/httpserver.md (deep-dive)
|
||||
|
|
@ -1,20 +0,0 @@
|
|||
# http_static_server.fun
|
||||
|
||||
- Location: examples/net/http_static_server.fun
|
||||
- Category: Networking / Sockets
|
||||
|
||||
Description
|
||||
- Minimal static HTTP server implemented directly on sockets. Accepts connections and always returns a small HTML page.
|
||||
|
||||
How to run
|
||||
- From the repository root:
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/net/http_static_server.fun
|
||||
- Then open http://127.0.0.1:8088/
|
||||
|
||||
Requirements
|
||||
- Uses core IO/socket stdlib (io/socket.fun). No optional extensions required.
|
||||
|
||||
See also
|
||||
- docs/examples/README.md
|
||||
- docs/examples/httpserver.md (deep-dive over HTTP servers)
|
||||
|
|
@ -1,134 +0,0 @@
|
|||
# HTTP server examples: architecture and how they work
|
||||
|
||||
This guide explains the HTTP server examples under `./examples/net/http_*` and the supporting standard library modules under `./lib/net/`.
|
||||
|
||||
It covers what each example does, how to run it, and how the request handling/CGI pieces are implemented.
|
||||
|
||||
## Prerequisites
|
||||
- Build the project so you have a `fun` executable, or ensure `fun` is on your PATH.
|
||||
- Typical local builds: `./build_debug/fun` or `./build_release/fun`.
|
||||
- For examples that serve files/CGI scripts, content is read from `./examples/data/htdocs` by default.
|
||||
- Helpful env vars used by some examples:
|
||||
- `FUN_LIB_DIR` — path to the stdlib (`./lib` when running from the repo).
|
||||
- `FUN_EXEC` — override path to the `fun` interpreter used to run CGI children.
|
||||
- `FUN_HTDOCS` — override htdocs directory for some examples (not all).
|
||||
- `FUN_PORT` — override port for some examples (mainly the MT CGI one).
|
||||
|
||||
## Supporting stdlib modules (lib/net)
|
||||
|
||||
- `net/http_server.fun` — Simple blocking HTTP server class serving static files, with a very small built-in “CGI for .fun files” (spawns `fun` with `QUERY_STRING`/`POST_DATA`).
|
||||
- `net/http_cgi_server.fun` — Blocking server with fuller CGI support using `net/cgi.fun` to translate CGI output into proper HTTP responses and richer request/header parsing.
|
||||
- `net/http_cgi_lib_server.fun` — Variant of the CGI server with the same core behavior, explicitly wiring the Fun interpreter path and using `CGI().cgi_to_http_response()` from `net/cgi.fun`.
|
||||
- `net/cgi.fun` — Helpers to work with CGI-style programs and to translate CGI output (headers + body) into full HTTP/1.1 responses.
|
||||
|
||||
See docs/stdlib.md → net/ for a quick index of these modules.
|
||||
|
||||
## Example: http_static_server.fun
|
||||
- File: `examples/net/http_static_server.fun`
|
||||
- Purpose: Minimal, hand-written HTTP server that ignores the request path and always responds with a fixed HTML page.
|
||||
- Key includes: `io/socket.fun`
|
||||
- Port/backlog: hard-coded `8088`, backlog 10.
|
||||
- Flow:
|
||||
- Creates `TcpServer(port, backlog)` → `listen()` → loop on `accept()`
|
||||
- `sock_recv()` reads and discards request
|
||||
- Constructs a literal HTTP/1.1 200 response with `Content-Length` and `Connection: close`
|
||||
- Sends the response with `sock_send()` and closes the client
|
||||
- Run:
|
||||
- `./examples/net/http_static_server.fun`
|
||||
- Open http://127.0.0.1:8080/
|
||||
|
||||
## Example: http_server.fun (static + simple .fun CGI)
|
||||
- File: `examples/net/http_server.fun`
|
||||
- Uses: `#include <net/http_server.fun>` (class `HTTPServer`)
|
||||
- Purpose: Blocking server that serves static files from an htdocs directory; if the requested path ends with `.fun`, it spawns `fun` to run the script and returns its output.
|
||||
- Defaults in example:
|
||||
- Port: `8080`
|
||||
- Htdocs: `./examples/data/htdocs`
|
||||
- Implementation highlights (see `lib/net/http_server.fun`):
|
||||
- Parses request line to get `method` and `path`; `/` maps to `/index.html`.
|
||||
- When path ends with `.fun`, builds a small environment:
|
||||
- `QUERY_STRING` (for `?a=b`), `POST_DATA` (raw body when `POST`).
|
||||
- Runs `proc_run("<env> fun <script>")` and uses `out` as response body.
|
||||
- Otherwise reads the file from `htdocs` and serves it as-is.
|
||||
- Sends basic HTTP/1.1 headers: 200/404, `Content-Type: text/html`, `Content-Length`, `Connection: close`.
|
||||
- Run:
|
||||
- `./examples/net/http_server.fun`
|
||||
- Open http://127.0.0.1:8080/ and the sample CGI endpoints like `/hello.fun?name=Fun`.
|
||||
|
||||
## Example: http_server_cgi.fun (CGI via external interpreter)
|
||||
- File: `examples/net/http_server_cgi.fun`
|
||||
- Uses: `#include <net/http_cgi_server.fun>` (class `HTTPCGIServer`)
|
||||
- Purpose: Blocking server that serves static files and executes `.fun` scripts under htdocs via a child Fun interpreter, with fuller CGI environment and header handling.
|
||||
- Defaults in example:
|
||||
- Port: `8080`
|
||||
- Htdocs: `./examples/data/htdocs`
|
||||
- Implementation highlights (see `lib/net/http_cgi_server.fun`):
|
||||
- Robust request-line extraction and header parsing (case-normalized to uppercase).
|
||||
- Path routing: `/` → `/index.html`; `.fun` → treat as CGI script.
|
||||
- Builds CGI env including: `FUN_LIB_DIR`, `REQUEST_METHOD`, `QUERY_STRING`, `SCRIPT_NAME`, `PATH_INFO`, `SERVER_NAME`, `SERVER_PORT`, `SERVER_PROTOCOL`, `HTTP_HOST`, `HTTP_USER_AGENT`, `HTTP_COOKIE`, `CONTENT_TYPE`, `CONTENT_LENGTH`, and `POST_DATA` (if any).
|
||||
- Interpreter selection priority: `$FUN_EXEC` → `./build_debug/fun` → `./build_release/fun` → `fun` from PATH.
|
||||
- Uses `net/cgi.fun` to convert CGI output (headers + body) into a proper HTTP/1.1 response before sending.
|
||||
- Run:
|
||||
- `./examples/net/http_server_cgi.fun`
|
||||
- Try: `/`, `/hello.fun?name=Fun`, `/info.fun` under http://127.0.0.1:8080/
|
||||
|
||||
## Example: http_server_cgi_lib.fun (CGI via stdlib wrapper)
|
||||
- File: `examples/net/http_server_cgi_lib.fun`
|
||||
- Uses: `#include <net/http_cgi_lib_server.fun>` (class `HTTPCGILibServer`)
|
||||
- Purpose: Same goal as the previous example but split into a slightly different stdlib class; also uses `CGI().cgi_to_http_response()` for translating CGI output.
|
||||
- Defaults and behavior mirror `HTTPCGIServer`: static files from htdocs, `.fun` as CGI with the same env block and interpreter selection logic.
|
||||
- Run:
|
||||
- `./examples/net/http_server_cgi_lib.fun`
|
||||
- Try: `/`, `/hello.fun?name=Fun`, `/info.fun` under http://127.0.0.1:8080/
|
||||
|
||||
## Example: http_mt_server.fun (thread-per-connection)
|
||||
- File: `examples/net/http_mt_server.fun`
|
||||
- Uses: `io/socket.fun`, `io/thread.fun`
|
||||
- Purpose: Hand-written multi-threaded server; main thread blocks in `accept()`, each connection handled in a new Fun thread.
|
||||
- Behavior: Reads request, replies with a fixed HTML 200 response, then closes the connection.
|
||||
- Defaults: `PORT = 8080`, `BACKLOG = 128` (note the comment mentions 8089 in a usage line; the code uses 8080).
|
||||
- Run: `./examples/net/http_mt_server.fun` then open http://127.0.0.1:8080/
|
||||
|
||||
## Example: http_mt_server_cgi.fun (thread-per-connection + CGI)
|
||||
- File: `examples/net/http_mt_server_cgi.fun`
|
||||
- Uses: `io/socket.fun`, `io/thread.fun`, `net/cgi.fun`
|
||||
- Purpose: Multi-threaded server that serves static files from htdocs and executes `.fun` scripts as CGI, implemented without higher-level string helpers to keep per-thread globals minimal.
|
||||
- Defaults: `PORT = 8080`, `BACKLOG = 128`, `HTDOCS = ./examples/data/htdocs`.
|
||||
- Request handling flow:
|
||||
- Reads request bytes, extracts the request line, splits out `method` and `target`.
|
||||
- Splits `path` and `query` on `?`; `/` becomes `/index.html`.
|
||||
- Parses headers into a map (uppercase keys) and optionally reads a request body.
|
||||
- Routing:
|
||||
- If `path` ends with `.fun`: build CGI env; spawn a child `fun` to execute the script; capture stdout; translate to HTTP via `_cgi_to_http_response()`; send back.
|
||||
- Else: attempt to read the static file from `HTDOCS + path`; send 200 or 404.
|
||||
- CGI environment variables set (subset):
|
||||
- `FUN_LIB_DIR`, `REQUEST_METHOD`, `QUERY_STRING`, `SCRIPT_NAME`, `PATH_INFO`, `SERVER_NAME`, `SERVER_PORT`, `SERVER_PROTOCOL`, `HTTP_HOST`, `HTTP_USER_AGENT`, `HTTP_COOKIE`, `CONTENT_TYPE`, `CONTENT_LENGTH`, `POST_DATA` (when present).
|
||||
- Interpreter selection (similar to CGI examples): `$FUN_EXEC` → `./build_debug/fun` → `./build_release/fun` → `fun` from PATH.
|
||||
- Notes:
|
||||
- Allows overriding `HTDOCS` & port via `FUN_HTDOCS` and `FUN_PORT` environment variables.
|
||||
- Implements its own small helpers (`_trim`, `_ends_with`, `_split_*`) to avoid heavy string utilities inside threads.
|
||||
- Run: `./examples/net/http_mt_server_cgi.fun` then open http://127.0.0.1:8080/
|
||||
|
||||
## Example: http_server_test.fun
|
||||
- File: `examples/net/http_server_test.fun`
|
||||
- Purpose: Small test harness to exercise/verify server pieces (implementation details may change). Check the source for exact behavior.
|
||||
|
||||
## Common behaviors and notes
|
||||
- Index handling: most servers map `/` to `/index.html` under the configured `htdocs` directory.
|
||||
- Static files: served by reading from `<htdocs><path>`; a missing file returns `404 Not Found`.
|
||||
- CGI scripts:
|
||||
- Any path ending in `.fun` under `htdocs` is executed with the Fun interpreter as a child process.
|
||||
- CGI output is expected to be a mix of optional headers and a body; the servers convert this to a valid HTTP/1.1 response (via `net/cgi.fun` or a local helper).
|
||||
- To ensure the child can `#include` stdlib modules, `FUN_LIB_DIR` is populated (defaults to `./lib` when run from repo root).
|
||||
- Content types: examples return `Content-Type: text/html; charset=utf-8` by default for dynamic responses; static file content types are not auto-detected in these examples.
|
||||
- Connection handling: responses include `Connection: close`; examples do not implement keep-alive or HTTP/1.1 request pipelining.
|
||||
- Security: these are demo servers. Do not expose them to untrusted networks. They lack path normalization, MIME sniffing, directory traversal protection, rate limiting, and TLS.
|
||||
|
||||
## How to point htdocs somewhere else
|
||||
- For class-based servers: call `set_htdocs("/path/to/site")` on the server instance before `start()`.
|
||||
- For the MT CGI example: set `FUN_HTDOCS=/path/to/site` in the environment before launch.
|
||||
|
||||
## Troubleshooting
|
||||
- If a CGI request yields a 500 and you see “CGI produced no output”, run the target `.fun` directly with your `fun` interpreter and fix any errors.
|
||||
- Confirm `FUN_LIB_DIR` points to the stdlib (especially when running CGI scripts that `#include` modules).
|
||||
- If the server cannot start, another process might be using the chosen port.
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# objects_basic.fun — overview
|
||||
|
||||
What it shows
|
||||
- OO basics: defining objects, fields, and invoking methods.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/objects_basic.fun
|
||||
- Or: fun examples/objects_basic.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# objects_more.fun — overview
|
||||
|
||||
What it shows
|
||||
- Additional object patterns: composition, methods, and utilities.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/objects_more.fun
|
||||
- Or: fun examples/objects_more.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# os_env.fun — overview
|
||||
|
||||
What it shows
|
||||
- Reading and writing environment variables from the operating system.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/os_env.fun
|
||||
- Or: fun examples/os_env.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# process_example.fun — overview
|
||||
|
||||
What it shows
|
||||
- Spawning and capturing subprocess output; simple process management.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/process_example.fun
|
||||
- Or: fun examples/process_example.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# progress.fun — overview
|
||||
|
||||
What it shows
|
||||
- Simple progress display in the terminal.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/progress.fun
|
||||
- Or: fun examples/progress.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# progress_inline.fun — overview
|
||||
|
||||
What it shows
|
||||
- Inline progress updates (same line updates) for simple terminal UIs.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/progress_inline.fun
|
||||
- Or: fun examples/progress_inline.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# random_demo.fun — overview
|
||||
|
||||
What it shows
|
||||
- Random number generator usage and seeding basics.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/random_demo.fun
|
||||
- Or: fun examples/random_demo.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# random_number_example.fun — overview
|
||||
|
||||
What it shows
|
||||
- Generating random numbers and printing them; small utility demo.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/random_number_example.fun
|
||||
- Or: fun examples/random_number_example.fun
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# regex_demo.fun — overview
|
||||
|
||||
What it shows
|
||||
- Regex helpers usage; simple matching and replacement tasks.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/regex_demo.fun
|
||||
- Or: fun examples/regex_demo.fun
|
||||
|
||||
Notes
|
||||
- Some regex examples depend on the optional PCRE2 extension; enable it in your build to run.
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# regex_procedural.fun — overview
|
||||
|
||||
What it shows
|
||||
- Procedural approach to regex work: compiling patterns and iterating matches.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/regex_procedural.fun
|
||||
- Or: fun examples/regex_procedural.fun
|
||||
|
||||
Notes
|
||||
- May require the optional PCRE2 extension in your build.
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# rust_hello.fun — overview
|
||||
|
||||
What it shows
|
||||
- Using Rust opcodes from Fun (when built with Rust support).
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/rust_hello.fun
|
||||
- Or: fun examples/rust_hello.fun
|
||||
|
||||
Notes
|
||||
- Requires building with FUN_WITH_RUST; otherwise this example will be unavailable.
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# rust_hello_args.fun — overview
|
||||
|
||||
What it shows
|
||||
- Passing arguments into Rust-backed opcodes and handling returns.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/rust_hello_args.fun
|
||||
- Or: fun examples/rust_hello_args.fun
|
||||
|
||||
Notes
|
||||
- Requires building with FUN_WITH_RUST.
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# rust_hello_args_return.fun — overview
|
||||
|
||||
What it shows
|
||||
- Demonstrates returning values from Rust-backed opcodes with arguments.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/rust_hello_args_return.fun
|
||||
- Or: fun examples/rust_hello_args_return.fun
|
||||
|
||||
Notes
|
||||
- Requires building with FUN_WITH_RUST.
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# serial_demo.fun — overview
|
||||
|
||||
What it shows
|
||||
- Serial port access and basic read/write (when available on your system).
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/serial_demo.fun
|
||||
- Or: fun examples/serial_demo.fun
|
||||
|
||||
Notes
|
||||
- Requires serial device access; may depend on platform support and permissions.
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# short_circuit_test.fun — overview
|
||||
|
||||
What it shows
|
||||
- Boolean evaluation order and short-circuit behavior with && and ||.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/short_circuit_test.fun
|
||||
- Or: fun examples/short_circuit_test.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# signed_ints.fun — overview
|
||||
|
||||
What it shows
|
||||
- Signed integer types and operations; ranges and conversions.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/signed_ints.fun
|
||||
- Or: fun examples/signed_ints.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# stdlib_showcase.fun — overview
|
||||
|
||||
What it shows
|
||||
- Sampler of common standard library modules and utilities.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/stdlib_showcase.fun
|
||||
- Or: fun examples/stdlib_showcase.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# strings_test.fun — overview
|
||||
|
||||
What it shows
|
||||
- String helpers and edge cases; splitting, joining, trimming, and formatting.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/strings_test.fun
|
||||
- Or: fun examples/strings_test.fun
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# tcp_http_get.fun — overview
|
||||
|
||||
What it shows
|
||||
- Manual HTTP client over raw TCP sockets: connect, write request, read response.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/tcp_http_get.fun
|
||||
- Or: fun examples/tcp_http_get.fun
|
||||
|
||||
Notes
|
||||
- Requires network access to the target host used in the script.
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# tcp_http_get_class.fun — overview
|
||||
|
||||
What it shows
|
||||
- Manual HTTP client implemented with a small helper class over sockets.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/tcp_http_get_class.fun
|
||||
- Or: fun examples/tcp_http_get_class.fun
|
||||
|
||||
Notes
|
||||
- Requires network access to the target host used in the script.
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# test_bits.fun — overview
|
||||
|
||||
What it shows
|
||||
- Bitwise utilities demonstration (and/or/xor/shifts) and small tests.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_bits.fun
|
||||
- Or: fun examples/test_bits.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# test_dec_to_hex.fun — overview
|
||||
|
||||
What it shows
|
||||
- Decimal to hexadecimal conversion helper/tests.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_dec_to_hex.fun
|
||||
- Or: fun examples/test_dec_to_hex.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# test_hex_to_dec.fun — overview
|
||||
|
||||
What it shows
|
||||
- Hexadecimal to decimal conversion helper/tests.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_hex_to_dec.fun
|
||||
- Or: fun examples/test_hex_to_dec.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# test_include.fun — overview
|
||||
|
||||
What it shows
|
||||
- Small include mechanics test; ensures local and stdlib includes work.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_include.fun
|
||||
- Or: fun examples/test_include.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# test_rol.fun — overview
|
||||
|
||||
What it shows
|
||||
- Bit rotation (ROL) helper/tests.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_rol.fun
|
||||
- Or: fun examples/test_rol.fun
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
# test_serial.fun — overview
|
||||
|
||||
What it shows
|
||||
- Serial port test; opens a port and exchanges a few bytes (when available).
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_serial.fun
|
||||
- Or: fun examples/test_serial.fun
|
||||
|
||||
Notes
|
||||
- Requires serial device access; may depend on platform support and permissions.
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# test_shl.fun — overview
|
||||
|
||||
What it shows
|
||||
- Bit shift left (SHL) helper/tests.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_shl.fun
|
||||
- Or: fun examples/test_shl.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# test_types.fun — overview
|
||||
|
||||
What it shows
|
||||
- Type checks and simple assertions around type behavior.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_types.fun
|
||||
- Or: fun examples/test_types.fun
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
# test_xor.fun — overview
|
||||
|
||||
What it shows
|
||||
- Bitwise XOR helper/tests.
|
||||
|
||||
How to run
|
||||
- export FUN_LIB_DIR="./lib"
|
||||
- ./build_debug/fun examples/test_xor.fun
|
||||
- Or: fun examples/test_xor.fun
|
||||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue