ca-certs: generate install artifacts and improve certdata/trust-store compatibility
- stop committing generated man/completion files in contrib/ - generate man page and shell completions during Meson install via install-generated-docs.sh - switch reqwest to native-tls and add Mozilla hg bootstrap certs with openssl fallback fetch - make certdata sync use a temporary auto-cleaned workspace by default - add BLFS/make-ca compatibility outputs and symlinks under /etc/pki and /etc/ssl - validate extracted outputs are non-empty and add tests for temp sync output behavior
This commit is contained in:
Generated
+135
-507
@@ -64,28 +64,6 @@ version = "1.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1505bd5d3d116872e7271a6d4e16d81d0c8570876c8de68093a09ac269d8aac0"
|
||||
|
||||
[[package]]
|
||||
name = "aws-lc-rs"
|
||||
version = "1.16.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d9a7b350e3bb1767102698302bc37256cbd48422809984b98d292c40e2579aa9"
|
||||
dependencies = [
|
||||
"aws-lc-sys",
|
||||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "aws-lc-sys"
|
||||
version = "0.37.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b092fe214090261288111db7a2b2c2118e5a7f30dc2569f1732c4069a6840549"
|
||||
dependencies = [
|
||||
"cc",
|
||||
"cmake",
|
||||
"dunce",
|
||||
"fs_extra",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "base64"
|
||||
version = "0.22.1"
|
||||
@@ -129,29 +107,15 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "aebf35691d1bfb0ac386a69bac2fde4dd276fb618cf8bf4f5318fe285e821bb2"
|
||||
dependencies = [
|
||||
"find-msvc-tools",
|
||||
"jobserver",
|
||||
"libc",
|
||||
"shlex",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cesu8"
|
||||
version = "1.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6d43a04d8753f35258c91f8ec639f792891f748a1edbd759cf1dcea3382ad83c"
|
||||
|
||||
[[package]]
|
||||
name = "cfg-if"
|
||||
version = "1.0.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9330f8b2ff13f34540b44e946ef35111825727b38d33286ef986142615121801"
|
||||
|
||||
[[package]]
|
||||
name = "cfg_aliases"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "613afe47fcd5fac7ccf1db93babcb082c5994d996f20b8b159f2ad1658eb5724"
|
||||
|
||||
[[package]]
|
||||
name = "clap"
|
||||
version = "4.5.60"
|
||||
@@ -211,36 +175,17 @@ dependencies = [
|
||||
"roff",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cmake"
|
||||
version = "0.1.57"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "75443c44cd6b379beb8c5b45d85d0773baf31cce901fe7bb252f4eff3008ef7d"
|
||||
dependencies = [
|
||||
"cc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "colorchoice"
|
||||
version = "1.0.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b05b61dc5112cbb17e4b6cd61790d9845d13888356391624cbe7e41efeac1e75"
|
||||
|
||||
[[package]]
|
||||
name = "combine"
|
||||
version = "4.6.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ba5a308b75df32fe02788e748662718f03fde005016435c444eea572398219fd"
|
||||
dependencies = [
|
||||
"bytes",
|
||||
"memchr",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "core-foundation"
|
||||
version = "0.10.1"
|
||||
version = "0.9.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b2a6cd9ae233e7f62ba4e9353e81a88df7fc8a5987b8d445b4d90c879bd156f6"
|
||||
checksum = "91e195e091a93c46f7102ec7818a2aa394e1e1771c3ab4825963fa03e45afb8f"
|
||||
dependencies = [
|
||||
"core-foundation-sys",
|
||||
"libc",
|
||||
@@ -264,10 +209,20 @@ dependencies = [
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dunce"
|
||||
version = "1.0.5"
|
||||
name = "errno"
|
||||
version = "0.3.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "92773504d58c093f6de2459af4af33faa518c13451eb8f2b5698ed3d36e7c813"
|
||||
checksum = "39cab71617ae0d63f51a36d69f866391735b51691dbda63cf6f96d042b63efeb"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fastrand"
|
||||
version = "2.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "37909eebbb50d72f9059c3b6d82c0463f2ff062c9e95845c43a6c9c0355411be"
|
||||
|
||||
[[package]]
|
||||
name = "find-msvc-tools"
|
||||
@@ -275,6 +230,21 @@ version = "0.1.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5baebc0774151f905a1a2cc41989300b1e6fbb29aff0ceffa1064fdd3088d582"
|
||||
|
||||
[[package]]
|
||||
name = "foreign-types"
|
||||
version = "0.3.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f6f339eb8adc052cd2ca78910fda869aefa38d22d5cb648e6485e4d3fc06f3b1"
|
||||
dependencies = [
|
||||
"foreign-types-shared",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "foreign-types-shared"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b"
|
||||
|
||||
[[package]]
|
||||
name = "form_urlencoded"
|
||||
version = "1.2.2"
|
||||
@@ -284,12 +254,6 @@ dependencies = [
|
||||
"percent-encoding",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fs_extra"
|
||||
version = "1.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "42703706b716c37f96a77aea830392ad231f44c9e9a67872fa5548707e11b11c"
|
||||
|
||||
[[package]]
|
||||
name = "futures-channel"
|
||||
version = "0.3.32"
|
||||
@@ -339,19 +303,6 @@ dependencies = [
|
||||
"slab",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "getrandom"
|
||||
version = "0.2.17"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ff2abc00be7fca6ebc474524697ae276ad847ad0a6b3faa4bcb027e9a4614ad0"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"js-sys",
|
||||
"libc",
|
||||
"wasi",
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "getrandom"
|
||||
version = "0.3.4"
|
||||
@@ -359,11 +310,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "899def5c37c4fd7b2664648c28120ecec138e4d395b459e5ca34f9cce2dd77fd"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"js-sys",
|
||||
"libc",
|
||||
"r-efi",
|
||||
"wasip2",
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -433,18 +382,18 @@ dependencies = [
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "hyper-rustls"
|
||||
version = "0.27.7"
|
||||
name = "hyper-tls"
|
||||
version = "0.6.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e3c93eb611681b207e1fe55d5a71ecf91572ec8a6705cdb6857f7d8d5242cf58"
|
||||
checksum = "70206fc6890eaca9fde8a0bf71caa2ddfc9fe045ac9e5c70df101a7dbde866e0"
|
||||
dependencies = [
|
||||
"http",
|
||||
"bytes",
|
||||
"http-body-util",
|
||||
"hyper",
|
||||
"hyper-util",
|
||||
"rustls",
|
||||
"rustls-pki-types",
|
||||
"native-tls",
|
||||
"tokio",
|
||||
"tokio-rustls",
|
||||
"tokio-native-tls",
|
||||
"tower-service",
|
||||
]
|
||||
|
||||
@@ -601,38 +550,6 @@ version = "1.0.17"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "92ecc6618181def0457392ccd0ee51198e065e016d1d527a7ac1b6dc7c1f09d2"
|
||||
|
||||
[[package]]
|
||||
name = "jni"
|
||||
version = "0.21.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1a87aa2bb7d2af34197c04845522473242e1aa17c12f4935d5856491a7fb8c97"
|
||||
dependencies = [
|
||||
"cesu8",
|
||||
"cfg-if",
|
||||
"combine",
|
||||
"jni-sys",
|
||||
"log",
|
||||
"thiserror 1.0.69",
|
||||
"walkdir",
|
||||
"windows-sys 0.45.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "jni-sys"
|
||||
version = "0.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8eaf4bc02d17cbdd7ff4c7438cafcdf7fb9a4613313ad11b4f8fefe7d3fa0130"
|
||||
|
||||
[[package]]
|
||||
name = "jobserver"
|
||||
version = "0.1.34"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9afb3de4395d6b3e67a780b6de64b51c978ecf11cb9a462c66be7d4ca9039d33"
|
||||
dependencies = [
|
||||
"getrandom 0.3.4",
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "js-sys"
|
||||
version = "0.3.88"
|
||||
@@ -649,6 +566,12 @@ version = "0.2.182"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6800badb6cb2082ffd7b6a67e6125bb39f18782f793520caee8cb8846be06112"
|
||||
|
||||
[[package]]
|
||||
name = "linux-raw-sys"
|
||||
version = "0.12.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "32a66949e030da00e8c7d4434b251670a91556f4144941d37452769c25d58a53"
|
||||
|
||||
[[package]]
|
||||
name = "litemap"
|
||||
version = "0.8.1"
|
||||
@@ -661,12 +584,6 @@ version = "0.4.29"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5e5032e24019045c762d3c0f28f5b6b8bbf38563a65908389bf7978758920897"
|
||||
|
||||
[[package]]
|
||||
name = "lru-slab"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "112b39cec0b298b6c1999fee3e31427f74f676e4cb9879ed1a121b43661a4154"
|
||||
|
||||
[[package]]
|
||||
name = "memchr"
|
||||
version = "2.8.0"
|
||||
@@ -684,6 +601,23 @@ dependencies = [
|
||||
"windows-sys 0.61.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "native-tls"
|
||||
version = "0.2.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "87de3442987e9dbec73158d5c715e7ad9072fda936bb03d19d7fa10e00520f0e"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"log",
|
||||
"openssl",
|
||||
"openssl-probe",
|
||||
"openssl-sys",
|
||||
"schannel",
|
||||
"security-framework",
|
||||
"security-framework-sys",
|
||||
"tempfile",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "once_cell"
|
||||
version = "1.21.3"
|
||||
@@ -697,10 +631,48 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "384b8ab6d37215f3c5301a95a4accb5d64aa607f1fcb26a11b5303878451b4fe"
|
||||
|
||||
[[package]]
|
||||
name = "openssl-probe"
|
||||
version = "0.2.1"
|
||||
name = "openssl"
|
||||
version = "0.10.75"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7c87def4c32ab89d880effc9e097653c8da5d6ef28e6b539d313baaacfbafcbe"
|
||||
checksum = "08838db121398ad17ab8531ce9de97b244589089e290a384c900cb9ff7434328"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"cfg-if",
|
||||
"foreign-types",
|
||||
"libc",
|
||||
"once_cell",
|
||||
"openssl-macros",
|
||||
"openssl-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "openssl-macros"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "openssl-probe"
|
||||
version = "0.1.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d05e27ee213611ffe7d6348b942e8f942b37114c00cc03cec254295a4a17852e"
|
||||
|
||||
[[package]]
|
||||
name = "openssl-sys"
|
||||
version = "0.9.111"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "82cab2d520aa75e3c58898289429321eb788c3106963d0dc886ec7a5f4adc321"
|
||||
dependencies = [
|
||||
"cc",
|
||||
"libc",
|
||||
"pkg-config",
|
||||
"vcpkg",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "percent-encoding"
|
||||
@@ -720,6 +692,12 @@ version = "0.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
|
||||
|
||||
[[package]]
|
||||
name = "pkg-config"
|
||||
version = "0.3.32"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7edddbd0b52d732b21ad9a5fab5c704c14cd949e5e9a1ec5929a24fded1b904c"
|
||||
|
||||
[[package]]
|
||||
name = "potential_utf"
|
||||
version = "0.1.4"
|
||||
@@ -729,15 +707,6 @@ dependencies = [
|
||||
"zerovec",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ppv-lite86"
|
||||
version = "0.2.21"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9"
|
||||
dependencies = [
|
||||
"zerocopy",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.106"
|
||||
@@ -747,62 +716,6 @@ dependencies = [
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "quinn"
|
||||
version = "0.11.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b9e20a958963c291dc322d98411f541009df2ced7b5a4f2bd52337638cfccf20"
|
||||
dependencies = [
|
||||
"bytes",
|
||||
"cfg_aliases",
|
||||
"pin-project-lite",
|
||||
"quinn-proto",
|
||||
"quinn-udp",
|
||||
"rustc-hash",
|
||||
"rustls",
|
||||
"socket2",
|
||||
"thiserror 2.0.18",
|
||||
"tokio",
|
||||
"tracing",
|
||||
"web-time",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "quinn-proto"
|
||||
version = "0.11.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f1906b49b0c3bc04b5fe5d86a77925ae6524a19b816ae38ce1e426255f1d8a31"
|
||||
dependencies = [
|
||||
"aws-lc-rs",
|
||||
"bytes",
|
||||
"getrandom 0.3.4",
|
||||
"lru-slab",
|
||||
"rand",
|
||||
"ring",
|
||||
"rustc-hash",
|
||||
"rustls",
|
||||
"rustls-pki-types",
|
||||
"slab",
|
||||
"thiserror 2.0.18",
|
||||
"tinyvec",
|
||||
"tracing",
|
||||
"web-time",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "quinn-udp"
|
||||
version = "0.5.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "addec6a0dcad8a8d96a771f815f0eaf55f9d1805756410b39f5fa81332574cbd"
|
||||
dependencies = [
|
||||
"cfg_aliases",
|
||||
"libc",
|
||||
"once_cell",
|
||||
"socket2",
|
||||
"tracing",
|
||||
"windows-sys 0.60.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "quote"
|
||||
version = "1.0.44"
|
||||
@@ -818,35 +731,6 @@ version = "5.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "69cdb34c158ceb288df11e18b4bd39de994f6657d83847bdffdbd7f346754b0f"
|
||||
|
||||
[[package]]
|
||||
name = "rand"
|
||||
version = "0.9.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6db2770f06117d490610c7488547d543617b21bfa07796d7a12f6f1bd53850d1"
|
||||
dependencies = [
|
||||
"rand_chacha",
|
||||
"rand_core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand_chacha"
|
||||
version = "0.9.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d3022b5f1df60f26e1ffddd6c66e8aa15de382ae63b3a0c1bfc0e4d3e3f325cb"
|
||||
dependencies = [
|
||||
"ppv-lite86",
|
||||
"rand_core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand_core"
|
||||
version = "0.9.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "76afc826de14238e6e8c374ddcc1fa19e374fd8dd986b0d2af0d02377261d83c"
|
||||
dependencies = [
|
||||
"getrandom 0.3.4",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "reqwest"
|
||||
version = "0.13.2"
|
||||
@@ -862,19 +746,17 @@ dependencies = [
|
||||
"http-body",
|
||||
"http-body-util",
|
||||
"hyper",
|
||||
"hyper-rustls",
|
||||
"hyper-tls",
|
||||
"hyper-util",
|
||||
"js-sys",
|
||||
"log",
|
||||
"native-tls",
|
||||
"percent-encoding",
|
||||
"pin-project-lite",
|
||||
"quinn",
|
||||
"rustls",
|
||||
"rustls-pki-types",
|
||||
"rustls-platform-verifier",
|
||||
"sync_wrapper",
|
||||
"tokio",
|
||||
"tokio-rustls",
|
||||
"tokio-native-tls",
|
||||
"tower",
|
||||
"tower-http",
|
||||
"tower-service",
|
||||
@@ -884,20 +766,6 @@ dependencies = [
|
||||
"web-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ring"
|
||||
version = "0.17.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a4689e6c2294d81e88dc6261c768b63bc4fcdb852be6d1352498b114f61383b7"
|
||||
dependencies = [
|
||||
"cc",
|
||||
"cfg-if",
|
||||
"getrandom 0.2.17",
|
||||
"libc",
|
||||
"untrusted",
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "roff"
|
||||
version = "0.2.2"
|
||||
@@ -905,35 +773,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "88f8660c1ff60292143c98d08fc6e2f654d722db50410e3f3797d40baaf9d8f3"
|
||||
|
||||
[[package]]
|
||||
name = "rustc-hash"
|
||||
version = "2.1.1"
|
||||
name = "rustix"
|
||||
version = "1.1.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "357703d41365b4b27c590e3ed91eabb1b663f07c4c084095e60cbed4362dff0d"
|
||||
|
||||
[[package]]
|
||||
name = "rustls"
|
||||
version = "0.23.36"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c665f33d38cea657d9614f766881e4d510e0eda4239891eea56b4cadcf01801b"
|
||||
checksum = "b6fe4565b9518b83ef4f91bb47ce29620ca828bd32cb7e408f0062e9930ba190"
|
||||
dependencies = [
|
||||
"aws-lc-rs",
|
||||
"once_cell",
|
||||
"rustls-pki-types",
|
||||
"rustls-webpki",
|
||||
"subtle",
|
||||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustls-native-certs"
|
||||
version = "0.8.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "612460d5f7bea540c490b2b6395d8e34a953e52b491accd6c86c8164c5932a63"
|
||||
dependencies = [
|
||||
"openssl-probe",
|
||||
"rustls-pki-types",
|
||||
"schannel",
|
||||
"security-framework",
|
||||
"bitflags",
|
||||
"errno",
|
||||
"libc",
|
||||
"linux-raw-sys",
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -942,64 +791,15 @@ version = "1.14.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "be040f8b0a225e40375822a563fa9524378b9d63112f53e19ffff34df5d33fdd"
|
||||
dependencies = [
|
||||
"web-time",
|
||||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustls-platform-verifier"
|
||||
version = "0.6.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1d99feebc72bae7ab76ba994bb5e121b8d83d910ca40b36e0921f53becc41784"
|
||||
dependencies = [
|
||||
"core-foundation",
|
||||
"core-foundation-sys",
|
||||
"jni",
|
||||
"log",
|
||||
"once_cell",
|
||||
"rustls",
|
||||
"rustls-native-certs",
|
||||
"rustls-platform-verifier-android",
|
||||
"rustls-webpki",
|
||||
"security-framework",
|
||||
"security-framework-sys",
|
||||
"webpki-root-certs",
|
||||
"windows-sys 0.61.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustls-platform-verifier-android"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f87165f0995f63a9fbeea62b64d10b4d9d8e78ec6d7d51fb2125fda7bb36788f"
|
||||
|
||||
[[package]]
|
||||
name = "rustls-webpki"
|
||||
version = "0.103.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d7df23109aa6c1567d1c575b9952556388da57401e4ace1d15f79eedad0d8f53"
|
||||
dependencies = [
|
||||
"aws-lc-rs",
|
||||
"ring",
|
||||
"rustls-pki-types",
|
||||
"untrusted",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustversion"
|
||||
version = "1.0.22"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b39cdef0fa800fc44525c84ccb54a029961a8215f9619753635a9c0d2538d46d"
|
||||
|
||||
[[package]]
|
||||
name = "same-file"
|
||||
version = "1.0.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502"
|
||||
dependencies = [
|
||||
"winapi-util",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "schannel"
|
||||
version = "0.1.28"
|
||||
@@ -1011,9 +811,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "security-framework"
|
||||
version = "3.7.0"
|
||||
version = "2.11.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b7f4bc775c73d9a02cde8bf7b2ec4c9d12743edf609006c7facc23998404cd1d"
|
||||
checksum = "897b2245f0b511c87893af39b033e5ca9cce68824c4d7e7630b5a1d339658d02"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"core-foundation",
|
||||
@@ -1102,12 +902,6 @@ version = "0.11.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7da8b5736845d9f2fcb837ea5d9e2628564b3b043a70948a3f0b778838c5fb4f"
|
||||
|
||||
[[package]]
|
||||
name = "subtle"
|
||||
version = "2.6.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "13c2bddecc57b384dee18652358fb23172facb8a2c51ccc10d74c157bdea3292"
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "2.0.117"
|
||||
@@ -1140,43 +934,16 @@ dependencies = [
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "thiserror"
|
||||
version = "1.0.69"
|
||||
name = "tempfile"
|
||||
version = "3.25.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b6aaf5339b578ea85b50e080feb250a3e8ae8cfcdff9a461c9ec2904bc923f52"
|
||||
checksum = "0136791f7c95b1f6dd99f9cc786b91bb81c3800b639b3478e561ddb7be95e5f1"
|
||||
dependencies = [
|
||||
"thiserror-impl 1.0.69",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "thiserror"
|
||||
version = "2.0.18"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4288b5bcbc7920c07a1149a35cf9590a2aa808e0bc1eafaade0b80947865fbc4"
|
||||
dependencies = [
|
||||
"thiserror-impl 2.0.18",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "thiserror-impl"
|
||||
version = "1.0.69"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4fee6c4efc90059e10f81e6d42c60a18f76588c3d74cb83a0b242a2b6c7504c1"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "thiserror-impl"
|
||||
version = "2.0.18"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ebc4ee7f67670e9b64d05fa4253e753e016c6c95ff35b89b7941d6b856dec1d5"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"fastrand",
|
||||
"getrandom",
|
||||
"once_cell",
|
||||
"rustix",
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1189,21 +956,6 @@ dependencies = [
|
||||
"zerovec",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tinyvec"
|
||||
version = "1.10.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bfa5fdc3bce6191a1dbc8c02d5c8bffcf557bafa17c124c5264a458f1b0613fa"
|
||||
dependencies = [
|
||||
"tinyvec_macros",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tinyvec_macros"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20"
|
||||
|
||||
[[package]]
|
||||
name = "tokio"
|
||||
version = "1.49.0"
|
||||
@@ -1219,12 +971,12 @@ dependencies = [
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tokio-rustls"
|
||||
version = "0.26.4"
|
||||
name = "tokio-native-tls"
|
||||
version = "0.3.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1729aa945f29d91ba541258c8df89027d5792d85a8841fb65e8bf0f4ede4ef61"
|
||||
checksum = "bbae76ab933c85776efabc971569dd6119c580d8f5d448769dec1764bf796ef2"
|
||||
dependencies = [
|
||||
"rustls",
|
||||
"native-tls",
|
||||
"tokio",
|
||||
]
|
||||
|
||||
@@ -1304,12 +1056,6 @@ version = "1.0.24"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e6e4313cd5fcd3dad5cafa179702e2b244f760991f45397d14d4ebf38247da75"
|
||||
|
||||
[[package]]
|
||||
name = "untrusted"
|
||||
version = "0.9.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1"
|
||||
|
||||
[[package]]
|
||||
name = "url"
|
||||
version = "2.5.8"
|
||||
@@ -1335,14 +1081,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "06abde3611657adf66d383f00b093d7faecc7fa57071cce2578660c9f1010821"
|
||||
|
||||
[[package]]
|
||||
name = "walkdir"
|
||||
version = "2.5.0"
|
||||
name = "vcpkg"
|
||||
version = "0.2.15"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "29790946404f91d9c5d06f9874efddea1dc06c5efe94541a7d6863108e3a5e4b"
|
||||
dependencies = [
|
||||
"same-file",
|
||||
"winapi-util",
|
||||
]
|
||||
checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426"
|
||||
|
||||
[[package]]
|
||||
name = "want"
|
||||
@@ -1437,49 +1179,12 @@ dependencies = [
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "web-time"
|
||||
version = "1.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5a6580f308b1fad9207618087a65c04e7a10bc77e02c8e84e9b00dd4b12fa0bb"
|
||||
dependencies = [
|
||||
"js-sys",
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "webpki-root-certs"
|
||||
version = "1.0.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "804f18a4ac2676ffb4e8b5b5fa9ae38af06df08162314f96a68d2a363e21a8ca"
|
||||
dependencies = [
|
||||
"rustls-pki-types",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "winapi-util"
|
||||
version = "0.1.11"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c2a7b1c03c876122aa43f3020e6c3c3ee5c05081c9a00739faf7503aeba10d22"
|
||||
dependencies = [
|
||||
"windows-sys 0.61.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-link"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f0805222e57f7521d6a62e36fa9163bc891acd422f971defe97d64e70d0a4fe5"
|
||||
|
||||
[[package]]
|
||||
name = "windows-sys"
|
||||
version = "0.45.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "75283be5efb2831d37ea142365f009c02ec203cd29a3ebecbc093d52315b66d0"
|
||||
dependencies = [
|
||||
"windows-targets 0.42.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-sys"
|
||||
version = "0.52.0"
|
||||
@@ -1507,21 +1212,6 @@ dependencies = [
|
||||
"windows-link",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-targets"
|
||||
version = "0.42.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8e5180c00cd44c9b1c88adb3693291f1cd93605ded80c250a75d472756b4d071"
|
||||
dependencies = [
|
||||
"windows_aarch64_gnullvm 0.42.2",
|
||||
"windows_aarch64_msvc 0.42.2",
|
||||
"windows_i686_gnu 0.42.2",
|
||||
"windows_i686_msvc 0.42.2",
|
||||
"windows_x86_64_gnu 0.42.2",
|
||||
"windows_x86_64_gnullvm 0.42.2",
|
||||
"windows_x86_64_msvc 0.42.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-targets"
|
||||
version = "0.52.6"
|
||||
@@ -1555,12 +1245,6 @@ dependencies = [
|
||||
"windows_x86_64_msvc 0.53.1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.42.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "597a5118570b68bc08d8d59125332c54f1ba9d9adeedeef5b99b02ba2b0698f8"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.52.6"
|
||||
@@ -1573,12 +1257,6 @@ version = "0.53.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a9d8416fa8b42f5c947f8482c43e7d89e73a173cead56d044f6a56104a6d1b53"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.42.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e08e8864a60f06ef0d0ff4ba04124db8b0fb3be5776a5cd47641e942e58c4d43"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.52.6"
|
||||
@@ -1591,12 +1269,6 @@ version = "0.53.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b9d782e804c2f632e395708e99a94275910eb9100b2114651e04744e9b125006"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.42.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c61d927d8da41da96a81f029489353e68739737d3beca43145c8afec9a31a84f"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.52.6"
|
||||
@@ -1621,12 +1293,6 @@ version = "0.53.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "fa7359d10048f68ab8b09fa71c3daccfb0e9b559aed648a8f95469c27057180c"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.42.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "44d840b6ec649f480a41c8d80f9c65108b92d89345dd94027bfe06ac444d1060"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.52.6"
|
||||
@@ -1639,12 +1305,6 @@ version = "0.53.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1e7ac75179f18232fe9c285163565a57ef8d3c89254a30685b57d83a38d326c2"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.42.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8de912b8b8feb55c064867cf047dda097f92d51efad5b491dfb98f6bbb70cb36"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.52.6"
|
||||
@@ -1657,12 +1317,6 @@ version = "0.53.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9c3842cdd74a865a8066ab39c8a7a473c0778a3f29370b5fd6b4b9aa7df4a499"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnullvm"
|
||||
version = "0.42.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "26d41b46a36d453748aedef1486d5c7a85db22e56aff34643984ea85514e94a3"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnullvm"
|
||||
version = "0.52.6"
|
||||
@@ -1675,12 +1329,6 @@ version = "0.53.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0ffa179e2d07eee8ad8f57493436566c7cc30ac536a3379fdf008f47f6bb7ae1"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.42.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9aec5da331524158c6d1a4ac0ab1541149c0b9505fde06423b02f5ef0106b9f0"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.52.6"
|
||||
@@ -1728,26 +1376,6 @@ dependencies = [
|
||||
"synstructure",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zerocopy"
|
||||
version = "0.8.39"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "db6d35d663eadb6c932438e763b262fe1a70987f9ae936e60158176d710cae4a"
|
||||
dependencies = [
|
||||
"zerocopy-derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zerocopy-derive"
|
||||
version = "0.8.39"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4122cd3169e94605190e77839c9a40d40ed048d305bfdc146e7df40ab0f3e517"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zerofrom"
|
||||
version = "0.1.6"
|
||||
|
||||
+1
-1
@@ -9,7 +9,7 @@ base64 = "0.22.1"
|
||||
clap = { version = "4.5.60", features = ["derive"] }
|
||||
clap_complete = "4.5.66"
|
||||
clap_mangen = "0.2.31"
|
||||
reqwest = { version = "0.13.2", default-features = false, features = ["blocking", "rustls"] }
|
||||
reqwest = { version = "0.13.2", default-features = false, features = ["blocking", "native-tls"] }
|
||||
|
||||
[lints.rust]
|
||||
warnings = "deny"
|
||||
|
||||
@@ -34,7 +34,7 @@ target/release/ca-certs
|
||||
|
||||
### Meson (packaging-friendly)
|
||||
|
||||
Builds the Rust binary and installs the man page + shell completions from `contrib/`.
|
||||
Builds the Rust binary and generates man/completion artifacts during install.
|
||||
|
||||
```bash
|
||||
meson setup build
|
||||
@@ -156,7 +156,7 @@ Run tests:
|
||||
cargo test
|
||||
```
|
||||
|
||||
The repository also includes a generated man page and shell completions under `contrib/`.
|
||||
Man page and shell completions are generated by `ca-certs gen-artifacts`.
|
||||
|
||||
## License
|
||||
|
||||
|
||||
@@ -1,31 +0,0 @@
|
||||
.ie \n(.g .ds Aq \(aq
|
||||
.el .ds Aq '
|
||||
.TH ca-certs 8 "ca-certs 0.1.0"
|
||||
.SH NAME
|
||||
ca\-certs \- Manage Linux CA trust store sources and extracted bundles (p11\-kit/trust)
|
||||
.SH SYNOPSIS
|
||||
\fBca\-certs\fR [\fB\-h\fR|\fB\-\-help\fR] [\fB\-V\fR|\fB\-\-version\fR] <\fIsubcommands\fR>
|
||||
.SH DESCRIPTION
|
||||
Manage Linux CA trust store sources and extracted bundles (p11\-kit/trust)
|
||||
.SH OPTIONS
|
||||
.TP
|
||||
\fB\-h\fR, \fB\-\-help\fR
|
||||
Print help
|
||||
.TP
|
||||
\fB\-V\fR, \fB\-\-version\fR
|
||||
Print version
|
||||
.SH SUBCOMMANDS
|
||||
.TP
|
||||
ca\-certs\-add(8)
|
||||
Add a PEM CA certificate to trust\-source/anchors and refresh extracted outputs
|
||||
.TP
|
||||
ca\-certs\-extract(8)
|
||||
Regenerate extracted trust bundles (like update\-ca\-trust extract)
|
||||
.TP
|
||||
ca\-certs\-certdata(8)
|
||||
Fetch and parse Mozilla/NSS certdata.txt (no certificate generation yet)
|
||||
.TP
|
||||
ca\-certs\-help(8)
|
||||
Print this message or the help of the given subcommand(s)
|
||||
.SH VERSION
|
||||
v0.1.0
|
||||
@@ -1,401 +0,0 @@
|
||||
#compdef ca-certs
|
||||
|
||||
autoload -U is-at-least
|
||||
|
||||
_ca-certs() {
|
||||
typeset -A opt_args
|
||||
typeset -a _arguments_options
|
||||
local ret=1
|
||||
|
||||
if is-at-least 5.2; then
|
||||
_arguments_options=(-s -S -C)
|
||||
else
|
||||
_arguments_options=(-s -C)
|
||||
fi
|
||||
|
||||
local context curcontext="$curcontext" state line
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
'-V[Print version]' \
|
||||
'--version[Print version]' \
|
||||
":: :_ca-certs_commands" \
|
||||
"*::: :->ca-certs" \
|
||||
&& ret=0
|
||||
case $state in
|
||||
(ca-certs)
|
||||
words=($line[1] "${words[@]}")
|
||||
(( CURRENT += 1 ))
|
||||
curcontext="${curcontext%:*:*}:ca-certs-command-$line[1]:"
|
||||
case $line[1] in
|
||||
(add)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'-n+[Output certificate name (without extension). Defaults to the input filename stem]:NAME:_default' \
|
||||
'--name=[Output certificate name (without extension). Defaults to the input filename stem]:NAME:_default' \
|
||||
'-o+[Extracted output directory inside the target root (default\: /etc/ca-certificates/extracted)]:OUTPUT:_files' \
|
||||
'--output=[Extracted output directory inside the target root (default\: /etc/ca-certificates/extracted)]:OUTPUT:_files' \
|
||||
'--root=[Target root filesystem (for chroot/image builds)]:ROOT:_files' \
|
||||
'--force[Overwrite an existing anchor if contents differ]' \
|
||||
'--no-extract[Add certificate but do not run extraction]' \
|
||||
'--dry-run[Print actions without modifying files]' \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
':cert -- Path to a PEM-encoded CA certificate:_files' \
|
||||
&& ret=0
|
||||
;;
|
||||
(extract)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'-o+[Extracted output directory inside the target root (default\: /etc/ca-certificates/extracted)]:OUTPUT:_files' \
|
||||
'--output=[Extracted output directory inside the target root (default\: /etc/ca-certificates/extracted)]:OUTPUT:_files' \
|
||||
'--root=[Target root filesystem (for chroot/image builds)]:ROOT:_files' \
|
||||
'--dry-run[Print actions without modifying files]' \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
&& ret=0
|
||||
;;
|
||||
(certdata)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
":: :_ca-certs__certdata_commands" \
|
||||
"*::: :->certdata" \
|
||||
&& ret=0
|
||||
|
||||
case $state in
|
||||
(certdata)
|
||||
words=($line[1] "${words[@]}")
|
||||
(( CURRENT += 1 ))
|
||||
curcontext="${curcontext%:*:*}:ca-certs-certdata-command-$line[1]:"
|
||||
case $line[1] in
|
||||
(fetch)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'--url=[Source URL for certdata.txt]:URL:_default' \
|
||||
'--log-url=[Override log URL used to determine the latest revision (optional)]:LOG_URL:_default' \
|
||||
'-o+[Output file path]:OUTPUT:_files' \
|
||||
'--output=[Output file path]:OUTPUT:_files' \
|
||||
'--force[Overwrite an existing file if contents differ]' \
|
||||
'--no-revision-check[Always download even if the local file revision matches the remote revision]' \
|
||||
'--no-parse[Skip parsing/summary after download]' \
|
||||
'--dry-run[Print actions without modifying files]' \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
&& ret=0
|
||||
;;
|
||||
(parse)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'--limit=[Print up to N object summaries after the aggregate stats]:LIMIT:_default' \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
'::input -- Path to certdata.txt:_files' \
|
||||
&& ret=0
|
||||
;;
|
||||
(convert)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'--root=[Target root filesystem (for chroot/image builds)]:ROOT:_files' \
|
||||
'--output=[Destination p11-kit trust source file inside the target root]:OUTPUT:_files' \
|
||||
'-o+[Extracted output directory inside the target root (default\: /etc/ca-certificates/extracted)]:EXTRACT_OUTPUT:_files' \
|
||||
'--extract-output=[Extracted output directory inside the target root (default\: /etc/ca-certificates/extracted)]:EXTRACT_OUTPUT:_files' \
|
||||
'--force[Overwrite an existing output file if contents differ]' \
|
||||
'--no-extract[Skip running trust extraction after writing the Mozilla source bundle]' \
|
||||
'--dry-run[Print actions without modifying files]' \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
'::input -- Path to certdata.txt:_files' \
|
||||
&& ret=0
|
||||
;;
|
||||
(sync)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'--url=[Source URL for certdata.txt]:URL:_default' \
|
||||
'--log-url=[Override log URL used to determine the latest revision (optional)]:LOG_URL:_default' \
|
||||
'--certdata-output=[Local certdata.txt path used for fetch and convert]:CERTDATA_OUTPUT:_files' \
|
||||
'--root=[Target root filesystem (for chroot/image builds)]:ROOT:_files' \
|
||||
'--mozilla-output=[Destination p11-kit trust source file inside the target root]:MOZILLA_OUTPUT:_files' \
|
||||
'-o+[Extracted output directory inside the target root (default\: /etc/ca-certificates/extracted)]:EXTRACT_OUTPUT:_files' \
|
||||
'--extract-output=[Extracted output directory inside the target root (default\: /etc/ca-certificates/extracted)]:EXTRACT_OUTPUT:_files' \
|
||||
'--force[Overwrite existing files if contents differ]' \
|
||||
'--no-revision-check[Always download even if the local certdata revision matches the remote revision]' \
|
||||
'--no-parse[Skip parsing/summary after download]' \
|
||||
'--no-extract[Skip running trust extraction after writing the Mozilla source bundle]' \
|
||||
'--dry-run[Print actions without modifying files]' \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
&& ret=0
|
||||
;;
|
||||
(help)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
":: :_ca-certs__certdata__help_commands" \
|
||||
"*::: :->help" \
|
||||
&& ret=0
|
||||
|
||||
case $state in
|
||||
(help)
|
||||
words=($line[1] "${words[@]}")
|
||||
(( CURRENT += 1 ))
|
||||
curcontext="${curcontext%:*:*}:ca-certs-certdata-help-command-$line[1]:"
|
||||
case $line[1] in
|
||||
(fetch)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(parse)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(convert)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(sync)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(help)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
(gen-artifacts)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
'--out-dir=[Directory to write generated packaging artifacts into]:OUT_DIR:_files' \
|
||||
'*--shell=[Shell completions to generate]:SHELLS:(bash fish zsh)' \
|
||||
'--dry-run[Print actions without modifying files]' \
|
||||
'-h[Print help]' \
|
||||
'--help[Print help]' \
|
||||
&& ret=0
|
||||
;;
|
||||
(help)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
":: :_ca-certs__help_commands" \
|
||||
"*::: :->help" \
|
||||
&& ret=0
|
||||
|
||||
case $state in
|
||||
(help)
|
||||
words=($line[1] "${words[@]}")
|
||||
(( CURRENT += 1 ))
|
||||
curcontext="${curcontext%:*:*}:ca-certs-help-command-$line[1]:"
|
||||
case $line[1] in
|
||||
(add)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(extract)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(certdata)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
":: :_ca-certs__help__certdata_commands" \
|
||||
"*::: :->certdata" \
|
||||
&& ret=0
|
||||
|
||||
case $state in
|
||||
(certdata)
|
||||
words=($line[1] "${words[@]}")
|
||||
(( CURRENT += 1 ))
|
||||
curcontext="${curcontext%:*:*}:ca-certs-help-certdata-command-$line[1]:"
|
||||
case $line[1] in
|
||||
(fetch)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(parse)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(convert)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(sync)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
(gen-artifacts)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
(help)
|
||||
_arguments "${_arguments_options[@]}" : \
|
||||
&& ret=0
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
(( $+functions[_ca-certs_commands] )) ||
|
||||
_ca-certs_commands() {
|
||||
local commands; commands=(
|
||||
'add:Add a PEM CA certificate to trust-source/anchors and refresh extracted outputs' \
|
||||
'extract:Regenerate extracted trust bundles (like update-ca-trust extract)' \
|
||||
'certdata:Fetch and parse Mozilla/NSS certdata.txt (no certificate generation yet)' \
|
||||
'gen-artifacts:' \
|
||||
'help:Print this message or the help of the given subcommand(s)' \
|
||||
)
|
||||
_describe -t commands 'ca-certs commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__add_commands] )) ||
|
||||
_ca-certs__add_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs add commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata_commands] )) ||
|
||||
_ca-certs__certdata_commands() {
|
||||
local commands; commands=(
|
||||
'fetch:Fetch certdata.txt from an NSS source URL' \
|
||||
'parse:Parse a local certdata.txt file and print a summary' \
|
||||
'convert:Convert certdata.txt into a Mozilla p11-kit trust bundle and optionally extract outputs' \
|
||||
'sync:Run the full pipeline\: fetch certdata.txt, convert to p11-kit source, then extract outputs' \
|
||||
'help:Print this message or the help of the given subcommand(s)' \
|
||||
)
|
||||
_describe -t commands 'ca-certs certdata commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__convert_commands] )) ||
|
||||
_ca-certs__certdata__convert_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata convert commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__fetch_commands] )) ||
|
||||
_ca-certs__certdata__fetch_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata fetch commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__help_commands] )) ||
|
||||
_ca-certs__certdata__help_commands() {
|
||||
local commands; commands=(
|
||||
'fetch:Fetch certdata.txt from an NSS source URL' \
|
||||
'parse:Parse a local certdata.txt file and print a summary' \
|
||||
'convert:Convert certdata.txt into a Mozilla p11-kit trust bundle and optionally extract outputs' \
|
||||
'sync:Run the full pipeline\: fetch certdata.txt, convert to p11-kit source, then extract outputs' \
|
||||
'help:Print this message or the help of the given subcommand(s)' \
|
||||
)
|
||||
_describe -t commands 'ca-certs certdata help commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__help__convert_commands] )) ||
|
||||
_ca-certs__certdata__help__convert_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata help convert commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__help__fetch_commands] )) ||
|
||||
_ca-certs__certdata__help__fetch_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata help fetch commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__help__help_commands] )) ||
|
||||
_ca-certs__certdata__help__help_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata help help commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__help__parse_commands] )) ||
|
||||
_ca-certs__certdata__help__parse_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata help parse commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__help__sync_commands] )) ||
|
||||
_ca-certs__certdata__help__sync_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata help sync commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__parse_commands] )) ||
|
||||
_ca-certs__certdata__parse_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata parse commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__certdata__sync_commands] )) ||
|
||||
_ca-certs__certdata__sync_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs certdata sync commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__extract_commands] )) ||
|
||||
_ca-certs__extract_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs extract commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__gen-artifacts_commands] )) ||
|
||||
_ca-certs__gen-artifacts_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs gen-artifacts commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help_commands] )) ||
|
||||
_ca-certs__help_commands() {
|
||||
local commands; commands=(
|
||||
'add:Add a PEM CA certificate to trust-source/anchors and refresh extracted outputs' \
|
||||
'extract:Regenerate extracted trust bundles (like update-ca-trust extract)' \
|
||||
'certdata:Fetch and parse Mozilla/NSS certdata.txt (no certificate generation yet)' \
|
||||
'gen-artifacts:' \
|
||||
'help:Print this message or the help of the given subcommand(s)' \
|
||||
)
|
||||
_describe -t commands 'ca-certs help commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__add_commands] )) ||
|
||||
_ca-certs__help__add_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs help add commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__certdata_commands] )) ||
|
||||
_ca-certs__help__certdata_commands() {
|
||||
local commands; commands=(
|
||||
'fetch:Fetch certdata.txt from an NSS source URL' \
|
||||
'parse:Parse a local certdata.txt file and print a summary' \
|
||||
'convert:Convert certdata.txt into a Mozilla p11-kit trust bundle and optionally extract outputs' \
|
||||
'sync:Run the full pipeline\: fetch certdata.txt, convert to p11-kit source, then extract outputs' \
|
||||
)
|
||||
_describe -t commands 'ca-certs help certdata commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__certdata__convert_commands] )) ||
|
||||
_ca-certs__help__certdata__convert_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs help certdata convert commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__certdata__fetch_commands] )) ||
|
||||
_ca-certs__help__certdata__fetch_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs help certdata fetch commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__certdata__parse_commands] )) ||
|
||||
_ca-certs__help__certdata__parse_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs help certdata parse commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__certdata__sync_commands] )) ||
|
||||
_ca-certs__help__certdata__sync_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs help certdata sync commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__extract_commands] )) ||
|
||||
_ca-certs__help__extract_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs help extract commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__gen-artifacts_commands] )) ||
|
||||
_ca-certs__help__gen-artifacts_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs help gen-artifacts commands' commands "$@"
|
||||
}
|
||||
(( $+functions[_ca-certs__help__help_commands] )) ||
|
||||
_ca-certs__help__help_commands() {
|
||||
local commands; commands=()
|
||||
_describe -t commands 'ca-certs help help commands' commands "$@"
|
||||
}
|
||||
|
||||
if [ "$funcstack[1]" = "_ca-certs" ]; then
|
||||
_ca-certs "$@"
|
||||
else
|
||||
compdef _ca-certs ca-certs
|
||||
fi
|
||||
@@ -1,558 +0,0 @@
|
||||
_ca-certs() {
|
||||
local i cur prev opts cmd
|
||||
COMPREPLY=()
|
||||
if [[ "${BASH_VERSINFO[0]}" -ge 4 ]]; then
|
||||
cur="$2"
|
||||
else
|
||||
cur="${COMP_WORDS[COMP_CWORD]}"
|
||||
fi
|
||||
prev="$3"
|
||||
cmd=""
|
||||
opts=""
|
||||
|
||||
for i in "${COMP_WORDS[@]:0:COMP_CWORD}"
|
||||
do
|
||||
case "${cmd},${i}" in
|
||||
",$1")
|
||||
cmd="ca__certs"
|
||||
;;
|
||||
ca__certs,add)
|
||||
cmd="ca__certs__add"
|
||||
;;
|
||||
ca__certs,certdata)
|
||||
cmd="ca__certs__certdata"
|
||||
;;
|
||||
ca__certs,extract)
|
||||
cmd="ca__certs__extract"
|
||||
;;
|
||||
ca__certs,gen-artifacts)
|
||||
cmd="ca__certs__gen__artifacts"
|
||||
;;
|
||||
ca__certs,help)
|
||||
cmd="ca__certs__help"
|
||||
;;
|
||||
ca__certs__certdata,convert)
|
||||
cmd="ca__certs__certdata__convert"
|
||||
;;
|
||||
ca__certs__certdata,fetch)
|
||||
cmd="ca__certs__certdata__fetch"
|
||||
;;
|
||||
ca__certs__certdata,help)
|
||||
cmd="ca__certs__certdata__help"
|
||||
;;
|
||||
ca__certs__certdata,parse)
|
||||
cmd="ca__certs__certdata__parse"
|
||||
;;
|
||||
ca__certs__certdata,sync)
|
||||
cmd="ca__certs__certdata__sync"
|
||||
;;
|
||||
ca__certs__certdata__help,convert)
|
||||
cmd="ca__certs__certdata__help__convert"
|
||||
;;
|
||||
ca__certs__certdata__help,fetch)
|
||||
cmd="ca__certs__certdata__help__fetch"
|
||||
;;
|
||||
ca__certs__certdata__help,help)
|
||||
cmd="ca__certs__certdata__help__help"
|
||||
;;
|
||||
ca__certs__certdata__help,parse)
|
||||
cmd="ca__certs__certdata__help__parse"
|
||||
;;
|
||||
ca__certs__certdata__help,sync)
|
||||
cmd="ca__certs__certdata__help__sync"
|
||||
;;
|
||||
ca__certs__help,add)
|
||||
cmd="ca__certs__help__add"
|
||||
;;
|
||||
ca__certs__help,certdata)
|
||||
cmd="ca__certs__help__certdata"
|
||||
;;
|
||||
ca__certs__help,extract)
|
||||
cmd="ca__certs__help__extract"
|
||||
;;
|
||||
ca__certs__help,gen-artifacts)
|
||||
cmd="ca__certs__help__gen__artifacts"
|
||||
;;
|
||||
ca__certs__help,help)
|
||||
cmd="ca__certs__help__help"
|
||||
;;
|
||||
ca__certs__help__certdata,convert)
|
||||
cmd="ca__certs__help__certdata__convert"
|
||||
;;
|
||||
ca__certs__help__certdata,fetch)
|
||||
cmd="ca__certs__help__certdata__fetch"
|
||||
;;
|
||||
ca__certs__help__certdata,parse)
|
||||
cmd="ca__certs__help__certdata__parse"
|
||||
;;
|
||||
ca__certs__help__certdata,sync)
|
||||
cmd="ca__certs__help__certdata__sync"
|
||||
;;
|
||||
*)
|
||||
;;
|
||||
esac
|
||||
done
|
||||
|
||||
case "${cmd}" in
|
||||
ca__certs)
|
||||
opts="-h -V --help --version add extract certdata gen-artifacts help"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 1 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__add)
|
||||
opts="-n -o -h --name --force --no-extract --output --root --dry-run --help <CERT>"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 2 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
--name)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
-n)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--output)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
-o)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--root)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata)
|
||||
opts="-h --help fetch parse convert sync help"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 2 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__convert)
|
||||
opts="-o -h --root --output --force --no-extract --extract-output --dry-run --help [INPUT]"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
--root)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--output)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--extract-output)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
-o)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__fetch)
|
||||
opts="-o -h --url --log-url --output --force --no-revision-check --no-parse --dry-run --help"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
--url)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--log-url)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--output)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
-o)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__help)
|
||||
opts="fetch parse convert sync help"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__help__convert)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__help__fetch)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__help__help)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__help__parse)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__help__sync)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__parse)
|
||||
opts="-h --limit --help [INPUT]"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
--limit)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__certdata__sync)
|
||||
opts="-o -h --url --log-url --certdata-output --root --mozilla-output --force --no-revision-check --no-parse --no-extract --extract-output --dry-run --help"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
--url)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--log-url)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--certdata-output)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--root)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--mozilla-output)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--extract-output)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
-o)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__extract)
|
||||
opts="-o -h --output --root --dry-run --help"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 2 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
--output)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
-o)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--root)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__gen__artifacts)
|
||||
opts="-h --out-dir --shell --dry-run --help"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 2 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
--out-dir)
|
||||
COMPREPLY=($(compgen -f "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
--shell)
|
||||
COMPREPLY=($(compgen -W "bash fish zsh" -- "${cur}"))
|
||||
return 0
|
||||
;;
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help)
|
||||
opts="add extract certdata gen-artifacts help"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 2 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__add)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__certdata)
|
||||
opts="fetch parse convert sync"
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__certdata__convert)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__certdata__fetch)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__certdata__parse)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__certdata__sync)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 4 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__extract)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__gen__artifacts)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
ca__certs__help__help)
|
||||
opts=""
|
||||
if [[ ${cur} == -* || ${COMP_CWORD} -eq 3 ]] ; then
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
fi
|
||||
case "${prev}" in
|
||||
*)
|
||||
COMPREPLY=()
|
||||
;;
|
||||
esac
|
||||
COMPREPLY=( $(compgen -W "${opts}" -- "${cur}") )
|
||||
return 0
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
if [[ "${BASH_VERSINFO[0]}" -eq 4 && "${BASH_VERSINFO[1]}" -ge 4 || "${BASH_VERSINFO[0]}" -gt 4 ]]; then
|
||||
complete -F _ca-certs -o nosort -o bashdefault -o default ca-certs
|
||||
else
|
||||
complete -F _ca-certs -o bashdefault -o default ca-certs
|
||||
fi
|
||||
@@ -1,99 +0,0 @@
|
||||
# Print an optspec for argparse to handle cmd's options that are independent of any subcommand.
|
||||
function __fish_ca_certs_global_optspecs
|
||||
string join \n h/help V/version
|
||||
end
|
||||
|
||||
function __fish_ca_certs_needs_command
|
||||
# Figure out if the current invocation already has a command.
|
||||
set -l cmd (commandline -opc)
|
||||
set -e cmd[1]
|
||||
argparse -s (__fish_ca_certs_global_optspecs) -- $cmd 2>/dev/null
|
||||
or return
|
||||
if set -q argv[1]
|
||||
# Also print the command, so this can be used to figure out what it is.
|
||||
echo $argv[1]
|
||||
return 1
|
||||
end
|
||||
return 0
|
||||
end
|
||||
|
||||
function __fish_ca_certs_using_subcommand
|
||||
set -l cmd (__fish_ca_certs_needs_command)
|
||||
test -z "$cmd"
|
||||
and return 1
|
||||
contains -- $cmd[1] $argv
|
||||
end
|
||||
|
||||
complete -c ca-certs -n "__fish_ca_certs_needs_command" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_needs_command" -s V -l version -d 'Print version'
|
||||
complete -c ca-certs -n "__fish_ca_certs_needs_command" -f -a "add" -d 'Add a PEM CA certificate to trust-source/anchors and refresh extracted outputs'
|
||||
complete -c ca-certs -n "__fish_ca_certs_needs_command" -f -a "extract" -d 'Regenerate extracted trust bundles (like update-ca-trust extract)'
|
||||
complete -c ca-certs -n "__fish_ca_certs_needs_command" -f -a "certdata" -d 'Fetch and parse Mozilla/NSS certdata.txt (no certificate generation yet)'
|
||||
complete -c ca-certs -n "__fish_ca_certs_needs_command" -f -a "gen-artifacts"
|
||||
complete -c ca-certs -n "__fish_ca_certs_needs_command" -f -a "help" -d 'Print this message or the help of the given subcommand(s)'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand add" -s n -l name -d 'Output certificate name (without extension). Defaults to the input filename stem' -r
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand add" -s o -l output -d 'Extracted output directory inside the target root (default: /etc/ca-certificates/extracted)' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand add" -l root -d 'Target root filesystem (for chroot/image builds)' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand add" -l force -d 'Overwrite an existing anchor if contents differ'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand add" -l no-extract -d 'Add certificate but do not run extraction'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand add" -l dry-run -d 'Print actions without modifying files'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand add" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand extract" -s o -l output -d 'Extracted output directory inside the target root (default: /etc/ca-certificates/extracted)' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand extract" -l root -d 'Target root filesystem (for chroot/image builds)' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand extract" -l dry-run -d 'Print actions without modifying files'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand extract" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and not __fish_seen_subcommand_from fetch parse convert sync help" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and not __fish_seen_subcommand_from fetch parse convert sync help" -f -a "fetch" -d 'Fetch certdata.txt from an NSS source URL'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and not __fish_seen_subcommand_from fetch parse convert sync help" -f -a "parse" -d 'Parse a local certdata.txt file and print a summary'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and not __fish_seen_subcommand_from fetch parse convert sync help" -f -a "convert" -d 'Convert certdata.txt into a Mozilla p11-kit trust bundle and optionally extract outputs'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and not __fish_seen_subcommand_from fetch parse convert sync help" -f -a "sync" -d 'Run the full pipeline: fetch certdata.txt, convert to p11-kit source, then extract outputs'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and not __fish_seen_subcommand_from fetch parse convert sync help" -f -a "help" -d 'Print this message or the help of the given subcommand(s)'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from fetch" -l url -d 'Source URL for certdata.txt' -r
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from fetch" -l log-url -d 'Override log URL used to determine the latest revision (optional)' -r
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from fetch" -s o -l output -d 'Output file path' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from fetch" -l force -d 'Overwrite an existing file if contents differ'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from fetch" -l no-revision-check -d 'Always download even if the local file revision matches the remote revision'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from fetch" -l no-parse -d 'Skip parsing/summary after download'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from fetch" -l dry-run -d 'Print actions without modifying files'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from fetch" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from parse" -l limit -d 'Print up to N object summaries after the aggregate stats' -r
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from parse" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from convert" -l root -d 'Target root filesystem (for chroot/image builds)' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from convert" -l output -d 'Destination p11-kit trust source file inside the target root' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from convert" -s o -l extract-output -d 'Extracted output directory inside the target root (default: /etc/ca-certificates/extracted)' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from convert" -l force -d 'Overwrite an existing output file if contents differ'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from convert" -l no-extract -d 'Skip running trust extraction after writing the Mozilla source bundle'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from convert" -l dry-run -d 'Print actions without modifying files'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from convert" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l url -d 'Source URL for certdata.txt' -r
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l log-url -d 'Override log URL used to determine the latest revision (optional)' -r
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l certdata-output -d 'Local certdata.txt path used for fetch and convert' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l root -d 'Target root filesystem (for chroot/image builds)' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l mozilla-output -d 'Destination p11-kit trust source file inside the target root' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -s o -l extract-output -d 'Extracted output directory inside the target root (default: /etc/ca-certificates/extracted)' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l force -d 'Overwrite existing files if contents differ'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l no-revision-check -d 'Always download even if the local certdata revision matches the remote revision'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l no-parse -d 'Skip parsing/summary after download'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l no-extract -d 'Skip running trust extraction after writing the Mozilla source bundle'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -l dry-run -d 'Print actions without modifying files'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from sync" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from help" -f -a "fetch" -d 'Fetch certdata.txt from an NSS source URL'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from help" -f -a "parse" -d 'Parse a local certdata.txt file and print a summary'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from help" -f -a "convert" -d 'Convert certdata.txt into a Mozilla p11-kit trust bundle and optionally extract outputs'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from help" -f -a "sync" -d 'Run the full pipeline: fetch certdata.txt, convert to p11-kit source, then extract outputs'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand certdata; and __fish_seen_subcommand_from help" -f -a "help" -d 'Print this message or the help of the given subcommand(s)'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand gen-artifacts" -l out-dir -d 'Directory to write generated packaging artifacts into' -r -F
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand gen-artifacts" -l shell -d 'Shell completions to generate' -r -f -a "bash\t''
|
||||
fish\t''
|
||||
zsh\t''"
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand gen-artifacts" -l dry-run -d 'Print actions without modifying files'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand gen-artifacts" -s h -l help -d 'Print help'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and not __fish_seen_subcommand_from add extract certdata gen-artifacts help" -f -a "add" -d 'Add a PEM CA certificate to trust-source/anchors and refresh extracted outputs'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and not __fish_seen_subcommand_from add extract certdata gen-artifacts help" -f -a "extract" -d 'Regenerate extracted trust bundles (like update-ca-trust extract)'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and not __fish_seen_subcommand_from add extract certdata gen-artifacts help" -f -a "certdata" -d 'Fetch and parse Mozilla/NSS certdata.txt (no certificate generation yet)'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and not __fish_seen_subcommand_from add extract certdata gen-artifacts help" -f -a "gen-artifacts"
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and not __fish_seen_subcommand_from add extract certdata gen-artifacts help" -f -a "help" -d 'Print this message or the help of the given subcommand(s)'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and __fish_seen_subcommand_from certdata" -f -a "fetch" -d 'Fetch certdata.txt from an NSS source URL'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and __fish_seen_subcommand_from certdata" -f -a "parse" -d 'Parse a local certdata.txt file and print a summary'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and __fish_seen_subcommand_from certdata" -f -a "convert" -d 'Convert certdata.txt into a Mozilla p11-kit trust bundle and optionally extract outputs'
|
||||
complete -c ca-certs -n "__fish_ca_certs_using_subcommand help; and __fish_seen_subcommand_from certdata" -f -a "sync" -d 'Run the full pipeline: fetch certdata.txt, convert to p11-kit source, then extract outputs'
|
||||
+7
-29
@@ -14,15 +14,6 @@ tracked_rust_inputs = files(
|
||||
'src/main.rs',
|
||||
)
|
||||
|
||||
# Track packaging assets in one place so install rules stay auditable.
|
||||
tracked_packaging_assets = files(
|
||||
'LICENSE',
|
||||
'contrib/ca-certs.8',
|
||||
'contrib/completions/ca-certs.bash',
|
||||
'contrib/completions/ca-certs.fish',
|
||||
'contrib/completions/_ca-certs',
|
||||
)
|
||||
|
||||
tracked_install_paths = [
|
||||
join_paths(get_option('bindir'), 'ca-certs'),
|
||||
join_paths(get_option('datadir'), 'licenses', meson.project_name(), 'LICENSE'),
|
||||
@@ -54,31 +45,18 @@ ca_certs_bin = custom_target(
|
||||
install_dir: get_option('bindir'),
|
||||
)
|
||||
|
||||
install_data(
|
||||
'contrib/ca-certs.8',
|
||||
install_dir: join_paths(get_option('mandir'), 'man8'),
|
||||
)
|
||||
|
||||
install_data(
|
||||
'contrib/completions/ca-certs.bash',
|
||||
install_dir: join_paths(get_option('datadir'), 'bash-completion', 'completions'),
|
||||
rename: 'ca-certs',
|
||||
)
|
||||
|
||||
install_data(
|
||||
'contrib/completions/ca-certs.fish',
|
||||
install_dir: join_paths(get_option('datadir'), 'fish', 'vendor_completions.d'),
|
||||
)
|
||||
|
||||
install_data(
|
||||
'contrib/completions/_ca-certs',
|
||||
install_dir: join_paths(get_option('datadir'), 'zsh', 'site-functions'),
|
||||
meson.add_install_script(
|
||||
sh,
|
||||
files('scripts/install-generated-docs.sh'),
|
||||
ca_certs_bin_path,
|
||||
get_option('mandir'),
|
||||
get_option('datadir'),
|
||||
)
|
||||
|
||||
summary(
|
||||
{
|
||||
'tracked rust inputs': tracked_rust_inputs.length(),
|
||||
'tracked packaging assets': tracked_packaging_assets.length(),
|
||||
'generated docs on install': true,
|
||||
'tracked install paths': '\n ' + '\n '.join(tracked_install_paths),
|
||||
},
|
||||
section: 'Packaging',
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
#!/bin/sh
|
||||
set -eu
|
||||
|
||||
bin="$1"
|
||||
mandir_opt="$2"
|
||||
datadir_opt="$3"
|
||||
|
||||
resolve_dir() {
|
||||
case "$1" in
|
||||
/*) printf '%s%s\n' "${DESTDIR:-}" "$1" ;;
|
||||
*) printf '%s/%s\n' "${MESON_INSTALL_DESTDIR_PREFIX:?}" "$1" ;;
|
||||
esac
|
||||
}
|
||||
|
||||
man_root="$(resolve_dir "$mandir_opt")"
|
||||
data_root="$(resolve_dir "$datadir_opt")"
|
||||
tmp_dir="$(mktemp -d "${TMPDIR:-/tmp}/ca-certs-docs.XXXXXX")"
|
||||
|
||||
cleanup() {
|
||||
rm -rf "$tmp_dir"
|
||||
}
|
||||
trap cleanup EXIT INT TERM
|
||||
|
||||
"$bin" gen-artifacts --out-dir "$tmp_dir"
|
||||
|
||||
install -Dm644 "$tmp_dir/ca-certs.8" \
|
||||
"$man_root/man8/ca-certs.8"
|
||||
install -Dm644 "$tmp_dir/completions/ca-certs.bash" \
|
||||
"$data_root/bash-completion/completions/ca-certs"
|
||||
install -Dm644 "$tmp_dir/completions/ca-certs.fish" \
|
||||
"$data_root/fish/vendor_completions.d/ca-certs.fish"
|
||||
install -Dm644 "$tmp_dir/completions/_ca-certs" \
|
||||
"$data_root/zsh/site-functions/_ca-certs"
|
||||
+491
-15
@@ -9,19 +9,84 @@ use std::io::Write;
|
||||
use std::os::unix::fs::{PermissionsExt, symlink};
|
||||
use std::path::{Path, PathBuf};
|
||||
use std::process::{Command, Stdio};
|
||||
use std::time::{SystemTime, UNIX_EPOCH};
|
||||
|
||||
// Default paths mirror the p11-kit / update-ca-trust layout used by this system.
|
||||
const DEFAULT_ROOT: &str = "/";
|
||||
const DEFAULT_ANCHORS_DIR: &str = "/etc/ca-certificates/trust-source/anchors";
|
||||
const DEFAULT_EXTRACTED_DIR: &str = "/etc/ca-certificates/extracted";
|
||||
const DEFAULT_SSL_CERTS_DIR: &str = "/etc/ssl/certs";
|
||||
const DEFAULT_SSL_CERT_PEM_LINK: &str = "/etc/ssl/cert.pem";
|
||||
const DEFAULT_SSL_CA_CERTIFICATES_BUNDLE_LINK: &str = "/etc/ssl/certs/ca-certificates.crt";
|
||||
const DEFAULT_SSL_CA_BUNDLE_CRT_LINK: &str = "/etc/ssl/certs/ca-bundle.crt";
|
||||
const DEFAULT_JAVA_CACERTS_LINK: &str = "/etc/ssl/certs/java/cacerts";
|
||||
// BLFS make-ca compatibility paths (commonly used by OpenSSL/libgit2 builds on LFS).
|
||||
const DEFAULT_PKI_TLS_CA_BUNDLE_CRT_LINK: &str = "/etc/pki/tls/certs/ca-bundle.crt";
|
||||
const DEFAULT_PKI_TLS_CA_BUNDLE_TRUST_CRT_LINK: &str = "/etc/pki/tls/certs/ca-bundle.trust.crt";
|
||||
const DEFAULT_PKI_TLS_JAVA_CACERTS_LINK: &str = "/etc/pki/tls/java/cacerts";
|
||||
const DEFAULT_CERTDATA_URL: &str =
|
||||
"https://hg.mozilla.org/projects/nss/raw-file/tip/lib/ckfw/builtins/certdata.txt";
|
||||
const DEFAULT_CERTDATA_OUTPUT: &str = "certdata.txt";
|
||||
const DEFAULT_MOZILLA_TRUST_P11KIT: &str =
|
||||
"/usr/share/ca-certificates/trust-source/mozilla.trust.p11-kit";
|
||||
const DEFAULT_PKI_MOZILLA_TRUST_P11KIT: &str = "/etc/pki/anchors/mozilla.trust.p11-kit";
|
||||
// make-ca uses a pinned ISRG Root X1 to bootstrap downloads from hg.mozilla.org
|
||||
// before the local trust store exists. We do the same for certdata fetch/sync.
|
||||
const MOZILLA_HG_BOOTSTRAP_ROOT_PEM: &str = r#"-----BEGIN CERTIFICATE-----
|
||||
MIIFazCCA1OgAwIBAgIRAIIQz7DSQONZRGPgu2OCiwAwDQYJKoZIhvcNAQELBQAw
|
||||
TzELMAkGA1UEBhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2Vh
|
||||
cmNoIEdyb3VwMRUwEwYDVQQDEwxJU1JHIFJvb3QgWDEwHhcNMTUwNjA0MTEwNDM4
|
||||
WhcNMzUwNjA0MTEwNDM4WjBPMQswCQYDVQQGEwJVUzEpMCcGA1UEChMgSW50ZXJu
|
||||
ZXQgU2VjdXJpdHkgUmVzZWFyY2ggR3JvdXAxFTATBgNVBAMTDElTUkcgUm9vdCBY
|
||||
MTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAK3oJHP0FDfzm54rVygc
|
||||
h77ct984kIxuPOZXoHj3dcKi/vVqbvYATyjb3miGbESTtrFj/RQSa78f0uoxmyF+
|
||||
0TM8ukj13Xnfs7j/EvEhmkvBioZxaUpmZmyPfjxwv60pIgbz5MDmgK7iS4+3mX6U
|
||||
A5/TR5d8mUgjU+g4rk8Kb4Mu0UlXjIB0ttov0DiNewNwIRt18jA8+o+u3dpjq+sW
|
||||
T8KOEUt+zwvo/7V3LvSye0rgTBIlDHCNAymg4VMk7BPZ7hm/ELNKjD+Jo2FR3qyH
|
||||
B5T0Y3HsLuJvW5iB4YlcNHlsdu87kGJ55tukmi8mxdAQ4Q7e2RCOFvu396j3x+UC
|
||||
B5iPNgiV5+I3lg02dZ77DnKxHZu8A/lJBdiB3QW0KtZB6awBdpUKD9jf1b0SHzUv
|
||||
KBds0pjBqAlkd25HN7rOrFleaJ1/ctaJxQZBKT5ZPt0m9STJEadao0xAH0ahmbWn
|
||||
OlFuhjuefXKnEgV4We0+UXgVCwOPjdAvBbI+e0ocS3MFEvzG6uBQE3xDk3SzynTn
|
||||
jh8BCNAw1FtxNrQHusEwMFxIt4I7mKZ9YIqioymCzLq9gwQbooMDQaHWBfEbwrbw
|
||||
qHyGO0aoSCqI3Haadr8faqU9GY/rOPNk3sgrDQoo//fb4hVC1CLQJ13hef4Y53CI
|
||||
rU7m2Ys6xt0nUW7/vGT1M0NPAgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNV
|
||||
HRMBAf8EBTADAQH/MB0GA1UdDgQWBBR5tFnme7bl5AFzgAiIyBpY9umbbjANBgkq
|
||||
hkiG9w0BAQsFAAOCAgEAVR9YqbyyqFDQDLHYGmkgJykIrGF1XIpu+ILlaS/V9lZL
|
||||
ubhzEFnTIZd+50xx+7LSYK05qAvqFyFWhfFQDlnrzuBZ6brJFe+GnY+EgPbk6ZGQ
|
||||
3BebYhtF8GaV0nxvwuo77x/Py9auJ/GpsMiu/X1+mvoiBOv/2X/qkSsisRcOj/KK
|
||||
NFtY2PwByVS5uCbMiogziUwthDyC3+6WVwW6LLv3xLfHTjuCvjHIInNzktHCgKQ5
|
||||
ORAzI4JMPJ+GslWYHb4phowim57iaztXOoJwTdwJx4nLCgdNbOhdjsnvzqvHu7Ur
|
||||
TkXWStAmzOVyyghqpZXjFaH3pO3JLF+l+/+sKAIuvtd7u+Nxe5AW0wdeRlN8NwdC
|
||||
jNPElpzVmbUq4JUagEiuTDkHzsxHpFKVK7q4+63SM1N95R1NbdWhscdCb+ZAJzVc
|
||||
oyi3B43njTOQ5yOf+1CceWxG1bQVs5ZufpsMljq4Ui0/1lvh+wjChP4kqKOJ2qxq
|
||||
4RgqsahDYVvTH9w7jXbyLeiNdd8XM2w9U/t7y0Ff/9yi0GE44Za4rF2LN9d11TPA
|
||||
mRGunUHBcnWEvgJBQl9nJEiU0Zsnvgc/ubhPgXRR4Xq37Z0j4r7g1SgEEzwxA57d
|
||||
emyPxgcYxn/eR44/KJ4EBs+lVDR3veyJm+kXQ99b21/+jh5Xos1AnX5iItreGCc=
|
||||
-----END CERTIFICATE-----
|
||||
"#;
|
||||
const MOZILLA_HG_BOOTSTRAP_DIGICERT_G2_ROOT_PEM: &str = r#"-----BEGIN CERTIFICATE-----
|
||||
MIIDjjCCAnagAwIBAgIQAzrx5qcRqaC7KGSxHQn65TANBgkqhkiG9w0BAQsFADBh
|
||||
MQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3
|
||||
d3cuZGlnaWNlcnQuY29tMSAwHgYDVQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBH
|
||||
MjAeFw0xMzA4MDExMjAwMDBaFw0zODAxMTUxMjAwMDBaMGExCzAJBgNVBAYTAlVT
|
||||
MRUwEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5j
|
||||
b20xIDAeBgNVBAMTF0RpZ2lDZXJ0IEdsb2JhbCBSb290IEcyMIIBIjANBgkqhkiG
|
||||
9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuzfNNNx7a8myaJCtSnX/RrohCgiN9RlUyfuI
|
||||
2/Ou8jqJkTx65qsGGmvPrC3oXgkkRLpimn7Wo6h+4FR1IAWsULecYxpsMNzaHxmx
|
||||
1x7e/dfgy5SDN67sH0NO3Xss0r0upS/kqbitOtSZpLYl6ZtrAGCSYP9PIUkY92eQ
|
||||
q2EGnI/yuum06ZIya7XzV+hdG82MHauVBJVJ8zUtluNJbd134/tJS7SsVQepj5Wz
|
||||
tCO7TG1F8PapspUwtP1MVYwnSlcUfIKdzXOS0xZKBgyMUNGPHgm+F6HmIcr9g+UQ
|
||||
vIOlCsRnKPZzFBQ9RnbDhxSJITRNrw9FDKZJobq7nMWxM4MphQIDAQABo0IwQDAP
|
||||
BgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBhjAdBgNVHQ4EFgQUTiJUIBiV
|
||||
5uNu5g/6+rkS7QYXjzkwDQYJKoZIhvcNAQELBQADggEBAGBnKJRvDkhj6zHd6mcY
|
||||
1Yl9PMWLSn/pvtsrF9+wX3N3KjITOYFnQoQj8kVnNeyIv/iPsGEMNKSuIEyExtv4
|
||||
NeF22d+mQrvHRAiGfzZ0JFrabA0UWTW98kndth/Jsw1HKj2ZL7tcu7XUIOGZX1NG
|
||||
Fdtom/DzMNU+MeKNhJ7jitralj41E6Vf8PlwUHBHQRFXGU7Aj64GxJUTFy8bJZ91
|
||||
8rGOmaFvE7FBcf6IKshPECBV1/MUReXgRPTqh5Uykw7+U0b6LJ3/iyK5S9kJRaTe
|
||||
pLiaWN0bfVKfjllDiIGknibVb63dDcY3fe0Dkhvld1927jyNxF1WW6LZZm6zNTfl
|
||||
MrY=
|
||||
-----END CERTIFICATE-----
|
||||
"#;
|
||||
|
||||
// Top-level CLI entrypoint with `add` and `extract` subcommands.
|
||||
#[derive(Parser, Debug)]
|
||||
@@ -194,9 +259,10 @@ struct CertdataSyncArgs {
|
||||
#[arg(long)]
|
||||
log_url: Option<String>,
|
||||
|
||||
/// Local certdata.txt path used for fetch and convert
|
||||
#[arg(long, default_value = DEFAULT_CERTDATA_OUTPUT)]
|
||||
certdata_output: PathBuf,
|
||||
/// Local certdata.txt path used for fetch and convert.
|
||||
/// Defaults to a temporary `/tmp/.../certdata.txt` path that is cleaned up.
|
||||
#[arg(long)]
|
||||
certdata_output: Option<PathBuf>,
|
||||
|
||||
/// Target root filesystem (for chroot/image builds)
|
||||
#[arg(long, default_value = DEFAULT_ROOT)]
|
||||
@@ -263,6 +329,24 @@ struct ExtractJob {
|
||||
relative_dest: &'static str,
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
struct TempWorkspaceCleanup {
|
||||
path: PathBuf,
|
||||
}
|
||||
|
||||
impl Drop for TempWorkspaceCleanup {
|
||||
fn drop(&mut self) {
|
||||
if let Err(err) = fs::remove_dir_all(&self.path) {
|
||||
if err.kind() != std::io::ErrorKind::NotFound {
|
||||
eprintln!(
|
||||
"warning: failed to remove temporary directory {}: {err}",
|
||||
self.path.display()
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Output set mirrors `/bin/update-ca-trust extract`.
|
||||
const EXTRACT_JOBS: &[ExtractJob] = &[
|
||||
ExtractJob {
|
||||
@@ -308,10 +392,10 @@ const EXTRACT_JOBS: &[ExtractJob] = &[
|
||||
relative_dest: "java-cacerts.jks",
|
||||
},
|
||||
ExtractJob {
|
||||
format: "pem-directory-hash",
|
||||
format: "openssl-directory",
|
||||
filter: "ca-anchors",
|
||||
purpose: Some("server-auth"),
|
||||
comment: false,
|
||||
purpose: None,
|
||||
comment: true,
|
||||
relative_dest: "cadir",
|
||||
},
|
||||
];
|
||||
@@ -399,11 +483,14 @@ fn run_certdata(command: CertdataCommands) -> Result<()> {
|
||||
}
|
||||
|
||||
fn run_certdata_sync(args: CertdataSyncArgs) -> Result<()> {
|
||||
let (certdata_output, _temp_workspace_guard) =
|
||||
resolve_sync_certdata_output(args.certdata_output, args.dry_run)?;
|
||||
|
||||
// Reuse the existing subcommand implementations so behavior stays aligned.
|
||||
run_certdata_fetch(CertdataFetchArgs {
|
||||
url: args.url,
|
||||
log_url: args.log_url,
|
||||
output: args.certdata_output.clone(),
|
||||
output: certdata_output.clone(),
|
||||
force: args.force,
|
||||
no_revision_check: args.no_revision_check,
|
||||
parse: args.parse,
|
||||
@@ -411,7 +498,7 @@ fn run_certdata_sync(args: CertdataSyncArgs) -> Result<()> {
|
||||
})?;
|
||||
|
||||
run_certdata_convert(CertdataConvertArgs {
|
||||
input: args.certdata_output,
|
||||
input: certdata_output,
|
||||
root: args.root,
|
||||
output: args.mozilla_output,
|
||||
force: args.force,
|
||||
@@ -421,6 +508,60 @@ fn run_certdata_sync(args: CertdataSyncArgs) -> Result<()> {
|
||||
})
|
||||
}
|
||||
|
||||
fn resolve_sync_certdata_output(
|
||||
requested: Option<PathBuf>,
|
||||
dry_run: bool,
|
||||
) -> Result<(PathBuf, Option<TempWorkspaceCleanup>)> {
|
||||
if let Some(path) = requested {
|
||||
return Ok((path, None));
|
||||
}
|
||||
|
||||
if dry_run {
|
||||
return Ok((build_sync_tmp_workspace_path(0).join(DEFAULT_CERTDATA_OUTPUT), None));
|
||||
}
|
||||
|
||||
let workspace = create_sync_tmp_workspace_dir()?;
|
||||
println!("Using temporary certdata workspace: {}", workspace.display());
|
||||
Ok((
|
||||
workspace.join(DEFAULT_CERTDATA_OUTPUT),
|
||||
Some(TempWorkspaceCleanup { path: workspace }),
|
||||
))
|
||||
}
|
||||
|
||||
fn create_sync_tmp_workspace_dir() -> Result<PathBuf> {
|
||||
let tmp_root = Path::new("/tmp");
|
||||
for attempt in 0..32_u32 {
|
||||
let candidate = build_sync_tmp_workspace_path(attempt);
|
||||
match fs::create_dir(&candidate) {
|
||||
Ok(()) => return Ok(candidate),
|
||||
Err(err) if err.kind() == std::io::ErrorKind::AlreadyExists => continue,
|
||||
Err(err) => {
|
||||
return Err(err).with_context(|| {
|
||||
format!(
|
||||
"failed to create temporary certdata directory {}",
|
||||
candidate.display()
|
||||
)
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
bail!(
|
||||
"failed to create a unique temporary certdata directory under {}",
|
||||
tmp_root.display()
|
||||
);
|
||||
}
|
||||
|
||||
fn build_sync_tmp_workspace_path(attempt: u32) -> PathBuf {
|
||||
let nonce = SystemTime::now()
|
||||
.duration_since(UNIX_EPOCH)
|
||||
.unwrap_or_default()
|
||||
.as_nanos();
|
||||
Path::new("/tmp").join(format!(
|
||||
"ca-certs-certdata-{}-{nonce:032x}-{attempt:02x}",
|
||||
std::process::id()
|
||||
))
|
||||
}
|
||||
|
||||
fn run_gen_artifacts(args: GenArtifactsArgs) -> Result<()> {
|
||||
let man_path = args.out_dir.join("ca-certs.8");
|
||||
let completions_dir = args.out_dir.join("completions");
|
||||
@@ -563,9 +704,7 @@ fn run_certdata_fetch(args: CertdataFetchArgs) -> Result<()> {
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
let client = reqwest::blocking::Client::builder()
|
||||
.build()
|
||||
.context("failed to build HTTP client")?;
|
||||
let client = build_http_client().context("failed to build HTTP client")?;
|
||||
let existing_revision = read_certdata_revision_from_path(&args.output)
|
||||
.ok()
|
||||
.flatten();
|
||||
@@ -613,15 +752,217 @@ fn run_certdata_fetch(args: CertdataFetchArgs) -> Result<()> {
|
||||
}
|
||||
|
||||
fn http_get_text(client: &reqwest::blocking::Client, url: &str) -> Result<String> {
|
||||
let response = client
|
||||
.get(url)
|
||||
.send()
|
||||
.with_context(|| format!("failed to request {url}"))?
|
||||
let response = match client.get(url).send() {
|
||||
Ok(response) => response,
|
||||
Err(err) if is_mozilla_hg_url(url) => {
|
||||
println!("reqwest fetch failed for Mozilla hg URL; retrying via openssl.");
|
||||
return openssl_https_get_text(url);
|
||||
}
|
||||
Err(err) => return Err(err).with_context(|| format!("failed to request {url}")),
|
||||
}
|
||||
.error_for_status()
|
||||
.with_context(|| format!("server returned an error for {url}"))?;
|
||||
response.text().context("failed to read response body")
|
||||
}
|
||||
|
||||
fn is_mozilla_hg_url(url: &str) -> bool {
|
||||
reqwest::Url::parse(url)
|
||||
.ok()
|
||||
.and_then(|parsed| parsed.host_str().map(str::to_ascii_lowercase))
|
||||
.map(|host| host == "hg.mozilla.org" || host == "hg-edge.mozilla.org")
|
||||
.unwrap_or(false)
|
||||
}
|
||||
|
||||
fn openssl_https_get_text(url: &str) -> Result<String> {
|
||||
let parsed = reqwest::Url::parse(url).with_context(|| format!("invalid URL: {url}"))?;
|
||||
if parsed.scheme() != "https" {
|
||||
bail!("openssl fallback only supports https URLs: {url}");
|
||||
}
|
||||
|
||||
let host = parsed.host_str().context("URL missing host")?;
|
||||
let port = parsed.port_or_known_default().context("URL missing port")?;
|
||||
let mut path = parsed.path().to_string();
|
||||
if path.is_empty() {
|
||||
path.push('/');
|
||||
}
|
||||
if let Some(query) = parsed.query() {
|
||||
path.push('?');
|
||||
path.push_str(query);
|
||||
}
|
||||
let host_header = match parsed.port() {
|
||||
Some(p) if p != 443 => format!("{host}:{p}"),
|
||||
_ => host.to_string(),
|
||||
};
|
||||
|
||||
let bootstrap_ca_path = write_bootstrap_ca_tempfile()?;
|
||||
let result = (|| {
|
||||
let mut cmd = Command::new("openssl");
|
||||
cmd.args([
|
||||
"s_client",
|
||||
"-quiet",
|
||||
"-verify_return_error",
|
||||
"-verifyCAfile",
|
||||
bootstrap_ca_path.to_str().unwrap_or(""),
|
||||
"-connect",
|
||||
&format!("{host}:{port}"),
|
||||
"-servername",
|
||||
host,
|
||||
]);
|
||||
if Path::new(DEFAULT_SSL_CERTS_DIR).is_dir() {
|
||||
cmd.args(["-verifyCApath", DEFAULT_SSL_CERTS_DIR]);
|
||||
}
|
||||
cmd.stdin(Stdio::piped())
|
||||
.stdout(Stdio::piped())
|
||||
.stderr(Stdio::piped());
|
||||
|
||||
let mut child = cmd.spawn().context("failed to spawn `openssl s_client`")?;
|
||||
{
|
||||
let stdin = child
|
||||
.stdin
|
||||
.as_mut()
|
||||
.context("failed to open openssl stdin")?;
|
||||
write!(
|
||||
stdin,
|
||||
"GET {path} HTTP/1.1\r\nHost: {host_header}\r\nConnection: close\r\n\r\n"
|
||||
)
|
||||
.context("failed to write HTTP request to openssl stdin")?;
|
||||
}
|
||||
|
||||
let output = child
|
||||
.wait_with_output()
|
||||
.context("failed to wait for `openssl s_client`")?;
|
||||
if !output.status.success() {
|
||||
bail!(
|
||||
"openssl s_client failed: {}",
|
||||
String::from_utf8_lossy(&output.stderr).trim()
|
||||
);
|
||||
}
|
||||
parse_http_response_text(&output.stdout)
|
||||
.with_context(|| format!("failed to parse HTTP response from openssl for {url}"))
|
||||
})();
|
||||
|
||||
let _ = fs::remove_file(&bootstrap_ca_path);
|
||||
result
|
||||
}
|
||||
|
||||
fn write_bootstrap_ca_tempfile() -> Result<PathBuf> {
|
||||
let nonce = SystemTime::now()
|
||||
.duration_since(UNIX_EPOCH)
|
||||
.unwrap_or_default()
|
||||
.as_nanos();
|
||||
let path = std::env::temp_dir().join(format!(
|
||||
"ca-certs-hg-bootstrap-{}-{nonce}.pem",
|
||||
std::process::id()
|
||||
));
|
||||
let bundle = format!(
|
||||
"{}{}",
|
||||
MOZILLA_HG_BOOTSTRAP_ROOT_PEM, MOZILLA_HG_BOOTSTRAP_DIGICERT_G2_ROOT_PEM
|
||||
);
|
||||
fs::write(&path, bundle)
|
||||
.with_context(|| format!("failed to write {}", path.display()))?;
|
||||
#[cfg(unix)]
|
||||
{
|
||||
fs::set_permissions(&path, fs::Permissions::from_mode(0o600))
|
||||
.with_context(|| format!("failed to set permissions on {}", path.display()))?;
|
||||
}
|
||||
Ok(path)
|
||||
}
|
||||
|
||||
fn parse_http_response_text(raw: &[u8]) -> Result<String> {
|
||||
let (header_bytes, body_bytes) = split_http_response(raw)?;
|
||||
let header_text = String::from_utf8_lossy(header_bytes);
|
||||
let mut header_lines = header_text.lines();
|
||||
|
||||
let status_line = header_lines.next().context("missing HTTP status line")?;
|
||||
let status_code = status_line
|
||||
.split_whitespace()
|
||||
.nth(1)
|
||||
.context("missing HTTP status code")?
|
||||
.parse::<u16>()
|
||||
.context("invalid HTTP status code")?;
|
||||
if !(200..300).contains(&status_code) {
|
||||
bail!("HTTP request failed with status {status_code}");
|
||||
}
|
||||
|
||||
let chunked = header_lines.any(|line| {
|
||||
line.split_once(':')
|
||||
.map(|(name, value)| {
|
||||
name.eq_ignore_ascii_case("transfer-encoding")
|
||||
&& value.to_ascii_lowercase().contains("chunked")
|
||||
})
|
||||
.unwrap_or(false)
|
||||
});
|
||||
|
||||
let body = if chunked {
|
||||
decode_http_chunked_body(body_bytes)?
|
||||
} else {
|
||||
body_bytes.to_vec()
|
||||
};
|
||||
String::from_utf8(body).context("HTTP response body was not UTF-8")
|
||||
}
|
||||
|
||||
fn split_http_response(raw: &[u8]) -> Result<(&[u8], &[u8])> {
|
||||
if let Some(idx) = raw.windows(4).position(|w| w == b"\r\n\r\n") {
|
||||
return Ok((&raw[..idx], &raw[idx + 4..]));
|
||||
}
|
||||
if let Some(idx) = raw.windows(2).position(|w| w == b"\n\n") {
|
||||
return Ok((&raw[..idx], &raw[idx + 2..]));
|
||||
}
|
||||
bail!("HTTP response missing header/body separator")
|
||||
}
|
||||
|
||||
fn decode_http_chunked_body(mut input: &[u8]) -> Result<Vec<u8>> {
|
||||
let mut out = Vec::new();
|
||||
loop {
|
||||
let (line, rest) = take_http_line(input).context("truncated chunk header")?;
|
||||
let size_hex = line.split(';').next().unwrap_or("").trim();
|
||||
let size = usize::from_str_radix(size_hex, 16)
|
||||
.with_context(|| format!("invalid chunk size `{size_hex}`"))?;
|
||||
input = rest;
|
||||
if size == 0 {
|
||||
break;
|
||||
}
|
||||
if input.len() < size {
|
||||
bail!("truncated chunk body");
|
||||
}
|
||||
out.extend_from_slice(&input[..size]);
|
||||
input = &input[size..];
|
||||
if input.starts_with(b"\r\n") {
|
||||
input = &input[2..];
|
||||
} else if input.starts_with(b"\n") {
|
||||
input = &input[1..];
|
||||
} else {
|
||||
bail!("missing chunk terminator");
|
||||
}
|
||||
}
|
||||
Ok(out)
|
||||
}
|
||||
|
||||
fn take_http_line(input: &[u8]) -> Option<(String, &[u8])> {
|
||||
if let Some(idx) = input.windows(2).position(|w| w == b"\r\n") {
|
||||
let line = String::from_utf8(input[..idx].to_vec()).ok()?;
|
||||
return Some((line, &input[idx + 2..]));
|
||||
}
|
||||
if let Some(idx) = input.iter().position(|b| *b == b'\n') {
|
||||
let line = String::from_utf8(input[..idx].to_vec()).ok()?;
|
||||
return Some((line, &input[idx + 1..]));
|
||||
}
|
||||
None
|
||||
}
|
||||
|
||||
fn build_http_client() -> Result<reqwest::blocking::Client> {
|
||||
let bootstrap_ca = reqwest::Certificate::from_pem(MOZILLA_HG_BOOTSTRAP_ROOT_PEM.as_bytes())
|
||||
.context("failed to parse bundled Mozilla hg bootstrap root certificate")?;
|
||||
let digicert_g2_ca =
|
||||
reqwest::Certificate::from_pem(MOZILLA_HG_BOOTSTRAP_DIGICERT_G2_ROOT_PEM.as_bytes())
|
||||
.context("failed to parse bundled DigiCert Global Root G2 bootstrap certificate")?;
|
||||
reqwest::blocking::Client::builder()
|
||||
.add_root_certificate(bootstrap_ca)
|
||||
.add_root_certificate(digicert_g2_ca)
|
||||
.build()
|
||||
.context("failed to construct reqwest client")
|
||||
}
|
||||
|
||||
fn derive_hg_log_url(raw_url: &str) -> Option<String> {
|
||||
if raw_url.contains("/raw-file/") {
|
||||
Some(raw_url.replacen("/raw-file/", "/log/", 1))
|
||||
@@ -759,10 +1100,17 @@ fn run_certdata_convert(args: CertdataConvertArgs) -> Result<()> {
|
||||
);
|
||||
}
|
||||
println!("[dry-run] Would write {}", output_host.display());
|
||||
if should_write_make_ca_mirror(&args.root, &output_target) {
|
||||
println!(
|
||||
"[dry-run] Would also write BLFS make-ca compatibility source {}",
|
||||
path_in_root(&args.root, Path::new(DEFAULT_PKI_MOZILLA_TRUST_P11KIT)).display()
|
||||
);
|
||||
}
|
||||
} else {
|
||||
let parsed = parsed.context("certdata parse result missing")?;
|
||||
let p11kit = convert_certdata_to_p11kit_bundle(&parsed)?;
|
||||
install_file(&output_host, p11kit.as_bytes(), args.force, false)?;
|
||||
maybe_install_make_ca_mozilla_mirror(&args.root, &output_target, &p11kit, args.force)?;
|
||||
}
|
||||
|
||||
if args.no_extract {
|
||||
@@ -774,10 +1122,57 @@ fn run_certdata_convert(args: CertdataConvertArgs) -> Result<()> {
|
||||
.extract_output
|
||||
.unwrap_or_else(|| PathBuf::from(DEFAULT_EXTRACTED_DIR));
|
||||
extract_trust(&args.root, &extract_output, args.dry_run)?;
|
||||
if !args.dry_run {
|
||||
ensure_nonempty_extraction_outputs(&args.root, &extract_output)?;
|
||||
}
|
||||
println!("certdata conversion and extraction complete.");
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn should_write_make_ca_mirror(root: &Path, output_target: &Path) -> bool {
|
||||
output_target == Path::new(DEFAULT_MOZILLA_TRUST_P11KIT)
|
||||
&& path_in_root(root, Path::new("/etc/pki")).exists()
|
||||
}
|
||||
|
||||
fn maybe_install_make_ca_mozilla_mirror(
|
||||
root: &Path,
|
||||
output_target: &Path,
|
||||
p11kit: &str,
|
||||
force: bool,
|
||||
) -> Result<()> {
|
||||
if !should_write_make_ca_mirror(root, output_target) {
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
let mirror_host = path_in_root(root, Path::new(DEFAULT_PKI_MOZILLA_TRUST_P11KIT));
|
||||
println!(
|
||||
"Installing BLFS make-ca compatibility trust source: {}",
|
||||
mirror_host.display()
|
||||
);
|
||||
install_file(&mirror_host, p11kit.as_bytes(), force, false)
|
||||
}
|
||||
|
||||
fn ensure_nonempty_extraction_outputs(root: &Path, extract_output: &Path) -> Result<()> {
|
||||
let tls_bundle = path_in_root(root, &extract_output.join("tls-ca-bundle.pem"));
|
||||
let trust_bundle = path_in_root(root, &extract_output.join("ca-bundle.trust.crt"));
|
||||
let cadir = path_in_root(root, &extract_output.join("cadir"));
|
||||
|
||||
let tls_size = fs::metadata(&tls_bundle).map(|m| m.len()).unwrap_or(0);
|
||||
let trust_size = fs::metadata(&trust_bundle).map(|m| m.len()).unwrap_or(0);
|
||||
let cadir_count = fs::read_dir(&cadir).map(|it| it.count()).unwrap_or(0);
|
||||
|
||||
if tls_size == 0 || trust_size == 0 || cadir_count == 0 {
|
||||
bail!(
|
||||
"trust extract produced empty outputs (tls-ca-bundle.pem={} bytes, ca-bundle.trust.crt={} bytes, cadir entries={}); p11-kit may be reading a different trust source layout (e.g. BLFS make-ca uses /etc/pki/anchors)",
|
||||
tls_size,
|
||||
trust_size,
|
||||
cadir_count
|
||||
);
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn count_cert_and_trust_objects(doc: &CertDataDocument) -> (usize, usize) {
|
||||
let mut certs = 0usize;
|
||||
let mut trusts = 0usize;
|
||||
@@ -1439,10 +1834,18 @@ fn run_trust_extract_job(
|
||||
|
||||
fn sync_system_ssl_symlinks(root: &Path, extracted_target: &Path, dry_run: bool) -> Result<()> {
|
||||
let ssl_certs_host = path_in_root(root, Path::new(DEFAULT_SSL_CERTS_DIR));
|
||||
let cert_pem_link_host = path_in_root(root, Path::new(DEFAULT_SSL_CERT_PEM_LINK));
|
||||
let ca_bundle_link_host =
|
||||
path_in_root(root, Path::new(DEFAULT_SSL_CA_CERTIFICATES_BUNDLE_LINK));
|
||||
let ca_bundle_crt_link_host = path_in_root(root, Path::new(DEFAULT_SSL_CA_BUNDLE_CRT_LINK));
|
||||
let java_link_host = path_in_root(root, Path::new(DEFAULT_JAVA_CACERTS_LINK));
|
||||
let pki_ca_bundle_crt_link_host =
|
||||
path_in_root(root, Path::new(DEFAULT_PKI_TLS_CA_BUNDLE_CRT_LINK));
|
||||
let pki_ca_bundle_trust_crt_link_host =
|
||||
path_in_root(root, Path::new(DEFAULT_PKI_TLS_CA_BUNDLE_TRUST_CRT_LINK));
|
||||
let pki_java_link_host = path_in_root(root, Path::new(DEFAULT_PKI_TLS_JAVA_CACERTS_LINK));
|
||||
let tls_bundle_src_host = path_in_root(root, &extracted_target.join("tls-ca-bundle.pem"));
|
||||
let trust_bundle_src_host = path_in_root(root, &extracted_target.join("ca-bundle.trust.crt"));
|
||||
let cadir_host = path_in_root(root, &extracted_target.join("cadir"));
|
||||
let java_src_host = path_in_root(root, &extracted_target.join("java-cacerts.jks"));
|
||||
|
||||
@@ -1459,16 +1862,41 @@ fn sync_system_ssl_symlinks(root: &Path, extracted_target: &Path, dry_run: bool)
|
||||
"[dry-run] Would delete broken symlinks in {}",
|
||||
ssl_certs_host.display()
|
||||
);
|
||||
println!(
|
||||
"[dry-run] Would link {} -> {}",
|
||||
cert_pem_link_host.display(),
|
||||
tls_bundle_src_host.display()
|
||||
);
|
||||
println!(
|
||||
"[dry-run] Would link {} -> {}",
|
||||
ca_bundle_link_host.display(),
|
||||
tls_bundle_src_host.display()
|
||||
);
|
||||
println!(
|
||||
"[dry-run] Would link {} -> {}",
|
||||
ca_bundle_crt_link_host.display(),
|
||||
tls_bundle_src_host.display()
|
||||
);
|
||||
println!(
|
||||
"[dry-run] Would link {} -> {}",
|
||||
java_link_host.display(),
|
||||
java_src_host.display()
|
||||
);
|
||||
println!(
|
||||
"[dry-run] Would link {} -> {}",
|
||||
pki_ca_bundle_crt_link_host.display(),
|
||||
tls_bundle_src_host.display()
|
||||
);
|
||||
println!(
|
||||
"[dry-run] Would link {} -> {}",
|
||||
pki_ca_bundle_trust_crt_link_host.display(),
|
||||
trust_bundle_src_host.display()
|
||||
);
|
||||
println!(
|
||||
"[dry-run] Would link {} -> {}",
|
||||
pki_java_link_host.display(),
|
||||
java_src_host.display()
|
||||
);
|
||||
return Ok(());
|
||||
}
|
||||
|
||||
@@ -1479,6 +1907,21 @@ fn sync_system_ssl_symlinks(root: &Path, extracted_target: &Path, dry_run: bool)
|
||||
.context("java cacerts link path has no parent")?;
|
||||
fs::create_dir_all(java_parent)
|
||||
.with_context(|| format!("failed to create {}", java_parent.display()))?;
|
||||
let pki_ca_bundle_parent = pki_ca_bundle_crt_link_host
|
||||
.parent()
|
||||
.context("pki ca-bundle.crt link path has no parent")?;
|
||||
fs::create_dir_all(pki_ca_bundle_parent)
|
||||
.with_context(|| format!("failed to create {}", pki_ca_bundle_parent.display()))?;
|
||||
let pki_ca_bundle_trust_parent = pki_ca_bundle_trust_crt_link_host
|
||||
.parent()
|
||||
.context("pki ca-bundle.trust.crt link path has no parent")?;
|
||||
fs::create_dir_all(pki_ca_bundle_trust_parent)
|
||||
.with_context(|| format!("failed to create {}", pki_ca_bundle_trust_parent.display()))?;
|
||||
let pki_java_parent = pki_java_link_host
|
||||
.parent()
|
||||
.context("pki java cacerts link path has no parent")?;
|
||||
fs::create_dir_all(pki_java_parent)
|
||||
.with_context(|| format!("failed to create {}", pki_java_parent.display()))?;
|
||||
|
||||
// Link every extracted hash file into `/etc/ssl/certs`, then prune stale links.
|
||||
for entry in fs::read_dir(&cadir_host)
|
||||
@@ -1491,8 +1934,13 @@ fn sync_system_ssl_symlinks(root: &Path, extracted_target: &Path, dry_run: bool)
|
||||
}
|
||||
|
||||
remove_broken_symlinks(&ssl_certs_host)?;
|
||||
replace_symlink(&tls_bundle_src_host, &cert_pem_link_host)?;
|
||||
replace_symlink(&tls_bundle_src_host, &ca_bundle_link_host)?;
|
||||
replace_symlink(&tls_bundle_src_host, &ca_bundle_crt_link_host)?;
|
||||
replace_symlink(&java_src_host, &java_link_host)?;
|
||||
replace_symlink(&tls_bundle_src_host, &pki_ca_bundle_crt_link_host)?;
|
||||
replace_symlink(&trust_bundle_src_host, &pki_ca_bundle_trust_crt_link_host)?;
|
||||
replace_symlink(&java_src_host, &pki_java_link_host)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
@@ -1866,6 +2314,34 @@ CKA_TRUST_SERVER_AUTH CK_TRUST CKT_NSS_TRUSTED_DELEGATOR
|
||||
assert_eq!(bytes, b"ABC");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn sync_certdata_output_respects_explicit_path() {
|
||||
let requested = PathBuf::from("/var/tmp/custom-certdata.txt");
|
||||
let (resolved, cleanup) = resolve_sync_certdata_output(Some(requested.clone()), false).unwrap();
|
||||
assert_eq!(resolved, requested);
|
||||
assert!(cleanup.is_none());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn sync_certdata_output_uses_tmp_workspace_and_cleans_it() {
|
||||
let (resolved, cleanup) = resolve_sync_certdata_output(None, false).unwrap();
|
||||
assert!(resolved.starts_with(Path::new("/tmp")));
|
||||
assert_eq!(resolved.file_name(), Some(OsStr::new(DEFAULT_CERTDATA_OUTPUT)));
|
||||
let workspace = resolved.parent().unwrap().to_path_buf();
|
||||
assert!(workspace.exists());
|
||||
|
||||
drop(cleanup);
|
||||
assert!(!workspace.exists());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn sync_certdata_output_dry_run_uses_tmp_path_without_creating_workspace() {
|
||||
let (resolved, cleanup) = resolve_sync_certdata_output(None, true).unwrap();
|
||||
assert!(resolved.starts_with(Path::new("/tmp")));
|
||||
assert_eq!(resolved.file_name(), Some(OsStr::new(DEFAULT_CERTDATA_OUTPUT)));
|
||||
assert!(cleanup.is_none());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn percent_encode_bytes_encodes_lower_hex() {
|
||||
assert_eq!(percent_encode_bytes(&[0x00, 0x2a, 0xff]), "%00%2a%ff");
|
||||
|
||||
Reference in New Issue
Block a user