Initial commit
This commit is contained in:
commit
be4a70102d
5
.cargo/config.toml
Normal file
5
.cargo/config.toml
Normal file
@ -0,0 +1,5 @@
|
||||
[build]
|
||||
target = "x86_64-unknown-mikros"
|
||||
|
||||
[install]
|
||||
root = "../os_build/sysroot"
|
1
.gitignore
vendored
Normal file
1
.gitignore
vendored
Normal file
@ -0,0 +1 @@
|
||||
/target
|
496
Cargo.lock
generated
Normal file
496
Cargo.lock
generated
Normal file
@ -0,0 +1,496 @@
|
||||
# This file is automatically @generated by Cargo.
|
||||
# It is not intended for manual editing.
|
||||
version = 3
|
||||
|
||||
[[package]]
|
||||
name = "atomic-polyfill"
|
||||
version = "1.0.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8cf2bce30dfe09ef0bfaef228b9d414faaf7e563035494d7fe092dba54b300f4"
|
||||
dependencies = [
|
||||
"critical-section",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "autocfg"
|
||||
version = "1.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0c4b4d0bd25bd0b74681c0ad21497610ce1b7c91b1022cd21c80c6fbdd9476b0"
|
||||
|
||||
[[package]]
|
||||
name = "binread"
|
||||
version = "2.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "16598dfc8e6578e9b597d9910ba2e73618385dc9f4b1d43dd92c349d6be6418f"
|
||||
dependencies = [
|
||||
"binread_derive",
|
||||
"rustversion",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "binread_derive"
|
||||
version = "2.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1d9672209df1714ee804b1f4d4f68c8eb2a90b1f7a07acf472f88ce198ef1fed"
|
||||
dependencies = [
|
||||
"either",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.109",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bit_field"
|
||||
version = "0.10.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "dc827186963e592360843fb5ba4b973e145841266c1357f7180c43526f2e5b61"
|
||||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "2.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cf4b9d6a944f767f8e5e0db018570623c85f3d925ac718db4e06d0187adb21c1"
|
||||
|
||||
[[package]]
|
||||
name = "byteorder"
|
||||
version = "1.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b"
|
||||
|
||||
[[package]]
|
||||
name = "cfg-if"
|
||||
version = "1.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
|
||||
|
||||
[[package]]
|
||||
name = "cobs"
|
||||
version = "0.2.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "67ba02a97a2bd10f4b59b25c7973101c79642302776489e030cd13cdab09ed15"
|
||||
|
||||
[[package]]
|
||||
name = "critical-section"
|
||||
version = "1.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7059fff8937831a9ae6f0fe4d658ffabf58f2ca96aa9dec1c889f936f705f216"
|
||||
|
||||
[[package]]
|
||||
name = "derive-try-from-primitive"
|
||||
version = "1.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "302ccf094df1151173bb6f5a2282fcd2f45accd5eae1bdf82dcbfefbc501ad5c"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.109",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "either"
|
||||
version = "1.12.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3dca9240753cf90908d7e4aac30f630662b02aebaa1b58a3cadabdb23385b58b"
|
||||
|
||||
[[package]]
|
||||
name = "embedded-io"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ef1a6892d9eef45c8fa6b9e0086428a2cca8491aca8f787c534a3d6d0bcb3ced"
|
||||
|
||||
[[package]]
|
||||
name = "equivalent"
|
||||
version = "1.0.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5"
|
||||
|
||||
[[package]]
|
||||
name = "hash32"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b0c35f58762feb77d74ebe43bdbc3210f09be9fe6742234d573bacc26ed92b67"
|
||||
dependencies = [
|
||||
"byteorder",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "hashbrown"
|
||||
version = "0.14.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e5274423e17b7c9fc20b6e7e208532f9b19825d82dfd615708b70edd83df41f1"
|
||||
|
||||
[[package]]
|
||||
name = "heapless"
|
||||
version = "0.7.17"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cdc6457c0eb62c71aac4bc17216026d8410337c4126773b9c5daba343f17964f"
|
||||
dependencies = [
|
||||
"atomic-polyfill",
|
||||
"hash32",
|
||||
"rustc_version",
|
||||
"serde",
|
||||
"spin",
|
||||
"stable_deref_trait",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "indexmap"
|
||||
version = "2.2.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "168fb715dda47215e360912c096649d23d58bf392ac62f73919e831745e40f26"
|
||||
dependencies = [
|
||||
"equivalent",
|
||||
"hashbrown",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.155"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "97b3888a4aecf77e811145cadf6eef5901f4782c53886191b2f693f24761847c"
|
||||
|
||||
[[package]]
|
||||
name = "lock_api"
|
||||
version = "0.4.12"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "07af8b9cdd281b7915f413fa73f29ebd5d55d0d3f0155584dade1ff18cea1b17"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
"scopeguard",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "memchr"
|
||||
version = "2.7.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "78ca9ab1a0babb1e7d5695e3530886289c18cf2f87ec19a575a0abdce112e3a3"
|
||||
|
||||
[[package]]
|
||||
name = "parking_lot"
|
||||
version = "0.12.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f1bf18183cf54e8d6059647fc3063646a1801cf30896933ec2311622cc4b9a27"
|
||||
dependencies = [
|
||||
"lock_api",
|
||||
"parking_lot_core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "parking_lot_core"
|
||||
version = "0.9.10"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1e401f977ab385c9e4e3ab30627d6f26d00e2c73eef317493c4ec6d468726cf8"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"libc",
|
||||
"redox_syscall",
|
||||
"smallvec",
|
||||
"windows-targets",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "pci"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"binread",
|
||||
"derive-try-from-primitive",
|
||||
"pci_rpc",
|
||||
"serde",
|
||||
"spin",
|
||||
"syslog_rpc",
|
||||
"toml",
|
||||
"x86_64",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "pci_rpc"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"parking_lot",
|
||||
"postcard",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "postcard"
|
||||
version = "1.0.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a55c51ee6c0db07e68448e336cf8ea4131a620edefebf9893e759b2d793420f8"
|
||||
dependencies = [
|
||||
"cobs",
|
||||
"embedded-io",
|
||||
"heapless",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.85"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "22244ce15aa966053a896d1accb3a6e68469b97c7f33f284b99f0d576879fc23"
|
||||
dependencies = [
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "quote"
|
||||
version = "1.0.36"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0fa76aaf39101c457836aec0ce2316dbdc3ab723cdda1c6bd4e6ad4208acaca7"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "redox_syscall"
|
||||
version = "0.5.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c82cf8cff14456045f55ec4241383baeff27af886adb72ffb2162f99911de0fd"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustc_version"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366"
|
||||
dependencies = [
|
||||
"semver",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustversion"
|
||||
version = "1.0.17"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "955d28af4278de8121b7ebeb796b6a45735dc01436d898801014aced2773a3d6"
|
||||
|
||||
[[package]]
|
||||
name = "scopeguard"
|
||||
version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49"
|
||||
|
||||
[[package]]
|
||||
name = "semver"
|
||||
version = "1.0.23"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "61697e0a1c7e512e84a621326239844a24d8207b4669b41bc18b32ea5cbf988b"
|
||||
|
||||
[[package]]
|
||||
name = "serde"
|
||||
version = "1.0.203"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7253ab4de971e72fb7be983802300c30b5a7f0c2e56fab8abfc6a214307c0094"
|
||||
dependencies = [
|
||||
"serde_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_derive"
|
||||
version = "1.0.203"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "500cbc0ebeb6f46627f50f3f5811ccf6bf00643be300b4c3eabc0ef55dc5b5ba"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 2.0.68",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_spanned"
|
||||
version = "0.6.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "79e674e01f999af37c49f70a6ede167a8a60b2503e56c5599532a65baa5969a0"
|
||||
dependencies = [
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "smallvec"
|
||||
version = "1.13.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3c5e1a9a646d36c3599cd173a41282daf47c44583ad367b8e6837255952e5c67"
|
||||
|
||||
[[package]]
|
||||
name = "spin"
|
||||
version = "0.9.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67"
|
||||
dependencies = [
|
||||
"lock_api",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "stable_deref_trait"
|
||||
version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3"
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "1.0.109"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "2.0.68"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "901fa70d88b9d6c98022e23b4136f9f3e54e4662c3bc1bd1d84a42a9a0f0c1e9"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "syslog_rpc"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"parking_lot",
|
||||
"postcard",
|
||||
"syslog_structs",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "syslog_structs"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "toml"
|
||||
version = "0.8.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6f49eb2ab21d2f26bd6db7bf383edc527a7ebaee412d17af4d40fdccd442f335"
|
||||
dependencies = [
|
||||
"serde",
|
||||
"serde_spanned",
|
||||
"toml_datetime",
|
||||
"toml_edit",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "toml_datetime"
|
||||
version = "0.6.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4badfd56924ae69bcc9039335b2e017639ce3f9b001c393c1b2d1ef846ce2cbf"
|
||||
dependencies = [
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "toml_edit"
|
||||
version = "0.22.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f21c7aaf97f1bd9ca9d4f9e73b0a6c74bd5afef56f2bc931943a6e1c37e04e38"
|
||||
dependencies = [
|
||||
"indexmap",
|
||||
"serde",
|
||||
"serde_spanned",
|
||||
"toml_datetime",
|
||||
"winnow",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "unicode-ident"
|
||||
version = "1.0.12"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b"
|
||||
|
||||
[[package]]
|
||||
name = "volatile"
|
||||
version = "0.4.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "442887c63f2c839b346c192d047a7c87e73d0689c9157b00b53dcc27dd5ea793"
|
||||
|
||||
[[package]]
|
||||
name = "windows-targets"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6f0713a46559409d202e70e28227288446bf7841d3211583a4b53e3f6d96e7eb"
|
||||
dependencies = [
|
||||
"windows_aarch64_gnullvm",
|
||||
"windows_aarch64_msvc",
|
||||
"windows_i686_gnu",
|
||||
"windows_i686_gnullvm",
|
||||
"windows_i686_msvc",
|
||||
"windows_x86_64_gnu",
|
||||
"windows_x86_64_gnullvm",
|
||||
"windows_x86_64_msvc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7088eed71e8b8dda258ecc8bac5fb1153c5cffaf2578fc8ff5d61e23578d3263"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9985fd1504e250c615ca5f281c3f7a6da76213ebd5ccc9561496568a2752afb6"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "88ba073cf16d5372720ec942a8ccbf61626074c6d4dd2e745299726ce8b89670"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnullvm"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "87f4261229030a858f36b459e748ae97545d6f1ec60e5e0d6a3d32e0dc232ee9"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "db3c2bf3d13d5b658be73463284eaf12830ac9a26a90c717b7f771dfe97487bf"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4e4246f76bdeff09eb48875a0fd3e2af6aada79d409d33011886d3e1581517d9"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnullvm"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "852298e482cd67c356ddd9570386e2862b5673c85bd5f88df9ab6802b334c596"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bec47e5bfd1bff0eeaf6d8b485cc1074891a197ab4225d504cb7a1ab88b02bf0"
|
||||
|
||||
[[package]]
|
||||
name = "winnow"
|
||||
version = "0.6.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "59b5e5f6c299a3c7890b876a2a587f3115162487e704907d9b6cd29473052ba1"
|
||||
dependencies = [
|
||||
"memchr",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "x86_64"
|
||||
version = "0.15.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4bc79523af8abf92fb1a970c3e086c5a343f6bcc1a0eb890f575cbb3b45743df"
|
||||
dependencies = [
|
||||
"bit_field",
|
||||
"bitflags",
|
||||
"rustversion",
|
||||
"volatile",
|
||||
]
|
14
Cargo.toml
Normal file
14
Cargo.toml
Normal file
@ -0,0 +1,14 @@
|
||||
[package]
|
||||
name = "pci"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
binread = "2.2.0"
|
||||
derive-try-from-primitive = "1.0.0"
|
||||
pci_rpc = { version = "0.1.0", path = "pci_rpc" }
|
||||
serde = { version = "1.0.203", features = ["derive"] }
|
||||
spin = "0.9.8"
|
||||
syslog_rpc = { version = "0.1.0", path = "../syslog/syslog_rpc" }
|
||||
toml = "0.8.14"
|
||||
x86_64 = "0.15.1"
|
1
pci_rpc/.gitignore
vendored
Normal file
1
pci_rpc/.gitignore
vendored
Normal file
@ -0,0 +1 @@
|
||||
/target
|
306
pci_rpc/Cargo.lock
generated
Normal file
306
pci_rpc/Cargo.lock
generated
Normal file
@ -0,0 +1,306 @@
|
||||
# This file is automatically @generated by Cargo.
|
||||
# It is not intended for manual editing.
|
||||
version = 3
|
||||
|
||||
[[package]]
|
||||
name = "atomic-polyfill"
|
||||
version = "1.0.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8cf2bce30dfe09ef0bfaef228b9d414faaf7e563035494d7fe092dba54b300f4"
|
||||
dependencies = [
|
||||
"critical-section",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "autocfg"
|
||||
version = "1.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0c4b4d0bd25bd0b74681c0ad21497610ce1b7c91b1022cd21c80c6fbdd9476b0"
|
||||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "2.6.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b048fb63fd8b5923fc5aa7b340d8e156aec7ec02f0c78fa8a6ddc2613f6f71de"
|
||||
|
||||
[[package]]
|
||||
name = "byteorder"
|
||||
version = "1.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b"
|
||||
|
||||
[[package]]
|
||||
name = "cfg-if"
|
||||
version = "1.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
|
||||
|
||||
[[package]]
|
||||
name = "cobs"
|
||||
version = "0.2.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "67ba02a97a2bd10f4b59b25c7973101c79642302776489e030cd13cdab09ed15"
|
||||
|
||||
[[package]]
|
||||
name = "critical-section"
|
||||
version = "1.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7059fff8937831a9ae6f0fe4d658ffabf58f2ca96aa9dec1c889f936f705f216"
|
||||
|
||||
[[package]]
|
||||
name = "embedded-io"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ef1a6892d9eef45c8fa6b9e0086428a2cca8491aca8f787c534a3d6d0bcb3ced"
|
||||
|
||||
[[package]]
|
||||
name = "hash32"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b0c35f58762feb77d74ebe43bdbc3210f09be9fe6742234d573bacc26ed92b67"
|
||||
dependencies = [
|
||||
"byteorder",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "heapless"
|
||||
version = "0.7.17"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cdc6457c0eb62c71aac4bc17216026d8410337c4126773b9c5daba343f17964f"
|
||||
dependencies = [
|
||||
"atomic-polyfill",
|
||||
"hash32",
|
||||
"rustc_version",
|
||||
"serde",
|
||||
"spin",
|
||||
"stable_deref_trait",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.155"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "97b3888a4aecf77e811145cadf6eef5901f4782c53886191b2f693f24761847c"
|
||||
|
||||
[[package]]
|
||||
name = "lock_api"
|
||||
version = "0.4.12"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "07af8b9cdd281b7915f413fa73f29ebd5d55d0d3f0155584dade1ff18cea1b17"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
"scopeguard",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "parking_lot"
|
||||
version = "0.12.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f1bf18183cf54e8d6059647fc3063646a1801cf30896933ec2311622cc4b9a27"
|
||||
dependencies = [
|
||||
"lock_api",
|
||||
"parking_lot_core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "parking_lot_core"
|
||||
version = "0.9.10"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1e401f977ab385c9e4e3ab30627d6f26d00e2c73eef317493c4ec6d468726cf8"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"libc",
|
||||
"redox_syscall",
|
||||
"smallvec",
|
||||
"windows-targets",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "pci_rpc"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"parking_lot",
|
||||
"postcard",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "postcard"
|
||||
version = "1.0.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a55c51ee6c0db07e68448e336cf8ea4131a620edefebf9893e759b2d793420f8"
|
||||
dependencies = [
|
||||
"cobs",
|
||||
"embedded-io",
|
||||
"heapless",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.86"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5e719e8df665df0d1c8fbfd238015744736151d4445ec0836b8e628aae103b77"
|
||||
dependencies = [
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "quote"
|
||||
version = "1.0.36"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0fa76aaf39101c457836aec0ce2316dbdc3ab723cdda1c6bd4e6ad4208acaca7"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "redox_syscall"
|
||||
version = "0.5.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2a908a6e00f1fdd0dfd9c0eb08ce85126f6d8bbda50017e74bc4a4b7d4a926a4"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustc_version"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366"
|
||||
dependencies = [
|
||||
"semver",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "scopeguard"
|
||||
version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49"
|
||||
|
||||
[[package]]
|
||||
name = "semver"
|
||||
version = "1.0.23"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "61697e0a1c7e512e84a621326239844a24d8207b4669b41bc18b32ea5cbf988b"
|
||||
|
||||
[[package]]
|
||||
name = "serde"
|
||||
version = "1.0.204"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bc76f558e0cbb2a839d37354c575f1dc3fdc6546b5be373ba43d95f231bf7c12"
|
||||
dependencies = [
|
||||
"serde_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_derive"
|
||||
version = "1.0.204"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e0cd7e117be63d3c3678776753929474f3b04a43a080c744d6b0ae2a8c28e222"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "smallvec"
|
||||
version = "1.13.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3c5e1a9a646d36c3599cd173a41282daf47c44583ad367b8e6837255952e5c67"
|
||||
|
||||
[[package]]
|
||||
name = "spin"
|
||||
version = "0.9.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67"
|
||||
dependencies = [
|
||||
"lock_api",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "stable_deref_trait"
|
||||
version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3"
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "2.0.72"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "dc4b9b9bf2add8093d3f2c0204471e951b2285580335de42f9d2534f3ae7a8af"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "unicode-ident"
|
||||
version = "1.0.12"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b"
|
||||
|
||||
[[package]]
|
||||
name = "windows-targets"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9b724f72796e036ab90c1021d4780d4d3d648aca59e491e6b98e725b84e99973"
|
||||
dependencies = [
|
||||
"windows_aarch64_gnullvm",
|
||||
"windows_aarch64_msvc",
|
||||
"windows_i686_gnu",
|
||||
"windows_i686_gnullvm",
|
||||
"windows_i686_msvc",
|
||||
"windows_x86_64_gnu",
|
||||
"windows_x86_64_gnullvm",
|
||||
"windows_x86_64_msvc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "32a4622180e7a0ec044bb555404c800bc9fd9ec262ec147edd5989ccd0c02cd3"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "09ec2a7bb152e2252b53fa7803150007879548bc709c039df7627cabbd05d469"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8e9b5ad5ab802e97eb8e295ac6720e509ee4c243f69d781394014ebfe8bbfa0b"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnullvm"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0eee52d38c090b3caa76c563b86c3a4bd71ef1a819287c19d586d7334ae8ed66"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66"
|
||||
|
||||
[[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_gnullvm"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.52.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec"
|
8
pci_rpc/Cargo.toml
Normal file
8
pci_rpc/Cargo.toml
Normal file
@ -0,0 +1,8 @@
|
||||
[package]
|
||||
name = "pci_rpc"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
parking_lot = "0.12.3"
|
||||
postcard = { version = "1.0.8", features = ["use-std"] }
|
49
pci_rpc/src/lib.rs
Normal file
49
pci_rpc/src/lib.rs
Normal file
@ -0,0 +1,49 @@
|
||||
#![allow(clippy::result_unit_err)]
|
||||
|
||||
use std::os::mikros::ipc::rpc::{self, IncomingCall};
|
||||
|
||||
use parking_lot::RwLock;
|
||||
|
||||
static SERVER: RwLock<Option<Box<dyn Server>>> = RwLock::new(None);
|
||||
|
||||
const PROTO: u16 = 6;
|
||||
|
||||
pub trait Server: Send + Sync {
|
||||
fn get_bars(&self, bus: u8, dev: u8, func: u8) -> Result<[(bool, u32, u32); 6], ()>;
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
pub struct Client(u64);
|
||||
|
||||
impl Client {
|
||||
pub fn new(pid: u64) -> Self {
|
||||
Self(pid)
|
||||
}
|
||||
|
||||
pub fn get_bars(&self, bus: u8, dev: u8, func: u8) -> Result<[(bool, u32, u32); 6], ()> {
|
||||
postcard::from_bytes(
|
||||
&rpc::send_call(self.0, PROTO, 0, &postcard::to_stdvec(&(bus, dev, func)).unwrap()).get_return(),
|
||||
)
|
||||
.unwrap()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn register_server(server: Box<dyn Server>) {
|
||||
*SERVER.write() = Some(server);
|
||||
rpc::register_callback(PROTO, callback);
|
||||
}
|
||||
|
||||
pub fn unregister_server() {
|
||||
rpc::unregister_callback(PROTO);
|
||||
*SERVER.write() = None;
|
||||
}
|
||||
|
||||
fn callback(call: IncomingCall) {
|
||||
let server_lock = SERVER.read();
|
||||
let server = server_lock.as_ref().unwrap();
|
||||
if call.func == 0 {
|
||||
let (bus, dev, func) = postcard::from_bytes(&call.args).unwrap();
|
||||
let ret = postcard::to_stdvec(&server.get_bars(bus, dev, func)).unwrap();
|
||||
call.send_return(&ret);
|
||||
}
|
||||
}
|
2
rust-toolchain.toml
Normal file
2
rust-toolchain.toml
Normal file
@ -0,0 +1,2 @@
|
||||
[toolchain]
|
||||
channel = "dev-x86_64-unknown-mikros"
|
621
src/device_types.rs
Normal file
621
src/device_types.rs
Normal file
@ -0,0 +1,621 @@
|
||||
use derive_try_from_primitive::TryFromPrimitive;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "class")]
|
||||
pub enum Class {
|
||||
Unclassified(UnclassifiedSub),
|
||||
MassStorage(MassStorageSub),
|
||||
Network(NetworkSub),
|
||||
Display(DisplaySub),
|
||||
Multimedia(MultimediaSub),
|
||||
Memory(MemorySub),
|
||||
Bridge(BridgeSub),
|
||||
Communication(CommunicationSub),
|
||||
BaseSystem(BaseSystemSub),
|
||||
InputDevice(InputDeviceSub),
|
||||
Docking(DockingSub),
|
||||
Processor(ProcessorSub),
|
||||
Serial(SerialSub),
|
||||
Wireless(WirelessSub),
|
||||
Intelligent(IntelligentSub),
|
||||
Satellite(SatelliteSub),
|
||||
Encryption(EncryptionSub),
|
||||
Signal(SignalSub),
|
||||
Accelerator,
|
||||
NonEssential,
|
||||
CoProcessor,
|
||||
Unassigned,
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct InvalidClass;
|
||||
|
||||
impl From<u8> for InvalidClass {
|
||||
fn from(_: u8) -> Self {
|
||||
InvalidClass {}
|
||||
}
|
||||
}
|
||||
|
||||
impl Class {
|
||||
pub fn new(class: u8, subclass: u8, progif: u8) -> Result<Self, InvalidClass> {
|
||||
match class {
|
||||
0 => Ok(Class::Unclassified(UnclassifiedSub::new(subclass)?)),
|
||||
1 => Ok(Class::MassStorage(MassStorageSub::new(subclass, progif)?)),
|
||||
2 => Ok(Class::Network(NetworkSub::try_from(subclass)?)),
|
||||
3 => Ok(Class::Display(DisplaySub::new(subclass, progif)?)),
|
||||
4 => Ok(Class::Multimedia(MultimediaSub::try_from(subclass)?)),
|
||||
5 => Ok(Class::Memory(MemorySub::try_from(subclass)?)),
|
||||
6 => Ok(Class::Bridge(BridgeSub::new(subclass, progif)?)),
|
||||
7 => Ok(Class::Communication(CommunicationSub::new(
|
||||
subclass, progif,
|
||||
)?)),
|
||||
8 => Ok(Class::BaseSystem(BaseSystemSub::new(subclass, progif)?)),
|
||||
9 => Ok(Class::InputDevice(InputDeviceSub::new(subclass, progif)?)),
|
||||
10 => Ok(Class::Docking(DockingSub::try_from(subclass)?)),
|
||||
11 => Ok(Class::Processor(ProcessorSub::try_from(subclass)?)),
|
||||
12 => Ok(Class::Serial(SerialSub::new(subclass, progif)?)),
|
||||
13 => Ok(Class::Wireless(WirelessSub::try_from(subclass)?)),
|
||||
14 => Ok(Class::Intelligent(IntelligentSub::try_from(subclass)?)),
|
||||
15 => Ok(Class::Satellite(SatelliteSub::try_from(subclass)?)),
|
||||
16 => Ok(Class::Encryption(EncryptionSub::try_from(subclass)?)),
|
||||
17 => Ok(Class::Signal(SignalSub::try_from(subclass)?)),
|
||||
18 => Ok(Class::Accelerator),
|
||||
19 => Ok(Class::NonEssential),
|
||||
0x40 => Ok(Class::CoProcessor),
|
||||
0xFF => Ok(Class::Unassigned),
|
||||
_ => Err(InvalidClass {}),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum UnclassifiedSub {
|
||||
NonVGACompat,
|
||||
VGACompat,
|
||||
}
|
||||
|
||||
impl UnclassifiedSub {
|
||||
fn new(subclass: u8) -> Result<Self, InvalidClass> {
|
||||
match subclass {
|
||||
0 => Ok(Self::NonVGACompat),
|
||||
1 => Ok(Self::VGACompat),
|
||||
_ => Err(InvalidClass),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum MassStorageSub {
|
||||
SCSI,
|
||||
IDE(IDEProg),
|
||||
Floppy,
|
||||
IPI,
|
||||
RAID,
|
||||
ATA(ATAProg),
|
||||
SATA(SATAProg),
|
||||
SAS(SASProg),
|
||||
NVM(NVMProg),
|
||||
Other,
|
||||
}
|
||||
|
||||
impl MassStorageSub {
|
||||
fn new(subclass: u8, progif: u8) -> Result<Self, InvalidClass> {
|
||||
match subclass {
|
||||
0 => Ok(Self::SCSI),
|
||||
1 => Ok(Self::IDE(IDEProg::try_from(progif)?)),
|
||||
2 => Ok(Self::Floppy),
|
||||
3 => Ok(Self::IPI),
|
||||
4 => Ok(Self::RAID),
|
||||
5 => Ok(Self::ATA(ATAProg::try_from(progif)?)),
|
||||
6 => Ok(Self::SATA(SATAProg::try_from(progif)?)),
|
||||
7 => Ok(Self::SAS(SASProg::try_from(progif)?)),
|
||||
8 => Ok(Self::NVM(NVMProg::try_from(progif)?)),
|
||||
0x80 => Ok(Self::Other),
|
||||
_ => Err(InvalidClass),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive, Debug)]
|
||||
#[repr(u8)]
|
||||
#[derive(Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum IDEProg {
|
||||
ISACompatOnly = 0,
|
||||
PCINativeOnly = 5,
|
||||
ISACompatPCISwitch = 0xA,
|
||||
PCINativeISASwitch = 0xF,
|
||||
ISANativeOnlyBusMaster = 0x80,
|
||||
PCINativeOnlyBusMaster = 0x85,
|
||||
ISACompatPCISwitchBusMaster = 0x8A,
|
||||
PCINativeISASwitchBusMaster = 0x8F,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive, Debug)]
|
||||
#[repr(u8)]
|
||||
#[derive(Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum ATAProg {
|
||||
SingleDMA = 0x20,
|
||||
ChainedDMA = 0x30,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive, Debug)]
|
||||
#[repr(u8)]
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum SATAProg {
|
||||
VendorSpecific = 0,
|
||||
AHCI1 = 1,
|
||||
SSB = 2,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive, Debug)]
|
||||
#[repr(u8)]
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum SASProg {
|
||||
SAS = 0,
|
||||
SSB = 1,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive, Debug)]
|
||||
#[repr(u8)]
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum NVMProg {
|
||||
NVMHCI = 1,
|
||||
NVME = 2,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive, Debug)]
|
||||
#[repr(u8)]
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum NetworkSub {
|
||||
Ethernet = 0,
|
||||
TokenRing = 1,
|
||||
FDDI = 2,
|
||||
ATM = 3,
|
||||
ISDN = 4,
|
||||
WorldFip = 5,
|
||||
PICMG214 = 6,
|
||||
Infiniband = 7,
|
||||
Fabric = 8,
|
||||
Other = 0x80,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum DisplaySub {
|
||||
VGACompat(VGACompatProg),
|
||||
XGA,
|
||||
ThreeD,
|
||||
Other,
|
||||
}
|
||||
|
||||
impl DisplaySub {
|
||||
fn new(subclass: u8, progif: u8) -> Result<Self, InvalidClass> {
|
||||
match subclass {
|
||||
0 => Ok(Self::VGACompat(VGACompatProg::try_from(progif)?)),
|
||||
1 => Ok(Self::XGA),
|
||||
2 => Ok(Self::ThreeD),
|
||||
0x80 => Ok(Self::Other),
|
||||
_ => Err(InvalidClass),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum VGACompatProg {
|
||||
VGA = 0,
|
||||
Compat8154 = 1,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum MultimediaSub {
|
||||
Video = 0,
|
||||
MultimediaAudio = 1,
|
||||
Telephony = 2,
|
||||
Audio = 3,
|
||||
Other = 0x80,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum MemorySub {
|
||||
RAM = 0,
|
||||
Flash = 1,
|
||||
Other = 0x80,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum BridgeSub {
|
||||
Host,
|
||||
ISA,
|
||||
EISA,
|
||||
MCA,
|
||||
PCItoPCI1(PCItoPCI1Prog),
|
||||
PCMCIA,
|
||||
NuBus,
|
||||
CardBus,
|
||||
RACEway(RACEwayProg),
|
||||
PCItoPCI2(PCItoPCI2Prog),
|
||||
InfinibandtoPCIHost,
|
||||
Other,
|
||||
}
|
||||
|
||||
impl BridgeSub {
|
||||
fn new(subclass: u8, progif: u8) -> Result<Self, InvalidClass> {
|
||||
match subclass {
|
||||
0 => Ok(Self::Host),
|
||||
1 => Ok(Self::ISA),
|
||||
2 => Ok(Self::EISA),
|
||||
3 => Ok(Self::MCA),
|
||||
4 => Ok(Self::PCItoPCI1(PCItoPCI1Prog::try_from(progif)?)),
|
||||
5 => Ok(Self::PCMCIA),
|
||||
6 => Ok(Self::NuBus),
|
||||
7 => Ok(Self::CardBus),
|
||||
8 => Ok(Self::RACEway(RACEwayProg::try_from(progif)?)),
|
||||
9 => Ok(Self::PCItoPCI2(PCItoPCI2Prog::try_from(progif)?)),
|
||||
0xA => Ok(Self::InfinibandtoPCIHost),
|
||||
0x80 => Ok(Self::Other),
|
||||
_ => Err(InvalidClass),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum PCItoPCI1Prog {
|
||||
NormalDecode,
|
||||
SubtractiveDecode,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum RACEwayProg {
|
||||
TransparentMode,
|
||||
EndpointMode,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum PCItoPCI2Prog {
|
||||
PrimaryHost = 0x40,
|
||||
SecondaryHost = 0x80,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum CommunicationSub {
|
||||
Serial(SerialProg),
|
||||
Parallel(ParallelProg),
|
||||
MultiportSerial,
|
||||
Modem(ModemProg),
|
||||
GPIB,
|
||||
SmartCard,
|
||||
Other,
|
||||
}
|
||||
|
||||
impl CommunicationSub {
|
||||
fn new(subclass: u8, progif: u8) -> Result<Self, InvalidClass> {
|
||||
match subclass {
|
||||
0 => Ok(Self::Serial(SerialProg::try_from(progif)?)),
|
||||
1 => Ok(Self::Parallel(ParallelProg::try_from(progif)?)),
|
||||
2 => Ok(Self::MultiportSerial),
|
||||
3 => Ok(Self::Modem(ModemProg::try_from(progif)?)),
|
||||
4 => Ok(Self::GPIB),
|
||||
5 => Ok(Self::SmartCard),
|
||||
0x80 => Ok(Self::Other),
|
||||
_ => Err(InvalidClass),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum SerialProg {
|
||||
Compat8250,
|
||||
Compat16450,
|
||||
Compat16550,
|
||||
Compat16650,
|
||||
Compat16750,
|
||||
Compat16850,
|
||||
Compat16950,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum ParallelProg {
|
||||
Standard = 0,
|
||||
Bidirectional = 1,
|
||||
ECP1 = 2,
|
||||
IEE1284Controller = 3,
|
||||
IEE1284TargetDevice = 0xFE,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum ModemProg {
|
||||
Generic,
|
||||
HAyes16450Compat,
|
||||
HAyes16550Compat,
|
||||
HAyes16650Compat,
|
||||
HAyes16750Compat,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum BaseSystemSub {
|
||||
Pic(PicProg),
|
||||
DMA(DMAProg),
|
||||
Timer(TimerProg),
|
||||
RTC(RTCProg),
|
||||
PCIHotPlug,
|
||||
SDHost,
|
||||
IOMMU,
|
||||
Other,
|
||||
}
|
||||
|
||||
impl BaseSystemSub {
|
||||
fn new(subclass: u8, progif: u8) -> Result<Self, InvalidClass> {
|
||||
match subclass {
|
||||
0 => Ok(Self::Pic(PicProg::try_from(progif)?)),
|
||||
1 => Ok(Self::DMA(DMAProg::try_from(progif)?)),
|
||||
2 => Ok(Self::Timer(TimerProg::try_from(progif)?)),
|
||||
3 => Ok(Self::RTC(RTCProg::try_from(progif)?)),
|
||||
4 => Ok(Self::PCIHotPlug),
|
||||
5 => Ok(Self::SDHost),
|
||||
6 => Ok(Self::IOMMU),
|
||||
0x80 => Ok(Self::Other),
|
||||
_ => Err(InvalidClass),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum PicProg {
|
||||
Generic8259Compat = 0,
|
||||
ISACompat = 1,
|
||||
EISACompat = 2,
|
||||
IOAPIC = 0x10,
|
||||
IOxAPIC = 0x20,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum DMAProg {
|
||||
Generic8237,
|
||||
ISA,
|
||||
EISA,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum TimerProg {
|
||||
Generic8234Compat,
|
||||
ISACompat,
|
||||
EISACompat,
|
||||
HPET,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum RTCProg {
|
||||
Generic,
|
||||
ISACompat,
|
||||
}
|
||||
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum InputDeviceSub {
|
||||
Keyboard,
|
||||
DigitizerPen,
|
||||
Mouse,
|
||||
Scanner,
|
||||
Gameport(GameportProg),
|
||||
Other,
|
||||
}
|
||||
|
||||
impl InputDeviceSub {
|
||||
fn new(subclass: u8, progif: u8) -> Result<Self, InvalidClass> {
|
||||
match subclass {
|
||||
0 => Ok(Self::Keyboard),
|
||||
1 => Ok(Self::DigitizerPen),
|
||||
2 => Ok(Self::Mouse),
|
||||
3 => Ok(Self::Scanner),
|
||||
4 => Ok(Self::Gameport(GameportProg::try_from(progif)?)),
|
||||
0x80 => Ok(Self::Other),
|
||||
_ => Err(InvalidClass),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum GameportProg {
|
||||
Generic = 0,
|
||||
Extended = 0x10,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum DockingSub {
|
||||
Generic = 0,
|
||||
Other = 0x80,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum ProcessorSub {
|
||||
I386 = 0,
|
||||
I486 = 1,
|
||||
Pentium = 2,
|
||||
PentiumPro = 3,
|
||||
Alpha = 0x10,
|
||||
PowerPC = 0x20,
|
||||
MIPS = 0x30,
|
||||
CoProcessor = 0x40,
|
||||
Other = 0x80,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum SerialSub {
|
||||
FireWire(FireWireProg),
|
||||
ACCESS,
|
||||
SSA,
|
||||
USB(USBProg),
|
||||
FibreChannel,
|
||||
SMBus,
|
||||
InfiniBand,
|
||||
IPMI(IPMIProg),
|
||||
SERCOS,
|
||||
CANbus,
|
||||
Other,
|
||||
}
|
||||
|
||||
impl SerialSub {
|
||||
fn new(subclass: u8, progif: u8) -> Result<Self, InvalidClass> {
|
||||
match subclass {
|
||||
0 => Ok(Self::FireWire(FireWireProg::try_from(progif)?)),
|
||||
1 => Ok(Self::ACCESS),
|
||||
2 => Ok(Self::SSA),
|
||||
3 => Ok(Self::USB(USBProg::try_from(progif)?)),
|
||||
4 => Ok(Self::FibreChannel),
|
||||
5 => Ok(Self::SMBus),
|
||||
6 => Ok(Self::InfiniBand),
|
||||
7 => Ok(Self::IPMI(IPMIProg::try_from(progif)?)),
|
||||
8 => Ok(Self::SERCOS),
|
||||
9 => Ok(Self::CANbus),
|
||||
0x80 => Ok(Self::Other),
|
||||
_ => Err(InvalidClass),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum FireWireProg {
|
||||
Generic = 0,
|
||||
OHCI = 0x10,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum USBProg {
|
||||
UHCI = 0,
|
||||
OHCI = 0x10,
|
||||
EHCI = 0x20,
|
||||
XHCI = 0x30,
|
||||
Unspecified = 0x80,
|
||||
Device = 0xFE,
|
||||
}
|
||||
|
||||
#[allow(clippy::upper_case_acronyms)]
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum IPMIProg {
|
||||
SMIC,
|
||||
Keyboard,
|
||||
BlockTransfer,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum WirelessSub {
|
||||
IRDACompat = 0,
|
||||
ConsumerIR = 1,
|
||||
RF = 0x10,
|
||||
Bluetooth = 0x11,
|
||||
Broadband = 0x12,
|
||||
Ethernet80211a = 0x20,
|
||||
Ethernet80211b = 0x21,
|
||||
Other = 0x80,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum IntelligentSub {
|
||||
I20 = 0,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum SatelliteSub {
|
||||
TV,
|
||||
Audio,
|
||||
Voice,
|
||||
Data,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum EncryptionSub {
|
||||
NetworkAndComputing = 0,
|
||||
Entertainment = 0x10,
|
||||
Other = 0x80,
|
||||
}
|
||||
|
||||
#[derive(TryFromPrimitive)]
|
||||
#[repr(u8)]
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq, Eq, Copy, Clone)]
|
||||
#[serde(tag = "subclass", content = "progif")]
|
||||
pub enum SignalSub {
|
||||
DPIOModule = 0,
|
||||
PerformanceCounter = 1,
|
||||
CommunicationSynchronizer = 0x10,
|
||||
SignalProcessingManagement = 0x20,
|
||||
Other = 0x80,
|
||||
}
|
418
src/main.rs
Normal file
418
src/main.rs
Normal file
@ -0,0 +1,418 @@
|
||||
#![allow(clippy::verbose_bit_mask)]
|
||||
use std::{
|
||||
fs,
|
||||
io::Cursor,
|
||||
os::mikros::{ipc, syscalls},
|
||||
path::{Path, PathBuf},
|
||||
};
|
||||
|
||||
use binread::prelude::*;
|
||||
use device_types::{Class, InvalidClass};
|
||||
use pci_rpc::Server;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use spin::Mutex;
|
||||
use x86_64::instructions::port::{Port, PortWriteOnly};
|
||||
|
||||
pub mod device_types;
|
||||
|
||||
static CONFIG_PORT: Mutex<PortWriteOnly<u32>> = Mutex::new(PortWriteOnly::new(0xCF8));
|
||||
static DATA_PORT: Mutex<Port<u32>> = Mutex::new(Port::new(0xCFC));
|
||||
|
||||
#[derive(Debug, Copy, Clone)]
|
||||
struct ConfigAccessor(u32);
|
||||
|
||||
impl ConfigAccessor {
|
||||
pub fn new(bus: u8, device: u8, function: u8) -> Self {
|
||||
assert!(device < 32);
|
||||
assert!(function < 8);
|
||||
Self(
|
||||
(u32::from(bus) << 16)
|
||||
| (u32::from(device) << 11)
|
||||
| (u32::from(function) << 8)
|
||||
| 0x8000_0000,
|
||||
)
|
||||
}
|
||||
|
||||
fn read(self, index: u8) -> u32 {
|
||||
assert!(index < 64);
|
||||
let register = index * 4;
|
||||
unsafe { CONFIG_PORT.lock().write(self.0 | u32::from(register)) }
|
||||
|
||||
unsafe { DATA_PORT.lock().read() }
|
||||
}
|
||||
|
||||
fn write(self, index: u8, data: u32) {
|
||||
assert!(index < 64);
|
||||
let register = index * 4;
|
||||
unsafe { CONFIG_PORT.lock().write(self.0 | u32::from(register)) }
|
||||
|
||||
unsafe { DATA_PORT.lock().write(data) }
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Copy, Clone)]
|
||||
pub struct InvalidHeaderType;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct ConfigRaw {
|
||||
pub data: [u8; 256],
|
||||
}
|
||||
|
||||
impl ConfigRaw {
|
||||
pub fn new(bus: u8, device: u8, function: u8) -> Self {
|
||||
let accessor = ConfigAccessor::new(bus, device, function);
|
||||
let mut data = [0; 256];
|
||||
for reg_num in 0..32 {
|
||||
let reg = accessor.read(reg_num);
|
||||
for (i, &byte) in reg.to_le_bytes().iter().enumerate() {
|
||||
data[usize::from(reg_num) * 4 + i] = byte;
|
||||
}
|
||||
}
|
||||
ConfigRaw { data }
|
||||
}
|
||||
|
||||
pub fn common(&self) -> ConfigCommon {
|
||||
Cursor::new(&self.data)
|
||||
.read_le()
|
||||
.expect("Unable to parse PCI device common config")
|
||||
}
|
||||
|
||||
pub fn config(&self) -> Result<ConfigTypeSpecific, InvalidHeaderType> {
|
||||
match Cursor::new(&self.data).read_le() {
|
||||
Ok(cfg) => Ok(cfg),
|
||||
Err(binread::Error::NoVariantMatch { pos: _ }) => Err(InvalidHeaderType),
|
||||
Err(err) => Err(err).expect("Only NoVariantMatch should be possible"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Copy, Clone, BinRead)]
|
||||
#[repr(C)]
|
||||
pub struct ConfigCommon {
|
||||
pub vendor_id: u16,
|
||||
pub device_id: u16,
|
||||
pub command: u16,
|
||||
pub status: u16,
|
||||
pub rev_id: u8,
|
||||
pub prog_if: u8,
|
||||
pub subclass: u8,
|
||||
pub class_code: u8,
|
||||
pub cache_line_size: u8,
|
||||
pub lat_timer: u8,
|
||||
pub header_type: u8,
|
||||
pub bist: u8,
|
||||
}
|
||||
|
||||
impl ConfigCommon {
|
||||
fn class(&self) -> Result<Class, InvalidClass> {
|
||||
Class::new(self.class_code, self.subclass, self.prog_if)
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Copy, Clone, BinRead)]
|
||||
pub enum ConfigTypeSpecific {
|
||||
Type0(ConfigType0),
|
||||
Type1(ConfigType1),
|
||||
Type2(ConfigType2),
|
||||
}
|
||||
|
||||
#[derive(Debug, Copy, Clone, BinRead)]
|
||||
#[repr(C)]
|
||||
pub struct ConfigType0 {
|
||||
pub vendor_id: u16,
|
||||
pub device_id: u16,
|
||||
pub command: u16,
|
||||
pub status: u16,
|
||||
pub rev_id: u8,
|
||||
pub prog_if: u8,
|
||||
pub subclass: u8,
|
||||
pub class_code: u8,
|
||||
pub cache_line_size: u8,
|
||||
pub lat_timer: u8,
|
||||
#[br(assert(header_type & 0x7F == 0))]
|
||||
pub header_type: u8,
|
||||
pub bist: u8,
|
||||
pub bars: [u32; 6],
|
||||
pub cardbus_cis: u32,
|
||||
pub sub_sys_vendor_id: u16,
|
||||
pub sub_sys_id: u16,
|
||||
pub exp_rom_base: u32,
|
||||
pub cap_ptr: u8,
|
||||
reserved: [u8; 7],
|
||||
pub int_line: u8,
|
||||
pub int_pin: u8,
|
||||
pub min_grant: u8,
|
||||
pub max_latency: u8,
|
||||
}
|
||||
|
||||
#[derive(Debug, Copy, Clone, BinRead)]
|
||||
#[repr(C)]
|
||||
pub struct ConfigType1 {
|
||||
pub vendor_id: u16,
|
||||
pub device_id: u16,
|
||||
pub command: u16,
|
||||
pub status: u16,
|
||||
pub rev_id: u8,
|
||||
pub prog_if: u8,
|
||||
pub subclass: u8,
|
||||
pub class_code: u8,
|
||||
pub cache_line_size: u8,
|
||||
pub lat_timer: u8,
|
||||
#[br(assert(header_type & 0x7F == 1))]
|
||||
pub header_type: u8,
|
||||
pub bist: u8,
|
||||
pub bars: [u32; 2],
|
||||
pub prim_bus_num: u8,
|
||||
pub sec_bus_num: u8,
|
||||
pub sub_bus_num: u8,
|
||||
pub sec_latency_timer: u8,
|
||||
pub io_base: u8,
|
||||
pub io_limit: u8,
|
||||
pub sec_status: u16,
|
||||
pub mem_base: u16,
|
||||
pub mem_limit: u16,
|
||||
pub prefetch_mem_base: u16,
|
||||
pub prefetch_mem_limit: u16,
|
||||
pub prefetch_mem_base_upper32: u32,
|
||||
pub prefetch_mem_limit_upper32: u32,
|
||||
pub io_base_upper16: u16,
|
||||
pub io_limit_upper16: u16,
|
||||
pub cap_ptr: u8,
|
||||
reserved: [u8; 3],
|
||||
pub exp_rom_base: u32,
|
||||
pub int_line: u8,
|
||||
pub int_pin: u8,
|
||||
pub bridge_control: u16,
|
||||
}
|
||||
|
||||
#[derive(Debug, Copy, Clone, BinRead)]
|
||||
#[repr(C)]
|
||||
#[repr(packed)]
|
||||
pub struct ConfigType2 {
|
||||
pub vendor_id: u16,
|
||||
pub device_id: u16,
|
||||
pub command: u16,
|
||||
pub status: u16,
|
||||
pub rev_id: u8,
|
||||
pub prog_if: u8,
|
||||
pub subclass: u8,
|
||||
pub class_code: u8,
|
||||
pub cache_line_size: u8,
|
||||
pub lat_timer: u8,
|
||||
#[br(assert(header_type & 0x7F == 2))]
|
||||
pub header_type: u8,
|
||||
pub bist: u8,
|
||||
pub cap_ptr: u8,
|
||||
reserved: u8,
|
||||
pub sec_status: u16,
|
||||
pub mem_base_0: u32,
|
||||
pub mem_limit_0: u32,
|
||||
pub mem_base_1: u32,
|
||||
pub mem_limit_1: u32,
|
||||
pub io_base_0: u32,
|
||||
pub io_limit_0: u32,
|
||||
pub io_base_1: u32,
|
||||
pub io_limit_1: u32,
|
||||
pub int_line: u8,
|
||||
pub int_pin: u8,
|
||||
pub bridge_control: u16,
|
||||
pub sub_sys_vendor_id: u16,
|
||||
pub sub_sys_id: u16,
|
||||
pub legacy_card_base: u32,
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
pub struct Device {
|
||||
pub bus: u8,
|
||||
pub device: u8,
|
||||
pub function: u8,
|
||||
pub common: ConfigCommon,
|
||||
pub type_specific: ConfigTypeSpecific,
|
||||
pub class: Class,
|
||||
}
|
||||
|
||||
#[derive(Serialize, Deserialize, Debug)]
|
||||
struct DriverConfig {
|
||||
mappings: Vec<DriverMapping>,
|
||||
}
|
||||
|
||||
#[derive(Serialize, Deserialize, Debug)]
|
||||
#[serde(tag = "type")]
|
||||
enum DriverMapping {
|
||||
GenericClass {
|
||||
#[serde(flatten)]
|
||||
class: Class,
|
||||
vend_dev_exclude: Option<Vec<(u16, u16)>>,
|
||||
path: PathBuf,
|
||||
},
|
||||
VendDev {
|
||||
list: Vec<(u16, u16)>,
|
||||
path: PathBuf,
|
||||
},
|
||||
}
|
||||
|
||||
impl DriverMapping {
|
||||
fn path(&self) -> &Path {
|
||||
match self {
|
||||
Self::GenericClass { path, .. } => path,
|
||||
Self::VendDev { path, .. } => path,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn scan_bus(bus: u8, device_vec: &mut Vec<Device>) {
|
||||
for device in 0..32 {
|
||||
scan_device(bus, device, device_vec);
|
||||
}
|
||||
}
|
||||
|
||||
fn scan_device(bus: u8, device: u8, device_vec: &mut Vec<Device>) {
|
||||
let func0cfg = ConfigRaw::new(bus, device, 0);
|
||||
if func0cfg.common().vendor_id == 0xFFFF {
|
||||
return;
|
||||
}
|
||||
let header_type = func0cfg.common().header_type;
|
||||
found_function(bus, device, 0, &func0cfg, device_vec);
|
||||
if (header_type & 0x80) != 0 {
|
||||
for func in 1..8 {
|
||||
let cfg = ConfigRaw::new(bus, device, func);
|
||||
if cfg.common().vendor_id != 0xFFFF {
|
||||
found_function(bus, device, func, &cfg, device_vec);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn found_function(
|
||||
bus: u8,
|
||||
device: u8,
|
||||
function: u8,
|
||||
cfg: &ConfigRaw,
|
||||
device_vec: &mut Vec<Device>,
|
||||
) {
|
||||
let type_specific = if let Ok(type_specific) = cfg.config() {
|
||||
type_specific
|
||||
} else {
|
||||
return;
|
||||
};
|
||||
let class = if let Ok(class) = cfg.common().class() {
|
||||
class
|
||||
} else {
|
||||
return;
|
||||
};
|
||||
let device = Device {
|
||||
bus,
|
||||
device,
|
||||
function,
|
||||
common: cfg.common(),
|
||||
type_specific,
|
||||
class,
|
||||
};
|
||||
device_vec.push(device);
|
||||
}
|
||||
|
||||
struct PCIServer(Vec<Device>);
|
||||
|
||||
impl Server for PCIServer {
|
||||
fn get_bars(&self, bus: u8, dev_no: u8, func: u8) -> Result<[(bool, u32, u32); 6], ()> {
|
||||
let device = self
|
||||
.0
|
||||
.iter()
|
||||
.find(|dev| dev.bus == bus && dev.device == dev_no && dev.function == func)
|
||||
.ok_or(())?;
|
||||
match device.type_specific {
|
||||
ConfigTypeSpecific::Type0(hdr) => {
|
||||
let accessor = ConfigAccessor::new(bus, dev_no, func);
|
||||
let mut res: [(bool, u32, u32); 6] = [(false, 0, 0); 6];
|
||||
for (i, bar) in hdr.bars.iter().copied().enumerate() {
|
||||
let bar_idx = (i + 0x4) as u8;
|
||||
accessor.write(bar_idx, 0xFFFF_FFFF);
|
||||
let bar_tmp = accessor.read(bar_idx);
|
||||
let info_bits = if bar & 0x1 == 1 {
|
||||
bar_tmp & !0x3
|
||||
} else {
|
||||
bar_tmp & !0xF
|
||||
};
|
||||
let size = !(info_bits) + 1;
|
||||
accessor.write(bar_idx, bar);
|
||||
if bar & 0x1 == 1 {
|
||||
res[i] = (true, bar & !0x3, size);
|
||||
} else {
|
||||
res[i] = (false, bar & !0xF, size);
|
||||
};
|
||||
}
|
||||
Ok(res)
|
||||
}
|
||||
ConfigTypeSpecific::Type1(_) => Err(()),
|
||||
ConfigTypeSpecific::Type2(_) => Err(()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let config: DriverConfig =
|
||||
toml::from_str(&fs::read_to_string("/etc/pci_config").unwrap()).unwrap();
|
||||
let syslog_pid = loop {
|
||||
if let Some(pid) = syscalls::try_get_registered(2) {
|
||||
break pid;
|
||||
}
|
||||
};
|
||||
let syslog_client = syslog_rpc::Client::new(syslog_pid);
|
||||
let mut device_vec = Vec::new();
|
||||
scan_bus(0, &mut device_vec);
|
||||
let srv = PCIServer(device_vec.clone());
|
||||
pci_rpc::register_server(Box::new(srv));
|
||||
for device in &device_vec {
|
||||
syslog_client.send_text_message(
|
||||
"pci",
|
||||
format!(
|
||||
"Bus {}, device {}, function {}: Type {:?}, Vendor ID {:#x}, Device ID {:#x}, Header type {}",
|
||||
device.bus,
|
||||
device.device,
|
||||
device.function,
|
||||
device.class,
|
||||
device.common.vendor_id,
|
||||
device.common.device_id,
|
||||
device.common.header_type,
|
||||
)
|
||||
).unwrap();
|
||||
let driver = config
|
||||
.mappings
|
||||
.iter()
|
||||
.find(|mapping| match mapping {
|
||||
DriverMapping::GenericClass {
|
||||
class,
|
||||
vend_dev_exclude,
|
||||
..
|
||||
} => {
|
||||
&device.class == class
|
||||
&& !vend_dev_exclude.as_ref().map_or(false, |x| {
|
||||
x.contains(&(device.common.vendor_id, device.common.device_id))
|
||||
})
|
||||
}
|
||||
DriverMapping::VendDev { list, .. } => {
|
||||
list.contains(&(device.common.vendor_id, device.common.device_id))
|
||||
}
|
||||
})
|
||||
.map(|mapping| mapping.path());
|
||||
if let Some(driver) = driver {
|
||||
syslog_client
|
||||
.send_text_message("pci", format!(" Driver {}", driver.display()))
|
||||
.unwrap();
|
||||
std::process::Command::new(driver)
|
||||
.arg(device.bus.to_string())
|
||||
.arg(device.device.to_string())
|
||||
.arg(device.function.to_string())
|
||||
.arg(syscalls::get_pid().to_string())
|
||||
.spawn()
|
||||
.unwrap();
|
||||
} else {
|
||||
syslog_client
|
||||
.send_text_message("pci", " WARN: No driver")
|
||||
.unwrap();
|
||||
}
|
||||
}
|
||||
loop {
|
||||
ipc::process_messages();
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user