Skip to main content

seqc/codegen/
runtime.rs

1//! Runtime function declarations for LLVM IR.
2//!
3//! All runtime functions are declared here in a single data-driven table.
4//! This eliminates ~500 lines of duplicate writeln! calls and ensures
5//! consistency between the FFI and non-FFI code paths.
6
7use super::error::CodeGenError;
8use std::collections::HashMap;
9use std::fmt::Write as _;
10use std::sync::LazyLock;
11
12/// A runtime function declaration for LLVM IR.
13pub struct RuntimeDecl {
14    /// LLVM declaration string (e.g., "declare ptr @patch_seq_add(ptr)")
15    pub decl: &'static str,
16    /// Optional category comment (e.g., "; Stack operations")
17    pub category: Option<&'static str>,
18}
19
20/// All runtime function declarations, organized by category.
21/// Each entry generates a single `declare` statement in the LLVM IR.
22pub static RUNTIME_DECLARATIONS: LazyLock<Vec<RuntimeDecl>> = LazyLock::new(|| {
23    vec![
24        // Core push operations
25        RuntimeDecl {
26            decl: "declare ptr @patch_seq_push_int(ptr, i64)",
27            category: Some("; Runtime function declarations"),
28        },
29        RuntimeDecl {
30            decl: "declare ptr @patch_seq_push_string(ptr, ptr)",
31            category: None,
32        },
33        RuntimeDecl {
34            decl: "declare ptr @patch_seq_push_symbol(ptr, ptr)",
35            category: None,
36        },
37        RuntimeDecl {
38            decl: "declare ptr @patch_seq_push_interned_symbol(ptr, ptr)",
39            category: None,
40        },
41        // I/O operations
42        RuntimeDecl {
43            decl: "declare ptr @patch_seq_write(ptr)",
44            category: None,
45        },
46        RuntimeDecl {
47            decl: "declare ptr @patch_seq_write_line(ptr)",
48            category: None,
49        },
50        RuntimeDecl {
51            decl: "declare ptr @patch_seq_read_line(ptr)",
52            category: None,
53        },
54        RuntimeDecl {
55            decl: "declare ptr @patch_seq_read_line_plus(ptr)",
56            category: None,
57        },
58        RuntimeDecl {
59            decl: "declare ptr @patch_seq_read_n(ptr)",
60            category: None,
61        },
62        // Type conversions
63        RuntimeDecl {
64            decl: "declare ptr @patch_seq_int_to_string(ptr)",
65            category: None,
66        },
67        RuntimeDecl {
68            decl: "declare ptr @patch_seq_symbol_to_string(ptr)",
69            category: None,
70        },
71        RuntimeDecl {
72            decl: "declare ptr @patch_seq_string_to_symbol(ptr)",
73            category: None,
74        },
75        // Integer arithmetic
76        RuntimeDecl {
77            decl: "declare ptr @patch_seq_add(ptr)",
78            category: None,
79        },
80        RuntimeDecl {
81            decl: "declare ptr @patch_seq_subtract(ptr)",
82            category: None,
83        },
84        RuntimeDecl {
85            decl: "declare ptr @patch_seq_multiply(ptr)",
86            category: None,
87        },
88        RuntimeDecl {
89            decl: "declare ptr @patch_seq_divide(ptr)",
90            category: None,
91        },
92        RuntimeDecl {
93            decl: "declare ptr @patch_seq_modulo(ptr)",
94            category: None,
95        },
96        // Integer comparisons
97        RuntimeDecl {
98            decl: "declare ptr @patch_seq_eq(ptr)",
99            category: None,
100        },
101        RuntimeDecl {
102            decl: "declare ptr @patch_seq_lt(ptr)",
103            category: None,
104        },
105        RuntimeDecl {
106            decl: "declare ptr @patch_seq_gt(ptr)",
107            category: None,
108        },
109        RuntimeDecl {
110            decl: "declare ptr @patch_seq_lte(ptr)",
111            category: None,
112        },
113        RuntimeDecl {
114            decl: "declare ptr @patch_seq_gte(ptr)",
115            category: None,
116        },
117        RuntimeDecl {
118            decl: "declare ptr @patch_seq_neq(ptr)",
119            category: None,
120        },
121        // Boolean operations
122        RuntimeDecl {
123            decl: "declare ptr @patch_seq_and(ptr)",
124            category: Some("; Boolean operations"),
125        },
126        RuntimeDecl {
127            decl: "declare ptr @patch_seq_or(ptr)",
128            category: None,
129        },
130        RuntimeDecl {
131            decl: "declare ptr @patch_seq_not(ptr)",
132            category: None,
133        },
134        // Bitwise operations
135        RuntimeDecl {
136            decl: "declare ptr @patch_seq_band(ptr)",
137            category: Some("; Bitwise operations"),
138        },
139        RuntimeDecl {
140            decl: "declare ptr @patch_seq_bor(ptr)",
141            category: None,
142        },
143        RuntimeDecl {
144            decl: "declare ptr @patch_seq_bxor(ptr)",
145            category: None,
146        },
147        RuntimeDecl {
148            decl: "declare ptr @patch_seq_bnot(ptr)",
149            category: None,
150        },
151        RuntimeDecl {
152            decl: "declare ptr @patch_seq_shl(ptr)",
153            category: None,
154        },
155        RuntimeDecl {
156            decl: "declare ptr @patch_seq_shr(ptr)",
157            category: None,
158        },
159        RuntimeDecl {
160            decl: "declare ptr @patch_seq_popcount(ptr)",
161            category: None,
162        },
163        RuntimeDecl {
164            decl: "declare ptr @patch_seq_clz(ptr)",
165            category: None,
166        },
167        RuntimeDecl {
168            decl: "declare ptr @patch_seq_ctz(ptr)",
169            category: None,
170        },
171        RuntimeDecl {
172            decl: "declare ptr @patch_seq_int_bits(ptr)",
173            category: None,
174        },
175        // LLVM intrinsics
176        RuntimeDecl {
177            decl: "declare i64 @llvm.ctpop.i64(i64)",
178            category: None,
179        },
180        RuntimeDecl {
181            decl: "declare i64 @llvm.ctlz.i64(i64, i1)",
182            category: None,
183        },
184        RuntimeDecl {
185            decl: "declare i64 @llvm.cttz.i64(i64, i1)",
186            category: None,
187        },
188        RuntimeDecl {
189            decl: "declare void @llvm.memmove.p0.p0.i64(ptr, ptr, i64, i1)",
190            category: None,
191        },
192        RuntimeDecl {
193            decl: "declare void @llvm.trap() noreturn nounwind",
194            category: None,
195        },
196        // Stack operations
197        RuntimeDecl {
198            decl: "declare ptr @patch_seq_dup(ptr)",
199            category: Some("; Stack operations"),
200        },
201        RuntimeDecl {
202            decl: "declare ptr @patch_seq_drop_op(ptr)",
203            category: None,
204        },
205        RuntimeDecl {
206            decl: "declare ptr @patch_seq_swap(ptr)",
207            category: None,
208        },
209        RuntimeDecl {
210            decl: "declare ptr @patch_seq_over(ptr)",
211            category: None,
212        },
213        RuntimeDecl {
214            decl: "declare ptr @patch_seq_rot(ptr)",
215            category: None,
216        },
217        RuntimeDecl {
218            decl: "declare ptr @patch_seq_nip(ptr)",
219            category: None,
220        },
221        RuntimeDecl {
222            decl: "declare void @patch_seq_clone_value(ptr, ptr)",
223            category: None,
224        },
225        RuntimeDecl {
226            decl: "declare ptr @patch_seq_tuck(ptr)",
227            category: None,
228        },
229        RuntimeDecl {
230            decl: "declare ptr @patch_seq_2dup(ptr)",
231            category: None,
232        },
233        RuntimeDecl {
234            decl: "declare ptr @patch_seq_pick_op(ptr)",
235            category: None,
236        },
237        RuntimeDecl {
238            decl: "declare ptr @patch_seq_roll(ptr)",
239            category: None,
240        },
241        RuntimeDecl {
242            decl: "declare ptr @patch_seq_push_value(ptr, %Value)",
243            category: None,
244        },
245        // Quotation operations
246        RuntimeDecl {
247            decl: "declare ptr @patch_seq_push_quotation(ptr, i64, i64)",
248            category: Some("; Quotation operations"),
249        },
250        RuntimeDecl {
251            decl: "declare ptr @patch_seq_call(ptr)",
252            category: None,
253        },
254        RuntimeDecl {
255            decl: "declare ptr @patch_seq_dip(ptr)",
256            category: Some("; Dataflow combinators"),
257        },
258        RuntimeDecl {
259            decl: "declare ptr @patch_seq_keep(ptr)",
260            category: None,
261        },
262        RuntimeDecl {
263            decl: "declare ptr @patch_seq_bi(ptr)",
264            category: None,
265        },
266        RuntimeDecl {
267            decl: "declare i64 @patch_seq_peek_is_quotation(ptr)",
268            category: None,
269        },
270        RuntimeDecl {
271            decl: "declare i64 @patch_seq_peek_quotation_fn_ptr(ptr)",
272            category: None,
273        },
274        RuntimeDecl {
275            decl: "declare ptr @patch_seq_spawn(ptr)",
276            category: None,
277        },
278        RuntimeDecl {
279            decl: "declare ptr @patch_seq_weave(ptr)",
280            category: None,
281        },
282        RuntimeDecl {
283            decl: "declare ptr @patch_seq_resume(ptr)",
284            category: None,
285        },
286        RuntimeDecl {
287            decl: "declare ptr @patch_seq_weave_cancel(ptr)",
288            category: None,
289        },
290        RuntimeDecl {
291            decl: "declare ptr @patch_seq_yield(ptr)",
292            category: None,
293        },
294        RuntimeDecl {
295            decl: "declare ptr @patch_seq_cond(ptr)",
296            category: None,
297        },
298        // Closure operations
299        RuntimeDecl {
300            decl: "declare ptr @patch_seq_create_env(i32)",
301            category: Some("; Closure operations"),
302        },
303        RuntimeDecl {
304            decl: "declare void @patch_seq_env_set(ptr, i32, %Value)",
305            category: None,
306        },
307        RuntimeDecl {
308            decl: "declare %Value @patch_seq_env_get(ptr, i64, i32)",
309            category: None,
310        },
311        RuntimeDecl {
312            decl: "declare i64 @patch_seq_env_get_int(ptr, i64, i32)",
313            category: None,
314        },
315        RuntimeDecl {
316            decl: "declare i64 @patch_seq_env_get_bool(ptr, i64, i32)",
317            category: None,
318        },
319        RuntimeDecl {
320            decl: "declare double @patch_seq_env_get_float(ptr, i64, i32)",
321            category: None,
322        },
323        RuntimeDecl {
324            decl: "declare i64 @patch_seq_env_get_quotation(ptr, i64, i32)",
325            category: None,
326        },
327        RuntimeDecl {
328            decl: "declare ptr @patch_seq_env_get_string(ptr, i64, i32)",
329            category: None,
330        },
331        RuntimeDecl {
332            decl: "declare ptr @patch_seq_env_push_string(ptr, ptr, i64, i32)",
333            category: None,
334        },
335        RuntimeDecl {
336            decl: "declare %Value @patch_seq_make_closure(i64, ptr)",
337            category: None,
338        },
339        RuntimeDecl {
340            decl: "declare ptr @patch_seq_push_closure(ptr, i64, i32)",
341            category: None,
342        },
343        RuntimeDecl {
344            decl: "declare ptr @patch_seq_push_seqstring(ptr, ptr)",
345            category: None,
346        },
347        // Concurrency operations
348        RuntimeDecl {
349            decl: "declare ptr @patch_seq_make_channel(ptr)",
350            category: Some("; Concurrency operations"),
351        },
352        RuntimeDecl {
353            decl: "declare ptr @patch_seq_chan_send(ptr)",
354            category: None,
355        },
356        RuntimeDecl {
357            decl: "declare ptr @patch_seq_chan_receive(ptr)",
358            category: None,
359        },
360        RuntimeDecl {
361            decl: "declare ptr @patch_seq_close_channel(ptr)",
362            category: None,
363        },
364        RuntimeDecl {
365            decl: "declare ptr @patch_seq_yield_strand(ptr)",
366            category: None,
367        },
368        RuntimeDecl {
369            decl: "declare void @patch_seq_maybe_yield()",
370            category: None,
371        },
372        // Scheduler operations
373        RuntimeDecl {
374            decl: "declare void @patch_seq_scheduler_init()",
375            category: Some("; Scheduler operations"),
376        },
377        RuntimeDecl {
378            decl: "declare ptr @patch_seq_scheduler_run()",
379            category: None,
380        },
381        RuntimeDecl {
382            decl: "declare i64 @patch_seq_strand_spawn(ptr, ptr)",
383            category: None,
384        },
385        // Exit code handling
386        RuntimeDecl {
387            decl: "declare void @patch_seq_set_exit_code(i64)",
388            category: Some("; Exit code handling"),
389        },
390        RuntimeDecl {
391            decl: "declare i64 @patch_seq_get_exit_code()",
392            category: None,
393        },
394        // Command-line argument operations
395        RuntimeDecl {
396            decl: "declare void @patch_seq_args_init(i32, ptr)",
397            category: Some("; Command-line argument operations"),
398        },
399        RuntimeDecl {
400            decl: "declare ptr @patch_seq_arg_count(ptr)",
401            category: None,
402        },
403        RuntimeDecl {
404            decl: "declare ptr @patch_seq_arg_at(ptr)",
405            category: None,
406        },
407        // File operations
408        RuntimeDecl {
409            decl: "declare ptr @patch_seq_file_slurp(ptr)",
410            category: Some("; File operations"),
411        },
412        RuntimeDecl {
413            decl: "declare ptr @patch_seq_file_exists(ptr)",
414            category: None,
415        },
416        RuntimeDecl {
417            decl: "declare ptr @patch_seq_file_for_each_line_plus(ptr)",
418            category: None,
419        },
420        RuntimeDecl {
421            decl: "declare ptr @patch_seq_file_spit(ptr)",
422            category: None,
423        },
424        RuntimeDecl {
425            decl: "declare ptr @patch_seq_file_append(ptr)",
426            category: None,
427        },
428        RuntimeDecl {
429            decl: "declare ptr @patch_seq_file_delete(ptr)",
430            category: None,
431        },
432        RuntimeDecl {
433            decl: "declare ptr @patch_seq_file_size(ptr)",
434            category: None,
435        },
436        // Directory operations
437        RuntimeDecl {
438            decl: "declare ptr @patch_seq_dir_exists(ptr)",
439            category: Some("; Directory operations"),
440        },
441        RuntimeDecl {
442            decl: "declare ptr @patch_seq_dir_make(ptr)",
443            category: None,
444        },
445        RuntimeDecl {
446            decl: "declare ptr @patch_seq_dir_delete(ptr)",
447            category: None,
448        },
449        RuntimeDecl {
450            decl: "declare ptr @patch_seq_dir_list(ptr)",
451            category: None,
452        },
453        // List operations
454        RuntimeDecl {
455            decl: "declare ptr @patch_seq_list_make(ptr)",
456            category: Some("; List operations"),
457        },
458        RuntimeDecl {
459            decl: "declare ptr @patch_seq_list_push(ptr)",
460            category: None,
461        },
462        RuntimeDecl {
463            decl: "declare ptr @patch_seq_list_get(ptr)",
464            category: None,
465        },
466        RuntimeDecl {
467            decl: "declare ptr @patch_seq_list_set(ptr)",
468            category: None,
469        },
470        RuntimeDecl {
471            decl: "declare ptr @patch_seq_list_map(ptr)",
472            category: None,
473        },
474        RuntimeDecl {
475            decl: "declare ptr @patch_seq_list_filter(ptr)",
476            category: None,
477        },
478        RuntimeDecl {
479            decl: "declare ptr @patch_seq_list_fold(ptr)",
480            category: None,
481        },
482        RuntimeDecl {
483            decl: "declare ptr @patch_seq_list_each(ptr)",
484            category: None,
485        },
486        RuntimeDecl {
487            decl: "declare ptr @patch_seq_list_length(ptr)",
488            category: None,
489        },
490        RuntimeDecl {
491            decl: "declare ptr @patch_seq_list_empty(ptr)",
492            category: None,
493        },
494        RuntimeDecl {
495            decl: "declare ptr @patch_seq_list_reverse(ptr)",
496            category: None,
497        },
498        // Map operations
499        RuntimeDecl {
500            decl: "declare ptr @patch_seq_make_map(ptr)",
501            category: Some("; Map operations"),
502        },
503        RuntimeDecl {
504            decl: "declare ptr @patch_seq_map_get(ptr)",
505            category: None,
506        },
507        RuntimeDecl {
508            decl: "declare ptr @patch_seq_map_set(ptr)",
509            category: None,
510        },
511        RuntimeDecl {
512            decl: "declare ptr @patch_seq_map_has(ptr)",
513            category: None,
514        },
515        RuntimeDecl {
516            decl: "declare ptr @patch_seq_map_remove(ptr)",
517            category: None,
518        },
519        RuntimeDecl {
520            decl: "declare ptr @patch_seq_map_keys(ptr)",
521            category: None,
522        },
523        RuntimeDecl {
524            decl: "declare ptr @patch_seq_map_values(ptr)",
525            category: None,
526        },
527        RuntimeDecl {
528            decl: "declare ptr @patch_seq_map_size(ptr)",
529            category: None,
530        },
531        RuntimeDecl {
532            decl: "declare ptr @patch_seq_map_empty(ptr)",
533            category: None,
534        },
535        RuntimeDecl {
536            decl: "declare ptr @patch_seq_map_each(ptr)",
537            category: None,
538        },
539        RuntimeDecl {
540            decl: "declare ptr @patch_seq_map_fold(ptr)",
541            category: None,
542        },
543        // TCP operations
544        RuntimeDecl {
545            decl: "declare ptr @patch_seq_tcp_listen(ptr)",
546            category: Some("; TCP operations"),
547        },
548        RuntimeDecl {
549            decl: "declare ptr @patch_seq_tcp_accept(ptr)",
550            category: None,
551        },
552        RuntimeDecl {
553            decl: "declare ptr @patch_seq_tcp_read(ptr)",
554            category: None,
555        },
556        RuntimeDecl {
557            decl: "declare ptr @patch_seq_tcp_write(ptr)",
558            category: None,
559        },
560        RuntimeDecl {
561            decl: "declare ptr @patch_seq_tcp_close(ptr)",
562            category: None,
563        },
564        // OS operations
565        RuntimeDecl {
566            decl: "declare ptr @patch_seq_getenv(ptr)",
567            category: Some("; OS operations"),
568        },
569        RuntimeDecl {
570            decl: "declare ptr @patch_seq_home_dir(ptr)",
571            category: None,
572        },
573        RuntimeDecl {
574            decl: "declare ptr @patch_seq_current_dir(ptr)",
575            category: None,
576        },
577        RuntimeDecl {
578            decl: "declare ptr @patch_seq_path_exists(ptr)",
579            category: None,
580        },
581        RuntimeDecl {
582            decl: "declare ptr @patch_seq_path_is_file(ptr)",
583            category: None,
584        },
585        RuntimeDecl {
586            decl: "declare ptr @patch_seq_path_is_dir(ptr)",
587            category: None,
588        },
589        RuntimeDecl {
590            decl: "declare ptr @patch_seq_path_join(ptr)",
591            category: None,
592        },
593        RuntimeDecl {
594            decl: "declare ptr @patch_seq_path_parent(ptr)",
595            category: None,
596        },
597        RuntimeDecl {
598            decl: "declare ptr @patch_seq_path_filename(ptr)",
599            category: None,
600        },
601        RuntimeDecl {
602            decl: "declare ptr @patch_seq_exit(ptr)",
603            category: None,
604        },
605        RuntimeDecl {
606            decl: "declare ptr @patch_seq_os_name(ptr)",
607            category: None,
608        },
609        RuntimeDecl {
610            decl: "declare ptr @patch_seq_os_arch(ptr)",
611            category: None,
612        },
613        // Signal handling
614        RuntimeDecl {
615            decl: "declare ptr @patch_seq_signal_trap(ptr)",
616            category: Some("; Signal handling"),
617        },
618        RuntimeDecl {
619            decl: "declare ptr @patch_seq_signal_received(ptr)",
620            category: None,
621        },
622        RuntimeDecl {
623            decl: "declare ptr @patch_seq_signal_pending(ptr)",
624            category: None,
625        },
626        RuntimeDecl {
627            decl: "declare ptr @patch_seq_signal_default(ptr)",
628            category: None,
629        },
630        RuntimeDecl {
631            decl: "declare ptr @patch_seq_signal_ignore(ptr)",
632            category: None,
633        },
634        RuntimeDecl {
635            decl: "declare ptr @patch_seq_signal_clear(ptr)",
636            category: None,
637        },
638        RuntimeDecl {
639            decl: "declare ptr @patch_seq_signal_sigint(ptr)",
640            category: None,
641        },
642        RuntimeDecl {
643            decl: "declare ptr @patch_seq_signal_sigterm(ptr)",
644            category: None,
645        },
646        RuntimeDecl {
647            decl: "declare ptr @patch_seq_signal_sighup(ptr)",
648            category: None,
649        },
650        RuntimeDecl {
651            decl: "declare ptr @patch_seq_signal_sigpipe(ptr)",
652            category: None,
653        },
654        RuntimeDecl {
655            decl: "declare ptr @patch_seq_signal_sigusr1(ptr)",
656            category: None,
657        },
658        RuntimeDecl {
659            decl: "declare ptr @patch_seq_signal_sigusr2(ptr)",
660            category: None,
661        },
662        RuntimeDecl {
663            decl: "declare ptr @patch_seq_signal_sigchld(ptr)",
664            category: None,
665        },
666        RuntimeDecl {
667            decl: "declare ptr @patch_seq_signal_sigalrm(ptr)",
668            category: None,
669        },
670        RuntimeDecl {
671            decl: "declare ptr @patch_seq_signal_sigcont(ptr)",
672            category: None,
673        },
674        // Terminal operations
675        RuntimeDecl {
676            decl: "declare ptr @patch_seq_terminal_raw_mode(ptr)",
677            category: Some("; Terminal operations"),
678        },
679        RuntimeDecl {
680            decl: "declare ptr @patch_seq_terminal_read_char(ptr)",
681            category: None,
682        },
683        RuntimeDecl {
684            decl: "declare ptr @patch_seq_terminal_read_char_nonblock(ptr)",
685            category: None,
686        },
687        RuntimeDecl {
688            decl: "declare ptr @patch_seq_terminal_width(ptr)",
689            category: None,
690        },
691        RuntimeDecl {
692            decl: "declare ptr @patch_seq_terminal_height(ptr)",
693            category: None,
694        },
695        RuntimeDecl {
696            decl: "declare ptr @patch_seq_terminal_flush(ptr)",
697            category: None,
698        },
699        // String operations
700        RuntimeDecl {
701            decl: "declare ptr @patch_seq_string_concat(ptr)",
702            category: Some("; String operations"),
703        },
704        RuntimeDecl {
705            decl: "declare ptr @patch_seq_string_length(ptr)",
706            category: None,
707        },
708        RuntimeDecl {
709            decl: "declare ptr @patch_seq_string_byte_length(ptr)",
710            category: None,
711        },
712        RuntimeDecl {
713            decl: "declare ptr @patch_seq_string_char_at(ptr)",
714            category: None,
715        },
716        RuntimeDecl {
717            decl: "declare ptr @patch_seq_string_substring(ptr)",
718            category: None,
719        },
720        RuntimeDecl {
721            decl: "declare ptr @patch_seq_char_to_string(ptr)",
722            category: None,
723        },
724        RuntimeDecl {
725            decl: "declare ptr @patch_seq_string_find(ptr)",
726            category: None,
727        },
728        RuntimeDecl {
729            decl: "declare ptr @patch_seq_string_split(ptr)",
730            category: None,
731        },
732        RuntimeDecl {
733            decl: "declare ptr @patch_seq_string_contains(ptr)",
734            category: None,
735        },
736        RuntimeDecl {
737            decl: "declare ptr @patch_seq_string_starts_with(ptr)",
738            category: None,
739        },
740        RuntimeDecl {
741            decl: "declare ptr @patch_seq_string_empty(ptr)",
742            category: None,
743        },
744        RuntimeDecl {
745            decl: "declare ptr @patch_seq_string_trim(ptr)",
746            category: None,
747        },
748        RuntimeDecl {
749            decl: "declare ptr @patch_seq_string_chomp(ptr)",
750            category: None,
751        },
752        RuntimeDecl {
753            decl: "declare ptr @patch_seq_string_to_upper(ptr)",
754            category: None,
755        },
756        RuntimeDecl {
757            decl: "declare ptr @patch_seq_string_to_lower(ptr)",
758            category: None,
759        },
760        RuntimeDecl {
761            decl: "declare ptr @patch_seq_string_equal(ptr)",
762            category: None,
763        },
764        RuntimeDecl {
765            decl: "declare ptr @patch_seq_string_join(ptr)",
766            category: None,
767        },
768        RuntimeDecl {
769            decl: "declare ptr @patch_seq_json_escape(ptr)",
770            category: None,
771        },
772        RuntimeDecl {
773            decl: "declare ptr @patch_seq_string_to_int(ptr)",
774            category: None,
775        },
776        // Encoding operations
777        RuntimeDecl {
778            decl: "declare ptr @patch_seq_base64_encode(ptr)",
779            category: Some("; Encoding operations"),
780        },
781        RuntimeDecl {
782            decl: "declare ptr @patch_seq_base64_decode(ptr)",
783            category: None,
784        },
785        RuntimeDecl {
786            decl: "declare ptr @patch_seq_base64url_encode(ptr)",
787            category: None,
788        },
789        RuntimeDecl {
790            decl: "declare ptr @patch_seq_base64url_decode(ptr)",
791            category: None,
792        },
793        RuntimeDecl {
794            decl: "declare ptr @patch_seq_hex_encode(ptr)",
795            category: None,
796        },
797        RuntimeDecl {
798            decl: "declare ptr @patch_seq_hex_decode(ptr)",
799            category: None,
800        },
801        // Crypto operations
802        RuntimeDecl {
803            decl: "declare ptr @patch_seq_sha256(ptr)",
804            category: Some("; Crypto operations"),
805        },
806        RuntimeDecl {
807            decl: "declare ptr @patch_seq_hmac_sha256(ptr)",
808            category: None,
809        },
810        RuntimeDecl {
811            decl: "declare ptr @patch_seq_constant_time_eq(ptr)",
812            category: None,
813        },
814        RuntimeDecl {
815            decl: "declare ptr @patch_seq_random_bytes(ptr)",
816            category: None,
817        },
818        RuntimeDecl {
819            decl: "declare ptr @patch_seq_random_int(ptr)",
820            category: None,
821        },
822        RuntimeDecl {
823            decl: "declare ptr @patch_seq_uuid4(ptr)",
824            category: None,
825        },
826        RuntimeDecl {
827            decl: "declare ptr @patch_seq_crypto_aes_gcm_encrypt(ptr)",
828            category: None,
829        },
830        RuntimeDecl {
831            decl: "declare ptr @patch_seq_crypto_aes_gcm_decrypt(ptr)",
832            category: None,
833        },
834        RuntimeDecl {
835            decl: "declare ptr @patch_seq_crypto_pbkdf2_sha256(ptr)",
836            category: None,
837        },
838        RuntimeDecl {
839            decl: "declare ptr @patch_seq_crypto_ed25519_keypair(ptr)",
840            category: None,
841        },
842        RuntimeDecl {
843            decl: "declare ptr @patch_seq_crypto_ed25519_sign(ptr)",
844            category: None,
845        },
846        RuntimeDecl {
847            decl: "declare ptr @patch_seq_crypto_ed25519_verify(ptr)",
848            category: None,
849        },
850        // HTTP client operations
851        RuntimeDecl {
852            decl: "declare ptr @patch_seq_http_get(ptr)",
853            category: Some("; HTTP client operations"),
854        },
855        RuntimeDecl {
856            decl: "declare ptr @patch_seq_http_post(ptr)",
857            category: None,
858        },
859        RuntimeDecl {
860            decl: "declare ptr @patch_seq_http_put(ptr)",
861            category: None,
862        },
863        RuntimeDecl {
864            decl: "declare ptr @patch_seq_http_delete(ptr)",
865            category: None,
866        },
867        // Symbol operations
868        RuntimeDecl {
869            decl: "declare ptr @patch_seq_symbol_equal(ptr)",
870            category: Some("; Symbol operations"),
871        },
872        // Variant operations
873        RuntimeDecl {
874            decl: "declare ptr @patch_seq_variant_field_count(ptr)",
875            category: Some("; Variant operations"),
876        },
877        RuntimeDecl {
878            decl: "declare ptr @patch_seq_variant_tag(ptr)",
879            category: None,
880        },
881        RuntimeDecl {
882            decl: "declare ptr @patch_seq_variant_field_at(ptr)",
883            category: None,
884        },
885        RuntimeDecl {
886            decl: "declare ptr @patch_seq_variant_append(ptr)",
887            category: None,
888        },
889        RuntimeDecl {
890            decl: "declare ptr @patch_seq_variant_last(ptr)",
891            category: None,
892        },
893        RuntimeDecl {
894            decl: "declare ptr @patch_seq_variant_init(ptr)",
895            category: None,
896        },
897        RuntimeDecl {
898            decl: "declare ptr @patch_seq_make_variant_0(ptr)",
899            category: None,
900        },
901        RuntimeDecl {
902            decl: "declare ptr @patch_seq_make_variant_1(ptr)",
903            category: None,
904        },
905        RuntimeDecl {
906            decl: "declare ptr @patch_seq_make_variant_2(ptr)",
907            category: None,
908        },
909        RuntimeDecl {
910            decl: "declare ptr @patch_seq_make_variant_3(ptr)",
911            category: None,
912        },
913        RuntimeDecl {
914            decl: "declare ptr @patch_seq_make_variant_4(ptr)",
915            category: None,
916        },
917        RuntimeDecl {
918            decl: "declare ptr @patch_seq_make_variant_5(ptr)",
919            category: None,
920        },
921        RuntimeDecl {
922            decl: "declare ptr @patch_seq_make_variant_6(ptr)",
923            category: None,
924        },
925        RuntimeDecl {
926            decl: "declare ptr @patch_seq_make_variant_7(ptr)",
927            category: None,
928        },
929        RuntimeDecl {
930            decl: "declare ptr @patch_seq_make_variant_8(ptr)",
931            category: None,
932        },
933        RuntimeDecl {
934            decl: "declare ptr @patch_seq_make_variant_9(ptr)",
935            category: None,
936        },
937        RuntimeDecl {
938            decl: "declare ptr @patch_seq_make_variant_10(ptr)",
939            category: None,
940        },
941        RuntimeDecl {
942            decl: "declare ptr @patch_seq_make_variant_11(ptr)",
943            category: None,
944        },
945        RuntimeDecl {
946            decl: "declare ptr @patch_seq_make_variant_12(ptr)",
947            category: None,
948        },
949        RuntimeDecl {
950            decl: "declare ptr @patch_seq_unpack_variant(ptr, i64)",
951            category: None,
952        },
953        RuntimeDecl {
954            decl: "declare ptr @patch_seq_symbol_eq_cstr(ptr, ptr)",
955            category: None,
956        },
957        // Float operations
958        RuntimeDecl {
959            decl: "declare ptr @patch_seq_push_float(ptr, double)",
960            category: Some("; Float operations"),
961        },
962        RuntimeDecl {
963            decl: "declare ptr @patch_seq_f_add(ptr)",
964            category: None,
965        },
966        RuntimeDecl {
967            decl: "declare ptr @patch_seq_f_subtract(ptr)",
968            category: None,
969        },
970        RuntimeDecl {
971            decl: "declare ptr @patch_seq_f_multiply(ptr)",
972            category: None,
973        },
974        RuntimeDecl {
975            decl: "declare ptr @patch_seq_f_divide(ptr)",
976            category: None,
977        },
978        RuntimeDecl {
979            decl: "declare ptr @patch_seq_f_eq(ptr)",
980            category: None,
981        },
982        RuntimeDecl {
983            decl: "declare ptr @patch_seq_f_lt(ptr)",
984            category: None,
985        },
986        RuntimeDecl {
987            decl: "declare ptr @patch_seq_f_gt(ptr)",
988            category: None,
989        },
990        RuntimeDecl {
991            decl: "declare ptr @patch_seq_f_lte(ptr)",
992            category: None,
993        },
994        RuntimeDecl {
995            decl: "declare ptr @patch_seq_f_gte(ptr)",
996            category: None,
997        },
998        RuntimeDecl {
999            decl: "declare ptr @patch_seq_f_neq(ptr)",
1000            category: None,
1001        },
1002        RuntimeDecl {
1003            decl: "declare ptr @patch_seq_int_to_float(ptr)",
1004            category: None,
1005        },
1006        RuntimeDecl {
1007            decl: "declare ptr @patch_seq_float_to_int(ptr)",
1008            category: None,
1009        },
1010        RuntimeDecl {
1011            decl: "declare ptr @patch_seq_float_to_string(ptr)",
1012            category: None,
1013        },
1014        RuntimeDecl {
1015            decl: "declare ptr @patch_seq_string_to_float(ptr)",
1016            category: None,
1017        },
1018        // Test framework operations
1019        RuntimeDecl {
1020            decl: "declare ptr @patch_seq_test_init(ptr)",
1021            category: Some("; Test framework operations"),
1022        },
1023        RuntimeDecl {
1024            decl: "declare ptr @patch_seq_test_finish(ptr)",
1025            category: None,
1026        },
1027        RuntimeDecl {
1028            decl: "declare ptr @patch_seq_test_has_failures(ptr)",
1029            category: None,
1030        },
1031        RuntimeDecl {
1032            decl: "declare ptr @patch_seq_test_assert(ptr)",
1033            category: None,
1034        },
1035        RuntimeDecl {
1036            decl: "declare ptr @patch_seq_test_assert_not(ptr)",
1037            category: None,
1038        },
1039        RuntimeDecl {
1040            decl: "declare ptr @patch_seq_test_assert_eq(ptr)",
1041            category: None,
1042        },
1043        RuntimeDecl {
1044            decl: "declare ptr @patch_seq_test_assert_eq_str(ptr)",
1045            category: None,
1046        },
1047        RuntimeDecl {
1048            decl: "declare ptr @patch_seq_test_fail(ptr)",
1049            category: None,
1050        },
1051        RuntimeDecl {
1052            decl: "declare ptr @patch_seq_test_pass_count(ptr)",
1053            category: None,
1054        },
1055        RuntimeDecl {
1056            decl: "declare ptr @patch_seq_test_fail_count(ptr)",
1057            category: None,
1058        },
1059        // Time operations
1060        RuntimeDecl {
1061            decl: "declare ptr @patch_seq_time_now(ptr)",
1062            category: Some("; Time operations"),
1063        },
1064        RuntimeDecl {
1065            decl: "declare ptr @patch_seq_time_nanos(ptr)",
1066            category: None,
1067        },
1068        RuntimeDecl {
1069            decl: "declare ptr @patch_seq_time_sleep_ms(ptr)",
1070            category: None,
1071        },
1072        // Stack introspection
1073        RuntimeDecl {
1074            decl: "declare ptr @patch_seq_stack_dump(ptr)",
1075            category: Some("; Stack introspection"),
1076        },
1077        // SON serialization
1078        RuntimeDecl {
1079            decl: "declare ptr @patch_seq_son_dump(ptr)",
1080            category: Some("; SON serialization"),
1081        },
1082        RuntimeDecl {
1083            decl: "declare ptr @patch_seq_son_dump_pretty(ptr)",
1084            category: None,
1085        },
1086        // Regex operations
1087        RuntimeDecl {
1088            decl: "declare ptr @patch_seq_regex_match(ptr)",
1089            category: Some("; Regex operations"),
1090        },
1091        RuntimeDecl {
1092            decl: "declare ptr @patch_seq_regex_find(ptr)",
1093            category: None,
1094        },
1095        RuntimeDecl {
1096            decl: "declare ptr @patch_seq_regex_find_all(ptr)",
1097            category: None,
1098        },
1099        RuntimeDecl {
1100            decl: "declare ptr @patch_seq_regex_replace(ptr)",
1101            category: None,
1102        },
1103        RuntimeDecl {
1104            decl: "declare ptr @patch_seq_regex_replace_all(ptr)",
1105            category: None,
1106        },
1107        RuntimeDecl {
1108            decl: "declare ptr @patch_seq_regex_captures(ptr)",
1109            category: None,
1110        },
1111        RuntimeDecl {
1112            decl: "declare ptr @patch_seq_regex_split(ptr)",
1113            category: None,
1114        },
1115        RuntimeDecl {
1116            decl: "declare ptr @patch_seq_regex_valid(ptr)",
1117            category: None,
1118        },
1119        // Compression operations
1120        RuntimeDecl {
1121            decl: "declare ptr @patch_seq_compress_gzip(ptr)",
1122            category: Some("; Compression operations"),
1123        },
1124        RuntimeDecl {
1125            decl: "declare ptr @patch_seq_compress_gzip_level(ptr)",
1126            category: None,
1127        },
1128        RuntimeDecl {
1129            decl: "declare ptr @patch_seq_compress_gunzip(ptr)",
1130            category: None,
1131        },
1132        RuntimeDecl {
1133            decl: "declare ptr @patch_seq_compress_zstd(ptr)",
1134            category: None,
1135        },
1136        RuntimeDecl {
1137            decl: "declare ptr @patch_seq_compress_zstd_level(ptr)",
1138            category: None,
1139        },
1140        RuntimeDecl {
1141            decl: "declare ptr @patch_seq_compress_unzstd(ptr)",
1142            category: None,
1143        },
1144        // Helpers for conditionals
1145        RuntimeDecl {
1146            decl: "declare i64 @patch_seq_peek_int_value(ptr)",
1147            category: Some("; Helpers for conditionals"),
1148        },
1149        RuntimeDecl {
1150            decl: "declare i1 @patch_seq_peek_bool_value(ptr)",
1151            category: None,
1152        },
1153        RuntimeDecl {
1154            decl: "declare ptr @patch_seq_pop_stack(ptr)",
1155            category: None,
1156        },
1157        // Tagged stack operations
1158        RuntimeDecl {
1159            decl: "declare ptr @seq_stack_new_default()",
1160            category: Some("; Tagged stack operations"),
1161        },
1162        RuntimeDecl {
1163            decl: "declare void @seq_stack_free(ptr)",
1164            category: None,
1165        },
1166        RuntimeDecl {
1167            decl: "declare ptr @seq_stack_base(ptr)",
1168            category: None,
1169        },
1170        RuntimeDecl {
1171            decl: "declare i64 @seq_stack_sp(ptr)",
1172            category: None,
1173        },
1174        RuntimeDecl {
1175            decl: "declare void @seq_stack_set_sp(ptr, i64)",
1176            category: None,
1177        },
1178        RuntimeDecl {
1179            decl: "declare void @seq_stack_grow(ptr, i64)",
1180            category: None,
1181        },
1182        RuntimeDecl {
1183            decl: "declare void @patch_seq_set_stack_base(ptr)",
1184            category: None,
1185        },
1186        // Report operations
1187        RuntimeDecl {
1188            decl: "declare void @patch_seq_report()",
1189            category: Some("; Report operations"),
1190        },
1191        RuntimeDecl {
1192            decl: "declare void @patch_seq_report_init(ptr, ptr, i64)",
1193            category: None,
1194        },
1195    ]
1196});
1197
1198/// Mapping from Seq word names to their C runtime symbol names.
1199/// This centralizes all the name transformations in one place:
1200/// - Symbolic operators (=, <, >) map to descriptive names (eq, lt, gt)
1201/// - Hyphens become underscores for C compatibility
1202/// - Special characters get escaped (?, +, ->)
1203/// - Reserved words get suffixes (drop -> drop_op)
1204pub static BUILTIN_SYMBOLS: LazyLock<HashMap<&'static str, &'static str>> = LazyLock::new(|| {
1205    HashMap::from([
1206        // I/O operations
1207        ("io.write", "patch_seq_write"),
1208        ("io.write-line", "patch_seq_write_line"),
1209        ("io.read-line", "patch_seq_read_line"),
1210        ("io.read-line+", "patch_seq_read_line_plus"),
1211        ("io.read-n", "patch_seq_read_n"),
1212        ("int->string", "patch_seq_int_to_string"),
1213        ("symbol->string", "patch_seq_symbol_to_string"),
1214        ("string->symbol", "patch_seq_string_to_symbol"),
1215        // Command-line arguments
1216        ("args.count", "patch_seq_arg_count"),
1217        ("args.at", "patch_seq_arg_at"),
1218        // Integer Arithmetic
1219        ("i.add", "patch_seq_add"),
1220        ("i.subtract", "patch_seq_subtract"),
1221        ("i.multiply", "patch_seq_multiply"),
1222        ("i.divide", "patch_seq_divide"),
1223        ("i.modulo", "patch_seq_modulo"),
1224        // Terse integer arithmetic aliases
1225        ("i.+", "patch_seq_add"),
1226        ("i.-", "patch_seq_subtract"),
1227        ("i.*", "patch_seq_multiply"),
1228        ("i./", "patch_seq_divide"),
1229        ("i.%", "patch_seq_modulo"),
1230        // Integer comparison (symbol form)
1231        ("i.=", "patch_seq_eq"),
1232        ("i.<", "patch_seq_lt"),
1233        ("i.>", "patch_seq_gt"),
1234        ("i.<=", "patch_seq_lte"),
1235        ("i.>=", "patch_seq_gte"),
1236        ("i.<>", "patch_seq_neq"),
1237        // Integer comparison (verbose form)
1238        ("i.eq", "patch_seq_eq"),
1239        ("i.lt", "patch_seq_lt"),
1240        ("i.gt", "patch_seq_gt"),
1241        ("i.lte", "patch_seq_lte"),
1242        ("i.gte", "patch_seq_gte"),
1243        ("i.neq", "patch_seq_neq"),
1244        // Boolean
1245        ("and", "patch_seq_and"),
1246        ("or", "patch_seq_or"),
1247        ("not", "patch_seq_not"),
1248        // Bitwise
1249        ("band", "patch_seq_band"),
1250        ("bor", "patch_seq_bor"),
1251        ("bxor", "patch_seq_bxor"),
1252        ("bnot", "patch_seq_bnot"),
1253        ("shl", "patch_seq_shl"),
1254        ("shr", "patch_seq_shr"),
1255        ("popcount", "patch_seq_popcount"),
1256        ("clz", "patch_seq_clz"),
1257        ("ctz", "patch_seq_ctz"),
1258        ("int-bits", "patch_seq_int_bits"),
1259        // Stack operations
1260        ("dup", "patch_seq_dup"),
1261        ("swap", "patch_seq_swap"),
1262        ("over", "patch_seq_over"),
1263        ("rot", "patch_seq_rot"),
1264        ("nip", "patch_seq_nip"),
1265        ("tuck", "patch_seq_tuck"),
1266        ("2dup", "patch_seq_2dup"),
1267        ("drop", "patch_seq_drop_op"),
1268        ("pick", "patch_seq_pick_op"),
1269        ("roll", "patch_seq_roll"),
1270        // Channel operations (errors are values, not crashes)
1271        ("chan.make", "patch_seq_make_channel"),
1272        ("chan.send", "patch_seq_chan_send"),
1273        ("chan.receive", "patch_seq_chan_receive"),
1274        ("chan.close", "patch_seq_close_channel"),
1275        ("chan.yield", "patch_seq_yield_strand"),
1276        // Quotation operations
1277        ("call", "patch_seq_call"),
1278        // Dataflow combinators
1279        ("dip", "patch_seq_dip"),
1280        ("keep", "patch_seq_keep"),
1281        ("bi", "patch_seq_bi"),
1282        ("strand.spawn", "patch_seq_spawn"),
1283        ("strand.weave", "patch_seq_weave"),
1284        ("strand.resume", "patch_seq_resume"),
1285        ("strand.weave-cancel", "patch_seq_weave_cancel"),
1286        ("yield", "patch_seq_yield"),
1287        ("cond", "patch_seq_cond"),
1288        // TCP operations
1289        ("tcp.listen", "patch_seq_tcp_listen"),
1290        ("tcp.accept", "patch_seq_tcp_accept"),
1291        ("tcp.read", "patch_seq_tcp_read"),
1292        ("tcp.write", "patch_seq_tcp_write"),
1293        ("tcp.close", "patch_seq_tcp_close"),
1294        // OS operations
1295        ("os.getenv", "patch_seq_getenv"),
1296        ("os.home-dir", "patch_seq_home_dir"),
1297        ("os.current-dir", "patch_seq_current_dir"),
1298        ("os.path-exists", "patch_seq_path_exists"),
1299        ("os.path-is-file", "patch_seq_path_is_file"),
1300        ("os.path-is-dir", "patch_seq_path_is_dir"),
1301        ("os.path-join", "patch_seq_path_join"),
1302        ("os.path-parent", "patch_seq_path_parent"),
1303        ("os.path-filename", "patch_seq_path_filename"),
1304        ("os.exit", "patch_seq_exit"),
1305        ("os.name", "patch_seq_os_name"),
1306        ("os.arch", "patch_seq_os_arch"),
1307        // Signal handling
1308        ("signal.trap", "patch_seq_signal_trap"),
1309        ("signal.received?", "patch_seq_signal_received"),
1310        ("signal.pending?", "patch_seq_signal_pending"),
1311        ("signal.default", "patch_seq_signal_default"),
1312        ("signal.ignore", "patch_seq_signal_ignore"),
1313        ("signal.clear", "patch_seq_signal_clear"),
1314        ("signal.SIGINT", "patch_seq_signal_sigint"),
1315        ("signal.SIGTERM", "patch_seq_signal_sigterm"),
1316        ("signal.SIGHUP", "patch_seq_signal_sighup"),
1317        ("signal.SIGPIPE", "patch_seq_signal_sigpipe"),
1318        ("signal.SIGUSR1", "patch_seq_signal_sigusr1"),
1319        ("signal.SIGUSR2", "patch_seq_signal_sigusr2"),
1320        ("signal.SIGCHLD", "patch_seq_signal_sigchld"),
1321        ("signal.SIGALRM", "patch_seq_signal_sigalrm"),
1322        ("signal.SIGCONT", "patch_seq_signal_sigcont"),
1323        // Terminal operations
1324        ("terminal.raw-mode", "patch_seq_terminal_raw_mode"),
1325        ("terminal.read-char", "patch_seq_terminal_read_char"),
1326        (
1327            "terminal.read-char?",
1328            "patch_seq_terminal_read_char_nonblock",
1329        ),
1330        ("terminal.width", "patch_seq_terminal_width"),
1331        ("terminal.height", "patch_seq_terminal_height"),
1332        ("terminal.flush", "patch_seq_terminal_flush"),
1333        // String operations
1334        ("string.concat", "patch_seq_string_concat"),
1335        ("string.length", "patch_seq_string_length"),
1336        ("string.byte-length", "patch_seq_string_byte_length"),
1337        ("string.char-at", "patch_seq_string_char_at"),
1338        ("string.substring", "patch_seq_string_substring"),
1339        ("char->string", "patch_seq_char_to_string"),
1340        ("string.find", "patch_seq_string_find"),
1341        ("string.split", "patch_seq_string_split"),
1342        ("string.contains", "patch_seq_string_contains"),
1343        ("string.starts-with", "patch_seq_string_starts_with"),
1344        ("string.empty?", "patch_seq_string_empty"),
1345        ("string.trim", "patch_seq_string_trim"),
1346        ("string.chomp", "patch_seq_string_chomp"),
1347        ("string.to-upper", "patch_seq_string_to_upper"),
1348        ("string.to-lower", "patch_seq_string_to_lower"),
1349        ("string.equal?", "patch_seq_string_equal"),
1350        ("string.join", "patch_seq_string_join"),
1351        ("string.json-escape", "patch_seq_json_escape"),
1352        ("string->int", "patch_seq_string_to_int"),
1353        // Encoding operations
1354        ("encoding.base64-encode", "patch_seq_base64_encode"),
1355        ("encoding.base64-decode", "patch_seq_base64_decode"),
1356        ("encoding.base64url-encode", "patch_seq_base64url_encode"),
1357        ("encoding.base64url-decode", "patch_seq_base64url_decode"),
1358        ("encoding.hex-encode", "patch_seq_hex_encode"),
1359        ("encoding.hex-decode", "patch_seq_hex_decode"),
1360        // Crypto operations
1361        ("crypto.sha256", "patch_seq_sha256"),
1362        ("crypto.hmac-sha256", "patch_seq_hmac_sha256"),
1363        ("crypto.constant-time-eq", "patch_seq_constant_time_eq"),
1364        ("crypto.random-bytes", "patch_seq_random_bytes"),
1365        ("crypto.random-int", "patch_seq_random_int"),
1366        ("crypto.uuid4", "patch_seq_uuid4"),
1367        ("crypto.aes-gcm-encrypt", "patch_seq_crypto_aes_gcm_encrypt"),
1368        ("crypto.aes-gcm-decrypt", "patch_seq_crypto_aes_gcm_decrypt"),
1369        ("crypto.pbkdf2-sha256", "patch_seq_crypto_pbkdf2_sha256"),
1370        ("crypto.ed25519-keypair", "patch_seq_crypto_ed25519_keypair"),
1371        ("crypto.ed25519-sign", "patch_seq_crypto_ed25519_sign"),
1372        ("crypto.ed25519-verify", "patch_seq_crypto_ed25519_verify"),
1373        // HTTP client operations
1374        ("http.get", "patch_seq_http_get"),
1375        ("http.post", "patch_seq_http_post"),
1376        ("http.put", "patch_seq_http_put"),
1377        ("http.delete", "patch_seq_http_delete"),
1378        // Regex operations
1379        ("regex.match?", "patch_seq_regex_match"),
1380        ("regex.find", "patch_seq_regex_find"),
1381        ("regex.find-all", "patch_seq_regex_find_all"),
1382        ("regex.replace", "patch_seq_regex_replace"),
1383        ("regex.replace-all", "patch_seq_regex_replace_all"),
1384        ("regex.captures", "patch_seq_regex_captures"),
1385        ("regex.split", "patch_seq_regex_split"),
1386        ("regex.valid?", "patch_seq_regex_valid"),
1387        // Compression operations
1388        ("compress.gzip", "patch_seq_compress_gzip"),
1389        ("compress.gzip-level", "patch_seq_compress_gzip_level"),
1390        ("compress.gunzip", "patch_seq_compress_gunzip"),
1391        ("compress.zstd", "patch_seq_compress_zstd"),
1392        ("compress.zstd-level", "patch_seq_compress_zstd_level"),
1393        ("compress.unzstd", "patch_seq_compress_unzstd"),
1394        // Symbol operations
1395        ("symbol.=", "patch_seq_symbol_equal"),
1396        // File operations
1397        ("file.slurp", "patch_seq_file_slurp"),
1398        ("file.exists?", "patch_seq_file_exists"),
1399        ("file.for-each-line+", "patch_seq_file_for_each_line_plus"),
1400        ("file.spit", "patch_seq_file_spit"),
1401        ("file.append", "patch_seq_file_append"),
1402        ("file.delete", "patch_seq_file_delete"),
1403        ("file.size", "patch_seq_file_size"),
1404        // Directory operations
1405        ("dir.exists?", "patch_seq_dir_exists"),
1406        ("dir.make", "patch_seq_dir_make"),
1407        ("dir.delete", "patch_seq_dir_delete"),
1408        ("dir.list", "patch_seq_dir_list"),
1409        // List operations
1410        ("list.make", "patch_seq_list_make"),
1411        ("list.push", "patch_seq_list_push"),
1412        ("list.get", "patch_seq_list_get"),
1413        ("list.set", "patch_seq_list_set"),
1414        ("list.map", "patch_seq_list_map"),
1415        ("list.filter", "patch_seq_list_filter"),
1416        ("list.fold", "patch_seq_list_fold"),
1417        ("list.each", "patch_seq_list_each"),
1418        ("list.length", "patch_seq_list_length"),
1419        ("list.empty?", "patch_seq_list_empty"),
1420        ("list.reverse", "patch_seq_list_reverse"),
1421        // Map operations
1422        ("map.make", "patch_seq_make_map"),
1423        ("map.get", "patch_seq_map_get"),
1424        ("map.set", "patch_seq_map_set"),
1425        ("map.has?", "patch_seq_map_has"),
1426        ("map.remove", "patch_seq_map_remove"),
1427        ("map.keys", "patch_seq_map_keys"),
1428        ("map.values", "patch_seq_map_values"),
1429        ("map.size", "patch_seq_map_size"),
1430        ("map.empty?", "patch_seq_map_empty"),
1431        ("map.each", "patch_seq_map_each"),
1432        ("map.fold", "patch_seq_map_fold"),
1433        // Variant operations
1434        ("variant.field-count", "patch_seq_variant_field_count"),
1435        ("variant.tag", "patch_seq_variant_tag"),
1436        ("variant.field-at", "patch_seq_variant_field_at"),
1437        ("variant.append", "patch_seq_variant_append"),
1438        ("variant.last", "patch_seq_variant_last"),
1439        ("variant.init", "patch_seq_variant_init"),
1440        ("variant.make-0", "patch_seq_make_variant_0"),
1441        ("variant.make-1", "patch_seq_make_variant_1"),
1442        ("variant.make-2", "patch_seq_make_variant_2"),
1443        ("variant.make-3", "patch_seq_make_variant_3"),
1444        ("variant.make-4", "patch_seq_make_variant_4"),
1445        ("variant.make-5", "patch_seq_make_variant_5"),
1446        ("variant.make-6", "patch_seq_make_variant_6"),
1447        ("variant.make-7", "patch_seq_make_variant_7"),
1448        ("variant.make-8", "patch_seq_make_variant_8"),
1449        ("variant.make-9", "patch_seq_make_variant_9"),
1450        ("variant.make-10", "patch_seq_make_variant_10"),
1451        ("variant.make-11", "patch_seq_make_variant_11"),
1452        ("variant.make-12", "patch_seq_make_variant_12"),
1453        // wrap-N aliases for dynamic variant construction (SON)
1454        ("wrap-0", "patch_seq_make_variant_0"),
1455        ("wrap-1", "patch_seq_make_variant_1"),
1456        ("wrap-2", "patch_seq_make_variant_2"),
1457        ("wrap-3", "patch_seq_make_variant_3"),
1458        ("wrap-4", "patch_seq_make_variant_4"),
1459        ("wrap-5", "patch_seq_make_variant_5"),
1460        ("wrap-6", "patch_seq_make_variant_6"),
1461        ("wrap-7", "patch_seq_make_variant_7"),
1462        ("wrap-8", "patch_seq_make_variant_8"),
1463        ("wrap-9", "patch_seq_make_variant_9"),
1464        ("wrap-10", "patch_seq_make_variant_10"),
1465        ("wrap-11", "patch_seq_make_variant_11"),
1466        ("wrap-12", "patch_seq_make_variant_12"),
1467        // Float arithmetic
1468        ("f.add", "patch_seq_f_add"),
1469        ("f.subtract", "patch_seq_f_subtract"),
1470        ("f.multiply", "patch_seq_f_multiply"),
1471        ("f.divide", "patch_seq_f_divide"),
1472        // Terse float arithmetic aliases
1473        ("f.+", "patch_seq_f_add"),
1474        ("f.-", "patch_seq_f_subtract"),
1475        ("f.*", "patch_seq_f_multiply"),
1476        ("f./", "patch_seq_f_divide"),
1477        // Float comparison (symbol form)
1478        ("f.=", "patch_seq_f_eq"),
1479        ("f.<", "patch_seq_f_lt"),
1480        ("f.>", "patch_seq_f_gt"),
1481        ("f.<=", "patch_seq_f_lte"),
1482        ("f.>=", "patch_seq_f_gte"),
1483        ("f.<>", "patch_seq_f_neq"),
1484        // Float comparison (verbose form)
1485        ("f.eq", "patch_seq_f_eq"),
1486        ("f.lt", "patch_seq_f_lt"),
1487        ("f.gt", "patch_seq_f_gt"),
1488        ("f.lte", "patch_seq_f_lte"),
1489        ("f.gte", "patch_seq_f_gte"),
1490        ("f.neq", "patch_seq_f_neq"),
1491        // Float type conversions
1492        ("int->float", "patch_seq_int_to_float"),
1493        ("float->int", "patch_seq_float_to_int"),
1494        ("float->string", "patch_seq_float_to_string"),
1495        ("string->float", "patch_seq_string_to_float"),
1496        // Test framework operations
1497        ("test.init", "patch_seq_test_init"),
1498        ("test.finish", "patch_seq_test_finish"),
1499        ("test.has-failures", "patch_seq_test_has_failures"),
1500        ("test.assert", "patch_seq_test_assert"),
1501        ("test.assert-not", "patch_seq_test_assert_not"),
1502        ("test.assert-eq", "patch_seq_test_assert_eq"),
1503        ("test.assert-eq-str", "patch_seq_test_assert_eq_str"),
1504        ("test.fail", "patch_seq_test_fail"),
1505        ("test.pass-count", "patch_seq_test_pass_count"),
1506        ("test.fail-count", "patch_seq_test_fail_count"),
1507        // Time operations
1508        ("time.now", "patch_seq_time_now"),
1509        ("time.nanos", "patch_seq_time_nanos"),
1510        ("time.sleep-ms", "patch_seq_time_sleep_ms"),
1511        // SON serialization
1512        ("son.dump", "patch_seq_son_dump"),
1513        ("son.dump-pretty", "patch_seq_son_dump_pretty"),
1514        // Stack introspection
1515        ("stack.dump", "patch_seq_stack_dump"),
1516    ])
1517});
1518
1519/// Emit all runtime function declarations to the IR string.
1520pub fn emit_runtime_decls(ir: &mut String) -> Result<(), CodeGenError> {
1521    for decl in RUNTIME_DECLARATIONS.iter() {
1522        if let Some(cat) = decl.category {
1523            writeln!(ir, "{}", cat)?;
1524        }
1525        writeln!(ir, "{}", decl.decl)?;
1526    }
1527    writeln!(ir)?;
1528    Ok(())
1529}