@typecad/cuttlefish 0.1.0-alpha.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (377) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +79 -0
  3. package/dist/api/board-types.d.ts +1 -0
  4. package/dist/api/board-types.js +4 -0
  5. package/dist/api/capabilities.d.ts +12 -0
  6. package/dist/api/capabilities.js +1 -0
  7. package/dist/api/config.d.ts +120 -0
  8. package/dist/api/config.js +7 -0
  9. package/dist/api/index.d.ts +5 -0
  10. package/dist/api/index.js +2 -0
  11. package/dist/api/schema/builder.d.ts +14 -0
  12. package/dist/api/schema/builder.js +15 -0
  13. package/dist/api/schema/index.d.ts +2 -0
  14. package/dist/api/schema/index.js +1 -0
  15. package/dist/api/schema/types.d.ts +257 -0
  16. package/dist/api/schema/types.js +4 -0
  17. package/dist/api/shared/async-runtime-static.d.ts +8 -0
  18. package/dist/api/shared/async-runtime-static.js +201 -0
  19. package/dist/api/shared/async-types.d.ts +42 -0
  20. package/dist/api/shared/async-types.js +8 -0
  21. package/dist/api/shared/board-resolver.d.ts +12 -0
  22. package/dist/api/shared/board-resolver.js +7 -0
  23. package/dist/api/shared/cpp-type-ir.d.ts +229 -0
  24. package/dist/api/shared/cpp-type-ir.js +672 -0
  25. package/dist/api/shared/display-adapter.d.ts +12 -0
  26. package/dist/api/shared/display-adapter.js +145 -0
  27. package/dist/api/shared/display-adapters/eink-mono.d.ts +2 -0
  28. package/dist/api/shared/display-adapters/eink-mono.js +53 -0
  29. package/dist/api/shared/display-adapters/sdl.d.ts +2 -0
  30. package/dist/api/shared/display-adapters/sdl.js +452 -0
  31. package/dist/api/shared/display-adapters/ssd1309.d.ts +2 -0
  32. package/dist/api/shared/display-adapters/ssd1309.js +136 -0
  33. package/dist/api/shared/display-adapters/st7796.d.ts +2 -0
  34. package/dist/api/shared/display-adapters/st7796.js +132 -0
  35. package/dist/api/shared/display-capabilities.d.ts +45 -0
  36. package/dist/api/shared/display-capabilities.js +54 -0
  37. package/dist/api/shared/display-op-ir.d.ts +62 -0
  38. package/dist/api/shared/display-op-ir.js +19 -0
  39. package/dist/api/shared/display-profile.d.ts +265 -0
  40. package/dist/api/shared/display-profile.js +338 -0
  41. package/dist/api/shared/graphics-strategy.d.ts +29 -0
  42. package/dist/api/shared/graphics-strategy.js +11 -0
  43. package/dist/api/shared/hal-op-ir.d.ts +393 -0
  44. package/dist/api/shared/hal-op-ir.js +18 -0
  45. package/dist/api/shared/index.d.ts +26 -0
  46. package/dist/api/shared/index.js +21 -0
  47. package/dist/api/shared/ir-core.d.ts +363 -0
  48. package/dist/api/shared/ir-core.js +8 -0
  49. package/dist/api/shared/ir-declarations.d.ts +201 -0
  50. package/dist/api/shared/ir-declarations.js +26 -0
  51. package/dist/api/shared/ir.d.ts +85 -0
  52. package/dist/api/shared/ir.js +13 -0
  53. package/dist/api/shared/platform-strategy.d.ts +402 -0
  54. package/dist/api/shared/platform-strategy.js +14 -0
  55. package/dist/api/shared/polyfill-helper-registry.d.ts +11 -0
  56. package/dist/api/shared/polyfill-helper-registry.js +86 -0
  57. package/dist/api/shared/polyfill-types.d.ts +33 -0
  58. package/dist/api/shared/polyfill-types.js +76 -0
  59. package/dist/api/shared/promise-runtime.d.ts +10 -0
  60. package/dist/api/shared/promise-runtime.js +244 -0
  61. package/dist/api/shared/snprintf-types.d.ts +29 -0
  62. package/dist/api/shared/snprintf-types.js +8 -0
  63. package/dist/api/shared/string-method-registry.d.ts +53 -0
  64. package/dist/api/shared/string-method-registry.js +168 -0
  65. package/dist/api/shared/toolchain-types.d.ts +63 -0
  66. package/dist/api/shared/toolchain-types.js +71 -0
  67. package/dist/api/shared/types.d.ts +50 -0
  68. package/dist/api/shared/types.js +6 -0
  69. package/dist/ast/parse.d.ts +2 -0
  70. package/dist/ast/parse.js +4 -0
  71. package/dist/cache.d.ts +26 -0
  72. package/dist/cache.js +95 -0
  73. package/dist/cli-utils.d.ts +37 -0
  74. package/dist/cli-utils.js +250 -0
  75. package/dist/cli.d.ts +2 -0
  76. package/dist/cli.js +635 -0
  77. package/dist/config-loader.d.ts +78 -0
  78. package/dist/config-loader.js +508 -0
  79. package/dist/config-schema.d.ts +233 -0
  80. package/dist/config-schema.js +83 -0
  81. package/dist/create/board-checklist.d.ts +2 -0
  82. package/dist/create/board-checklist.js +52 -0
  83. package/dist/create/board-codegen.d.ts +9 -0
  84. package/dist/create/board-codegen.js +238 -0
  85. package/dist/create/board-generators.d.ts +12 -0
  86. package/dist/create/board-generators.js +652 -0
  87. package/dist/create/board-spec.d.ts +640 -0
  88. package/dist/create/board-spec.js +215 -0
  89. package/dist/create/eslint-rules-template.d.ts +2 -0
  90. package/dist/create/eslint-rules-template.js +672 -0
  91. package/dist/create/index.d.ts +11 -0
  92. package/dist/create/index.js +8 -0
  93. package/dist/create/init-scaffold.d.ts +27 -0
  94. package/dist/create/init-scaffold.js +150 -0
  95. package/dist/create/init-templates.d.ts +24 -0
  96. package/dist/create/init-templates.js +379 -0
  97. package/dist/create/init-wizard.d.ts +8 -0
  98. package/dist/create/init-wizard.js +168 -0
  99. package/dist/debug/breakpoint-loader.d.ts +24 -0
  100. package/dist/debug/breakpoint-loader.js +137 -0
  101. package/dist/debug/index.d.ts +3 -0
  102. package/dist/debug/index.js +7 -0
  103. package/dist/debug/preprocessor.d.ts +9 -0
  104. package/dist/debug/preprocessor.js +214 -0
  105. package/dist/debug/types.d.ts +32 -0
  106. package/dist/debug/types.js +6 -0
  107. package/dist/diagnostics/diagnostics-report.d.ts +51 -0
  108. package/dist/diagnostics/diagnostics-report.js +333 -0
  109. package/dist/diagnostics/json-schema.d.ts +138 -0
  110. package/dist/diagnostics/json-schema.js +27 -0
  111. package/dist/diagnostics/md-writer.d.ts +10 -0
  112. package/dist/diagnostics/md-writer.js +336 -0
  113. package/dist/diagnostics/mermaid-builder.d.ts +65 -0
  114. package/dist/diagnostics/mermaid-builder.js +681 -0
  115. package/dist/emit/cpp-emitter.d.ts +6 -0
  116. package/dist/emit/cpp-emitter.js +48 -0
  117. package/dist/emit/emitters/class-emitter.d.ts +2 -0
  118. package/dist/emit/emitters/class-emitter.js +523 -0
  119. package/dist/emit/emitters/emitter-context.d.ts +174 -0
  120. package/dist/emit/emitters/emitter-context.js +1 -0
  121. package/dist/emit/emitters/entrypoint-synthesizer.d.ts +2 -0
  122. package/dist/emit/emitters/entrypoint-synthesizer.js +175 -0
  123. package/dist/emit/emitters/function-emitter-impl.d.ts +19 -0
  124. package/dist/emit/emitters/function-emitter-impl.js +428 -0
  125. package/dist/emit/emitters/line-appender.d.ts +15 -0
  126. package/dist/emit/emitters/line-appender.js +344 -0
  127. package/dist/emit/emitters/namespace-emitter.d.ts +2 -0
  128. package/dist/emit/emitters/namespace-emitter.js +324 -0
  129. package/dist/emit/emitters/output-finalizer.d.ts +4 -0
  130. package/dist/emit/emitters/output-finalizer.js +267 -0
  131. package/dist/emit/emitters/setup.d.ts +3 -0
  132. package/dist/emit/emitters/setup.js +851 -0
  133. package/dist/emit/emitters/top-level-prep.d.ts +2 -0
  134. package/dist/emit/emitters/top-level-prep.js +706 -0
  135. package/dist/emit/emitters/type-decl-emitter.d.ts +2 -0
  136. package/dist/emit/emitters/type-decl-emitter.js +251 -0
  137. package/dist/emit/emitters/ui-emitter.d.ts +21 -0
  138. package/dist/emit/emitters/ui-emitter.js +564 -0
  139. package/dist/emit/enum-emitter.d.ts +1 -0
  140. package/dist/emit/enum-emitter.js +1 -0
  141. package/dist/emit/expression-renderer.d.ts +283 -0
  142. package/dist/emit/expression-renderer.js +1477 -0
  143. package/dist/emit/native-helpers-emitter.d.ts +11 -0
  144. package/dist/emit/native-helpers-emitter.js +34 -0
  145. package/dist/emit/route-hal-op.d.ts +5 -0
  146. package/dist/emit/route-hal-op.js +13 -0
  147. package/dist/emit/snprintf-helpers.d.ts +17 -0
  148. package/dist/emit/snprintf-helpers.js +462 -0
  149. package/dist/emit/statement-renderer.d.ts +189 -0
  150. package/dist/emit/statement-renderer.js +948 -0
  151. package/dist/emit/utils/async-state-machine.d.ts +42 -0
  152. package/dist/emit/utils/async-state-machine.js +343 -0
  153. package/dist/emit/utils/comment-helpers.d.ts +20 -0
  154. package/dist/emit/utils/comment-helpers.js +31 -0
  155. package/dist/emit/utils/cpp-helpers.d.ts +47 -0
  156. package/dist/emit/utils/cpp-helpers.js +85 -0
  157. package/dist/emit/utils/include-resolver.d.ts +58 -0
  158. package/dist/emit/utils/include-resolver.js +155 -0
  159. package/dist/emit/utils/index.d.ts +8 -0
  160. package/dist/emit/utils/index.js +12 -0
  161. package/dist/emit/utils/type-inference.d.ts +159 -0
  162. package/dist/emit/utils/type-inference.js +559 -0
  163. package/dist/eslint-check.d.ts +10 -0
  164. package/dist/eslint-check.js +102 -0
  165. package/dist/framework-package.d.ts +10 -0
  166. package/dist/framework-package.js +58 -0
  167. package/dist/framework-registry.d.ts +39 -0
  168. package/dist/framework-registry.js +30 -0
  169. package/dist/incremental-cache.d.ts +116 -0
  170. package/dist/incremental-cache.js +335 -0
  171. package/dist/ir/adc-range-validation.d.ts +11 -0
  172. package/dist/ir/adc-range-validation.js +250 -0
  173. package/dist/ir/ast-node-utils.d.ts +8 -0
  174. package/dist/ir/ast-node-utils.js +32 -0
  175. package/dist/ir/board-pin-utils.d.ts +13 -0
  176. package/dist/ir/board-pin-utils.js +65 -0
  177. package/dist/ir/board-resolver.d.ts +36 -0
  178. package/dist/ir/board-resolver.js +437 -0
  179. package/dist/ir/build-ir-state.d.ts +167 -0
  180. package/dist/ir/build-ir-state.js +306 -0
  181. package/dist/ir/build-ir.d.ts +2 -0
  182. package/dist/ir/build-ir.js +808 -0
  183. package/dist/ir/call-graph.d.ts +35 -0
  184. package/dist/ir/call-graph.js +194 -0
  185. package/dist/ir/compile-time-only.d.ts +2 -0
  186. package/dist/ir/compile-time-only.js +16 -0
  187. package/dist/ir/declaration-builders.d.ts +9 -0
  188. package/dist/ir/declaration-builders.js +608 -0
  189. package/dist/ir/entry-points.d.ts +30 -0
  190. package/dist/ir/entry-points.js +191 -0
  191. package/dist/ir/expression-to-ir.d.ts +5 -0
  192. package/dist/ir/expression-to-ir.js +2249 -0
  193. package/dist/ir/extract-property-chain.d.ts +10 -0
  194. package/dist/ir/extract-property-chain.js +30 -0
  195. package/dist/ir/feature-prescan.d.ts +3 -0
  196. package/dist/ir/feature-prescan.js +43 -0
  197. package/dist/ir/feature-registry.d.ts +30 -0
  198. package/dist/ir/feature-registry.js +816 -0
  199. package/dist/ir/filter.d.ts +7 -0
  200. package/dist/ir/filter.js +85 -0
  201. package/dist/ir/function-builder.d.ts +19 -0
  202. package/dist/ir/function-builder.js +670 -0
  203. package/dist/ir/hal/hal-emitter.d.ts +62 -0
  204. package/dist/ir/hal/hal-emitter.js +735 -0
  205. package/dist/ir/hal/hal-parser.d.ts +61 -0
  206. package/dist/ir/hal/hal-parser.js +473 -0
  207. package/dist/ir/hal/hal-plugins.d.ts +34 -0
  208. package/dist/ir/hal/hal-plugins.js +706 -0
  209. package/dist/ir/hal-resolver.d.ts +5 -0
  210. package/dist/ir/hal-resolver.js +5 -0
  211. package/dist/ir/heap-analysis.d.ts +8 -0
  212. package/dist/ir/heap-analysis.js +350 -0
  213. package/dist/ir/heap-array-validation.d.ts +24 -0
  214. package/dist/ir/heap-array-validation.js +29 -0
  215. package/dist/ir/identifier-collector.d.ts +18 -0
  216. package/dist/ir/identifier-collector.js +439 -0
  217. package/dist/ir/interrupt-analysis.d.ts +39 -0
  218. package/dist/ir/interrupt-analysis.js +467 -0
  219. package/dist/ir/memory-budget-validation.d.ts +10 -0
  220. package/dist/ir/memory-budget-validation.js +86 -0
  221. package/dist/ir/namespace-builder.d.ts +7 -0
  222. package/dist/ir/namespace-builder.js +152 -0
  223. package/dist/ir/ownership-analysis.d.ts +9 -0
  224. package/dist/ir/ownership-analysis.js +1207 -0
  225. package/dist/ir/peripheral-ownership.d.ts +3 -0
  226. package/dist/ir/peripheral-ownership.js +152 -0
  227. package/dist/ir/peripheral-symbols.d.ts +7 -0
  228. package/dist/ir/peripheral-symbols.js +57 -0
  229. package/dist/ir/peripheral-usage.d.ts +54 -0
  230. package/dist/ir/peripheral-usage.js +691 -0
  231. package/dist/ir/peripheral-validation.d.ts +8 -0
  232. package/dist/ir/peripheral-validation.js +77 -0
  233. package/dist/ir/pin-alias-conflict.d.ts +4 -0
  234. package/dist/ir/pin-alias-conflict.js +34 -0
  235. package/dist/ir/pin-capability-validation.d.ts +6 -0
  236. package/dist/ir/pin-capability-validation.js +413 -0
  237. package/dist/ir/pin-mode-validation.d.ts +10 -0
  238. package/dist/ir/pin-mode-validation.js +301 -0
  239. package/dist/ir/pin-safety.d.ts +11 -0
  240. package/dist/ir/pin-safety.js +58 -0
  241. package/dist/ir/program-analysis.d.ts +44 -0
  242. package/dist/ir/program-analysis.js +589 -0
  243. package/dist/ir/pulldown-validation.d.ts +7 -0
  244. package/dist/ir/pulldown-validation.js +49 -0
  245. package/dist/ir/pwm-timer-sharing.d.ts +4 -0
  246. package/dist/ir/pwm-timer-sharing.js +93 -0
  247. package/dist/ir/reachability.d.ts +68 -0
  248. package/dist/ir/reachability.js +224 -0
  249. package/dist/ir/register-decorators.d.ts +6 -0
  250. package/dist/ir/register-decorators.js +49 -0
  251. package/dist/ir/render-expr.d.ts +4 -0
  252. package/dist/ir/render-expr.js +127 -0
  253. package/dist/ir/resource-analysis.d.ts +19 -0
  254. package/dist/ir/resource-analysis.js +153 -0
  255. package/dist/ir/statement-to-ir.d.ts +23 -0
  256. package/dist/ir/statement-to-ir.js +349 -0
  257. package/dist/ir/symbol-table.d.ts +68 -0
  258. package/dist/ir/symbol-table.js +179 -0
  259. package/dist/ir/symbol-types.d.ts +56 -0
  260. package/dist/ir/symbol-types.js +107 -0
  261. package/dist/ir/timer0-pwm-timing-conflict.d.ts +4 -0
  262. package/dist/ir/timer0-pwm-timing-conflict.js +71 -0
  263. package/dist/ir/timing-validation.d.ts +7 -0
  264. package/dist/ir/timing-validation.js +95 -0
  265. package/dist/ir/transformers/array-methods.d.ts +8 -0
  266. package/dist/ir/transformers/array-methods.js +493 -0
  267. package/dist/ir/transformers/call-statement.d.ts +5 -0
  268. package/dist/ir/transformers/call-statement.js +758 -0
  269. package/dist/ir/transformers/callback-context-registry.d.ts +20 -0
  270. package/dist/ir/transformers/callback-context-registry.js +55 -0
  271. package/dist/ir/transformers/canvas-lowering.d.ts +42 -0
  272. package/dist/ir/transformers/canvas-lowering.js +249 -0
  273. package/dist/ir/transformers/control-flow.d.ts +8 -0
  274. package/dist/ir/transformers/control-flow.js +508 -0
  275. package/dist/ir/transformers/expressions.d.ts +7 -0
  276. package/dist/ir/transformers/expressions.js +406 -0
  277. package/dist/ir/transformers/hal-call-resolver.d.ts +29 -0
  278. package/dist/ir/transformers/hal-call-resolver.js +274 -0
  279. package/dist/ir/transformers/hal-emit-helpers.d.ts +14 -0
  280. package/dist/ir/transformers/hal-emit-helpers.js +63 -0
  281. package/dist/ir/transformers/namespace-methods.d.ts +20 -0
  282. package/dist/ir/transformers/namespace-methods.js +110 -0
  283. package/dist/ir/transformers/register-assignment.d.ts +5 -0
  284. package/dist/ir/transformers/register-assignment.js +56 -0
  285. package/dist/ir/transformers/ui-call-resolver.d.ts +149 -0
  286. package/dist/ir/transformers/ui-call-resolver.js +1136 -0
  287. package/dist/ir/transformers/ui-callback-lowering.d.ts +62 -0
  288. package/dist/ir/transformers/ui-callback-lowering.js +623 -0
  289. package/dist/ir/transformers/ui-mount.d.ts +20 -0
  290. package/dist/ir/transformers/ui-mount.js +35 -0
  291. package/dist/ir/transformers/ui-reactive.d.ts +68 -0
  292. package/dist/ir/transformers/ui-reactive.js +129 -0
  293. package/dist/ir/transformers/variables.d.ts +14 -0
  294. package/dist/ir/transformers/variables.js +1045 -0
  295. package/dist/ir/try-catch-validation.d.ts +26 -0
  296. package/dist/ir/try-catch-validation.js +128 -0
  297. package/dist/ir/type-resolution.d.ts +31 -0
  298. package/dist/ir/type-resolution.js +977 -0
  299. package/dist/ir/ui-element-auto-wire.d.ts +50 -0
  300. package/dist/ir/ui-element-auto-wire.js +218 -0
  301. package/dist/ir/unit-suspicion-validation.d.ts +12 -0
  302. package/dist/ir/unit-suspicion-validation.js +296 -0
  303. package/dist/ir/utils/walk-ir.d.ts +6 -0
  304. package/dist/ir/utils/walk-ir.js +162 -0
  305. package/dist/ir/validation-orchestrator.d.ts +4 -0
  306. package/dist/ir/validation-orchestrator.js +45 -0
  307. package/dist/libdef/base-class-resolver.d.ts +23 -0
  308. package/dist/libdef/base-class-resolver.js +50 -0
  309. package/dist/libdef/cpp-to-decl.d.ts +34 -0
  310. package/dist/libdef/cpp-to-decl.js +584 -0
  311. package/dist/libdef/header-parser.d.ts +53 -0
  312. package/dist/libdef/header-parser.js +269 -0
  313. package/dist/libdef/registry.d.ts +10 -0
  314. package/dist/libdef/registry.js +142 -0
  315. package/dist/mapping/peripheral-names.d.ts +23 -0
  316. package/dist/mapping/peripheral-names.js +63 -0
  317. package/dist/mapping/source-map.d.ts +46 -0
  318. package/dist/mapping/source-map.js +207 -0
  319. package/dist/orchestrator/dts-generator.d.ts +17 -0
  320. package/dist/orchestrator/dts-generator.js +83 -0
  321. package/dist/orchestrator/graph-builder.d.ts +18 -0
  322. package/dist/orchestrator/graph-builder.js +218 -0
  323. package/dist/orchestrator/semantic-facts-verifier.d.ts +38 -0
  324. package/dist/orchestrator/semantic-facts-verifier.js +121 -0
  325. package/dist/orchestrator/semantic-facts.d.ts +141 -0
  326. package/dist/orchestrator/semantic-facts.js +652 -0
  327. package/dist/orchestrator/type-checker.d.ts +39 -0
  328. package/dist/orchestrator/type-checker.js +760 -0
  329. package/dist/platform/async-runtime.d.ts +8 -0
  330. package/dist/platform/async-runtime.js +26 -0
  331. package/dist/platform/generic-strategy.d.ts +101 -0
  332. package/dist/platform/generic-strategy.js +289 -0
  333. package/dist/platform/index.d.ts +4 -0
  334. package/dist/platform/index.js +9 -0
  335. package/dist/platform/registry.d.ts +21 -0
  336. package/dist/platform/registry.js +42 -0
  337. package/dist/platform/toolchain.d.ts +4 -0
  338. package/dist/platform/toolchain.js +43 -0
  339. package/dist/preview/client.d.ts +1 -0
  340. package/dist/preview/client.js +137 -0
  341. package/dist/preview/server.d.ts +5 -0
  342. package/dist/preview/server.js +199 -0
  343. package/dist/profiler/index.d.ts +28 -0
  344. package/dist/profiler/index.js +28 -0
  345. package/dist/profiler/profiler.d.ts +95 -0
  346. package/dist/profiler/profiler.js +338 -0
  347. package/dist/profiler/types.d.ts +87 -0
  348. package/dist/profiler/types.js +12 -0
  349. package/dist/stores/display-profile-store.d.ts +16 -0
  350. package/dist/stores/display-profile-store.js +48 -0
  351. package/dist/stores/theme-store.d.ts +13 -0
  352. package/dist/stores/theme-store.js +30 -0
  353. package/dist/testing.d.ts +45 -0
  354. package/dist/testing.js +47 -0
  355. package/dist/transpile/resolution.d.ts +29 -0
  356. package/dist/transpile/resolution.js +282 -0
  357. package/dist/transpile.d.ts +3 -0
  358. package/dist/transpile.js +722 -0
  359. package/dist/types.d.ts +217 -0
  360. package/dist/types.js +1 -0
  361. package/dist/ui/ui-bridge.d.ts +4 -0
  362. package/dist/ui/ui-bridge.js +34 -0
  363. package/dist/ui-hook.d.ts +84 -0
  364. package/dist/ui-hook.js +45 -0
  365. package/dist/utils/cli.d.ts +3 -0
  366. package/dist/utils/cli.js +463 -0
  367. package/dist/utils/fs.d.ts +4 -0
  368. package/dist/utils/fs.js +23 -0
  369. package/dist/utils/logger.d.ts +2 -0
  370. package/dist/utils/logger.js +8 -0
  371. package/dist/utils/strings.d.ts +35 -0
  372. package/dist/utils/strings.js +142 -0
  373. package/dist/utils/ui.d.ts +66 -0
  374. package/dist/utils/ui.js +149 -0
  375. package/dist/watch.d.ts +35 -0
  376. package/dist/watch.js +111 -0
  377. package/package.json +127 -0
