perf(rete): convert UWC Site #5 + document Sites #1+#2 blocker Site #5 (FlowNode no sub_nodes yet) converted from imperative 100-reschedule loop to cancel+final_pass with per-factory cancel-count tracking. First can_run_now returns cancel; final_pass dispatcher rehabs and re-invokes; second can_run_now returns ready so UWC.run() executes against settled state. Has_child trigger handles the success case (sub_node materialized by LTAN). Orchestrator-side enablement: _execute_one and _cancel_worker add canceled pairs to _final_pass_pending when the GFM opts into final_pass. Inert for GFMs that don't opt in. Sites #1+#2 remain imperative. Root cause documented at c2027e5a7: LocationGFM unconditionally writes wrapper-flow.amount from self.node.production_amount, overwriting the 50g inherited from DuplicateNodeMutation. Imperative path: UWC hasn't committed yet, overwrite skipped, 50g preserved. Conversion path: UWC commits 228g early, LocationGFM overwrites 50g→228g, wrapper FPA derives wrong value. Targeted fix recovers the FPA write but a downstream chain of TransportDecision/TransportModeDistance ordering assumptions keeps CO2 drifting +0.6%. Full fix requires architectural change: move FPA-boundary aggregation into a peer GFM consuming gfm_completed facts. Validation: - two_origins CO2=1.2568 invariant holds. - test_calculation_with_subrecipe CO2=0.0930 invariant holds. - test_orchestration_with_food_product_flow_and_declaration: data error 'No matching unit term found' still emitted. - 87/87 in core orchestrator + benchmark + GFM + isolation tests. - 41/44 legacy_recipe_router (3 pre-existing batch flakes only). See docs/uwc-fpa-boundary-conversion-design.md.