@cdxgen/cdxgen 13.1.0 → 13.3.0

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 (283) hide show
  1. package/README.md +32 -15
  2. package/bin/cdxgen.js +243 -122
  3. package/bin/evinse.js +7 -0
  4. package/bin/sign.js +88 -14
  5. package/bin/tracebom.js +64 -4
  6. package/bin/validate.js +29 -7
  7. package/bin/verify.js +79 -39
  8. package/data/crypto-oid.json +88 -12
  9. package/data/remediations.json +47 -0
  10. package/data/rules/ai-bom.yaml +78 -0
  11. package/data/rules/cargo-rust.yaml +132 -0
  12. package/data/rules/mcp-servers.yaml +122 -0
  13. package/lib/audit/targets.js +6 -1
  14. package/lib/cli/bomAssembly.js +117 -15
  15. package/lib/cli/cliOptions.js +93 -1
  16. package/lib/cli/index.js +235 -5
  17. package/lib/cli/jsBom.js +108 -26
  18. package/lib/cli/jvmBom.js +68 -12
  19. package/lib/cli/managedBom.js +264 -41
  20. package/lib/cli/nativeBom.js +923 -15
  21. package/lib/core/activity.js +120 -2
  22. package/lib/core/env.js +44 -7
  23. package/lib/core/fs.js +174 -6
  24. package/lib/core/metadataProperties.js +97 -0
  25. package/lib/core/projectConfig.js +31 -4
  26. package/lib/core/userAgent.js +151 -0
  27. package/lib/ecosystems/bunutils.js +269 -101
  28. package/lib/ecosystems/cargoCache.js +364 -0
  29. package/lib/ecosystems/caxa.js +447 -7
  30. package/lib/ecosystems/cmakeResolver.js +66 -0
  31. package/lib/ecosystems/cppEvidence.js +104 -33
  32. package/lib/ecosystems/ecosystems.js +260 -99
  33. package/lib/ecosystems/golem.js +11 -1
  34. package/lib/ecosystems/gradleutils.js +185 -9
  35. package/lib/ecosystems/jsEvidence.js +19 -20
  36. package/lib/ecosystems/kosi.js +1263 -0
  37. package/lib/ecosystems/npmutils.js +110 -9
  38. package/lib/ecosystems/parsers-crystal.js +179 -0
  39. package/lib/ecosystems/parsers-dotnet.js +120 -49
  40. package/lib/ecosystems/parsers-elm.js +816 -0
  41. package/lib/ecosystems/parsers-gleam.js +1 -1
  42. package/lib/ecosystems/parsers-go.js +47 -9
  43. package/lib/ecosystems/parsers-js.js +171 -50
  44. package/lib/ecosystems/parsers-julia.js +268 -0
  45. package/lib/ecosystems/parsers-lua.js +218 -0
  46. package/lib/ecosystems/parsers-misc.js +919 -161
  47. package/lib/ecosystems/parsers-nim.js +221 -0
  48. package/lib/ecosystems/parsers-opam.js +180 -0
  49. package/lib/ecosystems/parsers-perl.js +277 -0
  50. package/lib/ecosystems/parsers-python.js +27 -15
  51. package/lib/ecosystems/parsers-r.js +148 -0
  52. package/lib/ecosystems/parsers-rebar.js +411 -0
  53. package/lib/ecosystems/parsers-rust.js +954 -33
  54. package/lib/ecosystems/parsers-spack.js +204 -0
  55. package/lib/ecosystems/parsers-stack.js +264 -0
  56. package/lib/ecosystems/parsers-terraform.js +194 -0
  57. package/lib/ecosystems/rubyutils.js +1426 -166
  58. package/lib/ecosystems/rusi.js +158 -7
  59. package/lib/evinser/evinser.js +547 -129
  60. package/lib/evinser/swiftsem.js +1914 -302
  61. package/lib/helpers/agenticToolutils.js +925 -0
  62. package/lib/helpers/bomSigner.js +652 -221
  63. package/lib/inventory/agentFormulationParser.js +57 -4
  64. package/lib/inventory/aiCollector.js +504 -10
  65. package/lib/inventory/aiInventory.js +12 -0
  66. package/lib/inventory/analyzer.js +488 -30
  67. package/lib/inventory/astWorker.js +6 -0
  68. package/lib/inventory/atomUtils.js +568 -31
  69. package/lib/inventory/auditCategories.js +8 -0
  70. package/lib/inventory/cbomutils.js +30 -0
  71. package/lib/inventory/cdxrs.js +110 -14
  72. package/lib/inventory/communityAiConfigParser.js +215 -2
  73. package/lib/inventory/depsUtils.js +183 -11
  74. package/lib/inventory/display.js +4 -5
  75. package/lib/inventory/dosai.js +627 -13
  76. package/lib/inventory/dynamic.js +39 -1
  77. package/lib/inventory/envcontext.js +9 -6
  78. package/lib/inventory/evidenceUtils.js +26 -5
  79. package/lib/inventory/fetchBatch.js +190 -19
  80. package/lib/inventory/fetchRate.js +74 -11
  81. package/lib/inventory/forgeEnricher.js +3 -2
  82. package/lib/inventory/jvmToolEnv.js +6 -5
  83. package/lib/inventory/mcpConfigParser.js +166 -2
  84. package/lib/inventory/mcpDiscovery.js +11 -0
  85. package/lib/inventory/mcpServerManifest.js +389 -0
  86. package/lib/inventory/mcpbBundle.js +419 -0
  87. package/lib/inventory/plugins.js +3 -0
  88. package/lib/inventory/protobom.js +62 -89
  89. package/lib/inventory/protobomLoader.js +4 -0
  90. package/lib/inventory/purl.js +152 -3
  91. package/lib/inventory/rustFormulationParser.js +1 -1
  92. package/lib/inventory/sbomDocument.js +2 -70
  93. package/lib/inventory/source.js +47 -23
  94. package/lib/inventory/stylePackageRefs.js +41 -0
  95. package/lib/inventory/svelteUtils.js +524 -0
  96. package/lib/inventory/traceRunner.js +210 -21
  97. package/lib/managers/binary.js +115 -24
  98. package/lib/managers/docker.js +440 -20
  99. package/lib/managers/oci.js +39 -1
  100. package/lib/parsers/cmakeLists.js +452 -0
  101. package/lib/parsers/huggingfaceUtils.js +15 -7
  102. package/lib/parsers/largeJson.js +454 -0
  103. package/lib/parsers/npmrc.js +19 -1
  104. package/lib/parsers/onnx.js +294 -0
  105. package/lib/parsers/safetensors.js +114 -0
  106. package/lib/stages/postgen/introspection/markers.js +29 -6
  107. package/lib/stages/postgen/postgen.js +237 -16
  108. package/lib/third-party/arborist/snapshots/calc-dep-flags.test.cjs +462 -0
  109. package/lib/validator/bomValidator.js +6 -16
  110. package/lib/validator/index.js +48 -10
  111. package/lib/validator/reporters/console.js +3 -0
  112. package/lib/validator/reporters/json.js +1 -0
  113. package/lib/validator/reporters/sarif.js +7 -0
  114. package/package.json +27 -27
  115. package/types/lib/audit/targets.d.ts.map +1 -1
  116. package/types/lib/cli/bomAssembly.d.ts +2 -1
  117. package/types/lib/cli/bomAssembly.d.ts.map +1 -1
  118. package/types/lib/cli/cliOptions.d.ts +33 -1
  119. package/types/lib/cli/cliOptions.d.ts.map +1 -1
  120. package/types/lib/cli/index.d.ts +2 -2
  121. package/types/lib/cli/index.d.ts.map +1 -1
  122. package/types/lib/cli/jsBom.d.ts +23 -0
  123. package/types/lib/cli/jsBom.d.ts.map +1 -1
  124. package/types/lib/cli/jvmBom.d.ts.map +1 -1
  125. package/types/lib/cli/managedBom.d.ts +33 -0
  126. package/types/lib/cli/managedBom.d.ts.map +1 -1
  127. package/types/lib/cli/nativeBom.d.ts +88 -8
  128. package/types/lib/cli/nativeBom.d.ts.map +1 -1
  129. package/types/lib/core/activity.d.ts.map +1 -1
  130. package/types/lib/core/env.d.ts +21 -0
  131. package/types/lib/core/env.d.ts.map +1 -1
  132. package/types/lib/core/fs.d.ts +55 -0
  133. package/types/lib/core/fs.d.ts.map +1 -1
  134. package/types/lib/core/metadataProperties.d.ts +39 -0
  135. package/types/lib/core/metadataProperties.d.ts.map +1 -0
  136. package/types/lib/core/projectConfig.d.ts +6 -2
  137. package/types/lib/core/projectConfig.d.ts.map +1 -1
  138. package/types/lib/core/userAgent.d.ts +56 -0
  139. package/types/lib/core/userAgent.d.ts.map +1 -0
  140. package/types/lib/ecosystems/bunutils.d.ts +12 -5
  141. package/types/lib/ecosystems/bunutils.d.ts.map +1 -1
  142. package/types/lib/ecosystems/cargoCache.d.ts +75 -0
  143. package/types/lib/ecosystems/cargoCache.d.ts.map +1 -0
  144. package/types/lib/ecosystems/caxa.d.ts +14 -0
  145. package/types/lib/ecosystems/caxa.d.ts.map +1 -1
  146. package/types/lib/ecosystems/cmakeResolver.d.ts +23 -0
  147. package/types/lib/ecosystems/cmakeResolver.d.ts.map +1 -1
  148. package/types/lib/ecosystems/cppEvidence.d.ts +2 -2
  149. package/types/lib/ecosystems/cppEvidence.d.ts.map +1 -1
  150. package/types/lib/ecosystems/ecosystems.d.ts +15 -1
  151. package/types/lib/ecosystems/ecosystems.d.ts.map +1 -1
  152. package/types/lib/ecosystems/golem.d.ts.map +1 -1
  153. package/types/lib/ecosystems/gradleutils.d.ts +40 -4
  154. package/types/lib/ecosystems/gradleutils.d.ts.map +1 -1
  155. package/types/lib/ecosystems/jsEvidence.d.ts +5 -2
  156. package/types/lib/ecosystems/jsEvidence.d.ts.map +1 -1
  157. package/types/lib/ecosystems/kosi.d.ts +86 -0
  158. package/types/lib/ecosystems/kosi.d.ts.map +1 -0
  159. package/types/lib/ecosystems/npmutils.d.ts +42 -0
  160. package/types/lib/ecosystems/npmutils.d.ts.map +1 -1
  161. package/types/lib/ecosystems/parsers-crystal.d.ts +27 -0
  162. package/types/lib/ecosystems/parsers-crystal.d.ts.map +1 -0
  163. package/types/lib/ecosystems/parsers-dotnet.d.ts +19 -0
  164. package/types/lib/ecosystems/parsers-dotnet.d.ts.map +1 -1
  165. package/types/lib/ecosystems/parsers-elm.d.ts +79 -0
  166. package/types/lib/ecosystems/parsers-elm.d.ts.map +1 -0
  167. package/types/lib/ecosystems/parsers-go.d.ts +10 -0
  168. package/types/lib/ecosystems/parsers-go.d.ts.map +1 -1
  169. package/types/lib/ecosystems/parsers-js.d.ts +10 -4
  170. package/types/lib/ecosystems/parsers-js.d.ts.map +1 -1
  171. package/types/lib/ecosystems/parsers-julia.d.ts +57 -0
  172. package/types/lib/ecosystems/parsers-julia.d.ts.map +1 -0
  173. package/types/lib/ecosystems/parsers-lua.d.ts +50 -0
  174. package/types/lib/ecosystems/parsers-lua.d.ts.map +1 -0
  175. package/types/lib/ecosystems/parsers-misc.d.ts +90 -3
  176. package/types/lib/ecosystems/parsers-misc.d.ts.map +1 -1
  177. package/types/lib/ecosystems/parsers-nim.d.ts +43 -0
  178. package/types/lib/ecosystems/parsers-nim.d.ts.map +1 -0
  179. package/types/lib/ecosystems/parsers-opam.d.ts +31 -0
  180. package/types/lib/ecosystems/parsers-opam.d.ts.map +1 -0
  181. package/types/lib/ecosystems/parsers-perl.d.ts +36 -0
  182. package/types/lib/ecosystems/parsers-perl.d.ts.map +1 -0
  183. package/types/lib/ecosystems/parsers-python.d.ts.map +1 -1
  184. package/types/lib/ecosystems/parsers-r.d.ts +35 -0
  185. package/types/lib/ecosystems/parsers-r.d.ts.map +1 -0
  186. package/types/lib/ecosystems/parsers-rebar.d.ts +42 -0
  187. package/types/lib/ecosystems/parsers-rebar.d.ts.map +1 -0
  188. package/types/lib/ecosystems/parsers-rust.d.ts +199 -0
  189. package/types/lib/ecosystems/parsers-rust.d.ts.map +1 -1
  190. package/types/lib/ecosystems/parsers-spack.d.ts +33 -0
  191. package/types/lib/ecosystems/parsers-spack.d.ts.map +1 -0
  192. package/types/lib/ecosystems/parsers-stack.d.ts +35 -0
  193. package/types/lib/ecosystems/parsers-stack.d.ts.map +1 -0
  194. package/types/lib/ecosystems/parsers-terraform.d.ts +34 -0
  195. package/types/lib/ecosystems/parsers-terraform.d.ts.map +1 -0
  196. package/types/lib/ecosystems/pythonutils.d.ts +1 -1
  197. package/types/lib/ecosystems/rubyutils.d.ts +143 -2
  198. package/types/lib/ecosystems/rubyutils.d.ts.map +1 -1
  199. package/types/lib/ecosystems/rusi.d.ts +13 -0
  200. package/types/lib/ecosystems/rusi.d.ts.map +1 -1
  201. package/types/lib/evinser/evinser.d.ts +81 -2
  202. package/types/lib/evinser/evinser.d.ts.map +1 -1
  203. package/types/lib/evinser/swiftsem.d.ts +280 -15
  204. package/types/lib/evinser/swiftsem.d.ts.map +1 -1
  205. package/types/lib/helpers/agenticToolutils.d.ts +87 -0
  206. package/types/lib/helpers/agenticToolutils.d.ts.map +1 -0
  207. package/types/lib/helpers/bomSigner.d.ts +106 -13
  208. package/types/lib/helpers/bomSigner.d.ts.map +1 -1
  209. package/types/lib/inventory/agentFormulationParser.d.ts.map +1 -1
  210. package/types/lib/inventory/aiCollector.d.ts.map +1 -1
  211. package/types/lib/inventory/aiInventory.d.ts.map +1 -1
  212. package/types/lib/inventory/analyzer.d.ts.map +1 -1
  213. package/types/lib/inventory/atomUtils.d.ts +145 -3
  214. package/types/lib/inventory/atomUtils.d.ts.map +1 -1
  215. package/types/lib/inventory/auditCategories.d.ts +4 -0
  216. package/types/lib/inventory/auditCategories.d.ts.map +1 -1
  217. package/types/lib/inventory/cbomutils.d.ts.map +1 -1
  218. package/types/lib/inventory/cdxrs.d.ts +8 -3
  219. package/types/lib/inventory/cdxrs.d.ts.map +1 -1
  220. package/types/lib/inventory/communityAiConfigParser.d.ts.map +1 -1
  221. package/types/lib/inventory/depsUtils.d.ts +15 -0
  222. package/types/lib/inventory/depsUtils.d.ts.map +1 -1
  223. package/types/lib/inventory/display.d.ts.map +1 -1
  224. package/types/lib/inventory/dosai.d.ts +87 -1
  225. package/types/lib/inventory/dosai.d.ts.map +1 -1
  226. package/types/lib/inventory/dynamic.d.ts.map +1 -1
  227. package/types/lib/inventory/envcontext.d.ts.map +1 -1
  228. package/types/lib/inventory/evidenceUtils.d.ts.map +1 -1
  229. package/types/lib/inventory/fetchBatch.d.ts +34 -0
  230. package/types/lib/inventory/fetchBatch.d.ts.map +1 -1
  231. package/types/lib/inventory/fetchRate.d.ts +9 -6
  232. package/types/lib/inventory/fetchRate.d.ts.map +1 -1
  233. package/types/lib/inventory/forgeEnricher.d.ts.map +1 -1
  234. package/types/lib/inventory/jvmToolEnv.d.ts +5 -4
  235. package/types/lib/inventory/jvmToolEnv.d.ts.map +1 -1
  236. package/types/lib/inventory/mcpConfigParser.d.ts.map +1 -1
  237. package/types/lib/inventory/mcpDiscovery.d.ts.map +1 -1
  238. package/types/lib/inventory/mcpServerManifest.d.ts +19 -0
  239. package/types/lib/inventory/mcpServerManifest.d.ts.map +1 -0
  240. package/types/lib/inventory/mcpbBundle.d.ts +19 -0
  241. package/types/lib/inventory/mcpbBundle.d.ts.map +1 -0
  242. package/types/lib/inventory/plugins.d.ts.map +1 -1
  243. package/types/lib/inventory/protobom.d.ts +18 -13
  244. package/types/lib/inventory/protobom.d.ts.map +1 -1
  245. package/types/lib/inventory/protobomLoader.d.ts.map +1 -1
  246. package/types/lib/inventory/purl.d.ts +71 -2
  247. package/types/lib/inventory/purl.d.ts.map +1 -1
  248. package/types/lib/inventory/sbomDocument.d.ts.map +1 -1
  249. package/types/lib/inventory/source.d.ts.map +1 -1
  250. package/types/lib/inventory/stylePackageRefs.d.ts +17 -0
  251. package/types/lib/inventory/stylePackageRefs.d.ts.map +1 -0
  252. package/types/lib/inventory/svelteUtils.d.ts +124 -0
  253. package/types/lib/inventory/svelteUtils.d.ts.map +1 -0
  254. package/types/lib/inventory/traceRunner.d.ts +47 -1
  255. package/types/lib/inventory/traceRunner.d.ts.map +1 -1
  256. package/types/lib/managers/binary.d.ts +30 -1
  257. package/types/lib/managers/binary.d.ts.map +1 -1
  258. package/types/lib/managers/docker.d.ts +29 -0
  259. package/types/lib/managers/docker.d.ts.map +1 -1
  260. package/types/lib/managers/oci.d.ts +14 -0
  261. package/types/lib/managers/oci.d.ts.map +1 -1
  262. package/types/lib/parsers/cmakeLists.d.ts +76 -0
  263. package/types/lib/parsers/cmakeLists.d.ts.map +1 -0
  264. package/types/lib/parsers/huggingfaceUtils.d.ts +8 -1
  265. package/types/lib/parsers/huggingfaceUtils.d.ts.map +1 -1
  266. package/types/lib/parsers/largeJson.d.ts +52 -0
  267. package/types/lib/parsers/largeJson.d.ts.map +1 -0
  268. package/types/lib/parsers/npmrc.d.ts +5 -0
  269. package/types/lib/parsers/npmrc.d.ts.map +1 -1
  270. package/types/lib/parsers/onnx.d.ts +28 -0
  271. package/types/lib/parsers/onnx.d.ts.map +1 -0
  272. package/types/lib/parsers/safetensors.d.ts +22 -0
  273. package/types/lib/parsers/safetensors.d.ts.map +1 -0
  274. package/types/lib/stages/postgen/introspection/markers.d.ts +3 -2
  275. package/types/lib/stages/postgen/introspection/markers.d.ts.map +1 -1
  276. package/types/lib/stages/postgen/postgen.d.ts +33 -0
  277. package/types/lib/stages/postgen/postgen.d.ts.map +1 -1
  278. package/types/lib/validator/bomValidator.d.ts.map +1 -1
  279. package/types/lib/validator/index.d.ts +10 -1
  280. package/types/lib/validator/index.d.ts.map +1 -1
  281. package/types/lib/validator/reporters/console.d.ts.map +1 -1
  282. package/types/lib/validator/reporters/json.d.ts.map +1 -1
  283. package/types/lib/validator/reporters/sarif.d.ts.map +1 -1
