Development Setup
This guide covers how to build, run, and develop the rust-plc project.
Prerequisites
- Rust 1.85+ (edition 2024). Install via rustup.
- Node.js LTS (for the VSCode extension). The devcontainer installs this automatically.
- C compiler (for building tree-sitter). Usually available by default on Linux/macOS; on Windows use MSVC.
Clone and Build
git clone <repository-url>
cd rust-plc
# Build the CLI (and all dependencies)
cargo build -p st-cli
# Build the entire workspace
cargo build --workspace
The primary binary is st-cli, which serves as both the command-line tool and
the LSP server process.
Run Tests
# Run all tests across every crate
cargo test --workspace
# Run tests for a specific crate
cargo test -p st-grammar
cargo test -p st-semantics
# Run a single test by name
cargo test -p st-runtime test_arithmetic
Project Structure
rust-plc/
Cargo.toml Workspace root (10 members)
crates/
st-grammar/ Tree-sitter parser wrapper
src/lib.rs language(), kind constants, grammar tests
st-syntax/ AST definitions + CST-to-AST lowering
src/ast.rs Typed AST nodes (SourceFile, Statement, Expr...)
src/lower.rs Tree-sitter walk -> AST construction
src/lib.rs parse() convenience function
tests/
lower_tests.rs AST lowering tests
coverage_gaps.rs Additional coverage tests
st-semantics/ Semantic analysis
src/analyze.rs Two-pass analyzer
src/scope.rs Hierarchical symbol table
src/types.rs Ty enum, coercion rules, numeric ranking
src/diagnostic.rs Diagnostic codes and severities
src/lib.rs check() convenience function
tests/
end_to_end_tests.rs Full parse-analyze round trips
type_tests.rs Type checking
scope_tests.rs Scope resolution
call_tests.rs Function/FB call validation
control_flow_tests.rs IF/FOR/WHILE/CASE checks
struct_array_tests.rs UDT tests
warning_tests.rs Unused variable warnings etc.
coverage_gaps.rs Additional coverage
test_helpers.rs Shared test utilities
st-ir/ Intermediate representation
src/lib.rs Module, Function, Instruction, Value, MemoryLayout
st-compiler/ AST -> IR compilation
src/compile.rs ModuleCompiler + FunctionCompiler
src/lib.rs compile() public API
tests/
compile_tests.rs Compilation tests
st-runtime/ Bytecode VM + scan-cycle engine
src/vm.rs Vm, CallFrame, fetch-decode-execute loop
src/engine.rs Engine, CycleStats, watchdog
src/lib.rs Public re-exports
tests/
vm_tests.rs VM execution tests
st-lsp/ Language Server Protocol
src/server.rs tower-lsp Backend implementation
src/document.rs Per-document state (tree, AST, analysis)
src/completion.rs Completion provider
src/semantic_tokens.rs Semantic token encoding
src/lib.rs run_stdio()
tests/
lsp_integration.rs Subprocess-based LSP tests (13 tests)
unit_tests.rs In-process LSP tests (41 tests)
st-dap/ Debug Adapter Protocol (placeholder)
src/lib.rs
st-monitor/ WebSocket live monitoring (placeholder)
src/lib.rs
st-cli/ CLI entry point
src/main.rs serve, check, run commands
editors/
vscode/ VSCode extension
package.json Extension manifest
src/extension.ts Thin client: launches st-cli serve
syntaxes/ TextMate grammar for highlighting
language-configuration.json
docs/ mdBook documentation (you are here)
.devcontainer/ Development container definition
playground/ Example .st files for testing
Using the Devcontainer
The project includes a devcontainer configuration in .devcontainer/:
- Dockerfile builds an image with Rust and Node.js.
- devcontainer.json configures VSCode with rust-analyzer and ST file associations.
- post-create.sh runs after container creation to install dependencies.
To use it:
- Install the “Dev Containers” extension in VSCode.
- Open the project folder.
- VSCode will prompt “Reopen in Container” – accept.
- The container will build and configure itself automatically.
Launching the Extension Development Host
To test the VSCode extension with the LSP server:
- Open the project in VSCode.
- Make sure the Rust binary is built:
cargo build -p st-cli. - Open the
editors/vscode/folder in VSCode (or use the workspace). - Press F5 to launch the Extension Development Host.
- In the new VSCode window, open a
.stfile. The extension will launchst-cli serveand connect to it over stdio.
The server path is configured via structured-text.serverPath in settings.
The devcontainer sets this to ${workspaceFolder}/target/debug/st-cli.
Useful Commands
# Type check without running
cargo build --workspace 2>&1 | head -20
# Check a Structured Text file for errors
cargo run -p st-cli -- check playground/example.st
# Run a Structured Text program for 10 scan cycles
cargo run -p st-cli -- run playground/example.st -n 10
# Start the LSP server manually (for debugging)
cargo run -p st-cli -- serve
# Format all code
cargo fmt --all
# Run clippy lints
cargo clippy --workspace
# Build in release mode
cargo build --workspace --release
IDE Support
- CLion / RustRover – Open the workspace
Cargo.toml. The IDE will index all 10 crates automatically. - VSCode with rust-analyzer – Same; open the root folder. The devcontainer pre-configures this.
- The workspace uses
resolver = "3"(Rust 2024 edition) so all crates share a single dependency graph.