@@ -0,0 +1,652 @@
1
+ // ---------------------------------------------------------------------------
2
+ // board-generators.ts — Pure string-returning generators for the board-codegen
3
+ // tool. Each function takes a BoardSpec and returns the file content as a
4
+ // string. No filesystem I/O — the orchestrator (board-codegen.ts) writes files.
5
+ //
6
+ // Golden reference: the hand-written packages/mcu-esp32c6/ and
7
+ // packages/board-esp32c6/ packages. These generators reproduce them from a
8
+ // C6 spec.
9
+ // ---------------------------------------------------------------------------
10
+ // ---------------------------------------------------------------------------
11
+ // Helpers
12
+ // ---------------------------------------------------------------------------
13
+ /** Generate the list of GPIO numbers in the spec's range, minus exclusions. */
14
+ function gpioList(spec) {
15
+ const [first, last] = spec.gpioRange;
16
+ const excluded = new Set(spec.excludedGpio);
17
+ const list = [];
18
+ for (let n = first; n <= last; n++) {
19
+ if (!excluded.has(n))
20
+ list.push(n);
21
+ }
22
+ return list;
23
+ }
24
+ /** "GPIO0", "GPIO1", ... for the range. */
25
+ function gpioNames(spec) {
26
+ return gpioList(spec).map(n => `GPIO${n}`);
27
+ }
28
+ /** The first I2C/SPI/UART bus instance's default pins, as a lookup. */
29
+ function busDefaultPin(spec, bus, role) {
30
+ const map = spec[bus];
31
+ const firstKey = Object.keys(map)[0];
32
+ if (!firstKey)
33
+ return undefined;
34
+ return map[firstKey][role];
35
+ }
36
+ // ---------------------------------------------------------------------------
37
+ // MCU package generators
38
+ // ---------------------------------------------------------------------------
39
+ export function genMcuPackageJson(spec) {
40
+ const pkg = {
41
+ name: `@typecad/mcu-${spec.architecture}`,
42
+ version: '0.1.0',
43
+ description: `TypeCAD MCU definition for ${spec.mcuName} — datasheet pins, peripheral capabilities, and HAL instances`,
44
+ type: 'module',
45
+ main: './dist/index.js',
46
+ types: './dist/index.d.ts',
47
+ exports: {
48
+ '.': {
49
+ types: './dist/index.d.ts',
50
+ default: './dist/index.js',
51
+ },
52
+ },
53
+ files: ['dist'],
54
+ scripts: { build: 'tsc' },
55
+ dependencies: {
56
+ '@typecad/cuttlefish': '*',
57
+ '@typecad/hal': '*',
58
+ },
59
+ license: 'MIT',
60
+ };
61
+ return JSON.stringify(pkg, null, 2) + '\n';
62
+ }
63
+ export function genMcuTsconfig(_spec) {
64
+ // Static — identical for every MCU package.
65
+ return JSON.stringify({
66
+ compilerOptions: {
67
+ composite: true, target: 'ES2021', module: 'Node16', moduleResolution: 'Node16',
68
+ strict: true, esModuleInterop: true, skipLibCheck: true,
69
+ forceConsistentCasingInFileNames: true, declaration: true, declarationMap: true,
70
+ sourceMap: true, rootDir: 'src', outDir: 'dist',
71
+ experimentalDecorators: true, emitDecoratorMetadata: true,
72
+ },
73
+ include: ['src/**/*.ts'],
74
+ references: [{ path: '../hal' }, { path: '../cuttlefish' }],
75
+ }, null, 2) + '\n';
76
+ }
77
+ export function genMcuPins(spec) {
78
+ const gpios = gpioList(spec);
79
+ const lines = [
80
+ `// ---------------------------------------------------------------------------`,
81
+ `// @typecad/mcu-${spec.architecture} — Datasheet pin definitions`,
82
+ `//`,
83
+ `// Each pin is a Pin instance from @typecad/hal.`,
84
+ `// ---------------------------------------------------------------------------`,
85
+ '',
86
+ `import { Pin } from '@typecad/hal';`,
87
+ '',
88
+ ];
89
+ // GPIO constants
90
+ for (const n of gpios) {
91
+ lines.push(`export const GPIO${n} = new Pin(${n});`);
92
+ }
93
+ // Bus aliases
94
+ const sda = busDefaultPin(spec, 'i2c', 'sda');
95
+ const scl = busDefaultPin(spec, 'i2c', 'scl');
96
+ const mosi = busDefaultPin(spec, 'spi', 'mosi');
97
+ const miso = busDefaultPin(spec, 'spi', 'miso');
98
+ const sck = busDefaultPin(spec, 'spi', 'sck');
99
+ const ss = busDefaultPin(spec, 'spi', 'cs');
100
+ const tx = busDefaultPin(spec, 'uart', 'tx');
101
+ const rx = busDefaultPin(spec, 'uart', 'rx');
102
+ lines.push('');
103
+ lines.push('// ---------------------------------------------------------------------------');
104
+ lines.push('// Convenience aliases (Silicon-level defaults — match Arduino-ESP32 core)');
105
+ lines.push('// ---------------------------------------------------------------------------');
106
+ lines.push('');
107
+ if (sda)
108
+ lines.push(`/** I2C0 data line (${sda}). */`, `export const SDA = ${sda};`);
109
+ if (scl)
110
+ lines.push(`/** I2C0 clock line (${scl}). */`, `export const SCL = ${scl};`);
111
+ if (mosi)
112
+ lines.push(`/** SPI0 MOSI (${mosi}). */`, `export const MOSI = ${mosi};`);
113
+ if (miso)
114
+ lines.push(`/** SPI0 MISO (${miso}). */`, `export const MISO = ${miso};`);
115
+ if (sck)
116
+ lines.push(`/** SPI0 clock (${sck}). */`, `export const SCK = ${sck};`);
117
+ if (ss)
118
+ lines.push(`/** SPI0 slave select (${ss}). */`, `export const SS = ${ss};`);
119
+ if (tx)
120
+ lines.push(`/** UART0 transmit (${tx}). */`, `export const TX = ${tx};`);
121
+ if (rx)
122
+ lines.push(`/** UART0 receive (${rx}). */`, `export const RX = ${rx};`);
123
+ lines.push('');
124
+ return lines.join('\n');
125
+ }
126
+ export function genMcuPeripherals(spec) {
127
+ const arch = spec.architecture;
128
+ const mcuName = spec.mcuName;
129
+ const lines = [
130
+ `// ---------------------------------------------------------------------------`,
131
+ `// @typecad/mcu-${arch} — Hardware peripheral descriptions`,
132
+ `// ---------------------------------------------------------------------------`,
133
+ '',
134
+ `import type {`,
135
+ ` PeripheralInstance, ADCDefinition, PWMDefinition, TimerDefinition,`,
136
+ `} from '@typecad/cuttlefish/api/schema';`,
137
+ `import {`,
138
+ ` I2CBus, SPIBus, SerialPort, i2cName, spiName, serialName, createHALInstances,`,
139
+ `} from '@typecad/hal';`,
140
+ '',
141
+ ];
142
+ // I2C instances
143
+ lines.push('export const I2C_INSTANCES: readonly PeripheralInstance[] = [');
144
+ for (const inst of spec.peripheralInstances.i2c) {
145
+ const pins = Object.entries(inst.defaultPins).map(([k, v]) => `${k}: '${v}'`).join(', ');
146
+ lines.push(` { instance: ${inst.instance}, defaultPins: { ${pins} } },`);
147
+ }
148
+ lines.push('] as const;');
149
+ lines.push('');
150
+ // SPI instances
151
+ lines.push('export const SPI_INSTANCES: readonly PeripheralInstance[] = [');
152
+ for (const inst of spec.peripheralInstances.spi) {
153
+ const pins = Object.entries(inst.defaultPins).map(([k, v]) => `${k}: '${v}'`).join(', ');
154
+ lines.push(` { instance: ${inst.instance}, defaultPins: { ${pins} } },`);
155
+ }
156
+ lines.push('] as const;');
157
+ lines.push('');
158
+ // UART instances
159
+ lines.push('export const UART_INSTANCES: readonly PeripheralInstance[] = [');
160
+ for (const inst of spec.peripheralInstances.uart) {
161
+ const pins = Object.entries(inst.defaultPins).map(([k, v]) => `${k}: '${v}'`).join(', ');
162
+ lines.push(` { instance: ${inst.instance}, defaultPins: { ${pins} } },`);
163
+ }
164
+ lines.push('] as const;');
165
+ lines.push('');
166
+ // ADC instances
167
+ lines.push('export const ADC_INSTANCES: readonly ADCDefinition[] = [');
168
+ for (const adc of spec.adc) {
169
+ const refV = adc.referenceVoltages
170
+ ? `, referenceVoltages: { ${Object.entries(adc.referenceVoltages).map(([k, v]) => `${k}: ${v}`).join(', ')} }`
171
+ : '';
172
+ lines.push(` { instance: ${adc.instance}, channels: ${adc.channels}, resolution: ${adc.resolution}, referenceVoltage: ${adc.referenceVoltage}, maxValue: ${adc.maxValue}${refV} },`);
173
+ }
174
+ lines.push('] as const;');
175
+ lines.push('');
176
+ // PWM
177
+ lines.push('export const PWM_CAPABILITIES: PWMDefinition = {');
178
+ lines.push(` channels: ${spec.pwm.channels}, resolution: ${spec.pwm.resolution}, maxFrequency: ${spec.pwm.maxFrequency},`);
179
+ lines.push('} as const;');
180
+ lines.push('');
181
+ // Touch (conditional)
182
+ if (spec.touch) {
183
+ lines.push('export const TOUCH_CAPABILITIES = {');
184
+ lines.push(` channels: ${spec.touch.channels},`);
185
+ lines.push(` pins: [${spec.touch.pins.map(p => `'${p}'`).join(', ')}],`);
186
+ lines.push('};');
187
+ lines.push('');
188
+ }
189
+ // Timers
190
+ lines.push('export const TIMER_INSTANCES: readonly TimerDefinition[] = [');
191
+ for (const t of spec.timers) {
192
+ const feats = t.features ? `, features: [${t.features.map(f => `'${f}'`).join(', ')}]` : '';
193
+ lines.push(` { instance: ${t.instance}, type: '${t.type}', bits: ${t.bits} as 64${feats} },`);
194
+ }
195
+ lines.push('] as const;');
196
+ lines.push('');
197
+ // Connectivity
198
+ lines.push(`export const WIFI_CAPABILITIES = { type: '${spec.wifi.type}', supportsStation: ${spec.wifi.supportsStation}, supportsAp: ${spec.wifi.supportsAp} } as const;`);
199
+ lines.push(`export const BLUETOOTH_CAPABILITIES = { type: '${spec.bluetooth.type}', version: '${spec.bluetooth.version}' } as const;`);
200
+ lines.push(`export const USB_CAPABILITIES = { type: '${spec.usb.type}', vid: '${spec.usb.vid}', pid: '${spec.usb.pid}' } as const;`);
201
+ lines.push('');
202
+ // MCU_PERIPHERALS aggregate
203
+ lines.push('export const MCU_PERIPHERALS = {');
204
+ lines.push(' i2c: [...I2C_INSTANCES],');
205
+ lines.push(' spi: [...SPI_INSTANCES],');
206
+ lines.push(' uart: [...UART_INSTANCES],');
207
+ lines.push(' adc: [...ADC_INSTANCES],');
208
+ lines.push(' pwm: PWM_CAPABILITIES,');
209
+ if (spec.touch)
210
+ lines.push(' touch: TOUCH_CAPABILITIES,');
211
+ lines.push(' timers: [...TIMER_INSTANCES],');
212
+ lines.push(' wifi: WIFI_CAPABILITIES,');
213
+ lines.push(' bluetooth: BLUETOOTH_CAPABILITIES,');
214
+ lines.push(' usb: USB_CAPABILITIES,');
215
+ lines.push('} as const;');
216
+ lines.push('');
217
+ // HAL instances
218
+ const i2cNames = spec.peripheralInstances.i2c.map((_, i) => `I2C${i}`).join(', ');
219
+ const spiNames = spec.peripheralInstances.spi.map((_, i) => `SPI${i}`).join(', ');
220
+ const uartNames = spec.peripheralInstances.uart.map((_, i) => `UART${i}`).join(', ');
221
+ lines.push(`export const [${i2cNames}] = createHALInstances(I2C_INSTANCES, i => new I2CBus(i2cName(i)));`);
222
+ lines.push(`export const [${spiNames}] = createHALInstances(SPI_INSTANCES, i => new SPIBus(spiName(i)));`);
223
+ lines.push(`export const [${uartNames}] = createHALInstances(UART_INSTANCES, i => new SerialPort(serialName(i)));`);
224
+ lines.push('');
225
+ return lines.join('\n');
226
+ }
227
+ export function genMcuIndex(spec) {
228
+ const arch = spec.architecture;
229
+ const archUpper = arch.toUpperCase();
230
+ const lines = [
231
+ `// ---------------------------------------------------------------------------`,
232
+ `// @typecad/mcu-${arch} — MCU definition manifest`,
233
+ `// ---------------------------------------------------------------------------`,
234
+ '',
235
+ `import type { MCUDefinition } from '@typecad/cuttlefish/api/schema';`,
236
+ `import { MCU_PERIPHERALS } from './peripherals.js';`,
237
+ '',
238
+ `const NO = false as const;`,
239
+ `const YES = true as const;`,
240
+ '',
241
+ `const FULL_GPIO = {`,
242
+ ` digitalInput: YES, digitalOutput: YES,`,
243
+ ` analogInput: NO, analogOutput: NO,`,
244
+ ` pwm: YES, interrupt: YES,`,
245
+ ` pullUp: YES, pullDown: YES,`,
246
+ ` touch: NO, openDrain: NO,`,
247
+ `} as const;`,
248
+ '',
249
+ `const FULL_GPIO_ANALOG = { ...FULL_GPIO, analogInput: YES } as const;`,
250
+ ];
251
+ // Emit the capability flag helpers that are actually used by the pins
252
+ const usedCaps = new Set(spec.pins.map(p => p.capabilities));
253
+ if (usedCaps.has('FULL_GPIO_TOUCH')) {
254
+ lines.push(`const FULL_GPIO_TOUCH = { ...FULL_GPIO, touch: YES } as const;`);
255
+ }
256
+ if (usedCaps.has('FULL_GPIO_ANALOG_TOUCH')) {
257
+ lines.push(`const FULL_GPIO_ANALOG_TOUCH = { ...FULL_GPIO, analogInput: YES, touch: YES } as const;`);
258
+ }
259
+ if (usedCaps.has('FULL_GPIO_DAC')) {
260
+ lines.push(`const FULL_GPIO_DAC = { ...FULL_GPIO, analogInput: YES, analogOutput: YES } as const;`);
261
+ }
262
+ if (usedCaps.has('INPUT_ONLY')) {
263
+ lines.push(`const INPUT_ONLY = {`);
264
+ lines.push(` digitalInput: YES, digitalOutput: NO,`);
265
+ lines.push(` analogInput: YES, analogOutput: NO,`);
266
+ lines.push(` pwm: NO, interrupt: YES,`);
267
+ lines.push(` pullUp: NO, pullDown: NO,`);
268
+ lines.push(` touch: NO, openDrain: NO,`);
269
+ lines.push(`} as const;`);
270
+ }
271
+ lines.push('');
272
+ // adc/touch helpers
273
+ lines.push(`function adc(n: number, ch: number) {`, ` return { type: 'adc' as const, instance: n, role: \`ch\${ch}\` };`, `}`);
274
+ if (spec.touch) {
275
+ lines.push(`function touch(ch: number) {`, ` return { type: 'touch' as const, instance: 0, role: \`touch\${ch}\` };`, `}`);
276
+ }
277
+ lines.push('');
278
+ // MCU definition
279
+ lines.push(`export const ${archUpper}: MCUDefinition = {`);
280
+ lines.push(` id: '${spec.mcuId}',`);
281
+ lines.push(` name: '${spec.mcuName}',`);
282
+ lines.push(` architecture: '${arch}',`);
283
+ lines.push(` memory: {`);
284
+ lines.push(` flash: ${spec.memory.flash},`);
285
+ lines.push(` sram: ${spec.memory.sram},`);
286
+ lines.push(` eeprom: ${spec.memory.eeprom},`);
287
+ if (spec.memory.rtcMemory)
288
+ lines.push(` rtcMemory: ${spec.memory.rtcMemory},`);
289
+ lines.push(` },`);
290
+ // pins.all
291
+ lines.push(` pins: {`);
292
+ lines.push(` all: [`);
293
+ for (const pin of spec.pins) {
294
+ const parts = [`number: ${pin.gpio}`, `gpio: ${pin.gpio}`, `name: 'GPIO${pin.gpio}'`, `capabilities: ${pin.capabilities}`];
295
+ if (pin.functions && pin.functions.length > 0) {
296
+ const fns = pin.functions.map(f => {
297
+ if (f.type === 'adc')
298
+ return `adc(${f.instance}, ${f.role.replace('ch', '')})`;
299
+ if (f.type === 'touch')
300
+ return `touch(${f.role.replace('touch', '').replace('Touch', '')})`;
301
+ return `{ type: '${f.type}', instance: ${f.instance}, role: '${f.role}' }`;
302
+ }).join(', ');
303
+ parts.push(`functions: [${fns}]`);
304
+ }
305
+ if (pin.alt && pin.alt.length > 0) {
306
+ parts.push(`alternateFunctions: [${pin.alt.map(a => `'${a}'`).join(', ')}]`);
307
+ }
308
+ if (pin.warnings && pin.warnings.length > 0) {
309
+ parts.push(`warnings: [${pin.warnings.map(w => `'${w}'`).join(', ')}]`);
310
+ }
311
+ if (pin.unsafe)
312
+ parts.push(`unsafe: true`);
313
+ if (pin.notes)
314
+ parts.push(`notes: '${pin.notes}'`);
315
+ if (pin.onboardLed)
316
+ parts.push(`onboardLed: true`);
317
+ lines.push(` { ${parts.join(', ')} },`);
318
+ }
319
+ lines.push(` ],`);
320
+ // digital/analog/pwm/unsafe arrays
321
+ const allNames = gpioNames(spec);
322
+ lines.push(` digital: [${allNames.map(n => `'${n}'`).join(', ')}],`);
323
+ lines.push(` analog: [${spec.analog.map(n => `'${n}'`).join(', ')}],`);
324
+ // pwm = all GPIOs minus the unsafe flash/USB/strap pins at the end (use digital list minus unsafe)
325
+ const unsafeSet = new Set(spec.unsafe);
326
+ const pwmPins = allNames.filter(n => !unsafeSet.has(n) || true); // include all — pwm is permissive
327
+ lines.push(` pwm: [${pwmPins.map(n => `'${n}'`).join(', ')}],`);
328
+ lines.push(` unsafe: [${spec.unsafe.map(n => `'${n}'`).join(', ')}],`);
329
+ // bus maps
330
+ const i2cKey = Object.keys(spec.i2c)[0];
331
+ const i2cPins = spec.i2c[i2cKey];
332
+ lines.push(` i2c: { ${i2cKey}: { sda: '${i2cPins.sda}', scl: '${i2cPins.scl}' } },`);
333
+ const spiKey = Object.keys(spec.spi)[0];
334
+ const spiPins = spec.spi[spiKey];
335
+ lines.push(` spi: { ${spiKey}: { mosi: '${spiPins.mosi}', miso: '${spiPins.miso}', sck: '${spiPins.sck}', cs: '${spiPins.cs}' } },`);
336
+ const uartKey = Object.keys(spec.uart)[0];
337
+ const uartPins = spec.uart[uartKey];
338
+ lines.push(` uart: { ${uartKey}: { tx: '${uartPins.tx}', rx: '${uartPins.rx}' } },`);
339
+ lines.push(` },`);
340
+ lines.push(` peripherals: MCU_PERIPHERALS,`);
341
+ // features
342
+ const f = spec.features;
343
+ lines.push(` features: {`);
344
+ lines.push(` multicore: ${f.multicore},`);
345
+ lines.push(` coreCount: ${f.coreCount},`);
346
+ lines.push(` deepSleep: ${f.deepSleep},`);
347
+ lines.push(` watchdog: ${f.watchdog},`);
348
+ lines.push(` externalInterrupts: ${f.externalInterrupts},`);
349
+ lines.push(` hardwareRng: ${f.hardwareRng},`);
350
+ lines.push(` fpu: ${f.fpu},`);
351
+ lines.push(` },`);
352
+ lines.push(` build: { extraFlags: [] },`);
353
+ lines.push(`};`);
354
+ lines.push('');
355
+ lines.push(`export default ${archUpper};`);
356
+ lines.push('');
357
+ lines.push(`export * from './pins.js';`);
358
+ lines.push(`export * from './peripherals.js';`);
359
+ lines.push('');
360
+ // TypeCADManifest
361
+ lines.push('/**');
362
+ lines.push(' * Structured manifest consumed by the TypeCAD CLI for contract-based');
363
+ lines.push(' * board generation.');
364
+ lines.push(' */');
365
+ lines.push('export const TypeCADManifest = {');
366
+ lines.push(` pinNames: [${allNames.map(n => `'${n}'`).join(', ')}] as const,`);
367
+ const periNames = [];
368
+ spec.peripheralInstances.i2c.forEach((_, i) => periNames.push(`'I2C${i}'`));
369
+ spec.peripheralInstances.spi.forEach((_, i) => periNames.push(`'SPI${i}'`));
370
+ spec.peripheralInstances.uart.forEach((_, i) => periNames.push(`'UART${i}'`));
371
+ lines.push(` peripheralNames: [${periNames.join(', ')}] as const,`);
372
+ lines.push('} as const;');
373
+ lines.push('');
374
+ return lines.join('\n');
375
+ }
376
+ // ---------------------------------------------------------------------------
377
+ // Board package generators
378
+ // ---------------------------------------------------------------------------
379
+ export function genBoardPackageJson(spec) {
380
+ const pkg = {
381
+ name: `@typecad/board-${spec.architecture}`,
382
+ version: '0.1.0',
383
+ description: `TypeCAD ${spec.boardName} board definition with typed pins and peripherals`,
384
+ type: 'module',
385
+ main: './dist/index.js',
386
+ types: './dist/index.d.ts',
387
+ exports: { '.': { types: './dist/index.d.ts', default: './dist/index.js' } },
388
+ files: ['dist'],
389
+ scripts: { build: 'tsc' },
390
+ dependencies: {
391
+ '@typecad/cuttlefish': '*',
392
+ '@typecad/hal': '*',
393
+ [`@typecad/mcu-${spec.architecture}`]: '*',
394
+ },
395
+ license: 'MIT',
396
+ publishConfig: { access: 'public' },
397
+ };
398
+ return JSON.stringify(pkg, null, 2) + '\n';
399
+ }
400
+ export function genBoardTsconfig(spec) {
401
+ return JSON.stringify({
402
+ compilerOptions: {
403
+ composite: true, target: 'ES2021', module: 'Node16', moduleResolution: 'Node16',
404
+ strict: true, esModuleInterop: true, skipLibCheck: true,
405
+ forceConsistentCasingInFileNames: true, declaration: true, declarationMap: true,
406
+ sourceMap: true, rootDir: 'src', outDir: 'dist',
407
+ experimentalDecorators: true, emitDecoratorMetadata: true,
408
+ },
409
+ include: ['src/**/*.ts'],
410
+ references: [
411
+ { path: '../hal' }, { path: '../cuttlefish' }, { path: `../mcu-${spec.architecture}` },
412
+ ],
413
+ }, null, 2) + '\n';
414
+ }
415
+ export function genBoardAnalog(_spec) {
416
+ return [
417
+ '// ---------------------------------------------------------------------------',
418
+ `// @typecad/board-${_spec.architecture} — Analog constants`,
419
+ '// ---------------------------------------------------------------------------',
420
+ '',
421
+ '/** Default reference (3.3V). */',
422
+ 'export const DEFAULT = 0;',
423
+ '/** Internal 1.1V reference. */',
424
+ 'export const INTERNAL = 3;',
425
+ '',
426
+ ].join('\n');
427
+ }
428
+ export function genBoardPins(spec) {
429
+ const arch = spec.architecture;
430
+ // Dx aliases: GPIO in range, excluding unsafe flash pins (those at the end
431
+ // whose alt names start with "SPI"). We include all non-flash GPIOs.
432
+ const unsafeFlashPins = new Set(spec.pins.filter(p => p.unsafe && p.alt?.some(a => a.startsWith('SPI'))).map(p => p.gpio));
433
+ const dPins = gpioList(spec).filter(n => !unsafeFlashPins.has(n));
434
+ // Ax aliases: from spec.analog (ADC1 only)
435
+ const aPins = spec.analog.map(name => parseInt(name.replace('GPIO', ''), 10));
436
+ // Bus instance counts
437
+ const i2cCount = spec.peripheralInstances.i2c.length;
438
+ const spiCount = spec.peripheralInstances.spi.length;
439
+ const uartCount = spec.peripheralInstances.uart.length;
440
+ const i2cNames = Array.from({ length: i2cCount }, (_, i) => `I2C${i}`).join(', ');
441
+ const spiNames = Array.from({ length: spiCount }, (_, i) => `SPI${i}`).join(', ');
442
+ const uartNames = Array.from({ length: uartCount }, (_, i) => `UART${i}`).join(', ');
443
+ const lines = [
444
+ `// ---------------------------------------------------------------------------`,
445
+ `// @typecad/board-${arch} — Pin aliases`,
446
+ `// ---------------------------------------------------------------------------`,
447
+ '',
448
+ ];
449
+ // Import GPIO constants from MCU (only the ones we alias)
450
+ const allImportedGpio = Array.from(new Set([...dPins, ...aPins])).sort((a, b) => a - b);
451
+ const importList = allImportedGpio.map(n => `GPIO${n}`).join(', ');
452
+ lines.push(`import {`);
453
+ lines.push(` ${importList},`);
454
+ lines.push(`} from '@typecad/mcu-${arch}';`);
455
+ lines.push('');
456
+ // Dx aliases
457
+ lines.push(`// Arduino-style digital pin aliases (D-numbers match GPIO numbers)`);
458
+ for (const n of dPins) {
459
+ lines.push(`export const D${n} = GPIO${n};`);
460
+ }
461
+ lines.push('');
462
+ // Ax aliases
463
+ lines.push(`// Analog input aliases (ADC1 channels — usable while Wi-Fi is active).`);
464
+ aPins.forEach((n, i) => {
465
+ lines.push(`export const A${i} = GPIO${n};`);
466
+ });
467
+ lines.push('');
468
+ // Bus re-exports
469
+ lines.push(`// Bus aliases (default pins for I2C0 / SPI0 / UART0)`);
470
+ lines.push(`export { ${i2cNames}, ${spiNames}, ${uartNames} } from '@typecad/mcu-${arch}';`);
471
+ lines.push('');
472
+ return lines.join('\n');
473
+ }
474
+ export function genBoardIndex(spec) {
475
+ const arch = spec.architecture;
476
+ const archUpper = arch.toUpperCase();
477
+ const boardName = spec.boardName;
478
+ const desc = spec.description || `${spec.mcuName} generic devboard`;
479
+ // Dx pins (non-flash)
480
+ const unsafeFlashPins = new Set(spec.pins.filter(p => p.unsafe && p.alt?.some(a => a.startsWith('SPI'))).map(p => p.gpio));
481
+ const dPins = gpioList(spec).filter(n => !unsafeFlashPins.has(n));
482
+ // Analog GPIOs
483
+ const aGpios = spec.analog.map(name => `GPIO${parseInt(name.replace('GPIO', ''), 10)}`);
484
+ const lines = [
485
+ `// ---------------------------------------------------------------------------`,
486
+ `// @typecad/board-${arch} — Board definition manifest`,
487
+ `// ---------------------------------------------------------------------------`,
488
+ '',
489
+ `import type { BoardDefinition } from '@typecad/cuttlefish/api/schema';`,
490
+ `import { ${archUpper} } from '@typecad/mcu-${arch}';`,
491
+ '',
492
+ `const ARDUINO_CORE_VERSION = '10819';`,
493
+ '',
494
+ `export const ${archUpper}Board: BoardDefinition = {`,
495
+ ` id: '${spec.boardId}',`,
496
+ ` name: '${boardName}',`,
497
+ ` vendor: '${spec.vendor}',`,
498
+ ` description: '${desc.replace(/'/g, "\\'")}',`,
499
+ '',
500
+ ` mcu: ${archUpper},`,
501
+ ` clockSpeed: ${spec.clockSpeed},`,
502
+ '',
503
+ ];
504
+ // Memory
505
+ lines.push(` memory: {`);
506
+ if (spec.moduleFlash)
507
+ lines.push(` flash: ${spec.moduleFlash},`);
508
+ if (spec.externalRam)
509
+ lines.push(` externalRam: ${spec.externalRam},`);
510
+ lines.push(` },`);
511
+ lines.push('');
512
+ // Pins (spread MCU, no led for generic boards)
513
+ lines.push(` pins: {`);
514
+ lines.push(` ...${archUpper}.pins,`);
515
+ lines.push(` },`);
516
+ lines.push('');
517
+ // Peripherals with aliases
518
+ const i2cCount = spec.peripheralInstances.i2c.length;
519
+ const spiCount = spec.peripheralInstances.spi.length;
520
+ const uartCount = spec.peripheralInstances.uart.length;
521
+ lines.push(` peripherals: {`);
522
+ lines.push(` ...${archUpper}.peripherals,`);
523
+ lines.push(` aliases: {`);
524
+ const aliasEntries = [];
525
+ for (let i = 0; i < uartCount; i++)
526
+ aliasEntries.push(`UART${i}: 'Serial${i === 0 ? '' : i + 1}'`);
527
+ for (let i = 0; i < i2cCount; i++)
528
+ aliasEntries.push(`I2C${i}: 'Wire${i === 0 ? '' : i + 1}'`);
529
+ for (let i = 0; i < spiCount; i++)
530
+ aliasEntries.push(`SPI${i}: 'SPI${i === 0 ? '' : i + 1}'`);
531
+ lines.push(` ${aliasEntries.join(', ')},`);
532
+ lines.push(` },`);
533
+ lines.push(` },`);
534
+ lines.push('');
535
+ // Build config
536
+ lines.push(` build: {`);
537
+ lines.push(` frameworks: {`);
538
+ lines.push(` platformio: '${spec.platformioTarget}',`);
539
+ lines.push(` arduino: '${spec.fqbn}',`);
540
+ lines.push(` },`);
541
+ lines.push(` defines: {`);
542
+ lines.push(` F_CPU: '${spec.clockSpeed}UL',`);
543
+ lines.push(` ARDUINO: ARDUINO_CORE_VERSION,`);
544
+ lines.push(` ${spec.arduinoDefine}: '1',`);
545
+ lines.push(` },`);
546
+ lines.push(` },`);
547
+ lines.push(`};`);
548
+ lines.push('');
549
+ lines.push(`export default ${archUpper}Board;`);
550
+ lines.push('');
551
+ lines.push(`export * from '@typecad/mcu-${arch}';`);
552
+ lines.push('');
553
+ // HAL re-exports
554
+ lines.push(`export {`);
555
+ lines.push(` HIGH, LOW, INPUT, OUTPUT, INPUT_PULLUP,`);
556
+ lines.push(` delay, millis, micros, delayMicroseconds,`);
557
+ lines.push(` map, constrain,`);
558
+ lines.push(` abs, min, max, Num,`);
559
+ lines.push(` pulseIn, pulseInLong, Pulse,`);
560
+ lines.push(` shiftIn, shiftOut, Shift,`);
561
+ lines.push(` randomSeed, random, Random,`);
562
+ lines.push(` noInterrupts, interrupts, attachInterrupt, detachInterrupt,`);
563
+ lines.push(` ADC, AsyncClass, Async`);
564
+ lines.push(`} from '@typecad/hal';`);
565
+ lines.push('');
566
+ // Discovery arrays — import GPIO constants
567
+ const discoveryGpio = dPins.map(n => `GPIO${n}`).join(', ');
568
+ const analogGpio = aGpios.join(', ');
569
+ lines.push(`import {`);
570
+ lines.push(` ${discoveryGpio},`);
571
+ lines.push(`} from '@typecad/mcu-${arch}';`);
572
+ lines.push('');
573
+ lines.push(`export const pins = {`);
574
+ lines.push(` pwm: [${discoveryGpio}] as const,`);
575
+ lines.push(` analog: [${analogGpio}] as const,`);
576
+ lines.push(` interrupt: [${discoveryGpio}] as const,`);
577
+ lines.push(` digital: [${discoveryGpio}] as const,`);
578
+ lines.push(`} as const;`);
579
+ lines.push('');
580
+ // PeripheralPins
581
+ lines.push(`export const PeripheralPins = {`);
582
+ const i2cKey = Object.keys(spec.i2c)[0];
583
+ const i2cPins = spec.i2c[i2cKey];
584
+ lines.push(` I2C0: { SDA: '${i2cPins.sda}', SCL: '${i2cPins.scl}' } as const,`);
585
+ const spiKey = Object.keys(spec.spi)[0];
586
+ const spiPins = spec.spi[spiKey];
587
+ lines.push(` SPI0: { MOSI: '${spiPins.mosi}', MISO: '${spiPins.miso}', SCK: '${spiPins.sck}', CS: '${spiPins.cs}' } as const,`);
588
+ const uartKey = Object.keys(spec.uart)[0];
589
+ const uartPins = spec.uart[uartKey];
590
+ lines.push(` UART0: { TX: '${uartPins.tx}', RX: '${uartPins.rx}' } as const,`);
591
+ if (uartCount > 1) {
592
+ lines.push(` UART1: { TX: 'remappable', RX: 'remappable' } as const,`);
593
+ }
594
+ lines.push(`} as const;`);
595
+ lines.push('');
596
+ lines.push(`export * from './pins.js';`);
597
+ lines.push(`export * from './analog.js';`);
598
+ lines.push(`export { Board } from './board.js';`);
599
+ lines.push('');
600
+ return lines.join('\n');
601
+ }
602
+ export function genBoardNamespace(spec) {
603
+ const arch = spec.architecture;
604
+ const archUpper = arch.toUpperCase();
605
+ // Dx pins (non-flash)
606
+ const unsafeFlashPins = new Set(spec.pins.filter(p => p.unsafe && p.alt?.some(a => a.startsWith('SPI'))).map(p => p.gpio));
607
+ const dPins = gpioList(spec).filter(n => !unsafeFlashPins.has(n));
608
+ const aCount = spec.analog.length;
609
+ const dNames = dPins.map(n => `D${n}`);
610
+ const aNames = Array.from({ length: aCount }, (_, i) => `A${i}`);
611
+ const i2cCount = spec.peripheralInstances.i2c.length;
612
+ const spiCount = spec.peripheralInstances.spi.length;
613
+ const uartCount = spec.peripheralInstances.uart.length;
614
+ const periNames = [];
615
+ for (let i = 0; i < i2cCount; i++)
616
+ periNames.push(`I2C${i}`);
617
+ for (let i = 0; i < spiCount; i++)
618
+ periNames.push(`SPI${i}`);
619
+ for (let i = 0; i < uartCount; i++)
620
+ periNames.push(`UART${i}`);
621
+ const lines = [
622
+ `// ---------------------------------------------------------------------------`,
623
+ `// @typecad/board-${arch} — Board namespace`,
624
+ `// ---------------------------------------------------------------------------`,
625
+ '',
626
+ `import type { BoardDefinition } from '@typecad/cuttlefish/api/schema';`,
627
+ '',
628
+ `import {`,
629
+ ` ${dNames.join(', ')},`,
630
+ ` ${aNames.join(', ')},`,
631
+ `} from './pins.js';`,
632
+ '',
633
+ `import { ${periNames.join(', ')} } from '@typecad/mcu-${arch}';`,
634
+ `import { ${archUpper}Board } from './index.js';`,
635
+ '',
636
+ `export const Board = {`,
637
+ ` definition: ${archUpper}Board,`,
638
+ '',
639
+ ` ${dNames.join(', ')},`,
640
+ ` ${aNames.join(', ')},`,
641
+ '',
642
+ ` ${periNames.join(', ')},`,
643
+ '',
644
+ ` digital: { ${dNames.join(', ')} },`,
645
+ ` analog: { ${aNames.join(', ')} },`,
646
+ `};`,
647
+ '',
648
+ `export default Board;`,
649
+ '',
650
+ ];
651
+ return lines.join('\n');
652
+ }