package/bin/sign.js CHANGED
@@ -11,7 +11,11 @@ import {
11
11
  retrieveCdxgenVersion,
12
12
  safeExistsSync,
13
13
  } from "../lib/ecosystems/utils.js";
14
- import { signBom } from "../lib/helpers/bomSigner.js";
14
+ import {
15
+ checkSignatureEntries,
16
+ displayValue,
17
+ signBom,
18
+ } from "../lib/helpers/bomSigner.js";
15
19
  import {
16
20
  getNonCycloneDxErrorMessage,
17
21
  isCycloneDxBom,
@@ -31,12 +35,14 @@ const args = _yargs
31
35
  })
32
36
  .option("private-key", {
33
37
  alias: "k",
34
- description: "Private key in PEM format.",
38
+ description:
39
+ "Private key in PEM format, or the shared secret file for HS256, HS384, and HS512.",
35
40
  })
36
41
  .option("algorithm", {
37
42
  alias: "a",
38
43
  default: readEnvironmentVariable("SBOM_SIGN_ALGORITHM") || "RS512",
39
- description: "JSF Signature Algorithm (e.g., RS512, ES256, Ed25519).",
44
+ description:
45
+ "JSF Signature Algorithm (e.g., RS512, ES256, Ed25519). It must match the key type.",
40
46
  })
