@wenathlan/saddle 1.8.18 → 2.0.2

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 (802) hide show
  1. package/Dockerfile +1339 -0
  2. package/README.md +33 -12
  3. package/alternatives.ts +1218 -0
  4. package/biome.json +153 -0
  5. package/boards.json +1517 -0
  6. package/compute.ts +3144 -0
  7. package/cores.json +1801 -0
  8. package/dist/acquisition.d.ts +359 -0
  9. package/dist/acquisition.d.ts.map +1 -0
  10. package/dist/acquisition.js +629 -0
  11. package/dist/acquisition.js.map +1 -0
  12. package/dist/alternatives.d.ts +509 -0
  13. package/dist/alternatives.d.ts.map +1 -0
  14. package/dist/alternatives.js +951 -0
  15. package/dist/alternatives.js.map +1 -0
  16. package/dist/automation.d.ts +426 -0
  17. package/dist/automation.d.ts.map +1 -0
  18. package/dist/automation.js +561 -0
  19. package/dist/automation.js.map +1 -0
  20. package/dist/browser.d.ts +562 -0
  21. package/dist/browser.d.ts.map +1 -0
  22. package/dist/browser.js +1057 -0
  23. package/dist/browser.js.map +1 -0
  24. package/dist/capacitor.config.d.ts +13 -0
  25. package/dist/capacitor.config.d.ts.map +1 -0
  26. package/dist/capacitor.config.js +26 -0
  27. package/dist/capacitor.config.js.map +1 -0
  28. package/dist/cli.d.ts +17 -0
  29. package/dist/cli.d.ts.map +1 -0
  30. package/dist/cli.js +111 -0
  31. package/dist/cli.js.map +1 -0
  32. package/dist/communication.d.ts +192 -0
  33. package/dist/communication.d.ts.map +1 -0
  34. package/dist/communication.js +418 -0
  35. package/dist/communication.js.map +1 -0
  36. package/dist/compute.d.ts +1161 -0
  37. package/dist/compute.d.ts.map +1 -0
  38. package/dist/compute.js +2273 -0
  39. package/dist/compute.js.map +1 -0
  40. package/dist/distribution.d.ts +529 -0
  41. package/dist/distribution.d.ts.map +1 -0
  42. package/dist/distribution.js +811 -0
  43. package/dist/distribution.js.map +1 -0
  44. package/dist/execution.d.ts +530 -0
  45. package/dist/execution.d.ts.map +1 -0
  46. package/dist/execution.js +761 -0
  47. package/dist/execution.js.map +1 -0
  48. package/dist/format.d.ts +19 -0
  49. package/dist/format.d.ts.map +1 -0
  50. package/dist/format.js +60 -0
  51. package/dist/format.js.map +1 -0
  52. package/dist/foundation.d.ts +176 -0
  53. package/dist/foundation.d.ts.map +1 -0
  54. package/dist/foundation.js +309 -0
  55. package/dist/foundation.js.map +1 -0
  56. package/dist/index.d.ts +733 -123
  57. package/dist/index.d.ts.map +1 -1
  58. package/dist/index.js +1018 -123
  59. package/dist/index.js.map +1 -1
  60. package/dist/integration.d.ts +236 -0
  61. package/dist/integration.d.ts.map +1 -0
  62. package/dist/integration.js +236 -0
  63. package/dist/integration.js.map +1 -0
  64. package/dist/intelligence.d.ts +94 -0
  65. package/dist/intelligence.d.ts.map +1 -0
  66. package/dist/intelligence.js +145 -0
  67. package/dist/intelligence.js.map +1 -0
  68. package/dist/{isolation/contracts.d.ts → isolation.d.ts} +12 -1
  69. package/dist/isolation.d.ts.map +1 -0
  70. package/dist/{isolation/contracts.js → isolation.js} +13 -1
  71. package/dist/isolation.js.map +1 -0
  72. package/dist/media.d.ts +344 -0
  73. package/dist/media.d.ts.map +1 -0
  74. package/dist/media.js +986 -0
  75. package/dist/media.js.map +1 -0
  76. package/dist/modes.d.ts +359 -0
  77. package/dist/modes.d.ts.map +1 -0
  78. package/dist/modes.js +134 -0
  79. package/dist/modes.js.map +1 -0
  80. package/dist/{library/public.d.ts → operations.d.ts} +15 -1
  81. package/dist/operations.d.ts.map +1 -0
  82. package/dist/{library/public.js → operations.js} +18 -7
  83. package/dist/operations.js.map +1 -0
  84. package/dist/orchestrator.d.ts +1339 -0
  85. package/dist/orchestrator.d.ts.map +1 -0
  86. package/dist/orchestrator.js +4308 -0
  87. package/dist/orchestrator.js.map +1 -0
  88. package/dist/performance.d.ts +416 -0
  89. package/dist/performance.d.ts.map +1 -0
  90. package/dist/performance.js +827 -0
  91. package/dist/performance.js.map +1 -0
  92. package/dist/quantum.d.ts +810 -0
  93. package/dist/quantum.d.ts.map +1 -0
  94. package/dist/quantum.js +2073 -0
  95. package/dist/quantum.js.map +1 -0
  96. package/dist/render.d.ts +381 -0
  97. package/dist/render.d.ts.map +1 -0
  98. package/dist/render.js +1073 -0
  99. package/dist/render.js.map +1 -0
  100. package/dist/scheduler.d.ts +596 -0
  101. package/dist/scheduler.d.ts.map +1 -0
  102. package/dist/scheduler.js +1259 -0
  103. package/dist/scheduler.js.map +1 -0
  104. package/dist/security.d.ts +501 -0
  105. package/dist/security.d.ts.map +1 -0
  106. package/dist/security.js +1170 -0
  107. package/dist/security.js.map +1 -0
  108. package/dist/server.d.ts +21 -0
  109. package/dist/server.d.ts.map +1 -0
  110. package/dist/{server/node.js → server.js} +16 -2
  111. package/dist/server.js.map +1 -0
  112. package/dist/tiers.d.ts +1002 -0
  113. package/dist/tiers.d.ts.map +1 -0
  114. package/dist/tiers.js +2165 -0
  115. package/dist/tiers.js.map +1 -0
  116. package/dist/virtual.d.ts +641 -0
  117. package/dist/virtual.d.ts.map +1 -0
  118. package/dist/virtual.js +1285 -0
  119. package/dist/virtual.js.map +1 -0
  120. package/dist/virtualcpu.d.ts +316 -0
  121. package/dist/virtualcpu.d.ts.map +1 -0
  122. package/dist/virtualcpu.js +1180 -0
  123. package/dist/virtualcpu.js.map +1 -0
  124. package/dist/virtualgpu.d.ts +345 -0
  125. package/dist/virtualgpu.d.ts.map +1 -0
  126. package/dist/virtualgpu.js +1000 -0
  127. package/dist/virtualgpu.js.map +1 -0
  128. package/dist/virtualization.d.ts +607 -0
  129. package/dist/virtualization.d.ts.map +1 -0
  130. package/dist/virtualization.js +1187 -0
  131. package/dist/virtualization.js.map +1 -0
  132. package/dist/virtualmemory.d.ts +818 -0
  133. package/dist/virtualmemory.d.ts.map +1 -0
  134. package/dist/virtualmemory.js +1796 -0
  135. package/dist/virtualmemory.js.map +1 -0
  136. package/dist/webscrape.d.ts +720 -0
  137. package/dist/webscrape.d.ts.map +1 -0
  138. package/dist/webscrape.js +2697 -0
  139. package/dist/webscrape.js.map +1 -0
  140. package/docker.config +769 -0
  141. package/docs/CONVERSA.txt +1523 -0
  142. package/docs/alternatives.md +499 -0
  143. package/docs/architecture-1.8.19.md +76 -0
  144. package/docs/architecture-1.8.19.mmd +33 -0
  145. package/docs/architecture-1.8.19.png +0 -0
  146. package/docs/architecture.md +355 -0
  147. package/docs/brancharchive-2026-08-18.md +18 -0
  148. package/docs/browser.md +7 -0
  149. package/docs/consolidation.md +70 -0
  150. package/docs/e2ugh-engine.md +528 -0
  151. package/{dist/examples/localjob.js → docs/example-localjob.ts} +3 -3
  152. package/{dist/examples/publicapi.js → docs/example-publicapi.ts} +2 -2
  153. package/docs/hardware.md +342 -0
  154. package/docs/optimization.md +126 -0
  155. package/docs/performance.md +499 -0
  156. package/docs/planning.1.8.18.md +94 -0
  157. package/docs/planning.1.8.19.md +49 -0
  158. package/docs/releasenotes-1.8.19.md +35 -0
  159. package/docs/research-1.8.19-virtual-browser.md +27 -0
  160. package/docs/security.md +454 -0
  161. package/docs/todo-1.8.18.md +12 -0
  162. package/docs/todo-1.8.19.md +241 -0
  163. package/docs/viability.md +777 -0
  164. package/docs/virtualization.md +335 -0
  165. package/docs/web-duplicatecleanup.md +9 -0
  166. package/docs/web-ideas.md +106 -0
  167. package/docs/workflowimprovements-2026-08-19.md +70 -0
  168. package/gpumonitor.cpp +1543 -0
  169. package/gpus.json +2408 -0
  170. package/index.ts +1478 -0
  171. package/media.ts +1337 -0
  172. package/mttg.config +1549 -0
  173. package/orchestrator.ts +5462 -0
  174. package/package.json +304 -56
  175. package/passage.config +1331 -0
  176. package/performance.ts +1049 -0
  177. package/processors.json +2217 -0
  178. package/qemu.config +1062 -0
  179. package/qemubridge.py +1340 -0
  180. package/quantum.ts +2393 -0
  181. package/render.ts +1325 -0
  182. package/scheduler.ts +1600 -0
  183. package/security.ts +1449 -0
  184. package/tiers.ts +2871 -0
  185. package/tsconfig.json +29 -0
  186. package/virtualcpu.ts +1273 -0
  187. package/virtualgpu.ts +1181 -0
  188. package/virtualhardware.c +1011 -0
  189. package/virtualhardware.json +739 -0
  190. package/virtualization.ts +1628 -0
  191. package/virtualizationcore.cpp +4635 -0
  192. package/virtualmemory.ts +2303 -0
  193. package/vm.config.json +1910 -0
  194. package/{extension → web/extension}/manifest.json +1 -1
  195. package/web/readme.md +382 -0
  196. package/web/tsconfig.json +25 -0
  197. package/dist/adapters/forge.d.ts +0 -17
  198. package/dist/adapters/forge.d.ts.map +0 -1
  199. package/dist/adapters/forge.js +0 -19
  200. package/dist/adapters/forge.js.map +0 -1
  201. package/dist/adapters/forgejo.d.ts +0 -49
  202. package/dist/adapters/forgejo.d.ts.map +0 -1
  203. package/dist/adapters/forgejo.js +0 -8
  204. package/dist/adapters/forgejo.js.map +0 -1
  205. package/dist/adapters/github.d.ts +0 -12
  206. package/dist/adapters/github.d.ts.map +0 -1
  207. package/dist/adapters/github.js +0 -20
  208. package/dist/adapters/github.js.map +0 -1
  209. package/dist/adapters/gitlab.d.ts +0 -17
  210. package/dist/adapters/gitlab.d.ts.map +0 -1
  211. package/dist/adapters/gitlab.js +0 -10
  212. package/dist/adapters/gitlab.js.map +0 -1
  213. package/dist/adapters/huggingface.d.ts +0 -17
  214. package/dist/adapters/huggingface.d.ts.map +0 -1
  215. package/dist/adapters/huggingface.js +0 -6
  216. package/dist/adapters/huggingface.js.map +0 -1
  217. package/dist/adapters/socket.d.ts +0 -11
  218. package/dist/adapters/socket.d.ts.map +0 -1
  219. package/dist/adapters/socket.js +0 -17
  220. package/dist/adapters/socket.js.map +0 -1
  221. package/dist/adapters/transport.d.ts +0 -7
  222. package/dist/adapters/transport.d.ts.map +0 -1
  223. package/dist/adapters/transport.js +0 -36
  224. package/dist/adapters/transport.js.map +0 -1
  225. package/dist/ai/chunk.d.ts +0 -2
  226. package/dist/ai/chunk.d.ts.map +0 -1
  227. package/dist/ai/chunk.js +0 -36
  228. package/dist/ai/chunk.js.map +0 -1
  229. package/dist/ai/llmstxt.d.ts +0 -6
  230. package/dist/ai/llmstxt.d.ts.map +0 -1
  231. package/dist/ai/llmstxt.js +0 -12
  232. package/dist/ai/llmstxt.js.map +0 -1
  233. package/dist/ai/provenance.d.ts +0 -22
  234. package/dist/ai/provenance.d.ts.map +0 -1
  235. package/dist/ai/provenance.js +0 -25
  236. package/dist/ai/provenance.js.map +0 -1
  237. package/dist/ai/rag.d.ts +0 -26
  238. package/dist/ai/rag.d.ts.map +0 -1
  239. package/dist/ai/rag.js +0 -22
  240. package/dist/ai/rag.js.map +0 -1
  241. package/dist/ai/tokens.d.ts +0 -15
  242. package/dist/ai/tokens.d.ts.map +0 -1
  243. package/dist/ai/tokens.js +0 -9
  244. package/dist/ai/tokens.js.map +0 -1
  245. package/dist/api/auth.d.ts +0 -16
  246. package/dist/api/auth.d.ts.map +0 -1
  247. package/dist/api/auth.js +0 -19
  248. package/dist/api/auth.js.map +0 -1
  249. package/dist/api/contracts.d.ts +0 -28
  250. package/dist/api/contracts.d.ts.map +0 -1
  251. package/dist/api/contracts.js +0 -14
  252. package/dist/api/contracts.js.map +0 -1
  253. package/dist/api/control.d.ts +0 -10
  254. package/dist/api/control.d.ts.map +0 -1
  255. package/dist/api/control.js +0 -35
  256. package/dist/api/control.js.map +0 -1
  257. package/dist/api/http.d.ts +0 -7
  258. package/dist/api/http.d.ts.map +0 -1
  259. package/dist/api/http.js +0 -12
  260. package/dist/api/http.js.map +0 -1
  261. package/dist/api/rate.d.ts +0 -28
  262. package/dist/api/rate.d.ts.map +0 -1
  263. package/dist/api/rate.js +0 -36
  264. package/dist/api/rate.js.map +0 -1
  265. package/dist/api/security.d.ts +0 -12
  266. package/dist/api/security.d.ts.map +0 -1
  267. package/dist/api/security.js +0 -56
  268. package/dist/api/security.js.map +0 -1
  269. package/dist/api/service.d.ts +0 -5
  270. package/dist/api/service.d.ts.map +0 -1
  271. package/dist/api/service.js +0 -70
  272. package/dist/api/service.js.map +0 -1
  273. package/dist/apps/registry.d.ts +0 -33
  274. package/dist/apps/registry.d.ts.map +0 -1
  275. package/dist/apps/registry.js +0 -24
  276. package/dist/apps/registry.js.map +0 -1
  277. package/dist/binary/archive.d.ts +0 -27
  278. package/dist/binary/archive.d.ts.map +0 -1
  279. package/dist/binary/archive.js +0 -46
  280. package/dist/binary/archive.js.map +0 -1
  281. package/dist/binary/build.d.ts +0 -29
  282. package/dist/binary/build.d.ts.map +0 -1
  283. package/dist/binary/build.js +0 -17
  284. package/dist/binary/build.js.map +0 -1
  285. package/dist/binary/transform.d.ts +0 -70
  286. package/dist/binary/transform.d.ts.map +0 -1
  287. package/dist/binary/transform.js +0 -105
  288. package/dist/binary/transform.js.map +0 -1
  289. package/dist/bot/adapter.d.ts +0 -5
  290. package/dist/bot/adapter.d.ts.map +0 -1
  291. package/dist/bot/adapter.js +0 -11
  292. package/dist/bot/adapter.js.map +0 -1
  293. package/dist/bot/bot.d.ts +0 -28
  294. package/dist/bot/bot.d.ts.map +0 -1
  295. package/dist/bot/bot.js +0 -52
  296. package/dist/bot/bot.js.map +0 -1
  297. package/dist/bot/commands.d.ts +0 -8
  298. package/dist/bot/commands.d.ts.map +0 -1
  299. package/dist/bot/commands.js +0 -19
  300. package/dist/bot/commands.js.map +0 -1
  301. package/dist/bot/permissions.d.ts +0 -13
  302. package/dist/bot/permissions.d.ts.map +0 -1
  303. package/dist/bot/permissions.js +0 -16
  304. package/dist/bot/permissions.js.map +0 -1
  305. package/dist/browser/actions.d.ts +0 -33
  306. package/dist/browser/actions.d.ts.map +0 -1
  307. package/dist/browser/actions.js +0 -44
  308. package/dist/browser/actions.js.map +0 -1
  309. package/dist/browser/agent.d.ts +0 -21
  310. package/dist/browser/agent.d.ts.map +0 -1
  311. package/dist/browser/agent.js +0 -13
  312. package/dist/browser/agent.js.map +0 -1
  313. package/dist/browser/context.d.ts +0 -43
  314. package/dist/browser/context.d.ts.map +0 -1
  315. package/dist/browser/context.js +0 -54
  316. package/dist/browser/context.js.map +0 -1
  317. package/dist/browser/fingerprint.d.ts +0 -4
  318. package/dist/browser/fingerprint.d.ts.map +0 -1
  319. package/dist/browser/fingerprint.js +0 -12
  320. package/dist/browser/fingerprint.js.map +0 -1
  321. package/dist/browser/index.d.ts +0 -11
  322. package/dist/browser/index.d.ts.map +0 -1
  323. package/dist/browser/index.js +0 -11
  324. package/dist/browser/index.js.map +0 -1
  325. package/dist/browser/playwright.d.ts +0 -11
  326. package/dist/browser/playwright.d.ts.map +0 -1
  327. package/dist/browser/playwright.js +0 -24
  328. package/dist/browser/playwright.js.map +0 -1
  329. package/dist/browser/recorder.d.ts +0 -21
  330. package/dist/browser/recorder.d.ts.map +0 -1
  331. package/dist/browser/recorder.js +0 -58
  332. package/dist/browser/recorder.js.map +0 -1
  333. package/dist/browser/session.d.ts +0 -14
  334. package/dist/browser/session.d.ts.map +0 -1
  335. package/dist/browser/session.js +0 -21
  336. package/dist/browser/session.js.map +0 -1
  337. package/dist/browser/snapshot.d.ts +0 -69
  338. package/dist/browser/snapshot.d.ts.map +0 -1
  339. package/dist/browser/snapshot.js +0 -133
  340. package/dist/browser/snapshot.js.map +0 -1
  341. package/dist/captcha/contract.d.ts +0 -35
  342. package/dist/captcha/contract.d.ts.map +0 -1
  343. package/dist/captcha/contract.js +0 -17
  344. package/dist/captcha/contract.js.map +0 -1
  345. package/dist/captcha/evidence.d.ts +0 -10
  346. package/dist/captcha/evidence.d.ts.map +0 -1
  347. package/dist/captcha/evidence.js +0 -9
  348. package/dist/captcha/evidence.js.map +0 -1
  349. package/dist/captcha/guard.d.ts +0 -23
  350. package/dist/captcha/guard.d.ts.map +0 -1
  351. package/dist/captcha/guard.js +0 -12
  352. package/dist/captcha/guard.js.map +0 -1
  353. package/dist/cli/main.d.ts +0 -4
  354. package/dist/cli/main.d.ts.map +0 -1
  355. package/dist/cli/main.js +0 -46
  356. package/dist/cli/main.js.map +0 -1
  357. package/dist/core/errors.d.ts +0 -84
  358. package/dist/core/errors.d.ts.map +0 -1
  359. package/dist/core/errors.js +0 -54
  360. package/dist/core/errors.js.map +0 -1
  361. package/dist/core/events.d.ts +0 -9
  362. package/dist/core/events.d.ts.map +0 -1
  363. package/dist/core/events.js +0 -21
  364. package/dist/core/events.js.map +0 -1
  365. package/dist/core/hash.d.ts +0 -10
  366. package/dist/core/hash.d.ts.map +0 -1
  367. package/dist/core/hash.js +0 -82
  368. package/dist/core/hash.js.map +0 -1
  369. package/dist/core/ids.d.ts +0 -10
  370. package/dist/core/ids.d.ts.map +0 -1
  371. package/dist/core/ids.js +0 -15
  372. package/dist/core/ids.js.map +0 -1
  373. package/dist/delivery/manifest.d.ts +0 -35
  374. package/dist/delivery/manifest.d.ts.map +0 -1
  375. package/dist/delivery/manifest.js +0 -68
  376. package/dist/delivery/manifest.js.map +0 -1
  377. package/dist/deploy/index.d.ts +0 -6
  378. package/dist/deploy/index.d.ts.map +0 -1
  379. package/dist/deploy/index.js +0 -6
  380. package/dist/deploy/index.js.map +0 -1
  381. package/dist/dispatch/resumable.d.ts +0 -102
  382. package/dist/dispatch/resumable.d.ts.map +0 -1
  383. package/dist/dispatch/resumable.js +0 -64
  384. package/dist/dispatch/resumable.js.map +0 -1
  385. package/dist/dispatch/workflow.d.ts +0 -6
  386. package/dist/dispatch/workflow.d.ts.map +0 -1
  387. package/dist/dispatch/workflow.js +0 -37
  388. package/dist/dispatch/workflow.js.map +0 -1
  389. package/dist/domain/artifacts.d.ts +0 -12
  390. package/dist/domain/artifacts.d.ts.map +0 -1
  391. package/dist/domain/artifacts.js +0 -14
  392. package/dist/domain/artifacts.js.map +0 -1
  393. package/dist/domain/jobs.d.ts +0 -12
  394. package/dist/domain/jobs.d.ts.map +0 -1
  395. package/dist/domain/jobs.js +0 -20
  396. package/dist/domain/jobs.js.map +0 -1
  397. package/dist/domain/providers.d.ts +0 -10
  398. package/dist/domain/providers.d.ts.map +0 -1
  399. package/dist/domain/providers.js +0 -8
  400. package/dist/domain/providers.js.map +0 -1
  401. package/dist/domain/runtime.d.ts +0 -14
  402. package/dist/domain/runtime.d.ts.map +0 -1
  403. package/dist/domain/runtime.js +0 -10
  404. package/dist/domain/runtime.js.map +0 -1
  405. package/dist/domain/sessions.d.ts +0 -12
  406. package/dist/domain/sessions.d.ts.map +0 -1
  407. package/dist/domain/sessions.js +0 -57
  408. package/dist/domain/sessions.js.map +0 -1
  409. package/dist/examples/localjob.d.ts +0 -2
  410. package/dist/examples/localjob.d.ts.map +0 -1
  411. package/dist/examples/localjob.js.map +0 -1
  412. package/dist/examples/publicapi.d.ts +0 -2
  413. package/dist/examples/publicapi.d.ts.map +0 -1
  414. package/dist/examples/publicapi.js.map +0 -1
  415. package/dist/extension/build.d.ts +0 -9
  416. package/dist/extension/build.d.ts.map +0 -1
  417. package/dist/extension/build.js +0 -85
  418. package/dist/extension/build.js.map +0 -1
  419. package/dist/extension/content.d.ts +0 -6
  420. package/dist/extension/content.d.ts.map +0 -1
  421. package/dist/extension/content.js +0 -135
  422. package/dist/extension/content.js.map +0 -1
  423. package/dist/extension/index.d.ts +0 -7
  424. package/dist/extension/index.d.ts.map +0 -1
  425. package/dist/extension/index.js +0 -7
  426. package/dist/extension/index.js.map +0 -1
  427. package/dist/extension/pagebridge.d.ts +0 -6
  428. package/dist/extension/pagebridge.d.ts.map +0 -1
  429. package/dist/extension/pagebridge.js +0 -42
  430. package/dist/extension/pagebridge.js.map +0 -1
  431. package/dist/extension/permissions.d.ts +0 -26
  432. package/dist/extension/permissions.d.ts.map +0 -1
  433. package/dist/extension/permissions.js +0 -28
  434. package/dist/extension/permissions.js.map +0 -1
  435. package/dist/extension/popup.d.ts +0 -5
  436. package/dist/extension/popup.d.ts.map +0 -1
  437. package/dist/extension/popup.js +0 -26
  438. package/dist/extension/popup.js.map +0 -1
  439. package/dist/extension/protocol.d.ts +0 -58
  440. package/dist/extension/protocol.d.ts.map +0 -1
  441. package/dist/extension/protocol.js +0 -101
  442. package/dist/extension/protocol.js.map +0 -1
  443. package/dist/extension/serviceworker.d.ts +0 -25
  444. package/dist/extension/serviceworker.d.ts.map +0 -1
  445. package/dist/extension/serviceworker.js +0 -102
  446. package/dist/extension/serviceworker.js.map +0 -1
  447. package/dist/extension/worker.d.ts +0 -28
  448. package/dist/extension/worker.d.ts.map +0 -1
  449. package/dist/extension/worker.js +0 -22
  450. package/dist/extension/worker.js.map +0 -1
  451. package/dist/format/check.d.ts +0 -8
  452. package/dist/format/check.d.ts.map +0 -1
  453. package/dist/format/check.js +0 -38
  454. package/dist/format/check.js.map +0 -1
  455. package/dist/isolation/contracts.d.ts.map +0 -1
  456. package/dist/isolation/contracts.js.map +0 -1
  457. package/dist/library/public.d.ts.map +0 -1
  458. package/dist/library/public.js.map +0 -1
  459. package/dist/mcp/browser.d.ts +0 -9
  460. package/dist/mcp/browser.d.ts.map +0 -1
  461. package/dist/mcp/browser.js +0 -13
  462. package/dist/mcp/browser.js.map +0 -1
  463. package/dist/mcp/server.d.ts +0 -35
  464. package/dist/mcp/server.d.ts.map +0 -1
  465. package/dist/mcp/server.js +0 -40
  466. package/dist/mcp/server.js.map +0 -1
  467. package/dist/mcp/transport.d.ts +0 -7
  468. package/dist/mcp/transport.d.ts.map +0 -1
  469. package/dist/mcp/transport.js +0 -17
  470. package/dist/mcp/transport.js.map +0 -1
  471. package/dist/memory/bridge.d.ts +0 -14
  472. package/dist/memory/bridge.d.ts.map +0 -1
  473. package/dist/memory/bridge.js +0 -16
  474. package/dist/memory/bridge.js.map +0 -1
  475. package/dist/memory/engine.d.ts +0 -38
  476. package/dist/memory/engine.d.ts.map +0 -1
  477. package/dist/memory/engine.js +0 -109
  478. package/dist/memory/engine.js.map +0 -1
  479. package/dist/memory/modes.d.ts +0 -43
  480. package/dist/memory/modes.d.ts.map +0 -1
  481. package/dist/memory/modes.js +0 -66
  482. package/dist/memory/modes.js.map +0 -1
  483. package/dist/memory/objects.d.ts +0 -21
  484. package/dist/memory/objects.d.ts.map +0 -1
  485. package/dist/memory/objects.js +0 -20
  486. package/dist/memory/objects.js.map +0 -1
  487. package/dist/memory/planner.d.ts +0 -66
  488. package/dist/memory/planner.d.ts.map +0 -1
  489. package/dist/memory/planner.js +0 -108
  490. package/dist/memory/planner.js.map +0 -1
  491. package/dist/memory/targets.d.ts +0 -78
  492. package/dist/memory/targets.d.ts.map +0 -1
  493. package/dist/memory/targets.js +0 -29
  494. package/dist/memory/targets.js.map +0 -1
  495. package/dist/memory/transforms.d.ts +0 -19
  496. package/dist/memory/transforms.d.ts.map +0 -1
  497. package/dist/memory/transforms.js +0 -14
  498. package/dist/memory/transforms.js.map +0 -1
  499. package/dist/modes/matrix.d.ts +0 -23
  500. package/dist/modes/matrix.d.ts.map +0 -1
  501. package/dist/modes/matrix.js +0 -18
  502. package/dist/modes/matrix.js.map +0 -1
  503. package/dist/modes/modes.d.ts +0 -33
  504. package/dist/modes/modes.d.ts.map +0 -1
  505. package/dist/modes/modes.js +0 -15
  506. package/dist/modes/modes.js.map +0 -1
  507. package/dist/modes/resolve.d.ts +0 -96
  508. package/dist/modes/resolve.d.ts.map +0 -1
  509. package/dist/modes/resolve.js +0 -48
  510. package/dist/modes/resolve.js.map +0 -1
  511. package/dist/observability/metrics.d.ts +0 -14
  512. package/dist/observability/metrics.d.ts.map +0 -1
  513. package/dist/observability/metrics.js +0 -18
  514. package/dist/observability/metrics.js.map +0 -1
  515. package/dist/packager/manifest.d.ts +0 -66
  516. package/dist/packager/manifest.d.ts.map +0 -1
  517. package/dist/packager/manifest.js +0 -94
  518. package/dist/packager/manifest.js.map +0 -1
  519. package/dist/packager/publish.d.ts +0 -51
  520. package/dist/packager/publish.d.ts.map +0 -1
  521. package/dist/packager/publish.js +0 -18
  522. package/dist/packager/publish.js.map +0 -1
  523. package/dist/packager/targetcli.d.ts +0 -7
  524. package/dist/packager/targetcli.d.ts.map +0 -1
  525. package/dist/packager/targetcli.js +0 -22
  526. package/dist/packager/targetcli.js.map +0 -1
  527. package/dist/persistence/adapter.d.ts +0 -5
  528. package/dist/persistence/adapter.d.ts.map +0 -1
  529. package/dist/persistence/adapter.js +0 -11
  530. package/dist/persistence/adapter.js.map +0 -1
  531. package/dist/persistence/drizzle.d.ts +0 -2
  532. package/dist/persistence/drizzle.d.ts.map +0 -1
  533. package/dist/persistence/drizzle.js +0 -12
  534. package/dist/persistence/drizzle.js.map +0 -1
  535. package/dist/persistence/memory.d.ts +0 -2
  536. package/dist/persistence/memory.d.ts.map +0 -1
  537. package/dist/persistence/memory.js +0 -27
  538. package/dist/persistence/memory.js.map +0 -1
  539. package/dist/persistence/migrations.d.ts +0 -19
  540. package/dist/persistence/migrations.d.ts.map +0 -1
  541. package/dist/persistence/migrations.js +0 -13
  542. package/dist/persistence/migrations.js.map +0 -1
  543. package/dist/persistence/prisma.d.ts +0 -2
  544. package/dist/persistence/prisma.d.ts.map +0 -1
  545. package/dist/persistence/prisma.js +0 -25
  546. package/dist/persistence/prisma.js.map +0 -1
  547. package/dist/persistence/schema.d.ts +0 -63
  548. package/dist/persistence/schema.d.ts.map +0 -1
  549. package/dist/persistence/schema.js +0 -28
  550. package/dist/persistence/schema.js.map +0 -1
  551. package/dist/persistence/sql.d.ts +0 -3
  552. package/dist/persistence/sql.d.ts.map +0 -1
  553. package/dist/persistence/sql.js +0 -37
  554. package/dist/persistence/sql.js.map +0 -1
  555. package/dist/protocol/blocks.d.ts +0 -10
  556. package/dist/protocol/blocks.d.ts.map +0 -1
  557. package/dist/protocol/blocks.js +0 -26
  558. package/dist/protocol/blocks.js.map +0 -1
  559. package/dist/protocol/json.d.ts +0 -6
  560. package/dist/protocol/json.d.ts.map +0 -1
  561. package/dist/protocol/json.js +0 -6
  562. package/dist/protocol/json.js.map +0 -1
  563. package/dist/protocol/ndjson.d.ts +0 -3
  564. package/dist/protocol/ndjson.d.ts.map +0 -1
  565. package/dist/protocol/ndjson.js +0 -20
  566. package/dist/protocol/ndjson.js.map +0 -1
  567. package/dist/protocol/sse.d.ts +0 -7
  568. package/dist/protocol/sse.d.ts.map +0 -1
  569. package/dist/protocol/sse.js +0 -25
  570. package/dist/protocol/sse.js.map +0 -1
  571. package/dist/proxy/pool.d.ts +0 -9
  572. package/dist/proxy/pool.d.ts.map +0 -1
  573. package/dist/proxy/pool.js +0 -27
  574. package/dist/proxy/pool.js.map +0 -1
  575. package/dist/queue/idempotency.d.ts +0 -10
  576. package/dist/queue/idempotency.d.ts.map +0 -1
  577. package/dist/queue/idempotency.js +0 -13
  578. package/dist/queue/idempotency.js.map +0 -1
  579. package/dist/queue/persistent.d.ts +0 -14
  580. package/dist/queue/persistent.d.ts.map +0 -1
  581. package/dist/queue/persistent.js +0 -66
  582. package/dist/queue/persistent.js.map +0 -1
  583. package/dist/queue/queue.d.ts +0 -7
  584. package/dist/queue/queue.d.ts.map +0 -1
  585. package/dist/queue/queue.js +0 -55
  586. package/dist/queue/queue.js.map +0 -1
  587. package/dist/queue/saga.d.ts +0 -5
  588. package/dist/queue/saga.d.ts.map +0 -1
  589. package/dist/queue/saga.js +0 -20
  590. package/dist/queue/saga.js.map +0 -1
  591. package/dist/release/assets.d.ts +0 -144
  592. package/dist/release/assets.d.ts.map +0 -1
  593. package/dist/release/assets.js +0 -157
  594. package/dist/release/assets.js.map +0 -1
  595. package/dist/release/evidence.d.ts +0 -92
  596. package/dist/release/evidence.d.ts.map +0 -1
  597. package/dist/release/evidence.js +0 -148
  598. package/dist/release/evidence.js.map +0 -1
  599. package/dist/release/verify.d.ts +0 -12
  600. package/dist/release/verify.d.ts.map +0 -1
  601. package/dist/release/verify.js +0 -112
  602. package/dist/release/verify.js.map +0 -1
  603. package/dist/runners/chain.d.ts +0 -125
  604. package/dist/runners/chain.d.ts.map +0 -1
  605. package/dist/runners/chain.js +0 -95
  606. package/dist/runners/chain.js.map +0 -1
  607. package/dist/runners/health.d.ts +0 -36
  608. package/dist/runners/health.d.ts.map +0 -1
  609. package/dist/runners/health.js +0 -26
  610. package/dist/runners/health.js.map +0 -1
  611. package/dist/runners/heartbeat.d.ts +0 -23
  612. package/dist/runners/heartbeat.d.ts.map +0 -1
  613. package/dist/runners/heartbeat.js +0 -29
  614. package/dist/runners/heartbeat.js.map +0 -1
  615. package/dist/runners/inprocess.d.ts +0 -17
  616. package/dist/runners/inprocess.d.ts.map +0 -1
  617. package/dist/runners/inprocess.js +0 -20
  618. package/dist/runners/inprocess.js.map +0 -1
  619. package/dist/runners/scheduler.d.ts +0 -5
  620. package/dist/runners/scheduler.d.ts.map +0 -1
  621. package/dist/runners/scheduler.js +0 -19
  622. package/dist/runners/scheduler.js.map +0 -1
  623. package/dist/runtime/abort.d.ts +0 -8
  624. package/dist/runtime/abort.d.ts.map +0 -1
  625. package/dist/runtime/abort.js +0 -13
  626. package/dist/runtime/abort.js.map +0 -1
  627. package/dist/runtime/compatibility.d.ts +0 -37
  628. package/dist/runtime/compatibility.d.ts.map +0 -1
  629. package/dist/runtime/compatibility.js +0 -10
  630. package/dist/runtime/compatibility.js.map +0 -1
  631. package/dist/runtime/detect.d.ts +0 -13
  632. package/dist/runtime/detect.d.ts.map +0 -1
  633. package/dist/runtime/detect.js +0 -18
  634. package/dist/runtime/detect.js.map +0 -1
  635. package/dist/runtime/engine.d.ts +0 -20
  636. package/dist/runtime/engine.d.ts.map +0 -1
  637. package/dist/runtime/engine.js +0 -61
  638. package/dist/runtime/engine.js.map +0 -1
  639. package/dist/runtime/retry.d.ts +0 -19
  640. package/dist/runtime/retry.d.ts.map +0 -1
  641. package/dist/runtime/retry.js +0 -54
  642. package/dist/runtime/retry.js.map +0 -1
  643. package/dist/runtime/worker.d.ts +0 -10
  644. package/dist/runtime/worker.d.ts.map +0 -1
  645. package/dist/runtime/worker.js +0 -25
  646. package/dist/runtime/worker.js.map +0 -1
  647. package/dist/scrape/cache.d.ts +0 -45
  648. package/dist/scrape/cache.d.ts.map +0 -1
  649. package/dist/scrape/cache.js +0 -45
  650. package/dist/scrape/cache.js.map +0 -1
  651. package/dist/scrape/crawl.d.ts +0 -47
  652. package/dist/scrape/crawl.d.ts.map +0 -1
  653. package/dist/scrape/crawl.js +0 -114
  654. package/dist/scrape/crawl.js.map +0 -1
  655. package/dist/scrape/extract.d.ts +0 -63
  656. package/dist/scrape/extract.d.ts.map +0 -1
  657. package/dist/scrape/extract.js +0 -47
  658. package/dist/scrape/extract.js.map +0 -1
  659. package/dist/scrape/normalize.d.ts +0 -52
  660. package/dist/scrape/normalize.d.ts.map +0 -1
  661. package/dist/scrape/normalize.js +0 -102
  662. package/dist/scrape/normalize.js.map +0 -1
  663. package/dist/scrape/robots.d.ts +0 -37
  664. package/dist/scrape/robots.d.ts.map +0 -1
  665. package/dist/scrape/robots.js +0 -71
  666. package/dist/scrape/robots.js.map +0 -1
  667. package/dist/scrape/schema.d.ts +0 -23
  668. package/dist/scrape/schema.d.ts.map +0 -1
  669. package/dist/scrape/schema.js +0 -92
  670. package/dist/scrape/schema.js.map +0 -1
  671. package/dist/scrape/scraper.d.ts +0 -6
  672. package/dist/scrape/scraper.d.ts.map +0 -1
  673. package/dist/scrape/scraper.js +0 -46
  674. package/dist/scrape/scraper.js.map +0 -1
  675. package/dist/scrape/semantic.d.ts +0 -25
  676. package/dist/scrape/semantic.d.ts.map +0 -1
  677. package/dist/scrape/semantic.js +0 -27
  678. package/dist/scrape/semantic.js.map +0 -1
  679. package/dist/server/node.d.ts +0 -7
  680. package/dist/server/node.d.ts.map +0 -1
  681. package/dist/server/node.js.map +0 -1
  682. package/dist/sessions/file.d.ts +0 -25
  683. package/dist/sessions/file.d.ts.map +0 -1
  684. package/dist/sessions/file.js +0 -13
  685. package/dist/sessions/file.js.map +0 -1
  686. package/dist/sessions/replay.d.ts +0 -9
  687. package/dist/sessions/replay.d.ts.map +0 -1
  688. package/dist/sessions/replay.js +0 -70
  689. package/dist/sessions/replay.js.map +0 -1
  690. package/dist/sessions/store.d.ts +0 -25
  691. package/dist/sessions/store.d.ts.map +0 -1
  692. package/dist/sessions/store.js +0 -13
  693. package/dist/sessions/store.js.map +0 -1
  694. package/dist/storage/adapter.d.ts +0 -5
  695. package/dist/storage/adapter.d.ts.map +0 -1
  696. package/dist/storage/adapter.js +0 -11
  697. package/dist/storage/adapter.js.map +0 -1
  698. package/dist/storage/cache.d.ts +0 -23
  699. package/dist/storage/cache.d.ts.map +0 -1
  700. package/dist/storage/cache.js +0 -79
  701. package/dist/storage/cache.js.map +0 -1
  702. package/dist/storage/checksum.d.ts +0 -3
  703. package/dist/storage/checksum.d.ts.map +0 -1
  704. package/dist/storage/checksum.js +0 -19
  705. package/dist/storage/checksum.js.map +0 -1
  706. package/dist/storage/chunked.d.ts +0 -21
  707. package/dist/storage/chunked.d.ts.map +0 -1
  708. package/dist/storage/chunked.js +0 -67
  709. package/dist/storage/chunked.js.map +0 -1
  710. package/dist/storage/content.d.ts +0 -24
  711. package/dist/storage/content.d.ts.map +0 -1
  712. package/dist/storage/content.js +0 -44
  713. package/dist/storage/content.js.map +0 -1
  714. package/dist/storage/filehosting.d.ts +0 -2
  715. package/dist/storage/filehosting.d.ts.map +0 -1
  716. package/dist/storage/filehosting.js +0 -24
  717. package/dist/storage/filehosting.js.map +0 -1
  718. package/dist/storage/githubcontents.d.ts +0 -2
  719. package/dist/storage/githubcontents.d.ts.map +0 -1
  720. package/dist/storage/githubcontents.js +0 -29
  721. package/dist/storage/githubcontents.js.map +0 -1
  722. package/dist/storage/index.d.ts +0 -12
  723. package/dist/storage/index.d.ts.map +0 -1
  724. package/dist/storage/index.js +0 -12
  725. package/dist/storage/index.js.map +0 -1
  726. package/dist/storage/local.d.ts +0 -2
  727. package/dist/storage/local.d.ts.map +0 -1
  728. package/dist/storage/local.js +0 -72
  729. package/dist/storage/local.js.map +0 -1
  730. package/dist/storage/memory.d.ts +0 -6
  731. package/dist/storage/memory.d.ts.map +0 -1
  732. package/dist/storage/memory.js +0 -36
  733. package/dist/storage/memory.js.map +0 -1
  734. package/dist/storage/pool.d.ts +0 -95
  735. package/dist/storage/pool.d.ts.map +0 -1
  736. package/dist/storage/pool.js +0 -202
  737. package/dist/storage/pool.js.map +0 -1
  738. package/dist/storage/s3compatible.d.ts +0 -3
  739. package/dist/storage/s3compatible.d.ts.map +0 -1
  740. package/dist/storage/s3compatible.js +0 -70
  741. package/dist/storage/s3compatible.js.map +0 -1
  742. package/dist/storage/sync.d.ts +0 -47
  743. package/dist/storage/sync.d.ts.map +0 -1
  744. package/dist/storage/sync.js +0 -75
  745. package/dist/storage/sync.js.map +0 -1
  746. package/dist/surfaces/adapters.d.ts +0 -97
  747. package/dist/surfaces/adapters.d.ts.map +0 -1
  748. package/dist/surfaces/adapters.js +0 -50
  749. package/dist/surfaces/adapters.js.map +0 -1
  750. package/dist/surfaces/controls.d.ts +0 -18
  751. package/dist/surfaces/controls.d.ts.map +0 -1
  752. package/dist/surfaces/controls.js +0 -45
  753. package/dist/surfaces/controls.js.map +0 -1
  754. package/dist/surfaces/manifest.d.ts +0 -68
  755. package/dist/surfaces/manifest.d.ts.map +0 -1
  756. package/dist/surfaces/manifest.js +0 -42
  757. package/dist/surfaces/manifest.js.map +0 -1
  758. package/dist/surfaces/n8n.d.ts +0 -25
  759. package/dist/surfaces/n8n.d.ts.map +0 -1
  760. package/dist/surfaces/n8n.js +0 -31
  761. package/dist/surfaces/n8n.js.map +0 -1
  762. package/dist/surfaces/operations.d.ts +0 -32
  763. package/dist/surfaces/operations.d.ts.map +0 -1
  764. package/dist/surfaces/operations.js +0 -53
  765. package/dist/surfaces/operations.js.map +0 -1
  766. package/dist/surfaces/requirements.d.ts +0 -29
  767. package/dist/surfaces/requirements.d.ts.map +0 -1
  768. package/dist/surfaces/requirements.js +0 -50
  769. package/dist/surfaces/requirements.js.map +0 -1
  770. package/dist/surfaces/targets.d.ts +0 -196
  771. package/dist/surfaces/targets.d.ts.map +0 -1
  772. package/dist/surfaces/targets.js +0 -27
  773. package/dist/surfaces/targets.js.map +0 -1
  774. package/dist/webhook/delivery.d.ts +0 -18
  775. package/dist/webhook/delivery.d.ts.map +0 -1
  776. package/dist/webhook/delivery.js +0 -36
  777. package/dist/webhook/delivery.js.map +0 -1
  778. package/dist/webhook/receiver.d.ts +0 -26
  779. package/dist/webhook/receiver.d.ts.map +0 -1
  780. package/dist/webhook/receiver.js +0 -24
  781. package/dist/webhook/receiver.js.map +0 -1
  782. package/dist/webhook/signature.d.ts +0 -3
  783. package/dist/webhook/signature.d.ts.map +0 -1
  784. package/dist/webhook/signature.js +0 -7
  785. package/dist/webhook/signature.js.map +0 -1
  786. package/dist/workflow/manifest.d.ts +0 -22
  787. package/dist/workflow/manifest.d.ts.map +0 -1
  788. package/dist/workflow/manifest.js +0 -21
  789. package/dist/workflow/manifest.js.map +0 -1
  790. package/dist/workflow/registry.d.ts +0 -7
  791. package/dist/workflow/registry.d.ts.map +0 -1
  792. package/dist/workflow/registry.js +0 -18
  793. package/dist/workflow/registry.js.map +0 -1
  794. package/dist/workflow/templates.d.ts +0 -6
  795. package/dist/workflow/templates.d.ts.map +0 -1
  796. package/dist/workflow/templates.js +0 -18
  797. package/dist/workflow/templates.js.map +0 -1
  798. package/dist/workflow/triggers.d.ts +0 -64
  799. package/dist/workflow/triggers.d.ts.map +0 -1
  800. package/dist/workflow/triggers.js +0 -99
  801. package/dist/workflow/triggers.js.map +0 -1
  802. /package/{extension/README.md → docs/extension.md} +0 -0
