{"id":47724724,"url":"https://github.com/illegalstudio/elephc","last_synced_at":"2026-05-16T15:01:06.211Z","repository":{"id":346419203,"uuid":"1187949566","full_name":"illegalstudio/elephc","owner":"illegalstudio","description":"A PHP-to-native compiler. Takes a subset of PHP and compiles it directly to native assembly, producing standalone binaries for the currently supported targets: macOS ARM64, Linux ARM64, and Linux x86_64. No interpreter, no VM, no runtime dependencies.","archived":false,"fork":false,"pushed_at":"2026-05-13T14:57:35.000Z","size":8139,"stargazers_count":107,"open_issues_count":5,"forks_count":3,"subscribers_count":2,"default_branch":"main","last_synced_at":"2026-05-13T16:45:41.026Z","etag":null,"topics":["assembly","compiler","linux","macos","php"],"latest_commit_sha":null,"homepage":"https://elephc.dev/","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/illegalstudio.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":"ROADMAP.md","authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":"AGENTS.md","dco":null,"cla":null},"funding":{"github":"nahime0"}},"created_at":"2026-03-21T12:13:22.000Z","updated_at":"2026-05-13T15:13:01.000Z","dependencies_parsed_at":null,"dependency_job_id":"a55a7f9d-258a-4b3e-9024-c649364cfbc2","html_url":"https://github.com/illegalstudio/elephc","commit_stats":null,"previous_names":["illegalstudio/elephc"],"tags_count":81,"template":false,"template_full_name":null,"purl":"pkg:github/illegalstudio/elephc","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/illegalstudio%2Felephc","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/illegalstudio%2Felephc/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/illegalstudio%2Felephc/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/illegalstudio%2Felephc/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/illegalstudio","download_url":"https://codeload.github.com/illegalstudio/elephc/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/illegalstudio%2Felephc/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":33107564,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-16T04:41:52.686Z","status":"ssl_error","status_checked_at":"2026-05-16T04:41:52.009Z","response_time":115,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["assembly","compiler","linux","macos","php"],"created_at":"2026-04-02T20:10:30.042Z","updated_at":"2026-05-16T15:01:06.204Z","avatar_url":"https://github.com/illegalstudio.png","language":"Rust","funding_links":["https://github.com/sponsors/nahime0"],"categories":[],"sub_categories":[],"readme":"# elephc\n\n[![GitHub Stars](https://img.shields.io/github/stars/illegalstudio/elephc?style=flat-square\u0026logo=github\u0026label=stars)](https://github.com/illegalstudio/elephc/stargazers)\n[![GitHub Downloads](https://img.shields.io/github/downloads/illegalstudio/elephc/total?style=flat-square\u0026logo=github\u0026label=downloads)](https://github.com/illegalstudio/elephc/releases)\n[![Unique Cloners](.github/traffic/clones-badge.svg)](https://github.com/illegalstudio/elephc)\n[![License: MIT](https://img.shields.io/github/license/illegalstudio/elephc?style=flat-square)](LICENSE)\n[![Follow @nahime0 on X](https://img.shields.io/badge/Follow%20%40nahime0-000000?logo=x\u0026logoColor=white)](https://x.com/nahime0)\n\n\u003e 🐦 **[Follow me on X (@nahime0)](https://x.com/nahime0) for updates, new features, and behind-the-scenes development.**\n\n---\n\nA PHP-to-native compiler. Takes a subset of PHP and compiles it directly to native assembly, producing standalone binaries for the currently supported targets: **macOS ARM64**, **Linux ARM64**, and **Linux x86_64**. No interpreter, no VM, no Zend Engine, no opcode fallback.\n\n\u003e **If you like the idea or find it useful, please star the repo** — it helps others discover it and keeps the project going.\n\n\u003e **Want to support the project?** elephc is built and maintained independently. If you'd like to help it grow, consider [sponsoring on GitHub](https://github.com/sponsors/nahime0). Every contribution — big or small — makes a real difference.\n\n## DOOM rendered in PHP\n\nThe flagship showcase: a real-time 3D renderer that loads original DOOM WAD files and renders E1M1 — BSP traversal, perspective projection, per-column fog, sector lighting, collision detection, step climbing — entirely in PHP compiled to a native binary.\n\n![DOOM E1M1 rendered in PHP](showcases/doom/demo.gif)\n\nSee [showcases/doom/](showcases/doom/) for full source and build instructions.\n\n## Why\n\nMy first \"serious programming\" book was *PHP 4 and MySQL*. After years of experimenting with code, that book turned my passion into a profession. I've worked with many languages over the past 20 years, but PHP is the one that has most consistently put food on the table.\n\nPHP has a simple, approachable, and elegant syntax. Millions of developers worldwide already know it well. That makes it an ideal bridge to bring web developers closer to lower-level programming — systems work, native binaries, understanding what happens under the hood — without forcing them to learn an entirely new language first.\n\nOne thing I always missed about PHP was the ability to produce optimized, fast native binaries. While everyone else is busy building the next Facebook, I thought I could try to fill that gap and write a compiler for PHP.\n\nOf course, PHP has its limits when it comes to performance-critical or systems-level work. That's why elephc introduces compiler extensions like `packed class` for flat POD records, `buffer\u003cT\u003e` for contiguous typed arrays, `ptr` for raw memory access, and `extern` for FFI — constructs that give PHP developers the tools they need without abandoning the language they already know.\n\nIt's not perfect, but **it works**. It's a solid starting point, and more importantly, it's a great way to understand **how a compiler works** and how assembly language operates under the hood.\n\nI made the project as modular as possible. Every function has its own codegen file, and each one is **commented line by line**, so you can see exactly how a high-level construct gets translated into its low-level equivalent.\n\n## What you can expect\n\nYou can write PHP using the constructs documented in the [docs](docs/). Classes with single inheritance, interfaces, `instanceof`, nullsafe access (`?-\u003e`), abstract classes, final classes, methods and typed/static properties, PHP-style static property redeclarations, constructor property promotion, traits, constructors, instance/static methods, case-insensitive PHP symbol lookup for functions/classes/methods, `self::` / `parent::` / `static::` with late static binding, `readonly` properties and classes, enums, PHP 8 attributes on declarations, named arguments, first-class callables, typed function and method parameters and returns, `try` / `catch` / `finally` / `throw`, visibility modifiers, union and nullable types, copy-on-write arrays, associative arrays with PHP insertion order and integer/numeric-string key normalization, array union with `+`, closures, generator functions and generator closures with `yield` / `yield from`, namespaces, includes, compile-time Composer/SPL autoloading, class/introspection helpers, and PHP 8.1-style `Fiber` coroutines on macOS ARM64, Linux ARM64, and Linux x86_64.\n\nFor performance-oriented code, elephc exposes compiler extensions beyond standard PHP — see the Why section above.\n\nThen compile and run:\n\n```bash\nelephc myfile.php\n./myfile\n```\n\nThe compiler is experimental and evolving. Not everything PHP supports is implemented, and you will find bugs. But as the DOOM showcase demonstrates, you can build real, non-trivial programs with it today.\n\nIf you want to contribute, you're welcome. Mi casa es tu casa.\n\n## Learn how a compiler works\n\nelephc is designed to be read. The code generation and runtime layers are heavily annotated, so you can see what each lowering step and emitted instruction is doing — from stack frame setup to syscall invocation, from integer-to-string conversion to array memory layout. If you've ever wondered what happens between `echo \"hello\"` and the CPU executing it, follow the code from `src/codegen/` and read the comments. **No prior assembly knowledge required.**\n\n## How elephc is different\n\nThere are several ways to make PHP easier to distribute or faster to run: bundling a PHP runtime into one executable, encrypting bytecode, running through the Zend VM with JIT, or compiling selected hot paths while falling back to opcodes for dynamic code.\n\nelephc takes a narrower but cleaner route: it is a from-scratch compiler for a static subset of PHP. It parses PHP source, type-checks it, lowers it to target-specific assembly, assembles and links it into a native executable, and ships only the small runtime routines needed by the generated program. If elephc compiles a construct, that construct is native code rather than interpreted PHP.\n\nThat tradeoff is intentional:\n\n- **Less legacy compatibility** than a VM-backed PHP implementation.\n- **More mechanical transparency**: readable assembly output, source maps, line-by-line commented codegen, and a documented memory model.\n- **No hidden runtime dependency**: the generated binary does not need PHP, the Zend Engine, a loader extension, or an embedded interpreter.\n- **Native-oriented extensions**: `extern`, `ptr`, `buffer\u003cT\u003e`, and `packed class` let PHP-shaped code cross into systems, FFI, game, and performance-sensitive workloads.\n\nThat does not mean elephc has to live outside the existing PHP ecosystem. The current CLI path produces standalone executables, but the roadmap also includes shared/static library output and an experimental PHP extension bridge. That opens a practical middle path: keep a framework such as WordPress, Laravel, or Symfony running on PHP, then compile static, performance-sensitive modules into native libraries or PHP extensions.\n\nSo elephc is not a drop-in replacement for an entire dynamic framework today. The longer-term goal is more useful: make it possible to move the parts of PHP code that are static enough to compile into inspectable native code, while the rest of the application can stay in ordinary PHP.\n\n## Requirements\n\n- Rust toolchain (`cargo`)\n- A native assembler and linker for your host/target\n- On macOS: Xcode Command Line Tools (`xcode-select --install`)\n- On Linux: a standard native toolchain (`as`, `ld`, libc development files)\n\n## Install\n\n### Homebrew (recommended)\n\n```bash\nbrew install illegalstudio/tap/elephc\n```\n\n### From source\n\n```bash\ngit clone https://github.com/illegalstudio/elephc.git\ncd elephc\ncargo build --release\n```\n\nThe binary is at `./target/release/elephc`.\n\n### Manual download\n\nPre-built binaries are available on the [Releases](https://github.com/illegalstudio/elephc/releases) page. If macOS blocks the binary, run:\n\n```bash\nxattr -cr elephc\n```\n\n## Usage\n\n```bash\n# Compile a PHP file to a native binary\nelephc hello.php\n./hello\n\n# Custom heap size (default: 8MB)\nelephc --heap-size=16777216 heavy.php\n\n# Enable runtime heap verification while debugging ownership issues\nelephc --heap-debug heavy.php\n\n# Print allocation/free counters to stderr while debugging GC behavior\nelephc --gc-stats heavy.php\n\n# Enable compile-time feature branches\nelephc --define DEBUG app.php\n\n# Print per-phase compiler timings\nelephc --timings hello.php\n\n# Emit assembly and a simple source-map sidecar\nelephc --emit-asm --source-map hello.php\n\n# Run the front-end checks without writing assembly or a binary\nelephc --check hello.php\n\n# Link extra native libraries or frameworks for FFI\nelephc app.php -l sqlite3 -L /opt/homebrew/lib --framework Cocoa\n\n# Explicit target selection\n# Supported targets today: macos-aarch64, linux-aarch64, linux-x86_64\nelephc --target linux-aarch64 hello.php\nelephc --target linux-x86_64 hello.php\n```\n\nOr via cargo:\n\n```bash\ncargo run -- hello.php\n./hello\n```\n\n## Showcases\n\n| Showcase | Description |\n|---|---|\n| [DOOM E1M1](showcases/doom/) | Real-time 3D WAD renderer with BSP traversal, SDL2 FFI, `packed class` geometry, `buffer\u003cT\u003e` storage, collision detection, HUD |\n| [SDL framebuffer](examples/sdl_framebuffer/) | Pixel-level rendering with SDL2 via FFI |\n| [SDL audio](examples/sdl_audio/) | Audio playback with SDL2 via FFI |\n| [Hot-path buffers](examples/hot-path/) | `packed class` + `buffer\u003cT\u003e` for performance-critical data |\n| [FFI memory](examples/ffi-memory/) | Raw C memory patterns with `malloc`, `free`, `memcpy` via FFI |\n\n## FFI\n\nelephc can call native C functions directly through `extern` declarations.\n\n```php\n\u003c?php\nextern function atoi(string $s): int;\nextern function signal(int $sig, callable $handler): ptr;\nextern function raise(int $sig): int;\nextern global ptr $environ;\n\nfunction on_signal($sig) {\n    echo \"signal = \" . $sig . \"\\n\";\n}\n\necho atoi(\"999\") . \"\\n\";\necho ptr_is_null($environ) ? \"missing\\n\" : \"ok\\n\";\nsignal(15, \"on_signal\");\nraise(15);\n```\n\nNotes:\n\n- `extern function`, `extern \"lib\" { ... }`, `extern global`, and `extern class` are supported.\n- `string` arguments are copied to temporary null-terminated C strings for the duration of the native call.\n- `string` return values are copied back into owned elephc strings.\n- `callable` parameters pass a user-defined elephc function by string name, for example `\"on_signal\"`.\n- Callback functions must stay C-compatible: use `int`, `float`, `bool`, `ptr`, or `void`-shaped values. String callbacks are not supported yet.\n- Raw C memory patterns are supported through ordinary extern declarations such as `malloc`, `free`, `memcpy`, and `memset`.\n- Pointer helpers include byte/word buffer access (`ptr_read8`, `ptr_read32`, `ptr_write8`, `ptr_write32`) in addition to `ptr_get` / `ptr_set`.\n\n## What it compiles\n\nelephc supports a growing subset of PHP and aims to match PHP behavior for the language features it implements.\n\n```php\n\u003c?php\n$pi = M_PI;\necho \"Pi is approximately \" . number_format($pi, 5) . \"\\n\";\necho \"2 ** 10 = \" . (2 ** 10) . \"\\n\";\necho \"10 / 3 = \" . (10 / 3) . \"\\n\";\necho \"Type: \" . gettype($pi) . \"\\n\";\n\n$x = (int)$pi;\necho \"Truncated: \" . $x . \"\\n\";\n\nif ($x === 3) {\n    echo \"Correct!\\n\";\n}\n```\n\n### Supported types\n\n| Type | Example |\n|---|---|\n| `int` | `42`, `-7`, `0xFF`, `0755`, `0o755`, `0b1010`, `1_000_000`, `PHP_INT_MAX` |\n| `float` | `3.14`, `.5`, `1e-5`, `1_000.5`, `1e1_0`, `INF`, `NAN` |\n| `string` | `\"hello\\n\"`, `'raw'` |\n| `bool` | `true`, `false` |\n| `null` | `null` |\n| `void` | `function log_it(): void { echo \"ok\"; }` |\n| `never` | `function fail(): never { throw new Exception(\"boom\"); }` |\n| `mixed` | `mixed $x = 42;`, `function show(mixed $x): string { ... }` |\n| `iterable` | `function walk(iterable $items): iterable { ... }` (PHP `array \\| Traversable` pseudo-type; accepts indexed arrays, associative arrays, `Iterator`, and `IteratorAggregate`) |\n| `resource` | Successful `$f = fopen(\"file.txt\", \"r\")`, `STDIN`, `STDOUT`, `STDERR` |\n| `callable` | `function apply(callable $fn): int { return $fn(); }` |\n| `array` | `[1, 2, 3]`, `[\"key\" =\u003e \"value\"]`, `[[1,2],[3,4]]` (indexed, associative, multi-dimensional, copy-on-write, union with `+`) |\n| `object` | `new Foo()`, `$user-\u003ename` |\n| `pointer` | `ptr($x)`, `ptr_null()`, `ptr_cast\u003cint\u003e($p)` |\n| `enum` | `enum Color: int { case Red = 1; }`, `Color::Red-\u003evalue`, `Color::from(1)` |\n| `int\\|string` | `int\\|string $x = 42;`, `function show(int\\|string $x): string { ... }` |\n| `?int` | `?int $x = null;`, `function find(): ?int { ... }` |\n| `buffer\u003cT\u003e` | `buffer\u003cint\u003e $xs = buffer_new\u003cint\u003e(256)` |\n| `packed class` | `packed class Vec2 { public float $x; public float $y; }` |\n\n### Supported constructs\n\nThe full list of supported constructs, operators, and control structures is in the [docs](docs/). Highlights:\n\n- **OOP**: classes, abstract/final classes, typed/final/static properties and methods, PHP-style static property redeclarations, direct static array property writes, constructor property promotion, interfaces, `instanceof`, traits, enums, PHP 8 declaration attributes, limited attribute reflection (`ReflectionClass`/`ReflectionMethod`/`ReflectionProperty::getAttributes()`, `ReflectionAttribute::newInstance()`), `readonly`, static/instance methods, case-insensitive class/interface/trait and method lookup, `self::`/`parent::`/`static::`, `::class` reflection, `new self()` / `new static()` / `new parent()`, magic methods (`__toString`, `__get`, `__set`)\n- **Functions**: case-insensitive user and built-in function calls, default parameters, variadic/spread, pass by reference, named arguments, global variables, static locals, first-class callables, closures, arrow functions, static closures (`static function () { }`, `static fn () =\u003e ...`)\n- **Generators**: generator functions and closures, `yield`, key/value yields, `yield from`, `Generator::send()`, `throw()`, `getReturn()`, and `foreach` over `Iterator` / `IteratorAggregate`\n- **Fibers**: `Fiber`, `FiberError`, `Fiber::suspend()`, `Fiber::getCurrent()`, `start()`, `resume()`, `throw()`, `getReturn()`, state predicates, closure captures, guarded native stacks, and ARM64 / Linux x86_64 context switching\n- **Control flow**: if/elseif/else, while, do-while, for, foreach, switch, match, break/continue including multi-level depths, try/catch/finally/throw\n- **Statements and literals**: `const` / `define()` constants, `global` declarations, `static` locals, `print` expressions, list unpacking, PHP numeric literal forms, heredoc / nowdoc strings\n- **Operators**: arithmetic, comparison, `instanceof`, logical, bitwise, ternary, null coalescing (`??`), PHP 8.5 pipe (`|\u003e`), assignment expressions for local and stabilized non-local targets, null coalescing assignment (`??=`), error control (`@`), and compound assignments\n- **Types**: union types (`int|string`), nullable (`?int`), `never` return type, `iterable` pseudo-type, inferred `resource|false` values for `fopen()` and `resource` values for standard streams, type casting, typed properties, typed function, method, closure, and arrow parameters and returns\n- **Modules**: namespaces, use imports, include/require/include_once/require_once, compile-time Composer PSR-4/PSR-0/classmap/files autoloading, `spl_autoload_register()` rule extraction, PHP magic constants\n- **FFI**: extern functions, extern blocks, extern globals, extern classes, pointer builtins\n- **Extensions**: `ifdef`, `packed class`, `buffer\u003cT\u003e`, `buffer_new\u003cT\u003e()`, `buffer_len()`, `buffer_free()`\n\n### Built-in functions (290+)\n\n**Strings:** `strlen`, `substr`, `strpos`, `strrpos`, `strstr`, `str_replace`, `str_ireplace`, `substr_replace`, `strtolower`, `strtoupper`, `ucfirst`, `lcfirst`, `ucwords`, `trim`, `ltrim`, `rtrim`, `str_repeat`, `str_pad`, `strrev`, `str_split`, `strcmp`, `strcasecmp`, `str_contains`, `str_starts_with`, `str_ends_with`, `ord`, `chr`, `explode`, `implode`, `sprintf`, `printf`, `sscanf`, `md5`, `sha1`, `hash`, `number_format`, `addslashes`, `stripslashes`, `nl2br`, `wordwrap`, `bin2hex`, `hex2bin`, `htmlspecialchars`, `htmlentities`, `html_entity_decode`, `urlencode`, `urldecode`, `rawurlencode`, `rawurldecode`, `base64_encode`, `base64_decode`, `ctype_alpha`, `ctype_digit`, `ctype_alnum`, `ctype_space`\n\n**Arrays:** `count`, `array_push`, `array_pop`, `in_array`, `array_keys`, `array_values`, `sort`, `rsort`, `isset`, `array_key_exists`, `array_search`, `array_merge`, `array_slice`, `array_splice`, `array_combine`, `array_flip`, `array_reverse`, `array_unique`, `array_sum`, `array_product`, `array_chunk`, `array_pad`, `array_fill`, `array_fill_keys`, `array_diff`, `array_intersect`, `array_diff_key`, `array_intersect_key`, `array_unshift`, `array_shift`, `asort`, `arsort`, `ksort`, `krsort`, `natsort`, `natcasesort`, `shuffle`, `array_rand`, `array_column`, `range`, `array_map`, `array_filter`, `array_reduce`, `array_walk`, `usort`, `uksort`, `uasort`, `call_user_func`, `call_user_func_array`, `function_exists`\n\n**Math:** `abs`, `floor`, `ceil`, `round`, `sqrt`, `pow`, `min`, `max`, `intdiv`, `fmod`, `fdiv`, `rand`, `mt_rand`, `random_int`, `sin`, `cos`, `tan`, `asin`, `acos`, `atan`, `atan2`, `sinh`, `cosh`, `tanh`, `log`, `log2`, `log10`, `exp`, `hypot`, `deg2rad`, `rad2deg`, `pi`\n\n**Types and class introspection:** `gettype`, `settype`, `empty`, `unset`, `is_int`, `is_float`, `is_string`, `is_bool`, `is_null`, `is_numeric`, `is_nan`, `is_finite`, `is_infinite`, `is_iterable`, `is_callable`, `boolval`, `floatval`, `intval`, `class_exists`, `interface_exists`, `trait_exists`, `enum_exists`, `class_alias`, `get_class`, `get_parent_class`, `get_declared_classes`, `get_declared_interfaces`, `get_declared_traits`, `is_a`, `is_subclass_of`\n\n**I/O:** `fopen`, `fclose`, `fread`, `fwrite`, `fgets`, `fgetc`, `fpassthru`, `flock`, `tmpfile`, `readfile`, `feof`, `readline`, `fseek`, `ftell`, `rewind`, `file_get_contents`, `file_put_contents`, `file`, `fgetcsv`, `fputcsv`, `file_exists`, `is_file`, `is_dir`, `is_readable`, `is_writable`, `is_writeable`, `is_executable`, `is_link`, `symlink`, `link`, `readlink`, `linkinfo`, `filesize`, `filemtime`, `fileatime`, `filectime`, `fileperms`, `fileowner`, `filegroup`, `fileinode`, `filetype`, `stat`, `lstat`, `fstat`, `clearstatcache`, `basename`, `dirname`, `pathinfo`, `realpath`, `fnmatch`, `touch`, `chmod`, `chown`, `chgrp`, `umask`, `ftruncate`, `fflush`, `fsync`, `fdatasync`, `copy`, `rename`, `unlink`, `mkdir`, `rmdir`, `scandir`, `glob`, `getcwd`, `chdir`, `tempnam`, `sys_get_temp_dir`, `var_dump`, `print_r`\n\n**System:** `exit`, `die`, `time`, `microtime`, `date`, `mktime`, `strtotime`, `sleep`, `usleep`, `getenv`, `putenv`, `php_uname`, `phpversion`, `exec`, `shell_exec`, `system`, `passthru`, `json_encode`, `json_decode`, `json_last_error`, `json_last_error_msg`, `json_validate`, `preg_match`, `preg_match_all`, `preg_replace`, `preg_split`, `define`, `class_attribute_names`, `class_attribute_args`, `class_get_attributes`\n\n**SPL/autoload:** `spl_autoload_register`, `spl_autoload_unregister`, `spl_autoload_functions`, `spl_autoload_extensions`, `spl_autoload_call`, `spl_autoload`, `spl_classes`, `spl_object_id`, `spl_object_hash`\n\n**Pointers/Buffers:** `ptr`, `ptr_null`, `ptr_is_null`, `ptr_get`, `ptr_set`, `ptr_read8`, `ptr_read32`, `ptr_write8`, `ptr_write32`, `ptr_offset`, `ptr_cast\u003cT\u003e`, `ptr_sizeof`, `buffer_new\u003cT\u003e`, `buffer_len`, `buffer_free`\n\n### Constants\n\n`INF`, `NAN`, `PHP_INT_MAX`, `PHP_INT_MIN`, `PHP_FLOAT_MAX`, `PHP_FLOAT_MIN`, `PHP_FLOAT_EPSILON`, `M_PI`, `M_E`, `M_SQRT2`, `M_PI_2`, `M_PI_4`, `M_LOG2E`, `M_LOG10E`, `PHP_EOL`, `PHP_OS`, `DIRECTORY_SEPARATOR`, `STDIN`, `STDOUT`, `STDERR`, `PATHINFO_DIRNAME`, `PATHINFO_BASENAME`, `PATHINFO_EXTENSION`, `PATHINFO_FILENAME`, `PATHINFO_ALL`, `FNM_NOESCAPE`, `FNM_PATHNAME`, `FNM_PERIOD`, `FNM_CASEFOLD`, `LOCK_SH`, `LOCK_EX`, `LOCK_UN`, `LOCK_NB`, `JSON_HEX_TAG`, `JSON_HEX_AMP`, `JSON_HEX_APOS`, `JSON_HEX_QUOT`, `JSON_FORCE_OBJECT`, `JSON_NUMERIC_CHECK`, `JSON_UNESCAPED_SLASHES`, `JSON_PRETTY_PRINT`, `JSON_UNESCAPED_UNICODE`, `JSON_PARTIAL_OUTPUT_ON_ERROR`, `JSON_PRESERVE_ZERO_FRACTION`, `JSON_INVALID_UTF8_IGNORE`, `JSON_INVALID_UTF8_SUBSTITUTE`, `JSON_THROW_ON_ERROR`, `JSON_OBJECT_AS_ARRAY`, `JSON_BIGINT_AS_STRING`, `JSON_ERROR_NONE`, `JSON_ERROR_DEPTH`, `JSON_ERROR_STATE_MISMATCH`, `JSON_ERROR_CTRL_CHAR`, `JSON_ERROR_SYNTAX`, `JSON_ERROR_UTF8`, `JSON_ERROR_RECURSION`, `JSON_ERROR_INF_OR_NAN`, `JSON_ERROR_UNSUPPORTED_TYPE`, `JSON_ERROR_INVALID_PROPERTY_NAME`, `JSON_ERROR_UTF16`, `__DIR__`, `__FILE__`, `__LINE__`, `__FUNCTION__`, `__CLASS__`, `__METHOD__`, `__NAMESPACE__`, `__TRAIT__`\n\nUser-defined constants are also supported via `const NAME = value;` and `define(\"NAME\", value);`. Constants remain case-sensitive, matching PHP.\n\n## How it works\n\n```\nPHP source → Lexer → Parser (AST) → Magic constants (per-file) → Conditional (ifdef/--define) → Autoload registry build (Composer + SPL rules) → Resolver (include declaration discovery, include/require inlining, per-file constants, once guards, function variant marks) → NameResolver (namespaces/use/FQNs) → Autoload run (class-triggered file insertion) → Optimizer (constant folding) → Type Checker → Optimizer (constant propagation) → Optimizer (control-flow pruning) → Optimizer (control-flow normalization) → Optimizer (dead-code elimination) → Codegen → as + ld → native executable\n```\n\nThe compiler emits human-readable assembly for the selected target. You can inspect the `.s` file to see exactly what your PHP becomes:\n\n```bash\nelephc hello.php\ncat hello.s\n```\n\nIf you add `--source-map`, elephc also writes `hello.map`, a compact JSON sidecar that maps emitted assembly lines back to PHP line/column pairs. If you add `--timings`, the compiler prints per-phase durations such as lexing, parsing, early optimization, type checking, constant propagation, post-check pruning, control-flow normalization, dead-code elimination, runtime-cache preparation, code generation, assembling, and linking.\n\n### Current optimization passes\n\nelephc already performs a small but useful AST-level optimization pipeline before emitting assembly:\n\n- **Constant folding before type checking**: folds scalar arithmetic, bitwise ops, comparisons, logical ops, string-literal concatenation, scalar casts, ternaries, null coalescing, known `match` expressions, and scalar indexed/associative array-literal reads when the result is statically known.\n- **Constant propagation after type checking**: forwards scalar local values through straight-line code, across agreeing `if` / `switch` / `try` merges, through known-subject `switch` paths, through non-throwing `try` bodies without poisoning the merge with unreachable catches, through uniform local `?:` / `match` assignments, through fixed scalar destructuring like `[$a, $b] = [2, 3]`, and across simple loops when untouched locals or stable `for` init assignments can be proven safe even with conservative nested `switch`, `try/catch/finally`, `foreach`, other simple nested loop writes, local array mutations like `$items[] = $i` / `$items[0] = $i`, local property writes like `$box-\u003elast = $i` / `$box-\u003eitems[] = $i`, or targeted local invalidations like `unset($tmp)`. It also uses local loop path summaries for known `while(false)`, `do...while(false)`, `while(true)` / `for(;;)` break exits, and branch-local loop exits that agree on scalar values, which in turn unlocks more folding in later expressions such as `$x ** $y`.\n- **Control-flow pruning after type checking**: removes constant-dead `if` / `elseif` / `while (false)` / `for (...; false; ...)` branches, materializes constant `switch` execution, prunes `match` arms, and trims unreachable statements after terminating constructs such as `return`, `throw`, `break`, and `continue`.\n- **Control-flow normalization after pruning**: canonicalizes equivalent residual shapes such as nested `elseif` chains, merged `if` heads/tails, single-case or fallthrough-only `switch` shells, canonical multi-catch handlers, folded outer `finally` wrappers, and identical `if` branches so later passes see fewer structurally different but semantically identical trees.\n- **Dead-code elimination after normalization**: removes empty control shells, simplifies single-path conditionals, prunes guard contradictions across boolean, strict-scalar, loose-equality, and safe relational checks, uses CFG-lite reachability for local `if` / `switch` / `try` shapes, hoists safe non-throwing `try` prefixes, and drops unused pure expression statements and dead pure subexpressions when the surrounding expression already determines the result.\n- **Local effect summaries for purity / may-throw reasoning**: tracks known pure and non-throwing builtins, user functions, static methods, private `$this` methods, closures, first-class callables, and merged callable aliases through `if` / `switch` / `try` control flow so the optimizer can simplify `try` regions and prune dead handlers more precisely.\n\nThe optimizer is intentionally conservative. It does not yet do full function-level CFG fixed-point propagation, aggressive whole-program optimization, or assembly-level peephole rewriting, but it does compute lightweight effect summaries and local CFG-lite reachability for known call targets and structured control flow so AST rewrites can stay more precise without becoming risky.\n\n### Type system\n\nThe static type system tracks these runtime shapes at compile time:\n\n- **Int** — 64-bit signed integer\n- **Float** — 64-bit double-precision\n- **Str** — pointer + length pair\n- **Bool** — `true`/`false`, coerces to 0/1\n- **Void / null** — null sentinel value, coerces to 0/\"\"\n- **Never** — non-returning function/method/closure return type\n- **Iterable** — type-erased array / `Traversable` pseudo-type\n- **Array** — indexed arrays with inferred element type; heterogeneous payloads widen to boxed `Mixed`\n- **AssocArray** — associative arrays with key/value types\n- **Buffer** — fixed-size contiguous `buffer\u003cT\u003e` storage for hot-path values\n- **Mixed** — boxed runtime-tagged payload used for heterogeneous array values, union storage, and user-facing `mixed` hints\n- **Callable** — closures and callable function references\n- **Object** — heap-allocated class instances\n- **Packed** — nominal packed-record metadata used with pointers and buffers\n- **Pointer** — raw 64-bit addresses, optionally tagged via `ptr_cast\u003cT\u003e()`\n- **Resource** — stream handles such as successful `fopen()` results and standard streams\n- **Union** — declared union types lowered to boxed tagged runtime payloads\n\nA variable's type is set at first assignment. Compatible types (int/float/bool/null) can be reassigned between each other.\n\n## Error messages\n\nErrors include line and column numbers, and the compiler tries to recover far enough to report multiple independent syntax / semantic errors in one pass. Successful compilations may also emit non-fatal warnings such as unused variables / parameters or unreachable code:\n\n```\nerror[3:1]: Undefined variable: $x\nerror[5:7]: Type error: cannot reassign $x from Int to Str\nerror[2:1]: Required file not found: 'missing.php'\nwarning[9:5]: Unused variable: $tmp\nwarning[14:9]: Unreachable code\n```\n\n## Project structure\n\nHigh-level map of the source tree. The codebase contains more focused helper submodules than shown here; treat this as an orientation guide rather than a byte-for-byte file listing.\n\n```\nsrc/\n├── lib.rs               # Public module exports\n├── main.rs              # CLI binary entry point\n├── cli.rs               # Command-line argument parsing and options\n├── pipeline.rs          # Frontend/backend compilation pipeline\n├── linker.rs            # Assembler + linker invocation\n├── timings.rs           # Phase timing collection/reporting\n├── span.rs              # Source position tracking (line, col)\n├── conditional/         # Build-time `ifdef` pass driven by --define\n├── magic_constants.rs   # Per-file PHP magic constant lowering\n├── magic_constants/     # File/scope/trait magic-constant walkers\n├── autoload/            # Composer/SPL AOT autoload indexing and file insertion\n├── resolver/            # Include/require resolution, declaration discovery, once guards\n├── runtime_cache.rs     # Preassembled runtime object cache\n├── source_map.rs        # Assembly/source-map sidecar emission\n├── termination.rs       # Structured terminal-effect analysis\n├── optimize.rs          # Optimizer public entry points and effect context\n├── optimize/            # AST optimizer: folding, propagation, pruning, normalization, dead-code elimination\n├── names.rs             # Qualified/FQN name model + symbol mangling helpers\n├── name_resolver/       # Namespace/use resolution to canonical names\n│\n├── lexer/               # Source text → token stream\n│   ├── token.rs         # Token enum\n│   ├── scan.rs          # Main scanning loop, operators\n│   ├── literals.rs      # Literal scanning entry point\n│   ├── literals/        # Identifier, number, and string scanners\n│   └── cursor.rs        # Byte-level source reader\n│\n├── parser/              # Tokens → AST (Pratt parser)\n│   ├── ast/             # ExprKind, StmtKind, BinOp, CastType\n│   ├── expr/            # Expression parsing helpers and Pratt parser passes\n│   ├── stmt/            # Statement parsing, OOP, namespaces, FFI\n│   └── control.rs       # if, while, for, foreach, do-while, switch, try/catch/finally\n│\n├── types/               # Static type checking\n│   ├── mod.rs           # check() entry point and type exports\n│   ├── model.rs         # PhpType and TypeEnv\n│   ├── result.rs        # CheckResult and semantic metadata\n│   ├── signatures.rs    # Built-in and callable signatures\n│   ├── call_args/       # Shared named/spread call planner\n│   ├── schema.rs        # Class/interface/enum metadata\n│   ├── fibers.rs        # Fiber callback validation\n│   ├── traits.rs        # Trait flattening and conflict resolution\n│   ├── traits/          # Trait expansion, merge, and validation helpers\n│   ├── warnings/        # Non-fatal diagnostics (unused vars, unreachable code)\n│   └── checker/\n│       ├── mod.rs       # Type-checker orchestration\n│       ├── builtin_interfaces.rs # Built-in SPL/core interface injection\n│       ├── builtin_iterators.rs # Built-in Iterator / IteratorAggregate metadata\n│       ├── builtin_json.rs # JsonException / JsonSerializable metadata\n│       ├── builtin_spl_exceptions.rs # SPL exception hierarchy metadata\n│       ├── builtin_stdclass.rs # stdClass dynamic-property metadata\n│       ├── builtin_types/ # Built-in class/interface/enum metadata\n│       ├── builtins/    # Built-in function type signatures\n│       ├── callables/   # Callable values, first-class callables, and callback checks\n│       ├── driver/      # Checker initialization and orchestration helpers\n│       ├── functions/   # User function type inference\n│       ├── inference/   # Focused inference helpers\n│       ├── schema/      # Class/interface/trait/enum schema validation\n│       ├── stmt_check/  # Statement-level checking helpers\n│       ├── type_compat/ # Type compatibility and assignment rules\n│       └── yield_validation/ # Generator/yield placement validation\n│\n├── codegen/             # AST → target assembly\n│   ├── mod.rs           # Pipeline entry, main/global codegen orchestration\n│   ├── driver_support.rs # Pipeline glue and orchestration helpers\n│   ├── prescan.rs       # Pre-pass collecting program-wide codegen metadata\n│   ├── program_usage.rs # Usage analysis feeding metadata emission\n│   ├── expr.rs          # Expression codegen dispatcher\n│   ├── expr/            # Focused expression helpers (arrays, calls, objects, binops, ...)\n│   ├── stmt.rs          # Statement codegen dispatcher\n│   ├── stmt/            # Focused statement helpers (arrays, control_flow, io, storage, ...)\n│   ├── abi/             # Target-aware calling-convention, frame, and value helpers\n│   ├── functions/       # User function emission, wrappers, and epilogue cleanup\n│   ├── main_emission.rs # Top-level program emission\n│   ├── class_methods.rs # Class/static method emission orchestration\n│   ├── function_variants.rs # Include-loaded function dispatchers\n│   ├── interface_wrappers.rs # Interface dispatch return-shape adapters\n│   ├── ffi.rs           # Extern function/global/class codegen\n│   ├── context.rs       # Variables, labels, loop/finally stacks, ownership lattice\n│   ├── data_section.rs  # String/float literal .data section\n│   ├── emit.rs          # Assembly text buffer\n│   ├── platform/        # Target parsing, syscall remapping, Linux transforms\n│   │\n│   ├── builtins/        # Built-in function codegen (one file per language function)\n│   │   ├── strings/     # strlen, substr, strpos, explode, implode, ...\n│   │   ├── arrays/      # count, array_push, array_pop, sort, ...\n│   │   ├── math/        # abs, floor, pow, rand, fmod, ...\n│   │   ├── types/       # is_int, gettype, empty, unset, settype, ...\n│   │   ├── spl/         # spl_autoload_*, spl_classes, spl_object_id/hash\n│   │   ├── io/          # fopen, fclose, fread, fwrite, fgets, var_dump, print_r, file_get_contents, ...\n│   │   ├── pointers/    # ptr, ptr_get, ptr_set, ptr_read8, ptr_write8, ptr_offset, ...\n│   │   └── system/      # exit, die, time, sleep, getenv, exec, ...\n│   │\n│   └── runtime/         # Runtime routines and target-specific emission helpers\n│       ├── strings/     # itoa, concat, ftoa, strpos, str_replace, ...\n│       ├── arrays/      # heap_alloc, array_new, array_push, sort, ...\n│       ├── buffers/     # buffer_new, buffer_len, bounds and lifetime checks\n│       ├── data/        # fixed and user-program runtime data/metadata\n│       ├── exceptions.rs # exception runtime orchestration / re-exports\n│       ├── exceptions/  # setjmp/longjmp-based exception helpers\n│       ├── io/          # fopen, fclose, fread, fwrite, file_ops, ...\n│       ├── objects/     # stdClass, dynamic property, mixed object/index helpers\n│       ├── pointers/    # ptoa, ptr_check_nonnull, str_to_cstr, cstr_to_str\n│       ├── system/      # build_argv, time, getenv, shell_exec\n│       ├── fibers/      # Fiber stacks, context switch, entry trampoline, Fiber API\n│       └── generators/  # Generator frame layout and __rt_gen_* helpers\n│\n└── errors/              # Error formatting with line:col\n```\n\n## Tests\n\n3000+ tests across lexer, parser, codegen, and error reporting. Each codegen test compiles inline PHP source to a native binary, runs it, and asserts stdout.\n\n```bash\ncargo test                      # all tests\ncargo test -- --include-ignored # all tests, including ignored integration tests\ncargo test test_my_feature      # run specific tests\nELEPHC_PHP_CHECK=1 cargo test   # cross-check output with PHP interpreter\n./scripts/test-linux-arm64.sh   # Linux ARM64 suite in Docker\n./scripts/test-linux-x86_64.sh  # Linux x86_64 suite in Docker\n```\n\n## Documentation\n\nThe **[docs/](docs/)** directory is a complete wiki covering every aspect of the compiler. Inside you'll find:\n\n- **PHP syntax reference** — types, operators, control structures, functions, classes, namespaces, and all 290+ built-in functions with signatures and examples\n- **Compiler extensions** — pointers, `buffer\u003cT\u003e`, `packed class`, FFI with `extern`, and conditional compilation with `ifdef` — the features that take PHP beyond the web\n- **Compiler internals** — a step-by-step walkthrough of the full pipeline, from lexing to Pratt parsing to type checking to code generation and runtime structure\n- **ARM64 primer** — an introduction to ARM64 assembly for people who've never seen it, plus a quick reference of the ARM64 instruction set used by elephc's AArch64 backend\n- **Memory model** — how the stack, heap, concat buffer, and hash tables work under the hood\n\nIf you're new to compilers or assembly, start from the top and work your way down. No prior low-level knowledge required.\n\nFor runnable language samples, see `examples/`. For the benchmark harness and CI trend artifacts that compare elephc against PHP and equivalent C fixtures, see `benchmarks/README.md`. For a focused perf comparison, see `benchmarks/hot-path-buffer-vs-arrays`.\n\n## License\n\nMIT\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fillegalstudio%2Felephc","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fillegalstudio%2Felephc","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fillegalstudio%2Felephc/lists"}