41
47
  .option("mode", {
42
48
  alias: "m",
@@ -45,27 +51,36 @@ const args = _yargs
45
51
  description:
46
52
  "Signature mode. Use 'signers' for multi-signing, 'chain' for sequential chaining.",
47
53
  })
54
+ .option("verify-existing-with", {
55
+ type: "array",
56
+ string: true,
57
+ description:
58
+ "Public key (PEM) of an earlier signer. With --mode chain, every existing chain entry must verify with one of these keys before a new entry is appended.",
59
+ })
60
+ .option("allow-unverified-history", {
61
+ type: "boolean",
62
+ default: false,
63
+ description:
64
+ "With --mode chain, append even when existing chain entries cannot be verified with --verify-existing-with.",
65
+ })
48
66
  .option("key-id", {
49
67
  description:
50
68
  "Optional identifier for the key (keyId) to embed in the signature block.",
51
69
  })
52
70
  .option("sign-components", {
53
71
  type: "boolean",
54
- default: true,
55
72
  description:
56
- "Sign granular components. Disable (--no-sign-components) when appending multi-signatures.",
73
+ "Sign granular components. Defaults to true, or false when appending a signers or chain signature to a signed BOM.",
57
74
  })
58
75
  .option("sign-services", {
59
76
  type: "boolean",
60
- default: true,
61
77
  description:
62
- "Sign granular services. Disable (--no-sign-services) when appending multi-signatures.",
78
+ "Sign granular services. Defaults to true, or false when appending a signers or chain signature to a signed BOM.",
63
79
  })