@@ -0,0 +1,2073 @@
1
+ /**
2
+ * quantum.ts — classical quantum-simulation layer for saddle v18.
3
+ *
4
+ * the module is a 100 percent classical software statevector simulator:
5
+ * no hardware, no photons, no qpu. the engine "supports" quantum the same
6
+ * way it virtualizes cores, memory and gpus — as one more virtualization
7
+ * layer: every "qubit" is a pair of float64 lanes inside a 2^n amplitude
8
+ * vector (interleaved re/im), every "gate" is an in-place index-pair
9
+ * transformation and every "measurement" is a crypto-seeded collapse of
10
+ * that vector.
11
+ *
12
+ * contexts (22):
13
+ * 01 version anchors (algorithm dates, simulator envelope)
14
+ * 02 error catcher (quantumerror envelope)
15
+ * 03 complex math kernel (2x2 unitary type + gate matrices)
16
+ * 04 quantumsim statevector core (1-20 qubits, Disposable)
17
+ * 05 multi-qubit gate kernels (cnot, cz, toffoli, swap, ccz)
18
+ * 06 canonical circuits (bellstate, ghzstate)
19
+ * 07 grover search (grover2 provable, grover3 statistical)
20
+ * 08 deutsch oracle discrimination (deutsch)
21
+ * 09 quantum teleportation sketch (qteleport)
22
+ * 10 bb84 stations (alice, bob, eve over a simulated channel)
23
+ * 11 bb84 protocol runner (runbb84: sifting, qber, intercept detection)
24
+ * 12 e91 entangled pairs + chsh (rune91)
25
+ * 13 qrng (quantuminspiredrandom, honest anu fallback)
26
+ * 14 dnavault codec (goldman 2013 ternary rotation, framing, strands)
27
+ * 15 dnavault decode (checksum verification, redundancy, roundtrip)
28
+ * 16 dnavault capacity planner (215 pb/g, planodefault)
29
+ * 17 optical 5d quartz planner (360 tb/disc, femtosecond write plan)
30
+ * 18 holographic note (microsoft hsd) and storage compare
31
+ * 19 qram bucket brigade (giovannetti 2008, o(log n) routing, n=8)
32
+ * 20 shor plan (honest: theoretical 7-qubit circuit, never executed)
33
+ * 21 registry (quantumregistry capability catalog)
34
+ * 22 self check (quantumselfcheck: every claim, machine-verified)
35
+ *
36
+ * rules: lowercase identifiers, english jsdoc third person, no emoji,
37
+ * try/catch catcher on every fallible path, node:* built-ins only
38
+ * (node:crypto for all randomness), zero runtime dependencies, no
39
+ * filesystem, network or process coupling beyond the optional,
40
+ * always-fallback anu qrng fetch. ascii only.
41
+ */
42
+ var __addDisposableResource = (this && this.__addDisposableResource) || function (env, value, async) {
43
+ if (value !== null && value !== void 0) {
44
+ if (typeof value !== "object" && typeof value !== "function") throw new TypeError("Object expected.");
45
+ var dispose, inner;
46
+ if (async) {
47
+ if (!Symbol.asyncDispose) throw new TypeError("Symbol.asyncDispose is not defined.");
48
+ dispose = value[Symbol.asyncDispose];
49
+ }
50
+ if (dispose === void 0) {
51
+ if (!Symbol.dispose) throw new TypeError("Symbol.dispose is not defined.");
52
+ dispose = value[Symbol.dispose];
53
+ if (async) inner = dispose;
54
+ }
55
+ if (typeof dispose !== "function") throw new TypeError("Object not disposable.");
56
+ if (inner) dispose = function() { try { inner.call(this); } catch (e) { return Promise.reject(e); } };
57
+ env.stack.push({ value: value, dispose: dispose, async: async });
58
+ }
59
+ else if (async) {
60
+ env.stack.push({ async: true });
61
+ }
62
+ return value;
63
+ };
64
+ var __disposeResources = (this && this.__disposeResources) || (function (SuppressedError) {
65
+ return function (env) {
66
+ function fail(e) {
67
+ env.error = env.hasError ? new SuppressedError(e, env.error, "An error was suppressed during disposal.") : e;
68
+ env.hasError = true;
69
+ }
70
+ var r, s = 0;
71
+ function next() {
72
+ while (r = env.stack.pop()) {
73
+ try {
74
+ if (!r.async && s === 1) return s = 0, env.stack.push(r), Promise.resolve().then(next);
75
+ if (r.dispose) {
76
+ var result = r.dispose.call(r.value);
77
+ if (r.async) return s |= 2, Promise.resolve(result).then(next, function(e) { fail(e); return next(); });
78
+ }
79
+ else s |= 1;
80
+ }
81
+ catch (e) {
82
+ fail(e);
83
+ }
84
+ }
85
+ if (s === 1) return env.hasError ? Promise.reject(env.error) : Promise.resolve();
86
+ if (env.hasError) throw env.error;
87
+ }
88
+ return next();
89
+ };
90
+ })(typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
91
+ var e = new Error(message);
92
+ return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
93
+ });
94
+ import { randomBytes, randomInt } from 'node:crypto';
95
+ /* ------------------------------------------------------------------ */
96
+ /* context: version anchors (quantum simulation envelope) */
97
+ /* ------------------------------------------------------------------ */
98
+ /**
99
+ * frozen quantum layer anchors. every algorithm keeps its literature
100
+ * year so the registry can cite primary sources instead of folklore.
101
+ */
102
+ export const quantumversions = {
103
+ date: '2026-08-23',
104
+ simulator: 'statevector',
105
+ precision: 'float64 interleaved re/im',
106
+ maxqubits: 20,
107
+ amplitudelanes: 2097152,
108
+ grover: '1996 stoc',
109
+ deutschjozsa: '1992 proc r soc a',
110
+ bb84: '1984 bangalore proceedings',
111
+ e91: '1991 prl 67 661',
112
+ teleportation: '1993 prl 70 1895',
113
+ qram: '2008 prl 100 160501',
114
+ };
115
+ /* ------------------------------------------------------------------ */
116
+ /* context: error catcher */
117
+ /* ------------------------------------------------------------------ */
118
+ /**
119
+ * quantum layer failure envelope. every guard in this module throws it
120
+ * instead of a bare error so callers can branch on the code.
121
+ */
122
+ export class quantumerror extends Error {
123
+ code;
124
+ detail;
125
+ constructor(params) {
126
+ super(params.message);
127
+ this.name = 'quantumerror';
128
+ this.code = params.code;
129
+ this.detail = params.detail;
130
+ }
131
+ }
132
+ const invsqrt2 = Math.SQRT1_2;
133
+ /** hadamard matrix ((1/sqrt 2) [[1,1],[1,1]]). */
134
+ export const hmatrix = [invsqrt2, 0, invsqrt2, 0, invsqrt2, 0, invsqrt2, 0];
135
+ /** pauli x matrix [[0,1],[1,0]]. */
136
+ export const xmatrix = [0, 0, 1, 0, 1, 0, 0, 0];
137
+ /** pauli y matrix [[0,-i],[i,0]]. */
138
+ export const ymatrix = [0, 0, 0, -1, 0, 1, 0, 0];
139
+ /** pauli z matrix diag(1,-1). */
140
+ export const zmatrix = [1, 0, 0, 0, 0, 0, -1, 0];
141
+ /** phase gate s = diag(1, i). */
142
+ export const smatrix = [1, 0, 0, 0, 0, 0, 0, 1];
143
+ /** inverse phase gate sdg = diag(1, -i). */
144
+ export const sdgmatrix = [1, 0, 0, 0, 0, 0, 0, -1];
145
+ /** t gate = diag(1, exp(i pi/4)). */
146
+ export const tmatrix = [1, 0, 0, 0, 0, 0, invsqrt2, invsqrt2];
147
+ /** inverse t gate = diag(1, exp(-i pi/4)). */
148
+ export const tdgmatrix = [1, 0, 0, 0, 0, 0, invsqrt2, -invsqrt2];
149
+ /**
150
+ * builds the rotation-x matrix rx(theta) =
151
+ * [[cos(t/2), -i sin(t/2)], [-i sin(t/2), cos(t/2)]].
152
+ */
153
+ export function rxmatrix(theta) {
154
+ const c = Math.cos(theta / 2);
155
+ const s = Math.sin(theta / 2);
156
+ return [c, 0, 0, -s, 0, -s, c, 0];
157
+ }
158
+ /**
159
+ * builds the rotation-y matrix ry(theta) =
160
+ * [[cos(t/2), -sin(t/2)], [sin(t/2), cos(t/2)]]; ry(2a)|0> equals the
161
+ * polarization state cos(a)|0> + sin(a)|1>, which the e91 context uses
162
+ * to prepare and measure at arbitrary analyzer angles.
163
+ */
164
+ export function rymatrix(theta) {
165
+ const c = Math.cos(theta / 2);
166
+ const s = Math.sin(theta / 2);
167
+ return [c, 0, -s, 0, s, 0, c, 0];
168
+ }
169
+ /**
170
+ * builds the rotation-z matrix rz(theta) = diag(e^{-i t/2}, e^{i t/2}).
171
+ */
172
+ export function rzmatrix(theta) {
173
+ const c = Math.cos(theta / 2);
174
+ const s = Math.sin(theta / 2);
175
+ return [c, -s, 0, 0, 0, 0, c, s];
176
+ }
177
+ /* ------------------------------------------------------------------ */
178
+ /* context: quantumsim statevector core (1-20 qubits, Disposable) */
179
+ /* ------------------------------------------------------------------ */
180
+ /**
181
+ * pure-software statevector simulator. the state is one Float64Array of
182
+ * 2 * 2^n lanes holding interleaved real and imaginary parts; qubit q is
183
+ * bit q of the basis index (qubit 0 is the least significant bit), so
184
+ * for a single-qubit gate on qubit q the kernel iterates every index i
185
+ * with bit q = 0, takes j = i | 2^q and replaces the pair by
186
+ * u @ [amp(i), amp(j)] exactly as specified. the class is Disposable and
187
+ * meant to be used with `using` so amplitude memory is logically freed
188
+ * even though the gc owns it.
189
+ */
190
+ export class quantumsim {
191
+ #amp;
192
+ #n;
193
+ #disposed = false;
194
+ constructor(nqubits) {
195
+ if (!Number.isInteger(nqubits) || nqubits < 1 || nqubits > 20) {
196
+ throw new quantumerror({
197
+ code: 'qubitrange',
198
+ message: `quantumsim supports 1 to 20 qubits, got ${nqubits}`,
199
+ detail: '2^n amplitudes with n > 20 exceed the float64 lane budget',
200
+ });
201
+ }
202
+ this.#n = nqubits;
203
+ this.#amp = new Float64Array(2 << nqubits);
204
+ this.#amp[0] = 1;
205
+ }
206
+ /** number of qubits of the register. */
207
+ get nqubits() {
208
+ return this.#n;
209
+ }
210
+ /** hilbert space dimension 2^n. */
211
+ get dim() {
212
+ return 1 << this.#n;
213
+ }
214
+ /** true once Symbol.dispose released the state. */
215
+ get disposed() {
216
+ return this.#disposed;
217
+ }
218
+ #guardlive() {
219
+ if (this.#disposed) {
220
+ throw new quantumerror({
221
+ code: 'disposed',
222
+ message: 'quantumsim state was disposed; create a new register',
223
+ });
224
+ }
225
+ }
226
+ #guardqubit(q, gate) {
227
+ if (!Number.isInteger(q) || q < 0 || q >= this.#n) {
228
+ throw new quantumerror({
229
+ code: 'qubitrange',
230
+ message: `gate ${gate} needs a qubit in [0, ${this.#n - 1}], got ${q}`,
231
+ });
232
+ }
233
+ }
234
+ /**
235
+ * applies a 2x2 unitary to qubit q by visiting each amplitude pair
236
+ * (i, i|2^q) once; this is the mathematical core every named
237
+ * single-qubit gate forwards to.
238
+ */
239
+ #apply1(q, m, gate) {
240
+ this.#guardlive();
241
+ this.#guardqubit(q, gate);
242
+ const amp = this.#amp;
243
+ const mask = 1 << q;
244
+ const [u00re, u00im, u01re, u01im, u10re, u10im, u11re, u11im] = m;
245
+ for (let i = 0; i < this.dim; i++) {
246
+ if ((i & mask) !== 0)
247
+ continue;
248
+ const j = i | mask;
249
+ const i2 = i << 1;
250
+ const j2 = j << 1;
251
+ const are = amp[i2];
252
+ const aim = amp[i2 + 1];
253
+ const bre = amp[j2];
254
+ const bim = amp[j2 + 1];
255
+ amp[i2] = u00re * are - u00im * aim + u01re * bre - u01im * bim;
256
+ amp[i2 + 1] = u00re * aim + u00im * are + u01re * bim + u01im * bre;
257
+ amp[j2] = u10re * are - u10im * aim + u11re * bre - u11im * bim;
258
+ amp[j2 + 1] = u10re * aim + u10im * are + u11re * bim + u11im * bre;
259
+ }
260
+ return this;
261
+ }
262
+ /** hadamard on qubit q. */
263
+ h(q) {
264
+ return this.#apply1(q, hmatrix, 'h');
265
+ }
266
+ /** pauli x (bit flip) on qubit q. */
267
+ x(q) {
268
+ return this.#apply1(q, xmatrix, 'x');
269
+ }
270
+ /** pauli y on qubit q. */
271
+ y(q) {
272
+ return this.#apply1(q, ymatrix, 'y');
273
+ }
274
+ /** pauli z (phase flip) on qubit q. */
275
+ z(q) {
276
+ return this.#apply1(q, zmatrix, 'z');
277
+ }
278
+ /** phase gate s = sqrt(z) on qubit q. */
279
+ s(q) {
280
+ return this.#apply1(q, smatrix, 's');
281
+ }
282
+ /** inverse phase gate on qubit q. */
283
+ sdg(q) {
284
+ return this.#apply1(q, sdgmatrix, 'sdg');
285
+ }
286
+ /** t = pi/8 gate on qubit q. */
287
+ t(q) {
288
+ return this.#apply1(q, tmatrix, 't');
289
+ }
290
+ /** inverse t gate on qubit q. */
291
+ tdg(q) {
292
+ return this.#apply1(q, tdgmatrix, 'tdg');
293
+ }
294
+ /** rotation-x by theta radians on qubit q. */
295
+ rx(theta, q) {
296
+ return this.#apply1(q, rxmatrix(theta), `rx(${theta})`);
297
+ }
298
+ /** rotation-y by theta radians on qubit q. */
299
+ ry(theta, q) {
300
+ return this.#apply1(q, rymatrix(theta), `ry(${theta})`);
301
+ }
302
+ /** rotation-z by theta radians on qubit q. */
303
+ rz(theta, q) {
304
+ return this.#apply1(q, rzmatrix(theta), `rz(${theta})`);
305
+ }
306
+ /**
307
+ * cnot: for every index i with control bit 1 and target bit 0,
308
+ * swaps amplitudes i and i|2^target; each pair is visited once.
309
+ */
310
+ cnot(control, target) {
311
+ this.#guardlive();
312
+ this.#guardqubit(control, 'cnot');
313
+ this.#guardqubit(target, 'cnot');
314
+ if (control === target) {
315
+ throw new quantumerror({
316
+ code: 'qubitcollision',
317
+ message: `cnot control and target are both qubit ${control}`,
318
+ });
319
+ }
320
+ const amp = this.#amp;
321
+ const maskc = 1 << control;
322
+ const maskt = 1 << target;
323
+ for (let i = 0; i < this.dim; i++) {
324
+ if ((i & maskc) === 0 || (i & maskt) !== 0)
325
+ continue;
326
+ this.#swappair(amp, i, i | maskt);
327
+ }
328
+ return this;
329
+ }
330
+ /**
331
+ * cz: flips the sign of every amplitude whose control and target
332
+ * bits are both 1.
333
+ */
334
+ cz(control, target) {
335
+ this.#guardlive();
336
+ this.#guardqubit(control, 'cz');
337
+ this.#guardqubit(target, 'cz');
338
+ if (control === target) {
339
+ throw new quantumerror({
340
+ code: 'qubitcollision',
341
+ message: `cz control and target are both qubit ${control}`,
342
+ });
343
+ }
344
+ const amp = this.#amp;
345
+ const mask = (1 << control) | (1 << target);
346
+ for (let i = 0; i < this.dim; i++) {
347
+ if ((i & mask) !== mask)
348
+ continue;
349
+ const i2 = i << 1;
350
+ amp[i2] = -amp[i2];
351
+ amp[i2 + 1] = -amp[i2 + 1];
352
+ }
353
+ return this;
354
+ }
355
+ /**
356
+ * toffoli (ccnot): swaps amplitude pairs only when both control bits
357
+ * are 1 and the target bit is 0.
358
+ */
359
+ toffoli(control1, control2, target) {
360
+ this.#guardlive();
361
+ this.#guardqubit(control1, 'toffoli');
362
+ this.#guardqubit(control2, 'toffoli');
363
+ this.#guardqubit(target, 'toffoli');
364
+ if (control1 === target || control2 === target || control1 === control2) {
365
+ throw new quantumerror({
366
+ code: 'qubitcollision',
367
+ message: `toffoli needs three distinct qubits, got ${control1}, ${control2}, ${target}`,
368
+ });
369
+ }
370
+ const amp = this.#amp;
371
+ const mask1 = 1 << control1;
372
+ const mask2 = 1 << control2;
373
+ const maskt = 1 << target;
374
+ for (let i = 0; i < this.dim; i++) {
375
+ if ((i & mask1) === 0 || (i & mask2) === 0 || (i & maskt) !== 0)
376
+ continue;
377
+ this.#swappair(amp, i, i | maskt);
378
+ }
379
+ return this;
380
+ }
381
+ /**
382
+ * swap: exchanges qubits a and b by visiting each index pair once
383
+ * (bit a = 0 with bit b = 1 maps to its complement bit a = 1, bit
384
+ * b = 0), so no pair is touched twice.
385
+ */
386
+ swap(a, b) {
387
+ this.#guardlive();
388
+ this.#guardqubit(a, 'swap');
389
+ this.#guardqubit(b, 'swap');
390
+ if (a === b) {
391
+ throw new quantumerror({
392
+ code: 'qubitcollision',
393
+ message: `swap needs two distinct qubits, got ${a} twice`,
394
+ });
395
+ }
396
+ const amp = this.#amp;
397
+ const maska = 1 << a;
398
+ const maskb = 1 << b;
399
+ for (let i = 0; i < this.dim; i++) {
400
+ if ((i & maska) !== 0 || (i & maskb) === 0)
401
+ continue;
402
+ this.#swappair(amp, i, (i | maska) & ~maskb);
403
+ }
404
+ return this;
405
+ }
406
+ /** swaps the two interleaved complex amplitudes at basis indexes. */
407
+ #swappair(amp, i, j) {
408
+ const i2 = i << 1;
409
+ const j2 = j << 1;
410
+ const re = amp[i2];
411
+ const im = amp[i2 + 1];
412
+ amp[i2] = amp[j2];
413
+ amp[i2 + 1] = amp[j2 + 1];
414
+ amp[j2] = re;
415
+ amp[j2 + 1] = im;
416
+ }
417
+ /**
418
+ * measurement outcome sampler: draws one uniform from node:crypto
419
+ * (randomInt over 2^30 buckets, finer than any probability gap this
420
+ * module produces), compares it with the |1> branch probability and
421
+ * returns the observed branch.
422
+ */
423
+ #sample(pone) {
424
+ const roll = randomInt(0, 0x40000000) / 0x40000000;
425
+ return roll < pone ? 1 : 0;
426
+ }
427
+ /**
428
+ * measures qubit q in the computational basis, collapsing the state.
429
+ * returns the observed classical bit.
430
+ */
431
+ measure(q) {
432
+ this.#guardlive();
433
+ this.#guardqubit(q, 'measure');
434
+ const amp = this.#amp;
435
+ const mask = 1 << q;
436
+ let pone = 0;
437
+ for (let i = 0; i < this.dim; i++) {
438
+ if ((i & mask) === 0)
439
+ continue;
440
+ const i2 = i << 1;
441
+ pone += amp[i2] * amp[i2] + amp[i2 + 1] * amp[i2 + 1];
442
+ }
443
+ const outcome = this.#sample(pone);
444
+ const keep = outcome === 1 ? mask : 0;
445
+ let mass = 0;
446
+ for (let i = 0; i < this.dim; i++) {
447
+ const i2 = i << 1;
448
+ if ((i & mask) !== keep) {
449
+ amp[i2] = 0;
450
+ amp[i2 + 1] = 0;
451
+ }
452
+ else {
453
+ mass += amp[i2] * amp[i2] + amp[i2 + 1] * amp[i2 + 1];
454
+ }
455
+ }
456
+ if (mass <= 0) {
457
+ throw new quantumerror({
458
+ code: 'zerovector',
459
+ message: `collapse of qubit ${q} hit a zero-mass branch`,
460
+ });
461
+ }
462
+ const scale = 1 / Math.sqrt(mass);
463
+ for (let i = 0; i < this.#amp.length; i++) {
464
+ this.#amp[i] *= scale;
465
+ }
466
+ return outcome;
467
+ }
468
+ /**
469
+ * measures the full register in the computational basis and returns
470
+ * the observed basis index (qubit 0 in bit 0).
471
+ */
472
+ measureall() {
473
+ this.#guardlive();
474
+ const amp = this.#amp;
475
+ const roll = randomInt(0, 0x40000000) / 0x40000000;
476
+ let acc = 0;
477
+ let pick = this.dim - 1;
478
+ for (let i = 0; i < this.dim; i++) {
479
+ const i2 = i << 1;
480
+ acc += amp[i2] * amp[i2] + amp[i2 + 1] * amp[i2 + 1];
481
+ if (roll < acc) {
482
+ pick = i;
483
+ break;
484
+ }
485
+ }
486
+ amp.fill(0);
487
+ amp[pick << 1] = 1;
488
+ return pick;
489
+ }
490
+ /**
491
+ * returns the [p0, p1] distribution of qubit q without collapsing;
492
+ * p1 = sum of |amplitude|^2 over indices with bit q set.
493
+ */
494
+ probs(q) {
495
+ this.#guardlive();
496
+ this.#guardqubit(q, 'probs');
497
+ const amp = this.#amp;
498
+ const mask = 1 << q;
499
+ let pone = 0;
500
+ for (let i = 0; i < this.dim; i++) {
501
+ if ((i & mask) === 0)
502
+ continue;
503
+ const i2 = i << 1;
504
+ pone += amp[i2] * amp[i2] + amp[i2 + 1] * amp[i2 + 1];
505
+ }
506
+ return [1 - pone, pone];
507
+ }
508
+ /**
509
+ * returns the full |amplitude|^2 distribution over all 2^n basis
510
+ * states as a fresh Float64Array (index order: qubit 0 in bit 0).
511
+ */
512
+ probabilities() {
513
+ this.#guardlive();
514
+ const amp = this.#amp;
515
+ const out = new Float64Array(this.dim);
516
+ for (let i = 0; i < this.dim; i++) {
517
+ const i2 = i << 1;
518
+ out[i] = amp[i2] * amp[i2] + amp[i2 + 1] * amp[i2 + 1];
519
+ }
520
+ return out;
521
+ }
522
+ /** returns the complex amplitude of one basis index as [re, im]. */
523
+ amplitude(index) {
524
+ this.#guardlive();
525
+ if (!Number.isInteger(index) || index < 0 || index >= this.dim) {
526
+ throw new quantumerror({
527
+ code: 'indexrange',
528
+ message: `amplitude index must be in [0, ${this.dim - 1}], got ${index}`,
529
+ });
530
+ }
531
+ const i2 = index << 1;
532
+ return [this.#amp[i2], this.#amp[i2 + 1]];
533
+ }
534
+ /** returns a detached readonly snapshot copy of the state lanes. */
535
+ state() {
536
+ this.#guardlive();
537
+ return this.#amp.slice();
538
+ }
539
+ /** euclidean norm of the state vector (should stay within 1e-12 of 1). */
540
+ norm() {
541
+ this.#guardlive();
542
+ let sum = 0;
543
+ for (let i = 0; i < this.#amp.length; i++) {
544
+ sum += this.#amp[i] * this.#amp[i];
545
+ }
546
+ return Math.sqrt(sum);
547
+ }
548
+ /** renormalizes the state to unit norm (fixes float drift). */
549
+ normalize() {
550
+ this.#guardlive();
551
+ const n = this.norm();
552
+ if (n <= 0) {
553
+ throw new quantumerror({
554
+ code: 'zerovector',
555
+ message: 'cannot normalize a zero vector',
556
+ });
557
+ }
558
+ for (let i = 0; i < this.#amp.length; i++) {
559
+ this.#amp[i] /= n;
560
+ }
561
+ return this;
562
+ }
563
+ /** resets the register to |0...0>. */
564
+ reset() {
565
+ this.#guardlive();
566
+ this.#amp.fill(0);
567
+ this.#amp[0] = 1;
568
+ return this;
569
+ }
570
+ /** releases the amplitude lanes; any further gate call throws. */
571
+ [Symbol.dispose]() {
572
+ this.#amp = new Float64Array(0);
573
+ this.#disposed = true;
574
+ }
575
+ }
576
+ /* ------------------------------------------------------------------ */
577
+ /* context: multi-qubit gate kernels (module-level forms) */
578
+ /* ------------------------------------------------------------------ */
579
+ /**
580
+ * applies cnot(control, target) to sim; functional spelling of the
581
+ * quantumsim method for composition outside the class.
582
+ */
583
+ export function cnot(sim, control, target) {
584
+ return sim.cnot(control, target);
585
+ }
586
+ /**
587
+ * applies cz(control, target) to sim; the grover oracle for two qubits
588
+ * is exactly this gate on the |11> amplitude.
589
+ */
590
+ export function cz(sim, control, target) {
591
+ return sim.cz(control, target);
592
+ }
593
+ /**
594
+ * applies toffoli(control1, control2, target) to sim, the universal
595
+ * reversible gate of toffoli 1980 as used in every compiled oracle.
596
+ */
597
+ export function toffoli(sim, control1, control2, target) {
598
+ return sim.toffoli(control1, control2, target);
599
+ }
600
+ /**
601
+ * applies swap(a, b) to sim.
602
+ */
603
+ export function swap(sim, a, b) {
604
+ return sim.swap(a, b);
605
+ }
606
+ /**
607
+ * ccz: three-qubit phase flip, composed as toffoli conjugated by
608
+ * hadamard on the target; used as the grover oracle and diffuser core.
609
+ */
610
+ export function ccz(sim, control1, control2, target) {
611
+ sim.h(target);
612
+ sim.toffoli(control1, control2, target);
613
+ sim.h(target);
614
+ return sim;
615
+ }
616
+ /**
617
+ * builds the bell state (|00> + |11>)/sqrt(2) with h(0) then cnot(0,1);
618
+ * measurement of either qubit is a perfect coin and both always agree.
619
+ * expected distribution: [0.5, 0, 0.5, 0].
620
+ * reference: einstein-podolsky-rosen 1935; bell 1964; chapter 1 of
621
+ * nielsen and chuang, quantum computation and quantum information
622
+ * (2000).
623
+ */
624
+ export function bellstate() {
625
+ const sim = new quantumsim(2);
626
+ sim.h(0).cnot(0, 1);
627
+ return {
628
+ sim,
629
+ name: 'bell',
630
+ expectedprobs: [0.5, 0, 0.5, 0],
631
+ reference: 'bell 1964; nielsen and chuang 2000 ch. 1',
632
+ note: 'maximally entangled pair; probs(0) = probs(1) = [0.5, 0.5]',
633
+ };
634
+ }
635
+ /**
636
+ * builds an n-qubit ghz state (|0...0> + |1...1>)/sqrt(2) by h(0) plus
637
+ * a cnot fanout; expected distribution carries mass 0.5 on index 0 and
638
+ * index 2^n - 1 only. reference: greenberger-horne-zeilinger 1989.
639
+ */
640
+ export function ghzstate(n = 3) {
641
+ if (!Number.isInteger(n) || n < 2 || n > 12) {
642
+ throw new quantumerror({
643
+ code: 'qubitrange',
644
+ message: `ghzstate supports 2 to 12 qubits, got ${n}`,
645
+ detail: 'cap exists so expectedprobs stays readable',
646
+ });
647
+ }
648
+ const sim = new quantumsim(n);
649
+ sim.h(0);
650
+ for (let q = 1; q < n; q++) {
651
+ sim.cnot(0, q);
652
+ }
653
+ const expected = new Array(1 << n).fill(0);
654
+ expected[0] = 0.5;
655
+ expected[(1 << n) - 1] = 0.5;
656
+ return {
657
+ sim,
658
+ name: `ghz${n}`,
659
+ expectedprobs: expected,
660
+ reference: 'greenberger, horne, zeilinger 1989',
661
+ note: 'n-party entanglement witness; only |0...0> and |1...1> survive',
662
+ };
663
+ }
664
+ /* ------------------------------------------------------------------ */
665
+ /* context: grover search (grover2 provable, grover3 statistical) */
666
+ /* ------------------------------------------------------------------ */
667
+ /**
668
+ * grover2: exhaustive-search winner |11> on 2 qubits with exactly one
669
+ * oracle call. the circuit is the task-pinned sequence
670
+ * h,h -> cz -> h,h -> x,x -> cz -> h,h whose unique fixed point is
671
+ * amplitude -1 on |11>, so prob(11) = 1 up to 1e-12 float noise.
672
+ * expected distribution: [0, 0, 0, 1].
673
+ * reference: grover, a fast quantum mechanical algorithm for database
674
+ * search, stoc 1996 (arxiv:quant-ph/9605043).
675
+ */
676
+ export function grover2() {
677
+ const sim = new quantumsim(2);
678
+ sim.h(0).h(1);
679
+ sim.cz(0, 1);
680
+ sim.h(0).h(1);
681
+ sim.x(0).x(1);
682
+ sim.cz(0, 1);
683
+ sim.h(0).h(1);
684
+ return {
685
+ sim,
686
+ name: 'grover2',
687
+ expectedprobs: [0, 0, 0, 1],
688
+ reference: 'grover 1996 stoc (arxiv:quant-ph/9605043)',
689
+ note: 'one oracle call finds |11> with certainty (4 states, 1 marked)',
690
+ };
691
+ }
692
+ /**
693
+ * grover3: search over 8 items for winner |111> with two iterations of
694
+ * oracle ccz + diffuser (h x3, x x3, ccz, x x3, h x3). theory gives
695
+ * success sin^2(5 * asin(1/sqrt 8)) = 0.9461, comfortably above 0.9.
696
+ * reference: grover 1996; boyer, brassard, hoefer, tapp 1998 iteration
697
+ * counting for m = 1 marked item of n = 8.
698
+ */
699
+ export function grover3() {
700
+ const sim = new quantumsim(3);
701
+ sim.h(0).h(1).h(2);
702
+ for (let iteration = 0; iteration < 2; iteration++) {
703
+ ccz(sim, 0, 1, 2);
704
+ sim.h(0).h(1).h(2);
705
+ sim.x(0).x(1).x(2);
706
+ ccz(sim, 0, 1, 2);
707
+ sim.x(0).x(1).x(2);
708
+ sim.h(0).h(1).h(2);
709
+ }
710
+ const dim = sim.dim;
711
+ const expected = new Array(dim).fill(0.0077);
712
+ expected[dim - 1] = 0.9461;
713
+ return {
714
+ sim,
715
+ name: 'grover3',
716
+ expectedprobs: expected,
717
+ reference: 'grover 1996; boyer-brassard-hoefer-tapp 1998',
718
+ note: 'prob(111) = 0.9461 theoretical; measured within float noise',
719
+ };
720
+ }
721
+ /**
722
+ * deutsch algorithm on 2 qubits (input qubit 0, ancilla qubit 1 in
723
+ * |->). the oracle is built from the truth table of f exactly as the
724
+ * four possible (x, y) -> (x, y xor f(x)) unitaries: identity, x on
725
+ * the ancilla, cnot(0,1) for f(x) = x, and x + cnot for f(x) = not x.
726
+ * phase kickback leaves qubit 0 in |0> for constant f and |1> for
727
+ * balanced f, so a single measurement decides the promise problem.
728
+ * reference: deutsch 1985; deutsch and jozsa, rapid solution of
729
+ * problems by quantum computation, proc r soc lond a 439, 553 (1992).
730
+ */
731
+ export function deutsch(f) {
732
+ const f0 = f(0);
733
+ const f1 = f(1);
734
+ const sim = new quantumsim(2);
735
+ sim.x(1);
736
+ sim.h(0).h(1);
737
+ if (f0 === 0 && f1 === 0) {
738
+ // constant zero: identity oracle, no gates.
739
+ }
740
+ else if (f0 === 1 && f1 === 1) {
741
+ sim.x(1);
742
+ }
743
+ else if (f0 === 0 && f1 === 1) {
744
+ sim.cnot(0, 1);
745
+ }
746
+ else {
747
+ sim.x(1);
748
+ sim.cnot(0, 1);
749
+ }
750
+ sim.h(0);
751
+ const measured = sim.measure(0);
752
+ return {
753
+ sim,
754
+ verdict: measured === 0 ? 'constant' : 'balanced',
755
+ measured,
756
+ expected: f0 === f1 ? 'constant' : 'balanced',
757
+ reference: 'deutsch 1985; deutsch-jozsa 1992 proc r soc a 439 553',
758
+ };
759
+ }
760
+ /* ------------------------------------------------------------------ */
761
+ /* context: quantum teleportation sketch */
762
+ /* ------------------------------------------------------------------ */
763
+ /**
764
+ * qteleport: teleports the state of qubit 0 to qubit 2 through a bell
765
+ * pair on qubits 1 and 2 (h(1), cnot(1,2)), the bell-basis measurement
766
+ * cnot(0,1) + h(0), then the classical corrections x/z on qubit 2
767
+ * conditioned on the two outcomes. the simulator runs the whole loop so
768
+ * the fidelity is exactly 1 for any of the three prepared inputs; the
769
+ * fidelity is read off the two amplitudes that survive the bell
770
+ * measurement (index m1*2 + m0 and its +4 partner on qubit 2).
771
+ * reference: bennett, brassard, crepeau, jozsa, peres, wootters,
772
+ * teleporting an unknown quantum state via dual classical and
773
+ * einstein-podolsky-rosen channels, prl 70, 1895 (1993).
774
+ */
775
+ export function qteleport(input = 'one') {
776
+ const sim = new quantumsim(3);
777
+ if (input === 'one') {
778
+ sim.x(0);
779
+ }
780
+ else if (input === 'plus') {
781
+ sim.h(0);
782
+ }
783
+ sim.h(1);
784
+ sim.cnot(1, 2);
785
+ sim.cnot(0, 1);
786
+ sim.h(0);
787
+ const outcome1 = sim.measure(1);
788
+ const outcome0 = sim.measure(0);
789
+ if (outcome1 === 1) {
790
+ sim.x(2);
791
+ }
792
+ if (outcome0 === 1) {
793
+ sim.z(2);
794
+ }
795
+ const lowindex = (outcome1 << 1) | outcome0;
796
+ const alow = sim.amplitude(lowindex);
797
+ const ahigh = sim.amplitude(lowindex + 4);
798
+ const fidelity = input === 'plus'
799
+ ? ((alow[0] + ahigh[0]) / Math.SQRT2) ** 2 + ((alow[1] + ahigh[1]) / Math.SQRT2) ** 2
800
+ : input === 'one'
801
+ ? ahigh[0] * ahigh[0] + ahigh[1] * ahigh[1]
802
+ : alow[0] * alow[0] + alow[1] * alow[1];
803
+ return {
804
+ sim,
805
+ outcome0,
806
+ outcome1,
807
+ fidelity,
808
+ input,
809
+ reference: 'bennett, brassard, crepeau, jozsa, peres, wootters 1993 prl 70 1895',
810
+ };
811
+ }
812
+ /**
813
+ * alice station: draws random key bits and random bases from
814
+ * node:crypto and prepares one 1-qubit quantumsim photon per bit
815
+ * (x for bit 1, extra h when the basis is diagonal).
816
+ */
817
+ export class alice {
818
+ #bits = [];
819
+ #bases = [];
820
+ constructor(count) {
821
+ try {
822
+ for (let i = 0; i < count; i++) {
823
+ this.#bits.push(randomInt(0, 2));
824
+ this.#bases.push(randomInt(0, 2));
825
+ }
826
+ }
827
+ catch (cause) {
828
+ throw new quantumerror({
829
+ code: 'randomness',
830
+ message: 'alice could not draw randomness from node:crypto',
831
+ detail: String(cause),
832
+ });
833
+ }
834
+ }
835
+ /** alice's raw key bits. */
836
+ get bits() {
837
+ return this.#bits;
838
+ }
839
+ /** alice's basis string (0 rectilinear, 1 diagonal). */
840
+ get bases() {
841
+ return this.#bases;
842
+ }
843
+ /**
844
+ * prepares the photon burst; each photon is a real 1-qubit state so
845
+ * the channel, eve and bob all act on amplitudes, not on labels.
846
+ */
847
+ prepare() {
848
+ return this.#bits.map((bit, i) => {
849
+ const photon = new quantumsim(1);
850
+ if (bit === 1) {
851
+ photon.x(0);
852
+ }
853
+ if (this.#bases[i] === 1) {
854
+ photon.h(0);
855
+ }
856
+ return photon;
857
+ });
858
+ }
859
+ }
860
+ /**
861
+ * bob station: measures each incoming photon in his own random bases
862
+ * (h before the z measurement when diagonal), collapsing the photon.
863
+ */
864
+ export class bob {
865
+ #bases = [];
866
+ #outcomes = [];
867
+ constructor(count) {
868
+ try {
869
+ for (let i = 0; i < count; i++) {
870
+ this.#bases.push(randomInt(0, 2));
871
+ }
872
+ }
873
+ catch (cause) {
874
+ throw new quantumerror({
875
+ code: 'randomness',
876
+ message: 'bob could not draw randomness from node:crypto',
877
+ detail: String(cause),
878
+ });
879
+ }
880
+ }
881
+ /** bob's basis string. */
882
+ get bases() {
883
+ return this.#bases;
884
+ }
885
+ /** bob's raw measurement outcomes. */
886
+ get outcomes() {
887
+ return this.#outcomes;
888
+ }
889
+ /**
890
+ * measures the whole burst and stores the classical outcomes;
891
+ * measuring a diagonal-basis photon in the rectilinear basis
892
+ * genuinely yields a coin flip, which is where intercept-resend
893
+ * damage shows up.
894
+ */
895
+ measure(photons) {
896
+ this.#outcomes.length = 0;
897
+ for (let i = 0; i < photons.length; i++) {
898
+ const photon = photons[i];
899
+ if (this.#bases[i] === 1) {
900
+ photon.h(0);
901
+ }
902
+ this.#outcomes.push(photon.measure(0));
903
+ }
904
+ return this.#outcomes;
905
+ }
906
+ }
907
+ /**
908
+ * eve station: intercept-resend attacker. she measures every photon in
909
+ * her own random basis (collapsing it) and resends a fresh photon
910
+ * prepared in that basis with the bit she saw. on sifted bits where
911
+ * alice and bob used the same basis, eve chose the wrong basis half
912
+ * the time and bob then errs half of those, so the qber lands at 25
913
+ * percent against 0 percent on a clean channel.
914
+ * reference: the intercept-resend attack is exercise material of every
915
+ * bb84 treatment since bennett-brassard 1984.
916
+ */
917
+ export class eve {
918
+ #bases = [];
919
+ #bits = [];
920
+ /** bases eve used (for audits). */
921
+ get bases() {
922
+ return this.#bases;
923
+ }
924
+ /** bits eve extracted (for audits). */
925
+ get bits() {
926
+ return this.#bits;
927
+ }
928
+ /** taps the burst and returns the resent photons. */
929
+ intercept(photons) {
930
+ this.#bases.length = 0;
931
+ this.#bits.length = 0;
932
+ return photons.map((photon) => {
933
+ const basis = randomInt(0, 2);
934
+ if (basis === 1) {
935
+ photon.h(0);
936
+ }
937
+ const bit = photon.measure(0);
938
+ const resend = new quantumsim(1);
939
+ if (bit === 1) {
940
+ resend.x(0);
941
+ }
942
+ if (basis === 1) {
943
+ resend.h(0);
944
+ }
945
+ this.#bases.push(basis);
946
+ this.#bits.push(bit);
947
+ return resend;
948
+ });
949
+ }
950
+ }
951
+ /**
952
+ * bb84 quantum channel: a photon pipeline that alice fills, an optional
953
+ * eve taps (counted), and bob drains. no network, no localhost — the
954
+ * channel is an in-memory queue standing in for fiber.
955
+ */
956
+ export class bb84channel {
957
+ #inflight = [];
958
+ #taps = 0;
959
+ /** sends a photon burst onto the channel. */
960
+ send(photons) {
961
+ this.#inflight = [...photons];
962
+ }
963
+ /**
964
+ * taps the channel: the operator receives the in-flight burst and its
965
+ * return value replaces it (intercept-resend); taps are counted.
966
+ */
967
+ tap(operator) {
968
+ this.#taps += 1;
969
+ this.#inflight = operator(this.#inflight);
970
+ return this.#inflight;
971
+ }
972
+ /** drains the channel for the receiver. */
973
+ receive() {
974
+ const out = this.#inflight;
975
+ this.#inflight = [];
976
+ return out;
977
+ }
978
+ /** number of taps observed on the channel (informational). */
979
+ get tapped() {
980
+ return this.#taps;
981
+ }
982
+ }
983
+ /**
984
+ * runs the complete bb84 flow over the simulated channel: alice
985
+ * prepares, the optional eve taps, bob measures, both sides sift on
986
+ * equal bases, the qber is computed over the full sifted key and the
987
+ * detection verdict comes from comparing a public sample of up to 128
988
+ * sifted bits (abort threshold 11 percent, the one-way bb84
989
+ * reconciliation bound of the shor-preskill lineage).
990
+ * reference: bennett and brassard, quantum cryptography: public key
991
+ * distribution and coin tossing, proc ieee int conf on computers,
992
+ * systems and signal processing, bangalore 1984, pp. 175-179.
993
+ */
994
+ export function runbb84(options = {}) {
995
+ const bits = options.bits ?? 1024;
996
+ if (!Number.isInteger(bits) || bits < 64 || bits > 8192) {
997
+ throw new quantumerror({
998
+ code: 'bitcount',
999
+ message: `bb84 burst size must be in [64, 8192], got ${bits}`,
1000
+ detail: '1024 keeps the qber estimate comfortably outside noise bands',
1001
+ });
1002
+ }
1003
+ const a = new alice(bits);
1004
+ const b = new bob(bits);
1005
+ const channel = new bb84channel();
1006
+ channel.send(a.prepare());
1007
+ if (options.eve === true) {
1008
+ const attacker = new eve();
1009
+ channel.tap((photons) => attacker.intercept(photons));
1010
+ }
1011
+ b.measure(channel.receive());
1012
+ const sifted = [];
1013
+ for (let i = 0; i < bits; i++) {
1014
+ if (a.bases[i] === b.bases[i]) {
1015
+ sifted.push(i);
1016
+ }
1017
+ }
1018
+ if (sifted.length < 16) {
1019
+ throw new quantumerror({
1020
+ code: 'siftempty',
1021
+ message: 'sifting kept fewer than 16 bits; raise the burst size',
1022
+ });
1023
+ }
1024
+ let mismatches = 0;
1025
+ for (const i of sifted) {
1026
+ if (a.bits[i] !== b.outcomes[i]) {
1027
+ mismatches += 1;
1028
+ }
1029
+ }
1030
+ const qber = mismatches / sifted.length;
1031
+ const order = [...sifted.keys()];
1032
+ for (let i = order.length - 1; i > 0; i--) {
1033
+ const j = randomInt(0, i + 1);
1034
+ const tmp = order[i];
1035
+ order[i] = order[j];
1036
+ order[j] = tmp;
1037
+ }
1038
+ const samplecount = Math.min(128, Math.max(8, Math.floor(sifted.length / 2)));
1039
+ const sample = new Set(order.slice(0, samplecount));
1040
+ let samplemismatch = 0;
1041
+ for (const i of sample) {
1042
+ if (a.bits[i] !== b.outcomes[i]) {
1043
+ samplemismatch += 1;
1044
+ }
1045
+ }
1046
+ const sampledqber = samplemismatch / sample.size;
1047
+ const keyalice = [];
1048
+ const keybob = [];
1049
+ for (const i of sifted) {
1050
+ if (sample.has(i))
1051
+ continue;
1052
+ keyalice.push(a.bits[i]);
1053
+ keybob.push(b.outcomes[i]);
1054
+ }
1055
+ return {
1056
+ keyalice,
1057
+ keybob,
1058
+ qber,
1059
+ detected: sampledqber > 0.11,
1060
+ siftedlen: sifted.length,
1061
+ sampledlen: sample.size,
1062
+ sampledqber,
1063
+ threshold: 0.11,
1064
+ reference: 'bb84, bangalore 1984; abort threshold from shor-preskill 2000 lineage',
1065
+ };
1066
+ }
1067
+ const deg2rad = Math.PI / 180;
1068
+ /**
1069
+ * measures qubit q of sim at analyzer angle a (degrees): applies
1070
+ * ry(-2a) so outcome 0 projects onto cos(a)|0> + sin(a)|1> and outcome
1071
+ * 1 onto its orthogonal partner, then collapses via measure.
1072
+ */
1073
+ function measureatangle(sim, q, angledeg) {
1074
+ sim.ry(-2 * angledeg * deg2rad, q);
1075
+ return sim.measure(q);
1076
+ }
1077
+ /**
1078
+ * prepares a fresh |+a> = cos(a)|0> + sin(a)|1> photon on qubit q;
1079
+ * used by eve to resend exactly what she measured.
1080
+ */
1081
+ function prepareangle(sim, q, angledeg, bit) {
1082
+ if (bit === 1) {
1083
+ sim.x(q);
1084
+ }
1085
+ if (angledeg !== 0) {
1086
+ sim.ry(2 * angledeg * deg2rad, q);
1087
+ }
1088
+ }
1089
+ /**
1090
+ * rune91: ekert-1991 entanglement-based key distribution on |phi+>
1091
+ * pairs. each round is half the time a key round (both parties pick
1092
+ * 0 or 45 degrees; equal angles give perfectly correlated bits on a
1093
+ * clean source) and half the time a chsh round (alice 0 or 45 degrees,
1094
+ * bob 22.5 or 67.5 degrees). the chsh statistic
1095
+ * s = e(0,22.5) - e(0,67.5) + e(45,22.5) + e(45,67.5) converges to
1096
+ * 2 sqrt(2) = 2.8284 for the entangled source and cannot exceed the
1097
+ * classical bound 2 once eve collapses the pairs, which is exactly the
1098
+ * e91 security test (bell-inequality violation as the eavesdropper
1099
+ * detector). an intercept-resend eve also pushes the matched-angle key
1100
+ * qber to 25 percent.
1101
+ * reference: ekert, quantum cryptography based on bell's theorem,
1102
+ * prl 67, 661 (1991); clauser-horne-shimony-holt 1969 prl 23 880;
1103
+ * bell 1964; aspect, dalibard, roger 1982.
1104
+ */
1105
+ export function rune91(options = {}) {
1106
+ const pairs = options.pairs ?? 2400;
1107
+ if (!Number.isInteger(pairs) || pairs < 200 || pairs > 200000) {
1108
+ throw new quantumerror({
1109
+ code: 'paircount',
1110
+ message: `e91 needs 200 to 200000 pairs, got ${pairs}`,
1111
+ detail: '2400 pairs put the chsh noise band about three sigma from the verdict line',
1112
+ });
1113
+ }
1114
+ const keytotals = { matched: 0, mismatch: 0 };
1115
+ const buckets = new Map();
1116
+ for (let round = 0; round < pairs; round++) {
1117
+ let pair = new quantumsim(2);
1118
+ pair.h(0).cnot(0, 1);
1119
+ if (options.eve === true) {
1120
+ const b0 = randomInt(0, 2) === 1 ? 45 : 0;
1121
+ const b1 = randomInt(0, 2) === 1 ? 45 : 0;
1122
+ const m0 = measureatangle(pair, 0, b0);
1123
+ const m1 = measureatangle(pair, 1, b1);
1124
+ const resend = new quantumsim(2);
1125
+ prepareangle(resend, 0, b0, m0);
1126
+ prepareangle(resend, 1, b1, m1);
1127
+ pair = resend;
1128
+ }
1129
+ const mode = randomInt(0, 2);
1130
+ if (mode === 0) {
1131
+ const adeg = randomInt(0, 2) === 1 ? 45 : 0;
1132
+ const bdeg = randomInt(0, 2) === 1 ? 45 : 0;
1133
+ const ma = measureatangle(pair, 0, adeg);
1134
+ const mb = measureatangle(pair, 1, bdeg);
1135
+ if (adeg === bdeg) {
1136
+ keytotals.matched += 1;
1137
+ if (ma !== mb) {
1138
+ keytotals.mismatch += 1;
1139
+ }
1140
+ }
1141
+ }
1142
+ else {
1143
+ const adeg = randomInt(0, 2) === 1 ? 45 : 0;
1144
+ const bdeg = randomInt(0, 2) === 1 ? 67.5 : 22.5;
1145
+ const ea = measureatangle(pair, 0, adeg);
1146
+ const eb = measureatangle(pair, 1, bdeg);
1147
+ const keyname = `${adeg}:${bdeg}`;
1148
+ const bucket = buckets.get(keyname) ?? { n: 0, agree: 0 };
1149
+ bucket.n += 1;
1150
+ if (ea === eb) {
1151
+ bucket.agree += 1;
1152
+ }
1153
+ buckets.set(keyname, bucket);
1154
+ }
1155
+ }
1156
+ const correlation = (a, b) => {
1157
+ const bucket = buckets.get(`${a}:${b}`);
1158
+ if (!bucket || bucket.n === 0) {
1159
+ return Number.NaN;
1160
+ }
1161
+ return (2 * bucket.agree) / bucket.n - 1;
1162
+ };
1163
+ const s = correlation(0, 22.5) - correlation(0, 67.5) + correlation(45, 22.5) + correlation(45, 67.5);
1164
+ if (!Number.isFinite(s)) {
1165
+ throw new quantumerror({
1166
+ code: 'chshsample',
1167
+ message: 'a chsh angle pair received zero samples; raise the pair count',
1168
+ });
1169
+ }
1170
+ const keylen = keytotals.matched;
1171
+ const qber = keylen === 0 ? Number.NaN : keytotals.mismatch / keylen;
1172
+ let chshpairs = 0;
1173
+ for (const bucket of buckets.values()) {
1174
+ chshpairs += bucket.n;
1175
+ }
1176
+ const detected = s <= 2.4 || (Number.isFinite(qber) && qber > 0.05);
1177
+ return {
1178
+ s,
1179
+ classicalbound: 2,
1180
+ quantumbound: 2 * Math.SQRT2,
1181
+ detected,
1182
+ keylen,
1183
+ qber,
1184
+ pairs,
1185
+ chshpairs,
1186
+ reference: 'ekert 1991 prl 67 661; chsh 1969; bell 1964; aspect 1982',
1187
+ };
1188
+ }
1189
+ /* ------------------------------------------------------------------ */
1190
+ /* context: qrng (quantum-inspired random, honest anu fallback) */
1191
+ /* ------------------------------------------------------------------ */
1192
+ /**
1193
+ * quantuminspiredrandom: draws count integers in [min, max) from the
1194
+ * node crypto CSPRNG via randomInt (node rejection-samples internally,
1195
+ * so the stream is unbiased). this is a classical CSPRNG standing in
1196
+ * for a QRNG photon source; the API shape matches hardware QRNG
1197
+ * services (count + integer range in, uniform integers out) so the
1198
+ * integration seam is already quantum-ready. no physics is claimed.
1199
+ */
1200
+ export function quantuminspiredrandom(count, options = {}) {
1201
+ if (!Number.isInteger(count) || count < 1 || count > 1048576) {
1202
+ throw new quantumerror({
1203
+ code: 'countrange',
1204
+ message: `qrng count must be in [1, 1048576], got ${count}`,
1205
+ });
1206
+ }
1207
+ const min = options.min ?? 0;
1208
+ const max = options.max ?? 256;
1209
+ if (!Number.isInteger(min) || !Number.isInteger(max) || min >= max || max - min > 2 ** 36) {
1210
+ throw new quantumerror({
1211
+ code: 'range',
1212
+ message: `qrng range needs integers min < max with span <= 2^36, got [${min}, ${max})`,
1213
+ });
1214
+ }
1215
+ try {
1216
+ const values = [];
1217
+ for (let i = 0; i < count; i++) {
1218
+ values.push(randomInt(min, max));
1219
+ }
1220
+ return values;
1221
+ }
1222
+ catch (cause) {
1223
+ throw new quantumerror({
1224
+ code: 'randomness',
1225
+ message: 'crypto.randomInt failed while filling the qrng batch',
1226
+ detail: String(cause),
1227
+ });
1228
+ }
1229
+ }
1230
+ /**
1231
+ * anuqrng: optional asynchronous fetch of the australian national
1232
+ * university quantum random numbers service (api.quantumnumbers.io,
1233
+ * successor of qrng.anu.edu.au), which digitizes vacuum fluctuations.
1234
+ * the planner is honest: without network egress or an api key the call
1235
+ * fails fast (abort timeout 2500 ms default) and the function falls
1236
+ * back to the same CSPRNG as quantuminspiredrandom, reporting
1237
+ * source: 'csprng'. anu values are 64-bit unsigned integers folded
1238
+ * into the requested range with one modulo (bias below 2^-32 for any
1239
+ * practical span, documented here rather than hidden).
1240
+ */
1241
+ export async function anuqrng(count, options = {}) {
1242
+ const min = options.min ?? 0;
1243
+ const max = options.max ?? 256;
1244
+ const span = max - min;
1245
+ if (!Number.isInteger(count) ||
1246
+ count < 1 ||
1247
+ count > 1024 ||
1248
+ !Number.isInteger(min) ||
1249
+ min >= max) {
1250
+ throw new quantumerror({
1251
+ code: 'range',
1252
+ message: `anuqrng needs count in [1, 1024] and integer min < max, got count=${count}`,
1253
+ });
1254
+ }
1255
+ const timeoutms = options.timeoutms ?? 2500;
1256
+ const apikey = options.apikey ?? '';
1257
+ try {
1258
+ const url = `https://api.quantumnumbers.io/qranum/v1/generate?apikey=${apikey}` +
1259
+ `&number=${count}&size=8`;
1260
+ const response = await fetch(url, { signal: AbortSignal.timeout(timeoutms) });
1261
+ if (!response.ok) {
1262
+ throw new Error(`anu http status ${response.status}`);
1263
+ }
1264
+ const payload = (await response.json());
1265
+ if (!Array.isArray(payload.data) || payload.data.length < count) {
1266
+ throw new Error('anu payload did not carry enough values');
1267
+ }
1268
+ const values = payload.data.slice(0, count).map((value) => min + (Number(value) % span));
1269
+ if (values.some((value) => !Number.isInteger(value) || value < min || value >= max)) {
1270
+ throw new Error('anu payload contained non-integer entries');
1271
+ }
1272
+ return {
1273
+ values,
1274
+ source: 'anu',
1275
+ note: 'vacuum-fluctuation source, api.quantumnumbers.io',
1276
+ };
1277
+ }
1278
+ catch (cause) {
1279
+ return {
1280
+ values: quantuminspiredrandom(count, { min, max }),
1281
+ source: 'csprng',
1282
+ note: `anu fetch unavailable (${String(cause)}); honest CSPRNG fallback`,
1283
+ };
1284
+ }
1285
+ }
1286
+ /**
1287
+ * convenience bytes draw used by the self check and available to
1288
+ * integrators: crypto.randomBytes surfaced under the qrng banner with
1289
+ * the same honesty note as quantuminspiredrandom.
1290
+ */
1291
+ export function quantuminspiredbytes(count) {
1292
+ if (!Number.isInteger(count) || count < 1 || count > 1048576) {
1293
+ throw new quantumerror({
1294
+ code: 'countrange',
1295
+ message: `qrng byte count must be in [1, 1048576], got ${count}`,
1296
+ });
1297
+ }
1298
+ try {
1299
+ return randomBytes(count);
1300
+ }
1301
+ catch (cause) {
1302
+ throw new quantumerror({
1303
+ code: 'randomness',
1304
+ message: 'crypto.randomBytes failed',
1305
+ detail: String(cause),
1306
+ });
1307
+ }
1308
+ }
1309
+ /* ------------------------------------------------------------------ */
1310
+ /* context: dnavault codec (goldman 2013 ternary rotation) */
1311
+ /* ------------------------------------------------------------------ */
1312
+ /**
1313
+ * dnavault codec constants: 4 strands addressed by blockindex mod 4,
1314
+ * each block synthesized twice (on its home strand and the next one)
1315
+ * so decoding survives the loss of any single strand; every byte maps
1316
+ * to 6 ternary digits (3^6 = 729 > 256) and every digit to one
1317
+ * nucleotide through the goldman rotation next = (digit + 1 + previous)
1318
+ * mod 4, which makes consecutive repeats impossible (homopolymer run
1319
+ * length 1, stricter than the standard run-length <= 3 synthesis
1320
+ * constraint). reference: goldman et al., towards practical,
1321
+ * high-capacity, low-maintenance information storage in synthesized
1322
+ * dna, nature 494, 77-80 (2013), doi:10.1038/nature11875.
1323
+ */
1324
+ export const dnavaultspec = {
1325
+ strandcount: 4,
1326
+ redundancy: 2,
1327
+ blockpayloadbytes: 32,
1328
+ blockframebytes: 35,
1329
+ nucleotidesperblock: 210,
1330
+ tritsperbyte: 6,
1331
+ maxinputbytes: 65536,
1332
+ homopolymerrunmax: 1,
1333
+ rule: 'next = (digit + 1 + previous) mod 4, digit in {0,1,2}',
1334
+ reference: 'goldman et al. 2013 nature 494 77-80 doi:10.1038/nature11875',
1335
+ };
1336
+ const nucleotides = ['A', 'C', 'G', 'T'];
1337
+ const nucleotideindex = { A: 0, C: 1, G: 2, T: 3 };
1338
+ const powersof3 = [1, 3, 9, 27, 81, 243];
1339
+ /**
1340
+ * encodes bytes into four dna strands with real goldman-2013 rules:
1341
+ * a 4-byte big-endian length prefix, 32-byte payload blocks framed as
1342
+ * [index u16 be][payload 32][checksum u8 of index + payload], ternary
1343
+ * rotation encoding per byte, dual-strand placement (blockindex mod 4
1344
+ * and (blockindex + 1) mod 4). the archive planner guard caps input at
1345
+ * 64 kib; real synthesis runs are planned, not executed, here.
1346
+ */
1347
+ export function dnavaultencode(bytes) {
1348
+ if (bytes.length > dnavaultspec.maxinputbytes) {
1349
+ throw new quantumerror({
1350
+ code: 'archiveguard',
1351
+ message: `dnavaultencode is an archive planner: input capped at ${dnavaultspec.maxinputbytes} bytes, got ${bytes.length}`,
1352
+ detail: 'use the capacity planner (planodefault) for larger archives',
1353
+ });
1354
+ }
1355
+ const stream = [
1356
+ (bytes.length >>> 24) & 0xff,
1357
+ (bytes.length >>> 16) & 0xff,
1358
+ (bytes.length >>> 8) & 0xff,
1359
+ bytes.length & 0xff,
1360
+ ...bytes,
1361
+ ];
1362
+ const blocks = Math.ceil(stream.length / dnavaultspec.blockpayloadbytes);
1363
+ const strands = [[], [], [], []];
1364
+ for (let b = 0; b < blocks; b++) {
1365
+ const payload = [];
1366
+ for (let k = 0; k < dnavaultspec.blockpayloadbytes; k++) {
1367
+ payload.push(stream[b * dnavaultspec.blockpayloadbytes + k] ?? 0);
1368
+ }
1369
+ const hi = (b >>> 8) & 0xff;
1370
+ const lo = b & 0xff;
1371
+ let sum = hi + lo;
1372
+ for (const byte of payload) {
1373
+ sum += byte;
1374
+ }
1375
+ const frame = [hi, lo, ...payload, sum & 0xff];
1376
+ let oligo = '';
1377
+ let previous = 0;
1378
+ for (const byte of frame) {
1379
+ let value = byte;
1380
+ for (let k = 0; k < dnavaultspec.tritsperbyte; k++) {
1381
+ const digit = value % 3;
1382
+ value = (value - digit) / 3;
1383
+ const base = (digit + previous + 1) % 4;
1384
+ oligo += nucleotides[base];
1385
+ previous = base;
1386
+ }
1387
+ }
1388
+ strands[b % 4].push(oligo);
1389
+ strands[(b + 1) % 4].push(oligo);
1390
+ }
1391
+ const oligos = blocks * dnavaultspec.redundancy;
1392
+ return {
1393
+ strands: strands.map((strand) => strand.join('')),
1394
+ blocks,
1395
+ oligos,
1396
+ nucleotides: oligos * dnavaultspec.nucleotidesperblock,
1397
+ redundancy: dnavaultspec.redundancy,
1398
+ homopolymerrunmax: dnavaultspec.homopolymerrunmax,
1399
+ reference: dnavaultspec.reference,
1400
+ };
1401
+ }
1402
+ /* ------------------------------------------------------------------ */
1403
+ /* context: dnavault decode (checksums, redundancy, roundtrip) */
1404
+ /* ------------------------------------------------------------------ */
1405
+ /**
1406
+ * decodes strands back to bytes: every 210-nucleotide oligo is
1407
+ * de-rotated to a 35-byte frame, checksum-verified, deduplicated by
1408
+ * block index and reassembled in order. oligos failing checksum or
1409
+ * carrying invalid letters are dropped silently because every block
1410
+ * exists on two strands; a genuinely missing index throws.
1411
+ */
1412
+ export function dnavaultdecode(strands) {
1413
+ const byindex = new Map();
1414
+ for (const strand of strands) {
1415
+ const clean = strand.replace(/\s+/g, '').toUpperCase();
1416
+ for (let start = 0; start + dnavaultspec.nucleotidesperblock <= clean.length; start += dnavaultspec.nucleotidesperblock) {
1417
+ const oligo = clean.slice(start, start + dnavaultspec.nucleotidesperblock);
1418
+ try {
1419
+ const frame = [];
1420
+ let previous = 0;
1421
+ let value = 0;
1422
+ let power = 0;
1423
+ for (const letter of oligo) {
1424
+ const base = nucleotideindex[letter];
1425
+ if (base === undefined) {
1426
+ throw new Error(`non-nucleotide letter ${letter}`);
1427
+ }
1428
+ const digit = (((base - previous - 1) % 4) + 4) % 4;
1429
+ if (digit > 2) {
1430
+ throw new Error('rotation arithmetic produced an impossible digit');
1431
+ }
1432
+ value += digit * powersof3[power];
1433
+ power += 1;
1434
+ if (power === dnavaultspec.tritsperbyte) {
1435
+ frame.push(value);
1436
+ value = 0;
1437
+ power = 0;
1438
+ }
1439
+ previous = base;
1440
+ }
1441
+ const index = (frame[0] << 8) | frame[1];
1442
+ let sum = frame[0] + frame[1];
1443
+ for (let k = 2; k < frame.length - 1; k++) {
1444
+ sum += frame[k];
1445
+ }
1446
+ if ((sum & 0xff) !== frame[frame.length - 1]) {
1447
+ throw new Error(`checksum mismatch on block ${index}`);
1448
+ }
1449
+ if (!byindex.has(index)) {
1450
+ byindex.set(index, frame);
1451
+ }
1452
+ }
1453
+ catch {
1454
+ // corrupted oligo: redundancy owns recovery, skip it.
1455
+ }
1456
+ }
1457
+ }
1458
+ const count = byindex.size;
1459
+ if (count === 0) {
1460
+ throw new quantumerror({
1461
+ code: 'unrecoverable',
1462
+ message: 'no valid dnavault block survived decoding',
1463
+ });
1464
+ }
1465
+ for (let b = 0; b < count; b++) {
1466
+ if (!byindex.has(b)) {
1467
+ throw new quantumerror({
1468
+ code: 'blockmissing',
1469
+ message: `dnavault block ${b} is missing across all strands`,
1470
+ });
1471
+ }
1472
+ }
1473
+ const stream = [];
1474
+ for (let b = 0; b < count; b++) {
1475
+ const frame = byindex.get(b);
1476
+ if (!frame) {
1477
+ throw new quantumerror({
1478
+ code: 'blockmissing',
1479
+ message: `dnavault block ${b} vanished between the has check and the read`,
1480
+ });
1481
+ }
1482
+ for (let k = 2; k < frame.length - 1; k++) {
1483
+ stream.push(frame[k]);
1484
+ }
1485
+ }
1486
+ const length = ((stream[0] << 24) | (stream[1] << 16) | (stream[2] << 8) | stream[3]) >>> 0;
1487
+ if (length > stream.length - 4) {
1488
+ throw new quantumerror({
1489
+ code: 'lengthcorrupt',
1490
+ message: `declared length ${length} exceeds decoded payload ${stream.length - 4}`,
1491
+ });
1492
+ }
1493
+ return Uint8Array.from(stream.slice(4, 4 + length));
1494
+ }
1495
+ /* ------------------------------------------------------------------ */
1496
+ /* context: dnavault capacity planner (215 pb/g) */
1497
+ /* ------------------------------------------------------------------ */
1498
+ /**
1499
+ * dnavault capacity anchors: the widely quoted 215 petabytes per gram
1500
+ * of dna figure (church 2012 science era synthesis estimates, echoed
1501
+ * by the nature 2013 news coverage around goldman et al.) anchors the
1502
+ * physical planner; the codec rates above are what this module
1503
+ * actually charges.
1504
+ */
1505
+ export const dnacapacityspec = {
1506
+ bytespergram: 2.15e17,
1507
+ densityquote: '215 petabytes per gram of dna',
1508
+ densityreference: 'church, gao, kosuri 2012 science 337 1628 era estimates; nature news 2013',
1509
+ synthesispitch: 'archive planner only; no oligo is ordered or synthesized',
1510
+ };
1511
+ /**
1512
+ * dnavault capacity estimate for an archive of sizebytes: dna grams at
1513
+ * the 215 pb/g density, oligo and nucleotide counts at this codec's
1514
+ * real rates, and the storage overhead ratio.
1515
+ */
1516
+ export function dnacapacity(sizebytes) {
1517
+ if (!Number.isFinite(sizebytes) || sizebytes <= 0 || sizebytes > 2 ** 40) {
1518
+ throw new quantumerror({
1519
+ code: 'sizerange',
1520
+ message: `capacity planner accepts archives up to 1 tebibyte, got ${sizebytes}`,
1521
+ });
1522
+ }
1523
+ const payload = sizebytes + 4;
1524
+ const blocks = Math.ceil(payload / dnavaultspec.blockpayloadbytes);
1525
+ const oligos = blocks * dnavaultspec.redundancy;
1526
+ const nucleotides = oligos * dnavaultspec.nucleotidesperblock;
1527
+ return {
1528
+ grams: sizebytes / dnacapacityspec.bytespergram,
1529
+ oligos,
1530
+ nucleotides,
1531
+ overhead: (blocks * dnavaultspec.blockframebytes + 4) / sizebytes - 1,
1532
+ density: dnacapacityspec.densityquote,
1533
+ reference: dnacapacityspec.densityreference,
1534
+ };
1535
+ }
1536
+ /**
1537
+ * planodefault: the default dna archive plan for a payload of
1538
+ * sizebytes — dna mass in grams (215 pb/g density), number of oligo
1539
+ * strands to synthesize, and the codec overhead fraction. this is the
1540
+ * planner entry point for the storage tier; nothing is written.
1541
+ */
1542
+ export function planodefault(sizebytes) {
1543
+ const estimate = dnacapacity(sizebytes);
1544
+ return {
1545
+ grams: estimate.grams,
1546
+ strands: estimate.oligos,
1547
+ overhead: estimate.overhead,
1548
+ storage: 'dna (goldman 2013 ternary rotation, 4 strands, dual placement)',
1549
+ reference: `${dnavaultspec.reference}; ${estimate.reference}`,
1550
+ };
1551
+ }
1552
+ /* ------------------------------------------------------------------ */
1553
+ /* context: optical 5d quartz planner (360 tb/disc) */
1554
+ /* ------------------------------------------------------------------ */
1555
+ /**
1556
+ * opticalvault anchors: 5d femtosecond-laser nanostructuring of fused
1557
+ * quartz as demonstrated by the university of southampton
1558
+ * optoelectronics research centre (zhang, kazansky et al., 2013-2016):
1559
+ * 360 tb per disc headline capacity, survival to 1000 c and the quoted
1560
+ * 13.8-billion-year room-temperature stability. the five dimensions
1561
+ * are three spatial coordinates plus nanograting orientation and
1562
+ * retardance. the write parameters below are planning defaults for the
1563
+ * femtosecond pass, not device constants.
1564
+ */
1565
+ export const opticalvaultspec = {
1566
+ bytesperdisc: 3.6e14,
1567
+ layersperdisc: 100,
1568
+ logicalbitsperdot: 4,
1569
+ redundancycopies: 3,
1570
+ stabilityc: 1000,
1571
+ lifetimeyearsroom: 1.38e10,
1572
+ pulsedurationfs: 280,
1573
+ wavelengthnm: 1030,
1574
+ layerspacingum: 4.5,
1575
+ medium: 'fused quartz',
1576
+ dimensions: 'x, y, z + nanograting orientation + retardance',
1577
+ reference: 'zhang, gecavicius, beresna, kazansky 2013 cleo; southampton orc 2013-2016 (360 tb/disc, 13.8 billion years at room temperature)',
1578
+ };
1579
+ /**
1580
+ * opticalplan: recording plan for a 5d quartz archive of sizebytes:
1581
+ * disc count at 360 tb per disc with three-copy redundancy, layer and
1582
+ * nanograting dot counts at 4 logical bits per dot, and the
1583
+ * femtosecond write pass description. pure planner output.
1584
+ */
1585
+ export function opticalplan(sizebytes) {
1586
+ if (!Number.isFinite(sizebytes) || sizebytes <= 0 || sizebytes > 2 ** 50) {
1587
+ throw new quantumerror({
1588
+ code: 'sizerange',
1589
+ message: `optical planner accepts archives up to 1 pebibyte, got ${sizebytes}`,
1590
+ });
1591
+ }
1592
+ const stored = sizebytes * opticalvaultspec.redundancycopies;
1593
+ const discs = Math.max(1, Math.ceil(stored / opticalvaultspec.bytesperdisc));
1594
+ const dots = Math.ceil((stored * 8) / opticalvaultspec.logicalbitsperdot);
1595
+ return {
1596
+ discs,
1597
+ layers: discs * opticalvaultspec.layersperdisc,
1598
+ dots,
1599
+ redundancy: opticalvaultspec.redundancycopies,
1600
+ lifetimeyearsroom: opticalvaultspec.lifetimeyearsroom,
1601
+ stabilityc: opticalvaultspec.stabilityc,
1602
+ writeplan: {
1603
+ pulsedurationfs: opticalvaultspec.pulsedurationfs,
1604
+ wavelengthnm: opticalvaultspec.wavelengthnm,
1605
+ layerspacingum: opticalvaultspec.layerspacingum,
1606
+ dimensions: opticalvaultspec.dimensions,
1607
+ },
1608
+ reference: opticalvaultspec.reference,
1609
+ note: 'planning defaults, not device constants; lifetime figure is the quoted upper bound',
1610
+ };
1611
+ }
1612
+ /* ------------------------------------------------------------------ */
1613
+ /* context: holographic note (microsoft hsd) and storage compare */
1614
+ /* ------------------------------------------------------------------ */
1615
+ /**
1616
+ * holographic storage note for the storage tier compare: microsoft
1617
+ * research announced the holographic storage device (hsd) program in
1618
+ * 2024 — page-oriented holograms in a photosensitive wafer cartridge,
1619
+ * about 1.4 tb per 12-centimeter disc form factor with a multi-terabyte
1620
+ * roadmap. this module keeps it as a comparison note only; the
1621
+ * concrete planners shipped here are dna and 5d quartz.
1622
+ */
1623
+ export const holographicnote = {
1624
+ vendor: 'microsoft research',
1625
+ program: 'hsd (holographic storage device), announced 2024',
1626
+ capacity: 'about 1.4 tb per 12-cm disc, multi-terabyte roadmap',
1627
+ medium: 'photosensitive holographic wafer cartridges',
1628
+ position: 'comparison note; no planner shipped for this tier',
1629
+ };
1630
+ /**
1631
+ * storagecompare: one-line planner comparison across the three
1632
+ * quantum-adjacent storage tiers this module knows about.
1633
+ */
1634
+ export function storagecompare(sizebytes) {
1635
+ const dna = planodefault(sizebytes);
1636
+ const optical = opticalplan(sizebytes);
1637
+ return [
1638
+ {
1639
+ tier: 'dna',
1640
+ units: `${dna.strands} oligo strands`,
1641
+ massorunits: `${dna.grams.toExponential(3)} g of dna`,
1642
+ lifetime: 'centuries dry and dark (synthesis-dependent)',
1643
+ reference: 'goldman 2013 nature 494 77-80',
1644
+ },
1645
+ {
1646
+ tier: 'optical5d',
1647
+ units: `${optical.discs} quartz disc${optical.discs === 1 ? '' : 's'}`,
1648
+ massorunits: `${optical.layers} layers, ${optical.dots.toExponential(3)} dots`,
1649
+ lifetime: `quoted ${optical.lifetimeyearsroom.toExponential(2)} years at room temperature, ${optical.stabilityc} c survival`,
1650
+ reference: 'southampton orc 2013-2016',
1651
+ },
1652
+ {
1653
+ tier: 'holographic',
1654
+ units: `${Math.max(1, Math.ceil((sizebytes * 3) / 1.4e12))} hsd discs (planner sketch)`,
1655
+ massorunits: 'wafer cartridges',
1656
+ lifetime: 'decades, drive-dependent',
1657
+ reference: 'microsoft hsd 2024 announcement',
1658
+ },
1659
+ ];
1660
+ }
1661
+ /**
1662
+ * qrambucketbrigade: classical simulation of the giovannetti-lloyd-
1663
+ * maccone bucket-brigade qram. a classical ram read energizes n word
1664
+ * lines; the bucket brigade routes one bus down a binary switch tree so
1665
+ * only log2(n) switches per read must flip (and, in the quantum
1666
+ * version, only o(log n) qubits must be active, which is what makes
1667
+ * quantum-addressed lookup of a superposition affordable). the switch
1668
+ * tree is simulated hop by hop and the read result carries the trace.
1669
+ * reference: giovannetti, lloyd, maccone, quantum random access memory,
1670
+ * prl 100, 160501 (2008); giovannetti, lloyd, maccone, architectures
1671
+ * for a quantum random access memory, pra 78, 052310 (2008).
1672
+ */
1673
+ export class qrambucketbrigade {
1674
+ #cells;
1675
+ #addressbits;
1676
+ constructor(cells) {
1677
+ if (!Number.isInteger(cells) || cells < 2 || cells > 256 || (cells & (cells - 1)) !== 0) {
1678
+ throw new quantumerror({
1679
+ code: 'cellcount',
1680
+ message: `qram needs a power-of-two cell count in [2, 256], got ${cells}`,
1681
+ });
1682
+ }
1683
+ this.#cells = new Array(cells).fill(0);
1684
+ this.#addressbits = Math.round(Math.log2(cells));
1685
+ }
1686
+ /** number of addressable cells. */
1687
+ get cellscount() {
1688
+ return this.#cells.length;
1689
+ }
1690
+ /** address width in bits (the tree depth). */
1691
+ get addressbits() {
1692
+ return this.#addressbits;
1693
+ }
1694
+ /** switch count of the tree (inner nodes; n - 1 for n cells). */
1695
+ get switchcount() {
1696
+ return this.#cells.length - 1;
1697
+ }
1698
+ /** classical write into one cell (energizes one word line). */
1699
+ write(address, value) {
1700
+ this.#guardaddress(address);
1701
+ this.#cells[address] = value;
1702
+ }
1703
+ /** lists the cells as an address/value table. */
1704
+ cells() {
1705
+ return this.#cells.map((value, address) => ({ address, value }));
1706
+ }
1707
+ /**
1708
+ * routes one read down the bucket-brigade tree: at level l the switch
1709
+ * forwards along address bit (addressbits - 1 - l); the bus ends at
1710
+ * the leaf and the trace records every switch node id visited
1711
+ * (root id 1, children 2i and 2i + 1).
1712
+ */
1713
+ read(address) {
1714
+ this.#guardaddress(address);
1715
+ const path = [1];
1716
+ let node = 1;
1717
+ for (let level = 0; level < this.#addressbits; level++) {
1718
+ const bit = (address >> (this.#addressbits - 1 - level)) & 1;
1719
+ node = node * 2 + bit;
1720
+ path.push(node);
1721
+ }
1722
+ return {
1723
+ address,
1724
+ value: this.#cells[address],
1725
+ hops: this.#addressbits,
1726
+ path,
1727
+ switchesactive: this.#addressbits,
1728
+ classicalwritelines: this.#cells.length,
1729
+ };
1730
+ }
1731
+ #guardaddress(address) {
1732
+ if (!Number.isInteger(address) || address < 0 || address >= this.#cells.length) {
1733
+ throw new quantumerror({
1734
+ code: 'addressrange',
1735
+ message: `qram address must be in [0, ${this.#cells.length - 1}], got ${address}`,
1736
+ });
1737
+ }
1738
+ }
1739
+ }
1740
+ /**
1741
+ * qramdemo: the n=8 showcase — 3 switch levels, 7 switches, every read
1742
+ * routes 3 hops against 8 classical word lines, plus a note of what
1743
+ * the quantum version would query in one shot (a superposed address
1744
+ * returning a superposed memory word).
1745
+ */
1746
+ export function qramdemo() {
1747
+ const qram = new qrambucketbrigade(8);
1748
+ for (let address = 0; address < 8; address++) {
1749
+ qram.write(address, address * 100 + 7);
1750
+ }
1751
+ const reads = [qram.read(0), qram.read(3), qram.read(7)];
1752
+ return {
1753
+ reads,
1754
+ levels: qram.addressbits,
1755
+ switches: qram.switchcount,
1756
+ hops: qram.addressbits,
1757
+ classicalwritelines: qram.cellscount,
1758
+ reference: 'giovannetti, lloyd, maccone 2008 prl 100 160501',
1759
+ };
1760
+ }
1761
+ /**
1762
+ * shorplan(n): returns the theoretical shor circuit for the
1763
+ * factorization and never runs it. honesty clause: compiled
1764
+ * controlled-modular-exponentiation networks for any semiprime beyond
1765
+ * toy size grow past the 20-qubit statevector budget of this
1766
+ * simulator (numbers above 15 need more than 20 clean qubits plus
1767
+ * ancillas before scheduling even starts in js), and the 2013
1768
+ * "oversimplifying quantum factoring" literature shows compressed
1769
+ * order-finding circuits for 15 can factor without any genuine quantum
1770
+ * advantage — so the module plans, cites and stops.
1771
+ * references: shor 1994 focs / siam j comput 26 1484 (1997);
1772
+ * vedal, barenco, ekert 1996 pra 54 147; vandersypen et al. 2001
1773
+ * nature 414 883 (the 7-qubit nmr run of 15); smolin, gambetta,
1774
+ * smith 2013 pra 87 030302 "oversimplifying quantum factoring".
1775
+ */
1776
+ export function shorplan(n) {
1777
+ if (!Number.isInteger(n) || n < 4) {
1778
+ throw new quantumerror({
1779
+ code: 'compositerange',
1780
+ message: `shorplan needs an integer >= 4, got ${n}`,
1781
+ });
1782
+ }
1783
+ const isfifteen = n === 15;
1784
+ const workqubits = isfifteen ? 4 : Math.max(4, Math.ceil(Math.log2(n)));
1785
+ const countingqubits = isfifteen ? 3 : Math.max(3, 2 * workqubits - 5);
1786
+ const stages = [
1787
+ 'init work register to |1> (x on the low work qubit)',
1788
+ `hadamard over the ${countingqubits} counting qubits (uniform superposition of exponents x)`,
1789
+ 'controlled a^x mod n per exponent bit (order-4 swap pattern for a in {7, 11} when n = 15)',
1790
+ `inverse qft over the ${countingqubits} counting qubits`,
1791
+ 'measure counting register: phases concentrate on k/4 with r = 4',
1792
+ 'continued fractions on the measured phase -> candidate order r',
1793
+ 'gcd(a^(r/2) - 1, n), gcd(a^(r/2) + 1, n) -> classical factors',
1794
+ ];
1795
+ return {
1796
+ n,
1797
+ executable: false,
1798
+ qubits: countingqubits + workqubits,
1799
+ countingqubits,
1800
+ workqubits,
1801
+ bases: isfifteen ? [7, 11] : [2],
1802
+ expectedperiod: isfifteen ? 4 : 0,
1803
+ factors: isfifteen ? [3, 5] : [],
1804
+ stages,
1805
+ gatesestimate: isfifteen ? 400 : countingqubits * workqubits * workqubits * 12,
1806
+ reason: 'theoretical plan only: controlled modular exponentiation for semiprimes beyond 15 exceeds the 20-qubit statevector envelope of this simulator, and compressed 15-circuits are known to factor without quantum advantage (smolin-gambetta-smith 2013)',
1807
+ references: [
1808
+ 'shor 1994 focs; siam j comput 26 1484 (1997)',
1809
+ 'vedal-barenco-ekert 1996 pra 54 147',
1810
+ 'vandersypen et al. 2001 nature 414 883',
1811
+ 'smolin-gambetta-smith 2013 pra 87 030302',
1812
+ ],
1813
+ };
1814
+ }
1815
+ /* ------------------------------------------------------------------ */
1816
+ /* context: registry (capability catalog) */
1817
+ /* ------------------------------------------------------------------ */
1818
+ /**
1819
+ * freeze helper with a const type parameter so the registry literal
1820
+ * keeps its exact readonly member types after freezing.
1821
+ */
1822
+ function freeze(spec) {
1823
+ return Object.freeze(spec);
1824
+ }
1825
+ /**
1826
+ * quantumregistry: the capability catalog of this module for the engine
1827
+ * integrator: simulator envelope, provable algorithms, key-exchange
1828
+ * protocols, storage tiers, randomness sources and primary citations.
1829
+ */
1830
+ export const quantumregistry = freeze({
1831
+ simulator: 'statevector',
1832
+ precision: 'float64 interleaved re/im',
1833
+ maxqubits: 20,
1834
+ algorithms: [
1835
+ 'bellstate',
1836
+ 'ghzstate',
1837
+ 'grover2',
1838
+ 'grover3',
1839
+ 'deutsch',
1840
+ 'qteleport',
1841
+ 'shorplan (plan only)',
1842
+ ],
1843
+ protocols: ['bb84', 'e91'],
1844
+ storage: ['dna goldman 2013', 'optical 5d quartz', 'holographic note', 'qram bucket brigade'],
1845
+ random: ['csprng (node:crypto)', 'anu qrng (optional, fallback)'],
1846
+ sources: [
1847
+ 'goldman et al. 2013 nature 494 77-80 doi:10.1038/nature11875',
1848
+ 'church, gao, kosuri 2012 science 337 1628 (215 pb/g era)',
1849
+ 'grover 1996 stoc arxiv:quant-ph/9605043',
1850
+ 'deutsch-jozsa 1992 proc r soc lond a 439 553',
1851
+ 'bennett-brassard 1984 bangalore proceedings 175-179',
1852
+ 'ekert 1991 prl 67 661; chsh 1969 prl 23 880; bell 1964',
1853
+ 'bennett et al. 1993 prl 70 1895 (teleportation)',
1854
+ 'giovannetti-lloyd-maccone 2008 prl 100 160501 (qram)',
1855
+ 'shor 1994/1997; vandersypen 2001 nature 414 883; smolin-gambetta-smith 2013',
1856
+ 'zhang-kazansky et al. 2013-2016 southampton orc (5d quartz)',
1857
+ 'microsoft research hsd 2024 announcement',
1858
+ 'anu quantum numbers, api.quantumnumbers.io',
1859
+ ],
1860
+ });
1861
+ /**
1862
+ * quantumselfcheck: runs every documented claim of this module against
1863
+ * the real simulator — bell/grover/deutsch/teleport statistics, bb84
1864
+ * with and without an eavesdropper, the e91 chsh violation, the dna
1865
+ * roundtrip including strand loss, the qrng range, the qram routing
1866
+ * depth, the shor honesty clause, the 20-qubit envelope guard and the
1867
+ * using/disposal guard. returns the row table plus pass counts so the
1868
+ * integrator can gate ci on it. randomness is live node:crypto, so the
1869
+ * protocol rows carry the statistical margins described in their
1870
+ * circuit references.
1871
+ */
1872
+ export function quantumselfcheck() {
1873
+ const rows = [];
1874
+ const push = (name, pass, detail) => {
1875
+ rows.push({ name, pass, detail });
1876
+ };
1877
+ // 1. envelope guard: 21 qubits must be refused.
1878
+ let refused = false;
1879
+ try {
1880
+ new quantumsim(21);
1881
+ }
1882
+ catch (cause) {
1883
+ refused = cause instanceof quantumerror && cause.code === 'qubitrange';
1884
+ }
1885
+ push('maxqubits guard', refused, `quantumsim(21) refused: ${refused}`);
1886
+ // 2. norm stability under a 12-qubit hadamard ladder.
1887
+ {
1888
+ const env_1 = { stack: [], error: void 0, hasError: false };
1889
+ try {
1890
+ const ladder = __addDisposableResource(env_1, new quantumsim(12), false);
1891
+ for (let q = 0; q < 12; q++) {
1892
+ ladder.h(q);
1893
+ }
1894
+ const drift = Math.abs(ladder.norm() - 1);
1895
+ push('statevector norm', drift < 1e-12, `12 hadamards leave norm 1 within ${drift.toExponential(2)}`);
1896
+ }
1897
+ catch (e_1) {
1898
+ env_1.error = e_1;
1899
+ env_1.hasError = true;
1900
+ }
1901
+ finally {
1902
+ __disposeResources(env_1);
1903
+ }
1904
+ }
1905
+ // 3. bell state distribution.
1906
+ {
1907
+ const env_2 = { stack: [], error: void 0, hasError: false };
1908
+ try {
1909
+ const bell = __addDisposableResource(env_2, bellstate().sim, false);
1910
+ const p = bell.probabilities();
1911
+ const ok = Math.abs(p[0] - 0.5) < 1e-12 && Math.abs(p[3] - 0.5) < 1e-12 && p[1] < 1e-12 && p[2] < 1e-12;
1912
+ push('bellstate', ok, `probs [${p[0].toFixed(6)}, ${p[1].toFixed(6)}, ${p[2].toFixed(6)}, ${p[3].toFixed(6)}] ~ [0.5, 0, 0.5, 0]`);
1913
+ }
1914
+ catch (e_2) {
1915
+ env_2.error = e_2;
1916
+ env_2.hasError = true;
1917
+ }
1918
+ finally {
1919
+ __disposeResources(env_2);
1920
+ }
1921
+ }
1922
+ // 4. ghz corners.
1923
+ {
1924
+ const env_3 = { stack: [], error: void 0, hasError: false };
1925
+ try {
1926
+ const ghz = __addDisposableResource(env_3, ghzstate(4).sim, false);
1927
+ const p = ghz.probabilities();
1928
+ const ok = Math.abs(p[0] - 0.5) < 1e-12 && Math.abs(p[15] - 0.5) < 1e-12;
1929
+ push('ghzstate(4)', ok, `p[0000]=${p[0].toFixed(6)}, p[1111]=${p[15].toFixed(6)}`);
1930
+ }
1931
+ catch (e_3) {
1932
+ env_3.error = e_3;
1933
+ env_3.hasError = true;
1934
+ }
1935
+ finally {
1936
+ __disposeResources(env_3);
1937
+ }
1938
+ }
1939
+ // 5. grover2 certainty.
1940
+ {
1941
+ const env_4 = { stack: [], error: void 0, hasError: false };
1942
+ try {
1943
+ const g2 = __addDisposableResource(env_4, grover2().sim, false);
1944
+ const p11 = g2.probabilities()[3];
1945
+ push('grover2', p11 >= 0.99, `prob(11) = ${p11.toFixed(9)} (>= 0.99)`);
1946
+ }
1947
+ catch (e_4) {
1948
+ env_4.error = e_4;
1949
+ env_4.hasError = true;
1950
+ }
1951
+ finally {
1952
+ __disposeResources(env_4);
1953
+ }
1954
+ }
1955
+ // 6. grover3 statistics.
1956
+ {
1957
+ const env_5 = { stack: [], error: void 0, hasError: false };
1958
+ try {
1959
+ const g3 = __addDisposableResource(env_5, grover3().sim, false);
1960
+ const p111 = g3.probabilities()[7];
1961
+ push('grover3', p111 >= 0.9, `prob(111) = ${p111.toFixed(6)} (theory 0.9461, >= 0.9)`);
1962
+ }
1963
+ catch (e_5) {
1964
+ env_5.error = e_5;
1965
+ env_5.hasError = true;
1966
+ }
1967
+ finally {
1968
+ __disposeResources(env_5);
1969
+ }
1970
+ }
1971
+ // 7-8. deutsch both promises.
1972
+ {
1973
+ const constant = deutsch(() => 0);
1974
+ const balanced = deutsch((x) => x);
1975
+ push('deutsch constant', constant.verdict === 'constant' && constant.verdict === constant.expected, `f=0 -> ${constant.verdict} (measured ${constant.measured})`);
1976
+ push('deutsch balanced', balanced.verdict === 'balanced' && balanced.verdict === balanced.expected, `f=x -> ${balanced.verdict} (measured ${balanced.measured})`);
1977
+ }
1978
+ // 9-10. teleportation fidelity for both nontrivial inputs.
1979
+ {
1980
+ const one = qteleport('one');
1981
+ const plus = qteleport('plus');
1982
+ push('qteleport |1>', Math.abs(one.fidelity - 1) < 1e-12, `fidelity ${one.fidelity.toFixed(12)} (corrections m0=${one.outcome0}, m1=${one.outcome1})`);
1983
+ push('qteleport |+>', Math.abs(plus.fidelity - 1) < 1e-12, `fidelity ${plus.fidelity.toFixed(12)} (basis restored after z correction)`);
1984
+ }
1985
+ // 11-12. bb84 clean channel and intercept-resend.
1986
+ {
1987
+ const clean = runbb84({ eve: false, bits: 1024 });
1988
+ push('bb84 clean', clean.qber < 0.05 && !clean.detected, `qber ${clean.qber.toFixed(4)} < 0.05, detected ${clean.detected}, sifted ${clean.siftedlen}, key ${clean.keyalice.length} bits`);
1989
+ const attacked = runbb84({ eve: true, bits: 1024 });
1990
+ push('bb84 intercept-resend', attacked.detected && attacked.qber > 0.2, `qber ${attacked.qber.toFixed(4)} > 0.2, sampled ${attacked.sampledqber.toFixed(4)} > ${attacked.threshold}, detected ${attacked.detected}`);
1991
+ }
1992
+ // 13-14. e91 chsh violation and collapse under eve.
1993
+ {
1994
+ const clean = rune91({ eve: false, pairs: 2400 });
1995
+ push('e91 clean chsh', clean.s > 2.4 && !clean.detected, `s = ${clean.s.toFixed(4)} > 2.4 (tsirelson 2.8284), detected ${clean.detected}, keylen ${clean.keylen}`);
1996
+ const attacked = rune91({ eve: true, pairs: 2400 });
1997
+ push('e91 intercept-resend', attacked.detected, `s = ${attacked.s.toFixed(4)} (classical bound 2), qber ${Number.isFinite(attacked.qber) ? attacked.qber.toFixed(4) : 'n/a'}, detected ${attacked.detected}`);
1998
+ }
1999
+ // 15. dna roundtrip with a strand lost.
2000
+ {
2001
+ const payload = randomBytes(1000);
2002
+ const encoded = dnavaultencode(payload);
2003
+ const direct = dnavaultdecode(encoded.strands);
2004
+ const degraded = dnavaultdecode([encoded.strands[0], encoded.strands[2], encoded.strands[3]]);
2005
+ let equal = direct.length === payload.length && degraded.length === payload.length;
2006
+ for (let i = 0; equal && i < payload.length; i++) {
2007
+ equal = direct[i] === payload[i] && degraded[i] === payload[i];
2008
+ }
2009
+ let runmax = 1;
2010
+ for (const strand of encoded.strands) {
2011
+ let current = 1;
2012
+ for (let i = 1; i < strand.length; i++) {
2013
+ current = strand[i] === strand[i - 1] ? current + 1 : 1;
2014
+ if (current > runmax) {
2015
+ runmax = current;
2016
+ }
2017
+ }
2018
+ }
2019
+ push('dnavault roundtrip', equal && runmax <= 3, `1000 bytes roundtrip byte-perfect with strand 1 lost; longest homopolymer run ${runmax} (<= 3)`);
2020
+ }
2021
+ // 16. qrng range.
2022
+ {
2023
+ const values = quantuminspiredrandom(4096, { min: -7, max: 19 });
2024
+ const distinct = new Set(values).size;
2025
+ const inrange = values.every((value) => Number.isInteger(value) && value >= -7 && value < 19);
2026
+ push('qrng range', inrange && distinct > 16, `4096 draws in [-7, 19): all in range ${inrange}, ${distinct} distinct values`);
2027
+ }
2028
+ // 17. qram routing depth.
2029
+ {
2030
+ const demo = qramdemo();
2031
+ push('qram bucket brigade', demo.hops === 3 && demo.switches === 7 && demo.reads.every((read) => read.hops === 3), `n=8: ${demo.switches} switches, every read routes ${demo.hops} hops vs ${demo.classicalwritelines} word lines`);
2032
+ }
2033
+ // 18. shor plan honesty.
2034
+ {
2035
+ const plan = shorplan(15);
2036
+ push('shorplan honest', plan.executable === false && plan.qubits === 7 && plan.expectedperiod === 4, `n=15 plan: ${plan.qubits} qubits, period ${plan.expectedperiod}, factors [${plan.factors.join(', ')}], execution refused`);
2037
+ }
2038
+ // 19. using/disposal guard.
2039
+ {
2040
+ let survivor;
2041
+ {
2042
+ const env_6 = { stack: [], error: void 0, hasError: false };
2043
+ try {
2044
+ const disposable = __addDisposableResource(env_6, new quantumsim(2), false);
2045
+ disposable.h(0);
2046
+ survivor = disposable;
2047
+ }
2048
+ catch (e_6) {
2049
+ env_6.error = e_6;
2050
+ env_6.hasError = true;
2051
+ }
2052
+ finally {
2053
+ __disposeResources(env_6);
2054
+ }
2055
+ }
2056
+ let disposed = false;
2057
+ try {
2058
+ survivor.x(0);
2059
+ }
2060
+ catch (cause) {
2061
+ disposed = cause instanceof quantumerror && cause.code === 'disposed';
2062
+ }
2063
+ push('using disposal', disposed, 'post-using gate call threw quantumerror(disposed)');
2064
+ }
2065
+ const passed = rows.filter((row) => row.pass).length;
2066
+ return {
2067
+ rows,
2068
+ passed,
2069
+ failed: rows.length - passed,
2070
+ reference: 'task v18-quantum validation matrix; live node:crypto randomness',
2071
+ };
2072
+ }
2073
+ //# sourceMappingURL=quantum.js.map