diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml new file mode 100644 index 0000000..639e5bd --- /dev/null +++ b/.github/workflows/ci.yaml @@ -0,0 +1,59 @@ +name: CI + +on: + push: + branches: + - "*" + pull_request: + branches: + - "*" + +env: + CARGO_TERM_COLOR: always + +jobs: + build-latest: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - uses: dtolnay/rust-toolchain@stable + with: + toolchain: stable + components: clippy, rustfmt + - name: Build + run: cargo build + - name: Clippy + run: cargo clippy + - name: Formatting + run: cargo fmt -- --check + - name: Docs + run: cargo doc + - name: Tests + run: cargo test + + build-msrv: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - uses: dtolnay/rust-toolchain@stable + with: + toolchain: 1.75.0 + components: clippy, rustfmt + - name: Build + run: cargo build + - name: Clippy + run: cargo clippy + - name: Formatting + run: cargo fmt -- --check + - name: Docs + run: cargo doc + - name: Tests + run: cargo test + + links: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - name: Links + id: lychee + uses: lycheeverse/lychee-action@v2 diff --git a/Cargo.lock b/Cargo.lock index f642684..ea113fa 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1,490 +1,719 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + [[package]] -name = "aho-corasick" -version = "0.6.8" +name = "addr2line" +version = "0.24.2" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dfbe277e56a376000877090da837660b4427aad530e3028d44e0bffe4f89a1c1" dependencies = [ - "memchr 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "gimli", ] [[package]] -name = "ansi_term" -version = "0.11.0" +name = "adler2" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "320119579fcad9c21884f5c4861d16174d0e06250625266f50fe6898340abefa" + +[[package]] +name = "aho-corasick" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8e60d3430d3a69478ad0993f19238d2df97c507009a52b3c10addcd7f6bcb916" dependencies = [ - "winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", + "memchr", ] [[package]] -name = "atty" -version = "0.2.11" +name = "anstream" +version = "0.6.20" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3ae563653d1938f79b1ab1b5e668c87c76a9930414574a6583a7b7e11a8e6192" dependencies = [ - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", - "termion 1.5.1 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", + "anstyle", + "anstyle-parse", + "anstyle-query", + "anstyle-wincon", + "colorchoice", + "is_terminal_polyfill", + "utf8parse", ] [[package]] -name = "backtrace" -version = "0.3.9" +name = "anstyle" +version = "1.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "862ed96ca487e809f1c8e5a8447f6ee2cf102f846893800b20cebdf541fc6bbd" + +[[package]] +name = "anstyle-parse" +version = "0.2.7" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4e7644824f0aa2c7b9384579234ef10eb7efb6a0deb83f9630a49594dd9c15c2" dependencies = [ - "backtrace-sys 0.1.24 (registry+https://github.com/rust-lang/crates.io-index)", - "cfg-if 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", - "rustc-demangle 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", + "utf8parse", ] [[package]] -name = "backtrace-sys" -version = "0.1.24" +name = "anstyle-query" +version = "1.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e231f6134f61b71076a3eab506c379d4f36122f2af15a9ff04415ea4c3339e2" dependencies = [ - "cc 1.0.25 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", + "windows-sys", ] [[package]] -name = "bitflags" -version = "1.0.4" +name = "anstyle-wincon" +version = "3.0.10" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3e0633414522a32ffaac8ac6cc8f748e090c5717661fddeea04219e2344f5f2a" +dependencies = [ + "anstyle", + "once_cell_polyfill", + "windows-sys", +] [[package]] -name = "byteorder" -version = "1.2.6" +name = "autocfg" +version = "1.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c08606f8c3cbf4ce6ec8e28fb0014a2c086708fe954eaa885384a6165172e7e8" [[package]] -name = "bytes" -version = "0.4.10" +name = "backtrace" +version = "0.3.74" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8d82cb332cdfaed17ae235a638438ac4d4839913cc2af585c3c6746e8f8bee1a" dependencies = [ - "byteorder 1.2.6 (registry+https://github.com/rust-lang/crates.io-index)", - "iovec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", + "addr2line", + "cfg-if", + "libc", + "miniz_oxide", + "object", + "rustc-demangle", + "windows-targets 0.52.6", ] +[[package]] +name = "bitflags" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" + +[[package]] +name = "bitflags" +version = "2.9.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2261d10cca569e4643e526d8dc2e62e433cc8aba21ab764233731f8d369bf394" + [[package]] name = "cc" -version = "1.0.25" +version = "1.2.38" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "80f41ae168f955c12fb8960b057d70d0ca153fb83182b57d86380443527be7e9" +dependencies = [ + "find-msvc-tools", + "shlex", +] [[package]] name = "cfg-if" -version = "0.1.5" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2fd1289c04a9ea8cb22300a459a72a385d7c73d3259e2ed7dcb2af674838cfa9" + +[[package]] +name = "cfg_aliases" +version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "613afe47fcd5fac7ccf1db93babcb082c5994d996f20b8b159f2ad1658eb5724" [[package]] name = "clap" -version = "2.32.0" +version = "4.5.48" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2134bb3ea021b78629caa971416385309e0131b351b25e01dc16fb54e1b5fae" dependencies = [ - "ansi_term 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)", - "atty 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", - "bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)", - "strsim 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", - "textwrap 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)", - "unicode-width 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "vec_map 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)", + "clap_builder", + "clap_derive", ] [[package]] -name = "env_logger" -version = "0.5.13" +name = "clap_builder" +version = "4.5.48" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c2ba64afa3c0a6df7fa517765e31314e983f51dda798ffba27b988194fb65dc9" dependencies = [ - "atty 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", - "humantime 1.1.1 (registry+https://github.com/rust-lang/crates.io-index)", - "log 0.4.5 (registry+https://github.com/rust-lang/crates.io-index)", - "regex 1.0.5 (registry+https://github.com/rust-lang/crates.io-index)", - "termcolor 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)", + "anstream", + "anstyle", + "clap_lex", + "strsim", ] [[package]] -name = "error-chain" -version = "0.12.0" +name = "clap_derive" +version = "4.5.47" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbfd7eae0b0f1a6e63d4b13c9c478de77c2eb546fba158ad50b4203dc24b9f9c" dependencies = [ - "backtrace 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)", + "heck", + "proc-macro2", + "quote", + "syn", ] [[package]] -name = "gcc" -version = "0.3.55" +name = "clap_lex" +version = "0.7.5" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b94f61472cee1439c0b966b47e3aca9ae07e45d070759512cd390ea2bebc6675" [[package]] -name = "glob" -version = "0.2.11" +name = "colorchoice" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b05b61dc5112cbb17e4b6cd61790d9845d13888356391624cbe7e41efeac1e75" [[package]] -name = "gpio-utils" -version = "0.2.0" +name = "env_filter" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "186e05a59d4c50738528153b83b0b0194d3a29507dfec16eccd4b342903397d0" dependencies = [ - "clap 2.32.0 (registry+https://github.com/rust-lang/crates.io-index)", - "env_logger 0.5.13 (registry+https://github.com/rust-lang/crates.io-index)", - "error-chain 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)", - "glob 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", - "lazy_static 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "log 0.4.5 (registry+https://github.com/rust-lang/crates.io-index)", - "nix 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)", - "serde 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)", - "serde_derive 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)", - "sysfs_gpio 0.5.3 (registry+https://github.com/rust-lang/crates.io-index)", - "toml 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", - "users 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", + "log", + "regex", ] [[package]] -name = "humantime" -version = "1.1.1" +name = "env_logger" +version = "0.11.8" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "13c863f0904021b108aa8b2f55046443e6b1ebde8fd4a15c399893aae4fa069f" dependencies = [ - "quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)", + "anstream", + "anstyle", + "env_filter", + "jiff", + "log", ] [[package]] -name = "iovec" +name = "find-msvc-tools" version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1ced73b1dacfc750a6db6c0a0c3a3853c8b41997e2e2c563dc90804ae6867959" + +[[package]] +name = "gimli" +version = "0.31.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "07e28edb80900c19c28f1072f2e8aeca7fa06b23cd4169cefe1af5aa3260783f" + +[[package]] +name = "glob" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0cc23270f6e1808e30a928bdc84dea0b9b4136a8bc82338574f23baf47bbd280" + +[[package]] +name = "gpio-utils" +version = "0.3.0" dependencies = [ - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", + "backtrace", + "clap", + "env_logger", + "glob", + "lazy_static", + "log", + "nix 0.30.1", + "serde", + "serde_derive", + "serde_spanned", + "sysfs_gpio", + "thiserror", + "toml", + "toml_datetime", + "toml_parser", + "uzers", ] [[package]] -name = "lazy_static" -version = "1.1.0" +name = "heck" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea" + +[[package]] +name = "is_terminal_polyfill" +version = "1.70.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7943c866cc5cd64cbc25b2e01621d07fa8eb2a1a23160ee81ce38704e97b8ecf" + +[[package]] +name = "jiff" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be1f93b8b1eb69c77f24bbb0afdf66f54b632ee39af40ca21c4365a1d7347e49" +dependencies = [ + "jiff-static", + "log", + "portable-atomic", + "portable-atomic-util", + "serde", +] + +[[package]] +name = "jiff-static" +version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "03343451ff899767262ec32146f6d559dd759fdadf42ff0e227c7c48f72594b4" dependencies = [ - "version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", + "proc-macro2", + "quote", + "syn", ] +[[package]] +name = "lazy_static" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbd2bcb4c963f2ddae06a2efc7e9f3591312473c50c6685e1f298068316e66fe" + [[package]] name = "libc" -version = "0.2.43" +version = "0.2.175" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6a82ae493e598baaea5209805c49bbf2ea7de956d50d7da0da1164f9c6d28543" [[package]] name = "log" -version = "0.4.5" +version = "0.4.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34080505efa8e45a4b816c349525ebe327ceaa8559756f0356cba97ef3bf7432" + +[[package]] +name = "memchr" +version = "2.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "32a282da65faaf38286cf3be983213fcf1d2e2a58700e808f83f4ea9a4804bc0" + +[[package]] +name = "memoffset" +version = "0.6.5" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5aa361d4faea93603064a027415f07bd8e1d5c88c9fbf68bf56a285428fd79ce" dependencies = [ - "cfg-if 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", + "autocfg", ] [[package]] -name = "memchr" -version = "2.1.0" +name = "miniz_oxide" +version = "0.8.9" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1fa76a2c86f704bdb222d66965fb3d63269ce38518b83cb0575fca855ebb6316" dependencies = [ - "cfg-if 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", - "version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", + "adler2", ] [[package]] name = "nix" -version = "0.10.0" +version = "0.23.2" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f3790c00a0150112de0f4cd161e3d7fc4b2d8a5542ffc35f099a2562aecb35c" dependencies = [ - "bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)", - "bytes 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)", - "cfg-if 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "gcc 0.3.55 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", - "void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", + "bitflags 1.3.2", + "cc", + "cfg-if", + "libc", + "memoffset", ] [[package]] name = "nix" -version = "0.11.0" +version = "0.30.1" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74523f3a35e05aba87a1d978330aef40f67b0304ac79c1c00b294c9830543db6" dependencies = [ - "bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)", - "cc 1.0.25 (registry+https://github.com/rust-lang/crates.io-index)", - "cfg-if 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", - "void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", + "bitflags 2.9.4", + "cfg-if", + "cfg_aliases", + "libc", ] [[package]] -name = "proc-macro2" -version = "0.4.20" +name = "object" +version = "0.36.7" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62948e14d923ea95ea2c7c86c71013138b66525b86bdc08d2dcc262bdb497b87" dependencies = [ - "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "memchr", ] [[package]] -name = "quick-error" -version = "1.2.2" +name = "once_cell_polyfill" +version = "1.70.1" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4895175b425cb1f87721b59f0f286c2092bd4af812243672510e1ac53e2e0ad" [[package]] -name = "quote" -version = "0.6.8" +name = "portable-atomic" +version = "1.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f84267b20a16ea918e43c6a88433c2d54fa145c92a811b5b047ccbe153674483" + +[[package]] +name = "portable-atomic-util" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d8a2f0d8d040d7848a709caf78912debcc3f33ee4b3cac47d73d1e1069e83507" dependencies = [ - "proc-macro2 0.4.20 (registry+https://github.com/rust-lang/crates.io-index)", + "portable-atomic", ] [[package]] -name = "redox_syscall" -version = "0.1.40" +name = "proc-macro2" +version = "1.0.101" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "89ae43fd86e4158d6db51ad8e2b80f313af9cc74f5c0e03ccb87de09998732de" +dependencies = [ + "unicode-ident", +] [[package]] -name = "redox_termios" -version = "0.1.1" +name = "quote" +version = "1.0.40" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1885c039570dc00dcb4ff087a89e185fd56bae234ddc7f056a945bf36467248d" dependencies = [ - "redox_syscall 0.1.40 (registry+https://github.com/rust-lang/crates.io-index)", + "proc-macro2", ] [[package]] name = "regex" -version = "1.0.5" +version = "1.11.2" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23d7fd106d8c02486a8d64e778353d1cffe08ce79ac2e82f540c86d0facf6912" dependencies = [ - "aho-corasick 0.6.8 (registry+https://github.com/rust-lang/crates.io-index)", - "memchr 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "regex-syntax 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)", - "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", - "utf8-ranges 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", + "aho-corasick", + "memchr", + "regex-automata", + "regex-syntax", ] [[package]] -name = "regex-syntax" -version = "0.6.2" +name = "regex-automata" +version = "0.4.10" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6b9458fa0bfeeac22b5ca447c63aaf45f28439a709ccd244698632f9aa6394d6" dependencies = [ - "ucd-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", + "aho-corasick", + "memchr", + "regex-syntax", ] +[[package]] +name = "regex-syntax" +version = "0.8.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "caf4aa5b0f434c91fe5c7f1ecb6a5ece2130b02ad2a590589dda5146df959001" + [[package]] name = "rustc-demangle" -version = "0.1.9" +version = "0.1.26" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "56f7d92ca342cea22a06f2121d944b4fd82af56988c270852495420f961d4ace" [[package]] name = "serde" -version = "1.0.80" +version = "1.0.226" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0dca6411025b24b60bfa7ec1fe1f8e710ac09782dca409ee8237ba74b51295fd" +dependencies = [ + "serde_core", +] + +[[package]] +name = "serde_core" +version = "1.0.226" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba2ba63999edb9dac981fb34b3e5c0d111a69b0924e253ed29d83f7c99e966a4" +dependencies = [ + "serde_derive", +] [[package]] name = "serde_derive" -version = "1.0.80" +version = "1.0.226" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8db53ae22f34573731bafa1db20f04027b2d25e02d8205921b569171699cdb33" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + +[[package]] +name = "serde_spanned" +version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2789234a13a53fc4be1b51ea1bab45a3c338bdb884862a257d10e5a74ae009e6" dependencies = [ - "proc-macro2 0.4.20 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.6.8 (registry+https://github.com/rust-lang/crates.io-index)", - "syn 0.15.12 (registry+https://github.com/rust-lang/crates.io-index)", + "serde_core", ] +[[package]] +name = "shlex" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64" + [[package]] name = "strsim" -version = "0.7.0" +version = "0.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7da8b5736845d9f2fcb837ea5d9e2628564b3b043a70948a3f0b778838c5fb4f" [[package]] name = "syn" -version = "0.15.12" +version = "2.0.106" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ede7c438028d4436d71104916910f5bb611972c5cfd7f89b8300a8186e6fada6" dependencies = [ - "proc-macro2 0.4.20 (registry+https://github.com/rust-lang/crates.io-index)", - "quote 0.6.8 (registry+https://github.com/rust-lang/crates.io-index)", - "unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "proc-macro2", + "quote", + "unicode-ident", ] [[package]] name = "sysfs_gpio" -version = "0.5.3" +version = "0.6.2" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e8808c55bc926565c62ef7838bcaa8add51585236803e2bdfa1472e3a3ab5e17" dependencies = [ - "nix 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)", + "nix 0.23.2", ] [[package]] -name = "termcolor" -version = "1.0.4" +name = "thiserror" +version = "2.0.16" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3467d614147380f2e4e374161426ff399c91084acd2363eaf549172b3d5e60c0" dependencies = [ - "wincolor 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", + "thiserror-impl", ] [[package]] -name = "termion" -version = "1.5.1" +name = "thiserror-impl" +version = "2.0.16" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c5e1be1c48b9172ee610da68fd9cd2770e7a4056cb3fc98710ee6906f0c7960" dependencies = [ - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", - "redox_syscall 0.1.40 (registry+https://github.com/rust-lang/crates.io-index)", - "redox_termios 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", + "proc-macro2", + "quote", + "syn", ] [[package]] -name = "textwrap" -version = "0.10.0" +name = "toml" +version = "0.9.6" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ae2a4cf385da23d1d53bc15cdfa5c2109e93d8d362393c801e87da2f72f0e201" dependencies = [ - "unicode-width 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", + "serde_core", + "serde_spanned", + "toml_datetime", + "toml_parser", + "winnow", ] [[package]] -name = "thread_local" -version = "0.3.6" +name = "toml_datetime" +version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a197c0ec7d131bfc6f7e82c8442ba1595aeab35da7adbf05b6b73cd06a16b6be" dependencies = [ - "lazy_static 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "serde_core", ] [[package]] -name = "toml" -version = "0.4.8" +name = "toml_parser" +version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b551886f449aa90d4fe2bdaa9f4a2577ad2dde302c61ecf262d80b116db95c10" dependencies = [ - "serde 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)", + "winnow", ] [[package]] -name = "ucd-util" -version = "0.1.1" +name = "unicode-ident" +version = "1.0.19" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f63a545481291138910575129486daeaf8ac54aee4387fe7906919f7830c7d9d" [[package]] -name = "unicode-width" -version = "0.1.5" +name = "utf8parse" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "06abde3611657adf66d383f00b093d7faecc7fa57071cce2578660c9f1010821" [[package]] -name = "unicode-xid" -version = "0.1.0" +name = "uzers" +version = "0.12.1" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4df81ff504e7d82ad53e95ed1ad5b72103c11253f39238bcc0235b90768a97dd" +dependencies = [ + "libc", +] [[package]] -name = "users" -version = "0.8.0" +name = "windows-link" +version = "0.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5e6ad25900d524eaabdbbb96d20b4311e1e7ae1699af4fb28c17ae66c80d798a" + +[[package]] +name = "windows-sys" +version = "0.60.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f2f500e4d28234f72040990ec9d39e3a6b950f9f22d3dba18416c35882612bcb" dependencies = [ - "libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)", + "windows-targets 0.53.3", ] [[package]] -name = "utf8-ranges" -version = "1.0.1" +name = "windows-targets" +version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b724f72796e036ab90c1021d4780d4d3d648aca59e491e6b98e725b84e99973" +dependencies = [ + "windows_aarch64_gnullvm 0.52.6", + "windows_aarch64_msvc 0.52.6", + "windows_i686_gnu 0.52.6", + "windows_i686_gnullvm 0.52.6", + "windows_i686_msvc 0.52.6", + "windows_x86_64_gnu 0.52.6", + "windows_x86_64_gnullvm 0.52.6", + "windows_x86_64_msvc 0.52.6", +] [[package]] -name = "vec_map" -version = "0.8.1" +name = "windows-targets" +version = "0.53.3" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d5fe6031c4041849d7c496a8ded650796e7b6ecc19df1a431c1a363342e5dc91" +dependencies = [ + "windows-link", + "windows_aarch64_gnullvm 0.53.0", + "windows_aarch64_msvc 0.53.0", + "windows_i686_gnu 0.53.0", + "windows_i686_gnullvm 0.53.0", + "windows_i686_msvc 0.53.0", + "windows_x86_64_gnu 0.53.0", + "windows_x86_64_gnullvm 0.53.0", + "windows_x86_64_msvc 0.53.0", +] [[package]] -name = "version_check" -version = "0.1.5" +name = "windows_aarch64_gnullvm" +version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "32a4622180e7a0ec044bb555404c800bc9fd9ec262ec147edd5989ccd0c02cd3" [[package]] -name = "void" -version = "1.0.2" +name = "windows_aarch64_gnullvm" +version = "0.53.0" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "86b8d5f90ddd19cb4a147a5fa63ca848db3df085e25fee3cc10b39b6eebae764" [[package]] -name = "winapi" -version = "0.2.8" +name = "windows_aarch64_msvc" +version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09ec2a7bb152e2252b53fa7803150007879548bc709c039df7627cabbd05d469" [[package]] -name = "winapi" -version = "0.3.6" +name = "windows_aarch64_msvc" +version = "0.53.0" source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", -] +checksum = "c7651a1f62a11b8cbd5e0d42526e55f2c99886c77e007179efff86c2b137e66c" [[package]] -name = "winapi-i686-pc-windows-gnu" -version = "0.4.0" +name = "windows_i686_gnu" +version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8e9b5ad5ab802e97eb8e295ac6720e509ee4c243f69d781394014ebfe8bbfa0b" [[package]] -name = "winapi-util" -version = "0.1.1" +name = "windows_i686_gnu" +version = "0.53.0" source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", -] +checksum = "c1dc67659d35f387f5f6c479dc4e28f1d4bb90ddd1a5d3da2e5d97b42d6272c3" [[package]] -name = "winapi-x86_64-pc-windows-gnu" -version = "0.4.0" +name = "windows_i686_gnullvm" +version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0eee52d38c090b3caa76c563b86c3a4bd71ef1a819287c19d586d7334ae8ed66" [[package]] -name = "wincolor" -version = "1.0.1" +name = "windows_i686_gnullvm" +version = "0.53.0" source = "registry+https://github.com/rust-lang/crates.io-index" -dependencies = [ - "winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", - "winapi-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", -] - -[metadata] -"checksum aho-corasick 0.6.8 (registry+https://github.com/rust-lang/crates.io-index)" = "68f56c7353e5a9547cbd76ed90f7bb5ffc3ba09d4ea9bd1d8c06c8b1142eeb5a" -"checksum ansi_term 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ee49baf6cb617b853aa8d93bf420db2383fab46d314482ca2803b40d5fde979b" -"checksum atty 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "9a7d5b8723950951411ee34d271d99dddcc2035a16ab25310ea2c8cfd4369652" -"checksum backtrace 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)" = "89a47830402e9981c5c41223151efcced65a0510c13097c769cede7efb34782a" -"checksum backtrace-sys 0.1.24 (registry+https://github.com/rust-lang/crates.io-index)" = "c66d56ac8dabd07f6aacdaf633f4b8262f5b3601a810a0dcddffd5c22c69daa0" -"checksum bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)" = "228047a76f468627ca71776ecdebd732a3423081fcf5125585bcd7c49886ce12" -"checksum byteorder 1.2.6 (registry+https://github.com/rust-lang/crates.io-index)" = "90492c5858dd7d2e78691cfb89f90d273a2800fc11d98f60786e5d87e2f83781" -"checksum bytes 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)" = "0ce55bd354b095246fc34caf4e9e242f5297a7fd938b090cadfea6eee614aa62" -"checksum cc 1.0.25 (registry+https://github.com/rust-lang/crates.io-index)" = "f159dfd43363c4d08055a07703eb7a3406b0dac4d0584d96965a3262db3c9d16" -"checksum cfg-if 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "0c4e7bb64a8ebb0d856483e1e682ea3422f883c5f5615a90d51a2c82fe87fdd3" -"checksum clap 2.32.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b957d88f4b6a63b9d70d5f454ac8011819c6efa7727858f458ab71c756ce2d3e" -"checksum env_logger 0.5.13 (registry+https://github.com/rust-lang/crates.io-index)" = "15b0a4d2e39f8420210be8b27eeda28029729e2fd4291019455016c348240c38" -"checksum error-chain 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)" = "07e791d3be96241c77c43846b665ef1384606da2cd2a48730abe606a12906e02" -"checksum gcc 0.3.55 (registry+https://github.com/rust-lang/crates.io-index)" = "8f5f3913fa0bfe7ee1fd8248b6b9f42a5af4b9d65ec2dd2c3c26132b950ecfc2" -"checksum glob 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "8be18de09a56b60ed0edf84bc9df007e30040691af7acd1c41874faac5895bfb" -"checksum humantime 1.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0484fda3e7007f2a4a0d9c3a703ca38c71c54c55602ce4660c419fd32e188c9e" -"checksum iovec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "dbe6e417e7d0975db6512b90796e8ce223145ac4e33c377e4a42882a0e88bb08" -"checksum lazy_static 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ca488b89a5657b0a2ecd45b95609b3e848cf1755da332a0da46e2b2b1cb371a7" -"checksum libc 0.2.43 (registry+https://github.com/rust-lang/crates.io-index)" = "76e3a3ef172f1a0b9a9ff0dd1491ae5e6c948b94479a3021819ba7d860c8645d" -"checksum log 0.4.5 (registry+https://github.com/rust-lang/crates.io-index)" = "d4fcce5fa49cc693c312001daf1d13411c4a5283796bac1084299ea3e567113f" -"checksum memchr 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "4b3629fe9fdbff6daa6c33b90f7c08355c1aca05a3d01fa8063b822fcf185f3b" -"checksum nix 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b7fd5681d13fda646462cfbd4e5f2051279a89a544d50eb98c365b507246839f" -"checksum nix 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d37e713a259ff641624b6cb20e3b12b2952313ba36b6823c0f16e6cfd9e5de17" -"checksum proc-macro2 0.4.20 (registry+https://github.com/rust-lang/crates.io-index)" = "3d7b7eaaa90b4a90a932a9ea6666c95a389e424eff347f0f793979289429feee" -"checksum quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9274b940887ce9addde99c4eee6b5c44cc494b182b97e73dc8ffdcb3397fd3f0" -"checksum quote 0.6.8 (registry+https://github.com/rust-lang/crates.io-index)" = "dd636425967c33af890042c483632d33fa7a18f19ad1d7ea72e8998c6ef8dea5" -"checksum redox_syscall 0.1.40 (registry+https://github.com/rust-lang/crates.io-index)" = "c214e91d3ecf43e9a4e41e578973adeb14b474f2bee858742d127af75a0112b1" -"checksum redox_termios 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7e891cfe48e9100a70a3b6eb652fef28920c117d366339687bd5576160db0f76" -"checksum regex 1.0.5 (registry+https://github.com/rust-lang/crates.io-index)" = "2069749032ea3ec200ca51e4a31df41759190a88edca0d2d86ee8bedf7073341" -"checksum regex-syntax 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)" = "747ba3b235651f6e2f67dfa8bcdcd073ddb7c243cb21c442fc12395dfcac212d" -"checksum rustc-demangle 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "bcfe5b13211b4d78e5c2cadfebd7769197d95c639c35a50057eb4c05de811395" -"checksum serde 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)" = "15c141fc7027dd265a47c090bf864cf62b42c4d228bbcf4e51a0c9e2b0d3f7ef" -"checksum serde_derive 1.0.80 (registry+https://github.com/rust-lang/crates.io-index)" = "225de307c6302bec3898c51ca302fc94a7a1697ef0845fcee6448f33c032249c" -"checksum strsim 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "bb4f380125926a99e52bc279241539c018323fab05ad6368b56f93d9369ff550" -"checksum syn 0.15.12 (registry+https://github.com/rust-lang/crates.io-index)" = "34ab9797e47d24cb76b8dc4d24ff36807018c7cc549c4cba050b068be0c586b0" -"checksum sysfs_gpio 0.5.3 (registry+https://github.com/rust-lang/crates.io-index)" = "3d68f2cae3c7d39f54ce8a858cc31ffb01974744ee65e5b4999b6037cd691e3f" -"checksum termcolor 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)" = "4096add70612622289f2fdcdbd5086dc81c1e2675e6ae58d6c4f62a16c6d7f2f" -"checksum termion 1.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "689a3bdfaab439fd92bc87df5c4c78417d3cbe537487274e9b0b2dce76e92096" -"checksum textwrap 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "307686869c93e71f94da64286f9a9524c0f308a9e1c87a583de8e9c9039ad3f6" -"checksum thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)" = "c6b53e329000edc2b34dbe8545fd20e55a333362d0a321909685a19bd28c3f1b" -"checksum toml 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "4a2ecc31b0351ea18b3fe11274b8db6e4d82bce861bbb22e6dbed40417902c65" -"checksum ucd-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "fd2be2d6639d0f8fe6cdda291ad456e23629558d466e2789d2c3e9892bda285d" -"checksum unicode-width 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "882386231c45df4700b275c7ff55b6f3698780a650026380e72dabe76fa46526" -"checksum unicode-xid 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc" -"checksum users 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "bb3c80625ae5e77e1b402f8a0fa89afbd50622a6cae65128844720bd4e26b657" -"checksum utf8-ranges 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "fd70f467df6810094968e2fce0ee1bd0e87157aceb026a8c083bcf5e25b9efe4" -"checksum vec_map 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)" = "05c78687fb1a80548ae3250346c3db86a80a7cdd77bda190189f2d0a0987c81a" -"checksum version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "914b1a6776c4c929a602fafd8bc742e06365d4bcbe48c30f9cca5824f70dc9dd" -"checksum void 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "6a02e4885ed3bc0f2de90ea6dd45ebcbb66dacffe03547fadbb0eeae2770887d" -"checksum winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" -"checksum winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)" = "92c1eb33641e276cfa214a0522acad57be5c56b10cb348b3c5117db75f3ac4b0" -"checksum winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" -"checksum winapi-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "afc5508759c5bf4285e61feb862b6083c8480aec864fa17a81fdec6f69b461ab" -"checksum winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" -"checksum wincolor 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "561ed901ae465d6185fa7864d63fbd5720d0ef718366c9a4dc83cf6170d7e9ba" +checksum = "9ce6ccbdedbf6d6354471319e781c0dfef054c81fbc7cf83f338a4296c0cae11" + +[[package]] +name = "windows_i686_msvc" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66" + +[[package]] +name = "windows_i686_msvc" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "581fee95406bb13382d2f65cd4a908ca7b1e4c2f1917f143ba16efe98a589b5d" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "147a5c80aabfbf0c7d901cb5895d1de30ef2907eb21fbbab29ca94c5b08b1a78" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2e55b5ac9ea33f2fc1716d1742db15574fd6fc8dadc51caab1c16a3d3b4190ba" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0a6e035dd0599267ce1ee132e51c27dd29437f63325753051e71dd9e42406c57" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.52.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "271414315aff87387382ec3d271b52d7ae78726f5d44ac98b4f4030c91880486" + +[[package]] +name = "winnow" +version = "0.7.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "21a0236b59786fed61e2a80582dd500fe61f18b5dca67a4a067d0bc9039339cf" diff --git a/Cargo.toml b/Cargo.toml index fc92557..d2bc5a7 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -7,6 +7,8 @@ license = "MIT/Apache-2.0" readme = "README.md" homepage = "https://github.com/rust-embedded/gpio-utils" keywords = ["gpio", "linux", "sysfs_gpio", "cli", "command-line"] +edition = "2021" +rust-version = "1.75.0" description = """ Command-line utilities for interacting with GPIOs under Linux @@ -15,19 +17,31 @@ Rust applications or any other applications. """ [dependencies] -clap = "2.2" -error-chain = "0.12" -sysfs_gpio = "0.5.2" -toml = "0.4" -glob = "0.2" +clap = { version = "4.5.48", features = ["derive"] } +sysfs_gpio = "0.6.2" +toml = { version = "<=0.9.6", default-features = false, features = ["parse", "serde"] } +glob = "0.3.3" lazy_static = "1.1" log = "0.4" -env_logger = "0.5" -nix = "0.11" +env_logger = "0.11.8" +nix = { version = "0.30.1", features = ["fs", "user"] } serde_derive = "1.0" serde = "1.0" -users = "0.8" +uzers = { version = "0.12.1", default-features = false, features = ["cache"] } + +# TODO Cross check and unpin the transitive dependencies below after bumping +# our MSRV beyond 1.75.0. +backtrace = "=0.3.74" +serde_spanned = "<=1.0.1" +toml_datetime = "<=0.7.1" +toml_parser = "<=1.0.2" +thiserror = { version = "2.0.16", default-features = false } + [[bin]] name = "gpio" path = "src/main.rs" + +[lints.rust] +# The cfg `has_error_description_deprecated` is introduced by the error_chain crate. +unexpected_cfgs = { level = "warn", check-cfg = ['cfg(has_error_description_deprecated)'] } diff --git a/README.md b/README.md index f998c98..fb24b54 100644 --- a/README.md +++ b/README.md @@ -98,7 +98,7 @@ reliability) and seeks to operate with a minimum of overhead. ## Minimum Supported Rust Version (MSRV) -This crate is guaranteed to compile on stable Rust 1.26.2 and up. It *might* +This crate is guaranteed to compile on stable Rust 1.75.0 and up. It *might* compile with older versions but that may change in any new patch release. ## Contributing diff --git a/src/commands/gpio_export.rs b/src/commands/gpio_export.rs index c3c94d2..66430e3 100644 --- a/src/commands/gpio_export.rs +++ b/src/commands/gpio_export.rs @@ -6,9 +6,9 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::GpioConfig; -use export; -use options::GpioExportOptions; +use crate::config::GpioConfig; +use crate::export; +use crate::options::GpioExportOptions; use std::process::exit; pub fn main(config: &GpioConfig, opts: &GpioExportOptions) { diff --git a/src/commands/gpio_exportall.rs b/src/commands/gpio_exportall.rs index c16fef3..846e81d 100644 --- a/src/commands/gpio_exportall.rs +++ b/src/commands/gpio_exportall.rs @@ -6,9 +6,9 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::GpioConfig; -use export; -use options::GpioExportAllOptions; +use crate::config::GpioConfig; +use crate::export; +use crate::options::GpioExportAllOptions; use std::process::exit; pub fn main(config: &GpioConfig, opts: &GpioExportAllOptions) { diff --git a/src/commands/gpio_poll.rs b/src/commands/gpio_poll.rs index 84a7018..0f0efce 100644 --- a/src/commands/gpio_poll.rs +++ b/src/commands/gpio_poll.rs @@ -6,8 +6,8 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::GpioConfig; -use options::GpioPollOptions; +use crate::config::GpioConfig; +use crate::options::GpioPollOptions; use std::process::exit; use sysfs_gpio::Edge; diff --git a/src/commands/gpio_read.rs b/src/commands/gpio_read.rs index 753f9d1..20db8bc 100644 --- a/src/commands/gpio_read.rs +++ b/src/commands/gpio_read.rs @@ -6,8 +6,8 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::GpioConfig; -use options::GpioReadOptions; +use crate::config::GpioConfig; +use crate::options::GpioReadOptions; use std::process::exit; pub fn main(config: &GpioConfig, opts: &GpioReadOptions) { diff --git a/src/commands/gpio_status.rs b/src/commands/gpio_status.rs index 04c2e39..1cabbed 100644 --- a/src/commands/gpio_status.rs +++ b/src/commands/gpio_status.rs @@ -6,9 +6,9 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::GpioConfig; -use config::PinConfig; -use options::GpioStatusOptions; +use crate::config::GpioConfig; +use crate::config::PinConfig; +use crate::options::GpioStatusOptions; use std::process::exit; use sysfs_gpio::Direction; @@ -23,7 +23,7 @@ pub fn main(config: &GpioConfig, opts: &GpioStatusOptions) { } }; print_pin_header(); - print_pin_row(&pin_config, true); + print_pin_row(pin_config, true); } None => { print_pin_header(); diff --git a/src/commands/gpio_unexport.rs b/src/commands/gpio_unexport.rs index 66089f3..f0325f3 100644 --- a/src/commands/gpio_unexport.rs +++ b/src/commands/gpio_unexport.rs @@ -6,9 +6,9 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::GpioConfig; -use export; -use options::GpioUnexportOptions; +use crate::config::GpioConfig; +use crate::export; +use crate::options::GpioUnexportOptions; use std::process::exit; pub fn main(config: &GpioConfig, opts: &GpioUnexportOptions) { diff --git a/src/commands/gpio_unexportall.rs b/src/commands/gpio_unexportall.rs index 598b376..bb6aded 100644 --- a/src/commands/gpio_unexportall.rs +++ b/src/commands/gpio_unexportall.rs @@ -6,9 +6,9 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::GpioConfig; -use export; -use options::GpioUnexportAllOptions; +use crate::config::GpioConfig; +use crate::export; +use crate::options::GpioUnexportAllOptions; use std::process::exit; pub fn main(config: &GpioConfig, opts: &GpioUnexportAllOptions) { diff --git a/src/commands/gpio_write.rs b/src/commands/gpio_write.rs index d157e0d..c97564a 100644 --- a/src/commands/gpio_write.rs +++ b/src/commands/gpio_write.rs @@ -6,8 +6,8 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::GpioConfig; -use options::GpioWriteOptions; +use crate::config::GpioConfig; +use crate::options::GpioWriteOptions; use std::process::exit; use sysfs_gpio::Direction; diff --git a/src/config.rs b/src/config.rs index 40d04b3..6dc6b2d 100644 --- a/src/config.rs +++ b/src/config.rs @@ -7,6 +7,7 @@ // except according to those terms. use glob::glob; +use serde_derive::Deserialize; use std::collections::{BTreeSet, HashMap}; use std::fmt; use std::fs::{self, File}; @@ -114,10 +115,10 @@ impl FromStr for GpioConfig { type Err = Error; /// Load a GPIO configuration for the provided toml string fn from_str(config: &str) -> Result { - let cfg = toml::from_str(&config); + let cfg = toml::from_str(config); match cfg { Ok(cfg) => { - let val_config: GpioConfig = toml::from_str(&config).unwrap(); + let val_config: GpioConfig = toml::from_str(config).unwrap(); val_config.validate()?; Ok(cfg) } @@ -227,7 +228,7 @@ impl GpioConfig { /// Get the symlink root specified in the config (or the default) pub fn get_symlink_root(&self) -> &str { match self.config.symlink_root { - Some(ref root) => &root, + Some(ref root) => root, None => DEFAULT_SYMLINK_ROOT, } } diff --git a/src/error.rs b/src/error.rs index 0ac667e..2823052 100644 --- a/src/error.rs +++ b/src/error.rs @@ -10,14 +10,22 @@ use nix::Error as NixError; use std::io::Error as IoError; use sysfs_gpio::Error as GpioError; -error_chain! { - types { - Error, ErrorKind, ResultExt, Result; - } +#[derive(thiserror::Error, Debug)] +pub enum Error { + #[error(transparent)] + Gpio(#[from] GpioError), + #[error(transparent)] + Nix(#[from] NixError), + #[error(transparent)] + Io(#[from] IoError), + #[error("{0}")] + Msg(String), +} - foreign_links { - Gpio(GpioError); - Nix(NixError); - Io(IoError); +impl From for Error { + fn from(msg: String) -> Error { + Error::Msg(msg) } } + +pub type Result = std::result::Result; diff --git a/src/export.rs b/src/export.rs index 9847b77..5ec994e 100644 --- a/src/export.rs +++ b/src/export.rs @@ -6,8 +6,9 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use config::PinConfig; -use error::*; +use crate::config::PinConfig; +use crate::error::*; +use lazy_static::lazy_static; use nix::unistd::{chown, Gid, Uid}; use std::fs; use std::io::ErrorKind; @@ -16,7 +17,7 @@ use std::os::unix::fs::PermissionsExt; use std::path; use std::sync::Mutex; use sysfs_gpio; -use users::{Groups, Users, UsersCache}; +use uzers::{Groups, Users, UsersCache}; lazy_static! { static ref USERS_CACHE: Mutex = Mutex::new(UsersCache::new()); @@ -66,7 +67,7 @@ pub fn unexport(pin_config: &PinConfig, symlink_root: Option<&str>) -> Result<() /// /// 1. The GPIO pin itself is exported (via /sys/class/gpio/export) /// 2. For each GPIO name/alias, a symlink is created from -/// `/var/run/gpio/` -> `/sys/class/gpio`. +/// `/var/run/gpio/` -> `/sys/class/gpio`. /// /// If the GPIO is already exported, this function will continue /// without an error as the desired end state is achieved. @@ -126,14 +127,10 @@ pub fn export(pin_config: &PinConfig, symlink_root: Option<&str>) -> Result<()> fs::create_dir_all(symroot)?; // set active low - pin_config - .get_pin() - .set_active_low(pin_config.active_low)?; + pin_config.get_pin().set_active_low(pin_config.active_low)?; // set the pin direction - pin_config - .get_pin() - .set_direction(pin_config.direction)?; + pin_config.get_pin().set_direction(pin_config.direction)?; // create symlink for each name for name in &pin_config.names { diff --git a/src/lib.rs b/src/lib.rs index 90f0eed..39291cb 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -6,20 +6,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -#[macro_use] -extern crate error_chain; -extern crate glob; -#[macro_use] -extern crate lazy_static; -extern crate log; -extern crate nix; -extern crate serde; -#[macro_use] -extern crate serde_derive; -extern crate sysfs_gpio; -extern crate toml; -extern crate users; - pub mod commands; pub mod config; pub mod error; diff --git a/src/main.rs b/src/main.rs index 6e77562..11c6499 100644 --- a/src/main.rs +++ b/src/main.rs @@ -5,231 +5,170 @@ // , at your // option. This file may not be copied, modified, or distributed // except according to those terms. -extern crate clap; -extern crate env_logger; -extern crate gpio_utils; -extern crate log; -use clap::{App, AppSettings, Arg, SubCommand}; +use clap::{Parser, Subcommand}; use gpio_utils::commands::*; use gpio_utils::config::{self, GpioConfig}; use gpio_utils::options::*; -use std::process::exit; +use std::process; + +#[derive(Parser)] +#[command( + name = "GPIO Utils", + version, + about = "Read, Write, and Configure GPIOs" +)] +struct Cli { + /// additional configuration to use + #[arg(short, long = "config", value_name = "FILE")] + configs: Vec, + #[command(subcommand)] + command: Commands, +} + +#[derive(Subcommand)] +enum Commands { + /// Read the value of a GPIO Input + Read { + /// The pin name (or number) + pin: String, + }, + /// Wait for an event to happen on a GPIO Input + Poll { + /// The pin name (or number) + pin: String, + /// Timeout (in ms) for the poll operation (-1 to wait forever, default) + #[arg(short, long)] + timeout: Option, + /// The edge to poll on + #[arg(short, long)] + edge: Option, + }, + /// Write the value of a GPIO Output + Write { + /// The pin name (or number) + pin: String, + /// Value to write to pin (0|1) + value: u8, + }, + /// Export a given GPIO + Export { + /// The pin name (or number) + pin: String, + /// root directory for export symlinks + #[arg(short = 'r', long)] + symlink_root: Option, + }, + /// Export all configured GPIOs + ExportAll { + /// Export all configured GPIOs + #[arg(short = 'r', long)] + symlink_root: Option, + }, + /// Export all configured GPIOs + Unexport { + /// The pin name (or number) + pin: String, + /// root directory for export symlinks + #[arg(short = 'r', long)] + symlink_root: Option, + }, + /// Unexport all configured, exported GPIOs + UnexportAll { + /// root directory for export symlinks + #[arg(short = 'r', long)] + symlink_root: Option, + }, + /// Output status of a GPIO or all GPIOs if no pin is specified + Status { + /// The pin name (or number) + pin: Option, + }, +} fn main() { env_logger::init(); - let matches = App::new("GPIO Utils") - .version(env!("CARGO_PKG_VERSION")) - .about("Read, Write, and Configure GPIOs") - .setting(AppSettings::SubcommandRequired) - - // Global options - .arg(Arg::with_name("config") - .help("additional configuration to use") - .takes_value(true) - .short("c") - .long("config") - .multiple(true) - .required(false)) - - // gpio read - .subcommand(SubCommand::with_name("read") - .about("Read the value of a GPIO Input") - .arg(Arg::with_name("pin") - .help("The pin name (or number)") - .index(1) - .required(true))) - - // gpio poll - .subcommand(SubCommand::with_name("poll") - .about("Wait for an event to happen on a GPIO Input") - .arg(Arg::with_name("pin") - .help("The pin name (or number)") - .index(1) - .required(true)) - .arg(Arg::with_name("timeout") - .help("Timeout (in ms) for the poll operation (-1 to wait forever, default)") - .takes_value(true) - .short("t") - .long("timeout") - .required(false)) - .arg(Arg::with_name("edge") - .help("The edge to poll on") - .takes_value(true) - .short("e") - .long("edge") - .required(false))) - - // gpio write - .subcommand(SubCommand::with_name("write") - .about("Write the value of a GPIO Output") - .arg(Arg::with_name("pin") - .help("The pin name (or number)") - .index(1) - .required(true)) - .arg(Arg::with_name("value") - .help("Value to write to pin (0|1)") - .index(2) - .required(true))) - - // gpio export - .subcommand(SubCommand::with_name("export") - .about("Export a given GPIO") - .arg(Arg::with_name("pin") - .help("The pin name (or number)") - .index(1) - .required(true)) - .arg(Arg::with_name("symlink-root") - .help("root directory for export symlinks") - .takes_value(true) - .short("r") - .long("symlink-root") - .required(false))) - - // gpio export-all - .subcommand(SubCommand::with_name("export-all") - .about("Export all configured GPIOs") - .arg(Arg::with_name("symlink-root") - .help("root directory for export symlinks") - .takes_value(true) - .short("r") - .long("symlink-root") - .required(false))) - - // gpio unexport - .subcommand(SubCommand::with_name("unexport") - .about("Unexport a given GPIO") - .arg(Arg::with_name("pin") - .help("The pin name (or number)") - .index(1) - .required(true)) - .arg(Arg::with_name("symlink-root") - .help("root directory for export symlinks") - .takes_value(true) - .short("r") - .long("symlink-root") - .required(false))) - - // gpio unexport-all - .subcommand(SubCommand::with_name("unexport-all") - .about("Unexport all configured, exported GPIOs") - .arg(Arg::with_name("symlink-root") - .help("root directory for export symlinks") - .takes_value(true) - .short("r") - .long("symlink-root") - .required(false))) - - // gpio status - .subcommand(SubCommand::with_name("status") - .about("Output status of a GPIO or all GPIOs if no pin is specified") - .arg(Arg::with_name("pin") - .help("The pin name (or number)") - .index(1) - .required(false))) - - .get_matches(); + let cli = Cli::parse(); - // process global options - let gpio_options = GpioOptions { - configs: matches.values_of_lossy("config").unwrap_or_default(), + let gpio_opts = GpioOptions { + configs: cli.configs.clone(), }; // parse the config - let cfg = match GpioConfig::load(&gpio_options.configs[..]) { + let cfg = match GpioConfig::load(&gpio_opts.configs[..]) { Ok(cfg) => cfg, Err(config::Error::NoConfigFound) => Default::default(), Err(e) => { println!("Error parsing config. Details follow..."); println!("{}", e); - std::process::exit(1); + process::exit(1); } }; - match matches.subcommand() { - ("read", Some(m)) => { - let read_options = GpioReadOptions { - gpio_opts: gpio_options, - pin: m.value_of("pin").unwrap(), + // TODO: Why are we passing the gpio_options and the config parsed from it to `gpio_read::main` + // and the other handlers? + match cli.command { + Commands::Read { pin } => { + let options = GpioReadOptions { + gpio_opts, + pin: &pin, }; - gpio_read::main(&cfg, &read_options); + gpio_read::main(&cfg, &options); } - ("poll", Some(m)) => { - let timeout = m.value_of("timeout").map(|timeout| { - timeout.parse::().unwrap_or_else(|_| { - println!("Unable to parse timeout value {:?} as integer", timeout); - exit(1); - }) - }); - let poll_options = GpioPollOptions { - gpio_opts: gpio_options, - edge: m.value_of("edge").unwrap_or("both"), - pin: m.value_of("pin").unwrap(), + Commands::Poll { pin, timeout, edge } => { + let options = GpioPollOptions { + gpio_opts, timeout, + edge: &edge.unwrap_or_else(|| String::from("both")), + pin: &pin, }; - gpio_poll::main(&cfg, &poll_options); + gpio_poll::main(&cfg, &options); } - ("write", Some(m)) => { - let write_options = GpioWriteOptions { - gpio_opts: gpio_options, - pin: m.value_of("pin").unwrap(), - value: match m.value_of("value").unwrap().parse::() { - Ok(value) => value, - Err(_) => { - println!( - "Provided value {:?} is not valid", - m.value_of("value").unwrap() - ); - exit(1); - } - }, + Commands::Write { pin, value } => { + let options = GpioWriteOptions { + gpio_opts, + pin: &pin, + value, }; - gpio_write::main(&cfg, &write_options); + gpio_write::main(&cfg, &options); } - ("export", Some(m)) => { - let export_options = GpioExportOptions { - gpio_opts: gpio_options, - pin: m.value_of("pin").unwrap(), - symlink_root: match m.value_of("symlink-root") { - Some(slr) => Some(slr), - None => None, - }, + Commands::Export { pin, symlink_root } => { + let options = GpioExportOptions { + gpio_opts, + pin: &pin, + symlink_root: symlink_root.as_deref(), }; - gpio_export::main(&cfg, &export_options); + gpio_export::main(&cfg, &options); } - ("export-all", Some(m)) => { - let exportall_options = GpioExportAllOptions { - gpio_opts: gpio_options, - symlink_root: match m.value_of("symlink-root") { - Some(slr) => Some(slr), - None => None, - }, + Commands::ExportAll { symlink_root } => { + let options = GpioExportAllOptions { + gpio_opts, + symlink_root: symlink_root.as_deref(), }; - gpio_exportall::main(&cfg, &exportall_options); + gpio_exportall::main(&cfg, &options); } - ("unexport", Some(m)) => { - let unexport_options = GpioUnexportOptions { - gpio_opts: gpio_options, - pin: m.value_of("pin").unwrap(), - symlink_root: m.value_of("symlink-root"), + Commands::Unexport { pin, symlink_root } => { + let options = GpioUnexportOptions { + gpio_opts, + pin: &pin, + symlink_root: symlink_root.as_deref(), }; - gpio_unexport::main(&cfg, &unexport_options); + gpio_unexport::main(&cfg, &options); } - ("unexport-all", Some(m)) => { - let unexportall_options = GpioUnexportAllOptions { - gpio_opts: gpio_options, - symlink_root: m.value_of("symlink-root"), + Commands::UnexportAll { symlink_root } => { + let options = GpioUnexportAllOptions { + gpio_opts, + symlink_root: symlink_root.as_deref(), }; - gpio_unexportall::main(&cfg, &unexportall_options); + gpio_unexportall::main(&cfg, &options); } - ("status", Some(m)) => { - let status_options = GpioStatusOptions { - gpio_opts: gpio_options, - pin: m.value_of("pin"), + Commands::Status { pin } => { + let options = GpioStatusOptions { + gpio_opts, + pin: pin.as_deref(), }; - gpio_status::main(&cfg, &status_options); + gpio_status::main(&cfg, &options); } - _ => {} } }