64
80
  .option("sign-annotations", {
65
81
  type: "boolean",
66
- default: true,
67
82
  description:
68
- "Sign granular annotations. Disable (--no-sign-annotations) when appending multi-signatures.",
83
+ "Sign granular annotations. Defaults to true, or false when appending a signers or chain signature to a signed BOM.",
69
84
  })
70
85
  .option("attach", {
71
86
  type: "string",
@@ -97,7 +112,7 @@ const envPrivateKeyBase64 = readEnvironmentVariable(
97
112
 
98
113
  if (args.privateKey) {
99
114
  if (safeExistsSync(args.privateKey)) {
100
- privateKeyContent = fs.readFileSync(args.privateKey, "utf8");
115
+ privateKeyContent = fs.readFileSync(args.privateKey);
101
116
  hasPrivateKey = true;
102
117
  } else {
103
118
  console.error(`Private key file '${args.privateKey}' not found.`);
@@ -105,7 +120,7 @@ if (args.privateKey) {
105
120
  }
106
121
  } else if (envPrivateKeyFile) {
107
122
  if (safeExistsSync(envPrivateKeyFile)) {
108
- privateKeyContent = fs.readFileSync(envPrivateKeyFile, "utf8");
123
+ privateKeyContent = fs.readFileSync(envPrivateKeyFile);
109
124
  hasPrivateKey = true;
110
125
  } else {
111
126
  console.error(
@@ -115,9 +130,7 @@ if (args.privateKey) {
115
130
  }
116
131
  } else if (envPrivateKeyBase64) {
117
132
  try {
118
- privateKeyContent = Buffer.from(envPrivateKeyBase64, "base64").toString(
119
- "utf8",
120
- );
133
+ privateKeyContent = Buffer.from(envPrivateKeyBase64, "base64");
121
134
  hasPrivateKey = true;
122
135
  } catch {
123
136
  console.error(
@@ -147,6 +160,66 @@ function hasAnySignature(bomJson) {
147
160
  return false;
148
161
  }
149
162
 
163
+ function describeEntry(result) {
164
+ const parts = [];
165
+ if (result.algorithm !== undefined) {
166
+ parts.push(displayValue(result.algorithm));
167
+ }
168
+ if (result.keyId !== undefined) {
169
+ parts.push(`keyId '${displayValue(result.keyId)}'`);
170
+ }
171
+ return parts.length
172
+ ? `entry ${result.index} (${parts.join(", ")})`
173
+ : `entry ${result.index}`;
174
+ }
175
+
176
+ // A new chain entry covers every earlier entry, so the signer vouches for
177
+ // that history. Check it with the earlier signers' keys before appending.
178
+ function checkChainHistory(bomJson) {
179
+ const existing = bomJson.signature;
180
+ if (
181
+ args.mode !== "chain" ||
182
+ existing === undefined ||
183
+ (existing !== null &&
184
+ typeof existing === "object" &&
185
+ Object.hasOwn(existing, "signers"))
186
+ ) {
187
+ return;
188
+ }
189
+ const keys = (args.verifyExistingWith || []).map((keyFile) => {
190
+ if (!safeExistsSync(keyFile)) {
191
+ throw new Error(`Public key file '${keyFile}' not found.`);
192
+ }
193
+ return fs.readFileSync(keyFile, "utf8");
194
+ });
195
+ const unverified = checkSignatureEntries(bomJson, keys).filter(
196
+ (result) => !result.verified,
197
+ );
198
+ if (!unverified.length) {
199
+ return;
200
+ }
201
+ const details = unverified.map(
202
+ (result) =>
203
+ ` - ${describeEntry(result)}: ${result.reasons[0] || "no --verify-existing-with key was given"}`,
204
+ );
205
+ if (args.allowUnverifiedHistory) {
206
+ console.warn(
207
+ [
208
+ `Warning: appending to a chain with ${unverified.length} unverified entry(s):`,
209
+ ...details,
210
+ ].join("\n"),
211
+ );
212
+ return;
213
+ }
214
+ throw new Error(
215
+ [
216
+ `the new chain entry would vouch for ${unverified.length} existing entry(s) that could not be verified:`,
217
+ ...details,
218
+ "Pass --verify-existing-with <public key> for each earlier signer, or --allow-unverified-history to sign anyway.",
219
+ ].join("\n"),
220
+ );
221
+ }
222
+
150
223
  try {
151
224
  const bomJson = JSON.parse(fs.readFileSync(args.input, "utf8"));
152
225
  if (!isCycloneDxBom(bomJson)) {
@@ -156,6 +229,7 @@ try {
156
229
 
157
230
  let signedBom = bomJson;
158
231
  if (hasPrivateKey && privateKeyContent) {
232
+ checkChainHistory(bomJson);
159
233
  signedBom = signBom(bomJson, {
160
234
  privateKey: privateKeyContent,
161
235
  algorithm: args.algorithm,
package/bin/tracebom.js CHANGED
@@ -79,7 +79,7 @@ const args = _yargs
79
79
  })
80
80
  .option("disable-network", {
81
81
  description:
82
- "Disable network inside sandbox. Automatically disabled when --trace-http-urls is set.",
82
+ "Disable network inside sandbox. Automatically disabled when --trace-http-urls or --proxy-egress is set.",
83
83
  default: true,
84
84
  type: "boolean",
85
85
  })
@@ -170,6 +170,56 @@ const args = _yargs
170
170
  default: true,
171
171
  type: "boolean",
172
172
  })
173
+ .option("proxy-egress", {
174
+ description:
175
+ "Route all outbound traffic through safer-exec's hostname-pinning egress proxy. Only --allow-host (and --allow-url) hosts are reachable; allowed and denied targets are recorded as services. Enables the network.",
176
+ default: false,
177
+ type: "boolean",
178
+ })
179
+ .option("allow-loopback", {
180
+ description: "Allow the traced process to connect to loopback addresses.",
181
+ default: false,
182
+ type: "boolean",
183
+ })
184
+ .option("sandbox-dry-run", {
185
+ description:
186
+ "Deny every filesystem write and network connection and record the attempted operations as counts in the BOM metadata.",
187
+ default: false,
188
+ type: "boolean",
189
+ })
190
+ .option("policy", {
191
+ description:
192
+ "Apply a named safer-exec ecosystem policy (for example npm, pnpm, pypi, uv, maven, cargo, gomod, nuget) before the other sandbox options.",
193
+ type: "string",
194
+ })
195
+ .option("policy-file", {
196
+ description: "Apply a safer-exec JSON policy file.",
197
+ type: "string",
198
+ })
199
+ .option("block-interpreters", {
200
+ description:
201
+ "Block interpreters that carry sandbox or task-port exemptions (macOS only).",
202
+ default: false,
203
+ type: "boolean",
204
+ })
205
+ .option("deny-persistence-writes", {
206
+ description:
207
+ "Deny writes to auto-execution and persistence locations such as LaunchAgents, shell rc files and cron directories. Paths in --write-paths stay writable.",
208
+ default: false,
209
+ type: "boolean",
210
+ })
211
+ .option("private-tmp", {
212
+ description:
213
+ "Give the traced process private /tmp and /var/tmp mounts (Linux only).",
214
+ default: false,
215
+ type: "boolean",
216
+ })
217
+ .option("protect-home", {
218
+ description: "Isolate $HOME inside the sandbox (Linux only).",
219
+ choices: ["off", "read-only", "tmpfs"],
220
+ default: "off",
221
+ type: "string",
222
+ })
173
223
  .option("print", {
174
224
  description: "Print BOM to stdout.",
175
225
  default: false,
@@ -230,9 +280,10 @@ const options = {
230
280
  traceMaxMemoryMB: args.maxMemory,
231
281
  traceMaxProcesses: args.maxProcesses,
232
282
  traceTimeoutMs: args.timeout,
233
- traceDisableNetwork: args.traceHttpUrls
234
- ? false
235
- : (args.disableNetwork ?? true),
283
+ traceDisableNetwork:
284
+ args.traceHttpUrls || args.proxyEgress
285
+ ? false
286
+ : (args.disableNetwork ?? true),
236
287
  traceHTTPURLs: args.traceHttpUrls ?? false,
237
288
  tracePeriod: args.tracePeriod,
238
289
  traceMaxCPUCores: args.maxCpu,
@@ -265,6 +316,15 @@ const options = {
265
316
  ? args.blockExec.split(",").filter(Boolean)
266
317
  : [],
267
318
  traceCrypto: args.traceCrypto ?? true,
319
+ traceProxyEgress: args.proxyEgress ?? false,
320
+ traceAllowLoopback: args.allowLoopback ?? false,
321
+ traceDryRun: args.sandboxDryRun ?? false,
322
+ tracePolicy: args.policy,
323
+ tracePolicyFile: args.policyFile ? resolve(args.policyFile) : undefined,
324
+ traceBlockInterpreters: args.blockInterpreters ?? false,
325
+ traceDenyPersistenceWrites: args.denyPersistenceWrites ?? false,
326
+ tracePrivateTmp: args.privateTmp ?? false,
327
+ traceProtectHome: args.protectHome,
268
328
  cbom: undefined,
269
329
  projectType: ["dynamic"],
270
330
  output: resolve(args.output),
package/bin/validate.js CHANGED
@@ -114,11 +114,21 @@ const args = _yargs
114
114
  description:
115
115
  "Path to a PEM public key. When set, cdx-validate also verifies the BOM signature.",
116
116
  })
117
+ .option("secret-key", {
118
+ description:
119
+ "Path to the shared secret for HMAC (HS256, HS384, HS512) signatures. HMAC signatures are only accepted with this option.",
120
+ })
121
+ .option("nested-signatures", {
122
+ type: "boolean",
123
+ default: true,
124
+ description:
125
+ "Also verify component, service, and annotation signatures, as cdx-verify does. Pass --no-nested-signatures to verify only the root signature.",
126
+ })
117
127
  .option("require-signature", {
118
128
  type: "boolean",
119
129
  default: false,
120
130
  description:
121
- "Exit non-zero (4) when --public-key is provided but signature verification fails.",
131
+ "Exit non-zero (4) when --public-key or --secret-key is provided but signature verification fails.",
122
132
  })
123
133
  .option("strict", {
124
134
  type: "boolean",
@@ -162,13 +172,13 @@ async function loadBom(input, platform) {
162
172
  return undefined;
163
173
  }
164
174
 
165
- function loadPublicKey(path) {
175
+ function loadKeyFile(path, label, encoding) {
166
176
  if (!path) return null;
167
177
  if (!safeExistsSync(path)) {
168
- console.error(`Public key '${path}' not found.`);
178
+ console.error(`${label} '${path}' not found.`);
169
179
  process.exit(1);
170
180
  }
171
- return fs.readFileSync(path, "utf8");
181
+ return fs.readFileSync(path, encoding);
172
182
  }
173
183
 
174
184
  function splitCsv(value) {
@@ -199,14 +209,20 @@ function isLocalProtoBomInput(input) {
199
209
  }
200
210
 
201
211
  const bomJson = await loadBom(args.input, args.platform);
202
- const publicKeyStr = loadPublicKey(args.publicKey);
212
+ if (args.publicKey && args.secretKey) {
213
+ console.error("cdx-validate: use either --public-key or --secret-key.");
214
+ process.exit(1);
215
+ }
216
+ const publicKeyStr = loadKeyFile(args.publicKey, "Public key", "utf8");
217
+ const secretKey = loadKeyFile(args.secretKey, "Shared secret");
218
+ const verificationRequested = Boolean(publicKeyStr || secretKey);
203
219
  const inputIsLocalProtoBom = isLocalProtoBomInput(args.input);
204
220
  if (!isCycloneDxBom(bomJson)) {
205
221
  console.error(getNonCycloneDxErrorMessage(bomJson, "cdx-validate"));
206
222
  process.exit(1);
207
223
  }
208
224
 
209
- if (inputIsLocalProtoBom && publicKeyStr) {
225
+ if (inputIsLocalProtoBom && verificationRequested) {
210
226
  console.error(
211
227
  "cdx-validate: protobuf BOM input does not currently preserve JSF signature blocks. Verify signatures against the source JSON BOM instead.",
212
228
  );
@@ -222,6 +238,8 @@ const report = await validateBomAdvanced(bomJson, {
222
238
  includeManual: args.includeManual,
223
239
  includePass: args.includePass,
224
240
  publicKey: publicKeyStr || undefined,
241
+ secretKey: secretKey || undefined,
242
+ nestedSignatures: args.nestedSignatures,
225
243
  });
226
244
 
227
245
  let output;
@@ -242,10 +260,14 @@ try {
242
260
 
243
261
  writeOrPrint(output, args.reportFile);
244
262
 
263
+ for (const e of report.validationErrors || []) {
264
+ console.error(`cdx-validate: ${e.stage} validation threw: ${e.message}`);
265
+ }
266
+
245
267
  const { shouldFail: fail, reason } = shouldFail(report, {
246
268
  failSeverity: args.failSeverity,
247
269
  strict: args.strict,
248
- requireSignature: Boolean(args.requireSignature && publicKeyStr),
270
+ requireSignature: Boolean(args.requireSignature && verificationRequested),
249
271
  });
250
272
 
251
273
  if (report.signatureVerified === false && args.requireSignature) {
package/bin/verify.js CHANGED
@@ -13,7 +13,12 @@ import {
13
13
  retrieveCdxgenVersion,
14
14
  safeExistsSync,
15
15
  } from "../lib/ecosystems/utils.js";
16
- import { verifyNode } from "../lib/helpers/bomSigner.js";
16
+ import {
17
+ displayValue,
18
+ loadSharedSecret,
19
+ loadVerificationKey,
20
+ verifyNode,
21
+ } from "../lib/helpers/bomSigner.js";
17
22
  import {
18
23
  getNonCycloneDxErrorMessage,
19
24
  isCycloneDxBom,
@@ -36,8 +41,12 @@ const args = _yargs
36
41
  description: "The platform to validate. No default",
37
42
  })
38
43
  .option("public-key", {
39
- default: "public.key",
40
- description: "Public key in PEM format. Default public.key",
44
+ description:
45
+ "Public key in PEM format. Default public.key unless --secret-key is used",
46
+ })
47
+ .option("secret-key", {
48
+ description:
49
+ "File holding the shared secret for HMAC (HS256, HS384, HS512) signatures. HMAC signatures are only accepted with this option.",
41
50
  })
42
51
  .option("deep", {
43
52
  type: "boolean",
@@ -114,16 +123,50 @@ if (!isCycloneDxBom(bomJson)) {
114
123
  process.exit(1);
115
124
  }
116
125
 
117
- if (bomJson && !safeExistsSync(args.publicKey)) {
118
- console.log("Public key for signature verification is missing!");
126
+ if (args.publicKey && args.secretKey) {
127
+ console.log("Use either --public-key or --secret-key, not both.");
128
+ process.exit(1);
129
+ }
130
+ const keyFile = args.secretKey || args.publicKey || "public.key";
131
+ if (!args.secretKey && !args.publicKey) {
132
+ console.log(
133
+ `No --public-key given; using '${keyFile}' from the current directory. Pass --public-key to name the trusted key explicitly.`,
134
+ );
135
+ }
136
+ if (!safeExistsSync(keyFile)) {
137
+ console.log(
138
+ args.secretKey
139
+ ? "Shared secret for signature verification is missing!"
140
+ : "Public key for signature verification is missing!",
141
+ );
119
142
  process.exit(1);
120
143
  }
121
144
 
122
- const publicKeyStr = fs.readFileSync(args.publicKey, "utf8");
145
+ let verificationKey;
146
+ try {
147
+ verificationKey = args.secretKey
148
+ ? loadSharedSecret(fs.readFileSync(keyFile))
149
+ : loadVerificationKey(fs.readFileSync(keyFile, "utf8"));
150
+ } catch (error) {
151
+ console.log(`Unable to use '${keyFile}': ${error.message}`);
152
+ process.exit(1);
153
+ }
123
154
 
124
- let rootMatch = null;
155
+ function verify(node) {
156
+ const reasons = [];
157
+ const match = verifyNode(node, verificationKey, { reasons });
158
+ return { match, reasons };
159
+ }
160
+
161
+ function printReasons(reasons) {
162
+ for (const reason of new Set(reasons)) {
163
+ console.log(` - ${reason}`);
164
+ }
165
+ }
166
+
167
+ let rootResult = null;
125
168
  if (bomJson.signature) {
126
- rootMatch = verifyNode(bomJson, publicKeyStr);
169
+ rootResult = verify(bomJson);
127
170
  }
128
171
 
129
172
  const verifyNested = args.deep || !bomJson.signature;
@@ -131,36 +174,23 @@ let hasInvalidNested = false;
131
174
  let checkedNested = 0;
132
175
 
133
176
  if (verifyNested) {
134
- for (const comp of bomJson.components || []) {
135
- if (comp.signature) {
136
- checkedNested++;
137
- if (!verifyNode(comp, publicKeyStr)) {
138
- console.log(
139
- `Component '${comp["bom-ref"] || comp.name}' signature is invalid!`,
140
- );
141
- hasInvalidNested = true;
142
- }
143
- }
144
- }
145
- for (const svc of bomJson.services || []) {
146
- if (svc.signature) {
147
- checkedNested++;
148
- if (!verifyNode(svc, publicKeyStr)) {
149
- console.log(
150
- `Service '${svc["bom-ref"] || svc.name}' signature is invalid!`,
151
- );
152
- hasInvalidNested = true;
153
- }
154
- }
155
- }
156
- for (const ann of bomJson.annotations || []) {
157
- if (ann.signature) {
158
- checkedNested++;
159
- if (!verifyNode(ann, publicKeyStr)) {
160
- console.log(
161
- `Annotation '${ann["bom-ref"] || ann.subject}' signature is invalid!`,
162
- );
163
- hasInvalidNested = true;
177
+ const nestedTargets = [
178
+ ["components", "Component", (c) => c["bom-ref"] || c.name],
179
+ ["services", "Service", (s) => s["bom-ref"] || s.name],
180
+ ["annotations", "Annotation", (a) => a["bom-ref"] || a.subject],
181
+ ];
182
+ for (const [field, label, nameOf] of nestedTargets) {
183
+ for (const node of bomJson[field] || []) {
184
+ if (node?.signature) {
185
+ checkedNested++;
186
+ const result = verify(node);
187
+ if (!result.match) {
188
+ console.log(
189
+ `${label} '${displayValue(nameOf(node))}' signature is invalid!`,
190
+ );
191
+ printReasons(result.reasons);
192
+ hasInvalidNested = true;
193
+ }
164
194
  }
165
195
  }
166
196
  }
@@ -168,17 +198,27 @@ if (verifyNested) {
168
198
 
169
199
  if (hasInvalidNested) {
170
200
  console.log("One or more nested signatures are invalid!");
201
+ if (rootResult?.match) {
202
+ console.log(
203
+ "The root signature verifies with this key. Nested signatures belong to the party that created them, so pass --no-deep to verify only the root signature with this key.",
204
+ );
205
+ }
171
206
  process.exit(1);
172
207
  }
173
208
 
174
209
  if (bomJson.signature) {
210
+ const rootMatch = rootResult?.match;
175
211
  if (rootMatch) {
176
212
  const identifier = rootMatch.keyId
177
- ? `KeyId: '${rootMatch.keyId}'`
213
+ ? `KeyId: '${displayValue(rootMatch.keyId)}'`
178
214
  : `Algorithm: '${rootMatch.algorithm}'`;
179
215
  console.log(`✓ Signature is valid! (Matched ${identifier})`);
180
216
  } else {
181
217
  console.log("BOM signature is invalid!");
218
+ printReasons(rootResult?.reasons || []);
219
+ console.log(
220
+ "If this BOM was signed with cdxgen 13.2.0 or earlier, re-sign it with this version of cdx-sign.",
221
+ );
182
222
  process.exit(1);
183
223
  }
184
224
  } else if (checkedNested > 0 && !hasInvalidNested) {
@@ -40,11 +40,11 @@
40
40
  "description": "Korean SEED algorithm, CBC mode"
41
41
  },
42
42
  "seedOFB": {
43
- "oid": "1.2.410.200004.1.5",
43
+ "oid": "1.2.410.200004.1.6",
44
44
  "description": "Korean SEED algorithm, OFB mode"
45
45
  },
46
46
  "seedCFB": {
47
- "oid": "1.2.410.200004.1.6",
47
+ "oid": "1.2.410.200004.1.5",
48
48
  "description": "Korean SEED algorithm, CFB mode"
49
49
  },
50
50
  "seedMAC": {
@@ -233,11 +233,11 @@
233
233
  },
234
234
  "cryptoProECDH256": {
235
235
  "oid": "1.2.643.7.1.1.6.1",
236
- "description": "CryptoPro ECC DH algorithm for GOST R 34.10-2012 256 bit key"
236
+ "description": "TC26 GOST R 34.10-2012 256-bit key agreement"
237
237
  },
238
238
  "cryptoProECDH512": {
239
239
  "oid": "1.2.643.7.1.1.6.2",
240
- "description": "CryptoPro ECC DH algorithm for GOST R 34.10-2012 512 bit key"
240
+ "description": "TC26 GOST R 34.10-2012 512-bit key agreement"
241
241
  },
242
242
  "dsa": {
243
243
  "oid": "1.2.840.10040.4.1",
@@ -932,8 +932,8 @@
932
932
  "description": "Teletrust algorithm"
933
933
  },
934
934
  "rsaSignature": {
935
- "oid": "1.3.36.3.3.1",
936
- "description": "Teletrust signature algorithm"
935
+ "oid": "1.3.14.3.2.11",
936
+ "description": "RSA signature (OIW secsig)"
937
937
  },
938
938
  "rsaSignatureWithsha1": {
939
939
  "oid": "1.3.36.3.3.1.1",
@@ -1412,8 +1412,8 @@
1412
1412
  "description": "Novell encryption algorithm"
1413
1413
  },
1414
1414
  "sha-1": {
1415
- "oid": "2.16.840.1.113719.1.2.8.82",
1416
- "description": "Novell digest algorithm"
1415
+ "oid": "1.3.14.3.2.26",
1416
+ "description": "SHA-1 secure hash standard (OIW)"
1417
1417
  },
1418
1418
  "rc2BSafe1Cbc": {
1419
1419
  "oid": "2.16.840.1.113719.1.2.8.92",
@@ -1959,10 +1959,6 @@
1959
1959
  "oid": "1.2.156.10197.1.301.3",
1960
1960
  "description": "Chinese Cryptography Standardization Technology Committee (CCSTC)"
1961
1961
  },
1962
- "sm2sign_with_": {
1963
- "oid": "1.2.156.10197.1.501",
1964
- "description": "Chinese Cryptography Standardization Technology Committee (CCSTC)"
1965
- },
1966
1962
  "PBKDF2": {
1967
1963
  "oid": "1.2.840.113549.1.5.12",
1968
1964
  "description": "PBKDF2 key derivation algorithm"
@@ -1994,5 +1990,85 @@
1994
1990
  "pbeWithSHA1AndRC2-CBC": {
1995
1991
  "oid": "1.2.840.113549.1.5.11",
1996
1992
  "description": "Password Based Encryption Algorithm. Uses RC2 in Cipher Block Chaining Mode (RC2-CBC)."
1993
+ },
1994
+ "ml-dsa-44": {
1995
+ "oid": "2.16.840.1.101.3.4.3.17",
1996
+ "description": "ML-DSA-44 post-quantum signature (FIPS 204)"
1997
+ },
1998
+ "ml-dsa-65": {
1999
+ "oid": "2.16.840.1.101.3.4.3.18",
2000
+ "description": "ML-DSA-65 post-quantum signature (FIPS 204)"
2001
+ },
2002
+ "ml-dsa-87": {
2003
+ "oid": "2.16.840.1.101.3.4.3.19",
2004
+ "description": "ML-DSA-87 post-quantum signature (FIPS 204)"
2005
+ },
2006
+ "ml-kem-512": {
2007
+ "oid": "2.16.840.1.101.3.4.4.1",
2008
+ "description": "ML-KEM-512 post-quantum key encapsulation (FIPS 203)"
2009
+ },
2010
+ "ml-kem-768": {
2011
+ "oid": "2.16.840.1.101.3.4.4.2",
2012
+ "description": "ML-KEM-768 post-quantum key encapsulation (FIPS 203)"
2013
+ },
2014
+ "ml-kem-1024": {
2015
+ "oid": "2.16.840.1.101.3.4.4.3",
2016
+ "description": "ML-KEM-1024 post-quantum key encapsulation (FIPS 203)"
2017
+ },
2018
+ "x25519": {
2019
+ "oid": "1.3.101.110",
2020
+ "description": "X25519 Diffie-Hellman key agreement (RFC 7748)"
2021
+ },
2022
+ "slh-dsa-sha2-128s": {
2023
+ "oid": "2.16.840.1.101.3.4.3.20",
2024
+ "description": "SLH-DSA-SHA2-128s hash-based signature (FIPS 205)"
2025
+ },
2026
+ "slh-dsa-sha2-128f": {
2027
+ "oid": "2.16.840.1.101.3.4.3.21",
2028
+ "description": "SLH-DSA-SHA2-128f hash-based signature (FIPS 205)"
2029
+ },
2030
+ "slh-dsa-sha2-192s": {
2031
+ "oid": "2.16.840.1.101.3.4.3.22",
2032
+ "description": "SLH-DSA-SHA2-192s hash-based signature (FIPS 205)"
2033
+ },
2034
+ "slh-dsa-sha2-192f": {
2035
+ "oid": "2.16.840.1.101.3.4.3.23",
2036
+ "description": "SLH-DSA-SHA2-192f hash-based signature (FIPS 205)"
2037
+ },
2038
+ "slh-dsa-sha2-256s": {
2039
+ "oid": "2.16.840.1.101.3.4.3.24",
2040
+ "description": "SLH-DSA-SHA2-256s hash-based signature (FIPS 205)"
2041
+ },
2042
+ "slh-dsa-sha2-256f": {
2043
+ "oid": "2.16.840.1.101.3.4.3.25",
2044
+ "description": "SLH-DSA-SHA2-256f hash-based signature (FIPS 205)"
2045
+ },
2046
+ "slh-dsa-shake-128s": {
2047
+ "oid": "2.16.840.1.101.3.4.3.26",
2048
+ "description": "SLH-DSA-SHAKE-128s hash-based signature (FIPS 205)"
2049
+ },
2050
+ "slh-dsa-shake-128f": {
2051
+ "oid": "2.16.840.1.101.3.4.3.27",
2052
+ "description": "SLH-DSA-SHAKE-128f hash-based signature (FIPS 205)"
2053
+ },
2054
+ "slh-dsa-shake-192s": {
2055
+ "oid": "2.16.840.1.101.3.4.3.28",
2056
+ "description": "SLH-DSA-SHAKE-192s hash-based signature (FIPS 205)"
2057
+ },
2058
+ "slh-dsa-shake-192f": {
2059
+ "oid": "2.16.840.1.101.3.4.3.29",
2060
+ "description": "SLH-DSA-SHAKE-192f hash-based signature (FIPS 205)"
2061
+ },
2062
+ "slh-dsa-shake-256s": {
2063
+ "oid": "2.16.840.1.101.3.4.3.30",
2064
+ "description": "SLH-DSA-SHAKE-256s hash-based signature (FIPS 205)"
2065
+ },
2066
+ "slh-dsa-shake-256f": {
2067
+ "oid": "2.16.840.1.101.3.4.3.31",
2068
+ "description": "SLH-DSA-SHAKE-256f hash-based signature (FIPS 205)"
2069
+ },
2070
+ "sm2sign_with_sm3": {
2071
+ "oid": "1.2.156.10197.1.501",
2072
+ "description": "Chinese Cryptography Standardization Technology Committee (CCSTC)"
1997
2073
  }
1998
2074
  }