Skip to content

fix(fpc): complete opt-in function references - #632

Draft
edsontmarques wants to merge 1 commit into
HashLoad:masterfrom
edsontmarques:fix/fpc-function-reference-callbacks
Draft

edsontmarques wants to merge 1 commit into
HashLoad:masterfrom
edsontmarques:fix/fpc-function-reference-callbacks

Conversation

@edsontmarques

Copy link
Copy Markdown

Problem and change

With HORSE_FPC_FUNCTIONREFERENCES enabled, a callback capturing a local variable does not compile against base a0ac019be1d29fd9deb20f61ca779d5631718bdb: the FPC callback declaration still selects the procedural record. This patch completes the existing opt-in path so managed callbacks can be registered and invoked consistently through Tree, Radix, middleware and lifecycle hooks.

Horse has been useful in our projects. I would like to contribute this focused fix back and reduce the need to maintain a separate compatibility patch. I am opening it as a draft because I can provide the FPC results below, but cannot yet validate the full compiler and platform matrix.

The patch keeps procedural callbacks as the default. With the define enabled, it selects function-reference types, enables the required switches in the affected units, and uses typed managed callbacks for internal router continuations. TNextProc shares the identity of TProc in that mode. Older FPC versions receive an explicit diagnostic if the define is enabled. Applications must rebuild all units when switching modes.

Exception handling keeps the upstream propagation contract: middleware wrapping Next can still handle an exception before the existing outer fallback. The change adds no exception-catching fallback to NextCaller and no new global or thread-local state. Callback continuations remain synchronous; retaining Next beyond the request is outside this proposal.

Validation performed

All runs below target Linux x86_64. The trunk compiler identifies itself as 3.3.1-21317-g572d9b3138-unpushed (build 2026-10-15); these results apply to that revision.

Compiler / mode Result
FPC 3.3.1, opt-in function references 285 closure checks; 34/34 exception expectations
FPC 3.3.1, default procedural mode 34/34 exception expectations; 63 header-hash checks; URL decoding and router lifetime pass
FPC 3.2.2, default procedural mode Same legacy suites pass
FPC 3.2.2, define enabled Expected explicit compiler rejection verified
Original sources at the base above, new closure suite Expected compilation failure verified

The new suite covers Tree and Radix, captured strings/interfaces after the callback factory returns, release of captured interfaces, middleware before/after Next, request lifecycle hooks, abbreviated callbacks (including more than 64 registrations), separate instances, 404/405 finalizers and resuming Next after nested dispatch. Test executions reported no unfreed heap blocks. The existing exception suite retains its 34 expectations.

Reproduce from the repository root with Python 3, FPC and matching RTL/FCL units:

python3 tests/fpc-functionreferences/run.py --mode all

On FPC 3.2.2:

python3 tests/fpc-functionreferences/run.py --mode legacy

The runner supports --compiler, repeated --compiler-arg and --source-root for an isolated toolchain or a negative control. It rebuilds into separate temporary output directories for each test and mode. Instructions and compiler-support documentation are provided in English and Portuguese.

Validation still needed

I have not run Delphi, FPC 3.2.0, other platforms, HTTP-provider integration, broad concurrent traffic, or the full boss test suite. The Delphi branches have been inspected, but inspection does not establish compiler compatibility. The direct router tests above do not establish transport integration or concurrency safety.

I would appreciate help validating the shared units on Delphi and FPC 3.2.0, and running the full upstream test/CI matrix before considering this ready to merge. This draft does not claim that those compatibility requirements have been met.

Keep managed callback declarations and router invocations consistent
when HORSE_FPC_FUNCTIONREFERENCES is enabled, preserving procedural
callbacks by default and upstream exception propagation.

Add closure lifetime and routing regressions with bilingual guidance.
Validated on FPC 3.3.1 and legacy 3.2.2; Delphi and the full upstream
test matrix remain unverified.

Co-Authored-By: Codex GPT-6 <noreply@openai.com>

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants