27 Commits

Author SHA1 Message Date
3268b07ad9 use static cell instead of custom struct 2025-02-07 16:14:41 +01:00
1a1d330814 Merge pull request 'update some outdated dependencies' (#219) from update-outdated-deps into main
Reviewed-on: #219
2025-01-31 18:37:49 +01:00
ef7b5d66fe update some outdated dependencies 2025-01-31 18:37:12 +01:00
b3497e0592 Merge pull request 'update embedded examples' (#218) from update-embedded-examples into main
Reviewed-on: #218
2025-01-31 18:32:41 +01:00
73286e36c2 update embedded examples 2025-01-31 18:20:06 +01:00
ed266a11f6 Merge pull request 'Avoid static muts for static pool buffer declaration' (#215) from avoid-static-muts-static-pools into main
Reviewed-on: #215
2025-01-31 12:12:57 +01:00
af972e174f macro fix 2025-01-31 12:04:40 +01:00
3d12083c16 use full path to helper type 2025-01-31 11:56:38 +01:00
e8d2c020fa Merge pull request 'use released nexosim version' (#217) from use-released-nexosim into main
Reviewed-on: #217
2025-01-31 11:33:56 +01:00
69e172b633 avoid static muts for static pools 2025-01-31 11:27:09 +01:00
e1dda751bc use released nexosim version 2025-01-31 11:24:56 +01:00
b01628d8ef Merge pull request 'fix minisim tests' (#216) from update-minisim into main
Reviewed-on: #216
2025-01-31 11:18:03 +01:00
31844e4fe2 fix tests 2025-01-31 11:17:39 +01:00
738872f421 Merge pull request 'update mini simulator' (#214) from update-minisim into main
Reviewed-on: #214
2025-01-30 18:57:27 +01:00
309e39999f small tweak 2025-01-30 18:56:44 +01:00
1c43c3adf9 update mini simulator 2025-01-30 18:55:47 +01:00
d9e0abffa7 Merge pull request 'clippy and test fix' (#213) from clippy-fixes into main
Reviewed-on: #213
2025-01-23 17:22:46 +01:00
abec9dd448 clippy and test fix 2025-01-23 17:19:26 +01:00
c18fbb59ad Merge pull request 're-run formatter' (#212) from run-afmt into main
Reviewed-on: #212
2025-01-23 17:04:58 +01:00
c91ddcd658 re-run formatter 2025-01-23 17:02:16 +01:00
c5fa1955d7 Merge pull request 'Scheduling Table for std runtimes' (#210) from scheduling-table into main
Reviewed-on: #210
2024-11-20 17:22:08 +01:00
c9708810e6 changelog 2024-11-20 17:21:54 +01:00
79d0c2e222 Scheduling Table for std runtimes 2024-11-20 17:20:42 +01:00
8e87875c0e Merge pull request 'use released satrs-shared' (#209) from use-released-satrs-shared into main
Reviewed-on: #209
2024-11-15 12:15:06 +01:00
1ac6c02c06 use released satrs-shared 2024-11-15 12:14:33 +01:00
6e7907522e Merge pull request 'changelog satrs-shared' (#208) from satrs-shared-changelog into main
Reviewed-on: #208
2024-11-15 12:08:27 +01:00
f747a5efdc changelog satrs-shared 2024-11-15 12:07:32 +01:00
34 changed files with 1037 additions and 599 deletions

View File

@@ -10,5 +10,5 @@ members = [
exclude = [
"embedded-examples/stm32f3-disco-rtic",
"embedded-examples/stm32h7-rtic",
"embedded-examples/stm32h7-nucleo-rtic",
]

View File

@@ -1,6 +1,6 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 3
version = 4
[[package]]
name = "accelerometer"
@@ -11,20 +11,11 @@ dependencies = [
"micromath",
]
[[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"
version = "1.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0c4b4d0bd25bd0b74681c0ad21497610ce1b7c91b1022cd21c80c6fbdd9476b0"
checksum = "ace50bade8e6234aa140d9a2f552bbee1db4d353f69b8217bc503490fc1a9f26"
[[package]]
name = "bare-metal"
@@ -77,7 +68,7 @@ version = "0.2.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4c24dab4283a142afa2fdca129b80ad2c6284e073930f964c3a1293c225ee39a"
dependencies = [
"rustc_version 0.4.0",
"rustc_version 0.4.1",
]
[[package]]
@@ -88,9 +79,9 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
[[package]]
name = "chrono"
version = "0.4.38"
version = "0.4.39"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a21f936df1771bf62b77f047b726c4625ff2e8aa607c01ec06e5a05bd8463401"
checksum = "7e36cc9d416881d2e24f9a963be5fb1cd90966419ac844274161d10488b3e825"
dependencies = [
"num-traits",
]
@@ -103,8 +94,12 @@ checksum = "67ba02a97a2bd10f4b59b25c7973101c79642302776489e030cd13cdab09ed15"
[[package]]
name = "cobs"
version = "0.2.3"
source = "git+https://github.com/robamu/cobs.rs.git?branch=all_features#c70a7f30fd00a7cbdb7666dec12b437977385d40"
version = "0.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0fa961b519f0b462e3a3b4a34b64d119eeaca1d59af726fe450bbba07a9fc0a1"
dependencies = [
"thiserror",
]
[[package]]
name = "cortex-m"
@@ -121,22 +116,22 @@ dependencies = [
[[package]]
name = "cortex-m-rt"
version = "0.7.4"
version = "0.7.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2722f5b7d6ea8583cffa4d247044e280ccbb9fe501bed56552e2ba48b02d5f3d"
checksum = "801d4dec46b34c299ccf6b036717ae0fce602faa4f4fe816d9013b9a7c9f5ba6"
dependencies = [
"cortex-m-rt-macros",
]
[[package]]
name = "cortex-m-rt-macros"
version = "0.7.0"
version = "0.7.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f0f6f3e36f203cfedbc78b357fb28730aa2c6dc1ab060ee5c2405e843988d3c7"
checksum = "e37549a379a9e0e6e576fd208ee60394ccb8be963889eebba3ffe0980364f472"
dependencies = [
"proc-macro2",
"quote",
"syn 1.0.109",
"syn 2.0.96",
]
[[package]]
@@ -165,15 +160,15 @@ checksum = "19d374276b40fb8bbdee95aef7c7fa6b5316ec764510eb64b8dd0e2ed0d7e7f5"
[[package]]
name = "critical-section"
version = "1.1.2"
version = "1.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7059fff8937831a9ae6f0fe4d658ffabf58f2ca96aa9dec1c889f936f705f216"
checksum = "790eea4361631c5e7d22598ecd5723ff611904e3344ce8720784c93e3d83d40b"
[[package]]
name = "darling"
version = "0.20.9"
version = "0.20.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "83b2eb4d90d12bdda5ed17de686c2acb4c57914f8f921b8da7e112b5a36f3fe1"
checksum = "6f63b86c8a8826a49b8c21f08a2d07338eec8d900540f8630dc76284be802989"
dependencies = [
"darling_core",
"darling_macro",
@@ -181,33 +176,33 @@ dependencies = [
[[package]]
name = "darling_core"
version = "0.20.9"
version = "0.20.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "622687fe0bac72a04e5599029151f5796111b90f1baaa9b544d807a5e31cd120"
checksum = "95133861a8032aaea082871032f5815eb9e98cef03fa916ab4500513994df9e5"
dependencies = [
"fnv",
"ident_case",
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
name = "darling_macro"
version = "0.20.9"
version = "0.20.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "733cabb43482b1a1b53eee8583c2b9e8684d592215ea83efd305dd31bc2f0178"
checksum = "d336a2a514f6ccccaa3e09b02d41d35330c07ddf03a62165fcec10bb561c7806"
dependencies = [
"darling_core",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
name = "defmt"
version = "0.3.8"
version = "0.3.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a99dd22262668b887121d4672af5a64b238f026099f1a2a1b322066c9ecfe9e0"
checksum = "86f6162c53f659f65d00619fe31f14556a6e9f8752ccc4a41bd177ffcf3d6130"
dependencies = [
"bitflags",
"defmt-macros",
@@ -225,22 +220,22 @@ dependencies = [
[[package]]
name = "defmt-macros"
version = "0.3.9"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e3a9f309eff1f79b3ebdf252954d90ae440599c26c2c553fe87a2d17195f2dcb"
checksum = "9d135dd939bad62d7490b0002602d35b358dce5fd9233a709d3c1ef467d4bde6"
dependencies = [
"defmt-parser",
"proc-macro-error",
"proc-macro-error2",
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
name = "defmt-parser"
version = "0.3.4"
version = "0.4.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ff4a5fefe330e8d7f31b16a318f9ce81000d8e35e69b93eae154d16d2278f70f"
checksum = "3983b127f13995e68c1e29071e5d115cd96f215ccb5e6812e3728cd6f92653b3"
dependencies = [
"thiserror",
]
@@ -265,7 +260,7 @@ checksum = "984bc6eca246389726ac2826acc2488ca0fe5fcd6b8d9b48797021951d76a125"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
@@ -287,7 +282,7 @@ checksum = "d150dea618e920167e5973d70ae6ece4385b7164e0d799fe7c122dd0a5d912ad"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
@@ -315,6 +310,15 @@ version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "361a90feb7004eca4019fb28352a9465666b24f840f5c3cddf0ff13920590b89"
[[package]]
name = "embedded-hal-async"
version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0c4c685bbef7fe13c3c6dd4da26841ed3980ef33e841cddfa15ce8a8fb3f1884"
dependencies = [
"embedded-hal 1.0.0",
]
[[package]]
name = "embedded-time"
version = "0.12.1"
@@ -326,23 +330,23 @@ dependencies = [
[[package]]
name = "enumset"
version = "1.1.3"
version = "1.1.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "226c0da7462c13fb57e5cc9e0dc8f0635e7d27f276a3a7fd30054647f669007d"
checksum = "d07a4b049558765cef5f0c1a273c3fc57084d768b44d2f98127aef4cceb17293"
dependencies = [
"enumset_derive",
]
[[package]]
name = "enumset_derive"
version = "0.8.1"
version = "0.10.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e08b6c6ab82d70f08844964ba10c7babb716de2ecaeab9be5717918a5177d3af"
checksum = "59c3b24c345d8c314966bdc1832f6c2635bfcce8e7cf363bd115987bba2ee242"
dependencies = [
"darling",
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
@@ -368,21 +372,21 @@ dependencies = [
[[package]]
name = "futures-core"
version = "0.3.30"
version = "0.3.31"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dfc6580bb841c5a68e9ef15c77ccc837b40a7504914d52e47b8b0e9bbda25a1d"
checksum = "05f29059c0c2090612e8d742178b0580d2dc940c837851ad723096f87af6663e"
[[package]]
name = "futures-task"
version = "0.3.30"
version = "0.3.31"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "38d84fa142264698cdce1a9f9172cf383a0c82de1bddcf3092901442c4097004"
checksum = "f90f7dce0722e95104fcb095585910c0977252f286e354b5e3bd38902cd99988"
[[package]]
name = "futures-util"
version = "0.3.30"
version = "0.3.31"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3d6401deb83407ab3da39eba7e33987a73c3df0c82b4bb5813ee871c19c41d48"
checksum = "9fa08315bb612088cc391249efdc3bc77536f16c91f6cf495e6fbe85b20a4a81"
dependencies = [
"futures-core",
"futures-task",
@@ -426,9 +430,9 @@ dependencies = [
[[package]]
name = "hashbrown"
version = "0.14.5"
version = "0.15.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e5274423e17b7c9fc20b6e7e208532f9b19825d82dfd615708b70edd83df41f1"
checksum = "bf151400ff0baff5465007dd2f3e717f3fe502074ca563069ce3a6629d07b289"
[[package]]
name = "heapless"
@@ -448,9 +452,9 @@ checksum = "b9e0384b61958566e926dc50660321d12159025e767c18e043daf26b70104c39"
[[package]]
name = "indexmap"
version = "2.2.6"
version = "2.7.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "168fb715dda47215e360912c096649d23d58bf392ac62f73919e831745e40f26"
checksum = "8c9c992b02b5b4c94ea26e32fe5bccb7aa7d9f390ab5c1221ff895bc7ea8b652"
dependencies = [
"equivalent",
"hashbrown",
@@ -555,22 +559,22 @@ dependencies = [
[[package]]
name = "num_enum"
version = "0.7.2"
version = "0.7.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "02339744ee7253741199f897151b38e72257d13802d4ee837285cc2990a90845"
checksum = "4e613fc340b2220f734a8595782c551f1250e969d87d3be1ae0579e8d4065179"
dependencies = [
"num_enum_derive",
]
[[package]]
name = "num_enum_derive"
version = "0.7.2"
version = "0.7.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "681030a937600a36906c185595136d26abfebb4aa9c65701cefcaf8578bb982b"
checksum = "af1844ef2428cc3e1cb900be36181049ef3d3193c63e43026cfe202983b27a56"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
@@ -591,9 +595,9 @@ checksum = "57c0d7b74b563b49d38dae00a0c37d4d6de9b432382b2892f0574ddcae73fd0a"
[[package]]
name = "pin-project-lite"
version = "0.2.14"
version = "0.2.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bda66fc9667c18cb2758a2ac84d1167245054bcf85d5d1aaa6923f45801bdd02"
checksum = "3b3cff922bd51709b605d9ead9aa71031d81447142d828eb4a6eba76fe619f9b"
[[package]]
name = "pin-utils"
@@ -602,43 +606,47 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
[[package]]
name = "proc-macro-error"
version = "1.0.4"
name = "portable-atomic"
version = "1.10.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c"
checksum = "280dc24453071f1b63954171985a0b0d30058d287960968b9b2aca264c8d4ee6"
[[package]]
name = "proc-macro-error-attr2"
version = "2.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "96de42df36bb9bba5542fe9f1a054b8cc87e172759a1868aa05c1f3acc89dfc5"
dependencies = [
"proc-macro-error-attr",
"proc-macro2",
"quote",
"syn 1.0.109",
"version_check",
]
[[package]]
name = "proc-macro-error-attr"
version = "1.0.4"
name = "proc-macro-error2"
version = "2.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869"
checksum = "11ec05c52be0a07b08061f7dd003e7d7092e0472bc731b4af7bb1ef876109802"
dependencies = [
"proc-macro-error-attr2",
"proc-macro2",
"quote",
"version_check",
"syn 2.0.96",
]
[[package]]
name = "proc-macro2"
version = "1.0.83"
version = "1.0.93"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0b33eb56c327dec362a9e55b3ad14f9d2f0904fb5a5b03b513ab5465399e9f43"
checksum = "60946a68e5f9d28b0dc1c21bb8a97ee7d018a8b322fa57838ba31cc878e22d99"
dependencies = [
"unicode-ident",
]
[[package]]
name = "quote"
version = "1.0.36"
version = "1.0.38"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0fa76aaf39101c457836aec0ce2316dbdc3ab723cdda1c6bd4e6ad4208acaca7"
checksum = "0e4dccaaaf89514f546c693ddc140f729f958c247918a13380cccc6078391acc"
dependencies = [
"proc-macro2",
]
@@ -654,14 +662,14 @@ dependencies = [
[[package]]
name = "rtic"
version = "2.1.1"
version = "2.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c443db16326376bdd64377da268f6616d5f804aba8ce799bac7d1f7f244e9d51"
checksum = "401961431a1e491124cdd216a313fada2d395aa2b5bee2867c872fc8af7c1bc1"
dependencies = [
"atomic-polyfill",
"bare-metal 1.0.0",
"cortex-m",
"critical-section",
"portable-atomic",
"rtic-core",
"rtic-macros",
]
@@ -683,38 +691,40 @@ checksum = "d9369355b04d06a3780ec0f51ea2d225624db777acbc60abd8ca4832da5c1a42"
[[package]]
name = "rtic-macros"
version = "2.1.0"
version = "2.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "54053598ea24b1b74937724e366558412a1777eb2680b91ef646db540982789a"
checksum = "ac22ab522d80079b48f46ac66ded4d349e1adf81b52430d6a74faa3a7790ed80"
dependencies = [
"indexmap",
"proc-macro-error",
"proc-macro-error2",
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
name = "rtic-monotonics"
version = "1.5.0"
version = "2.0.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "058c2397dbd5bb4c5650a0e368c3920953e458805ff5097a0511b8147b3619d7"
checksum = "f1cb90bcfdbbacf3ca37340cdab52ec2de5611c744095ef7889e9c50c233b748"
dependencies = [
"atomic-polyfill",
"cfg-if",
"cortex-m",
"embedded-hal 1.0.0",
"fugit",
"portable-atomic",
"rtic-time",
]
[[package]]
name = "rtic-time"
version = "1.3.0"
version = "2.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "75b232e7aebc045cfea81cdd164bc2727a10aca9a4568d406d0a5661cdfd0f19"
checksum = "a7b1d853fa50dc125695414ce4510567a0d420221e455b1568cfa8c9aece9614"
dependencies = [
"critical-section",
"embedded-hal 1.0.0",
"embedded-hal-async",
"fugit",
"futures-util",
"rtic-common",
]
@@ -730,11 +740,11 @@ dependencies = [
[[package]]
name = "rustc_version"
version = "0.4.0"
version = "0.4.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366"
checksum = "cfcb3a22ef46e85b45de6ee7e79d063319ebb6594faafcf1c225ea92ab6e9b92"
dependencies = [
"semver 1.0.23",
"semver 1.0.25",
]
[[package]]
@@ -743,7 +753,7 @@ version = "0.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "866fcae3b683ccc37b5ad77982483a0ee01d5dc408dea5aad2117ad404b60fe1"
dependencies = [
"cobs 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)",
"cobs 0.2.3",
"crc",
"defmt",
"delegate",
@@ -769,7 +779,7 @@ dependencies = [
name = "satrs-stm32f3-disco-rtic"
version = "0.1.0"
dependencies = [
"cobs 0.2.3 (git+https://github.com/robamu/cobs.rs.git?branch=all_features)",
"cobs 0.3.0",
"cortex-m",
"cortex-m-rt",
"cortex-m-semihosting",
@@ -798,9 +808,9 @@ dependencies = [
[[package]]
name = "semver"
version = "1.0.23"
version = "1.0.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "61697e0a1c7e512e84a621326239844a24d8207b4669b41bc18b32ea5cbf988b"
checksum = "f79dfe2d285b0488816f30e700a7438c5a73d816b5b7d3ac72fbc48b0d185e03"
[[package]]
name = "semver-parser"
@@ -922,9 +932,9 @@ dependencies = [
[[package]]
name = "syn"
version = "2.0.65"
version = "2.0.96"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d2863d96a84c6439701d7a38f9de935ec562c8832cc55d1dde0f513b52fad106"
checksum = "d5d0adab1ae378d7f53bdebc67a39f1f151407ef230f0ce2883572f5d8985c80"
dependencies = [
"proc-macro2",
"quote",
@@ -933,22 +943,22 @@ dependencies = [
[[package]]
name = "thiserror"
version = "1.0.61"
version = "2.0.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c546c80d6be4bc6a00c0f01730c08df82eaa7a7a61f11d656526506112cc1709"
checksum = "d452f284b73e6d76dd36758a0c8684b1d5be31f92b89d07fd5822175732206fc"
dependencies = [
"thiserror-impl",
]
[[package]]
name = "thiserror-impl"
version = "1.0.61"
version = "2.0.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "46c3384250002a6d5af4d114f2845d37b57521033f30d5c3f46c4d70e1197533"
checksum = "26afc1baea8a989337eeb52b6e72a039780ce45c3edfcc9c5b9d112feeb173c2"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]
[[package]]
@@ -959,9 +969,9 @@ checksum = "42ff0bf0c66b8238c6f3b578df37d0b7848e55df8577b3f74f92a69acceeb825"
[[package]]
name = "unicode-ident"
version = "1.0.12"
version = "1.0.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b"
checksum = "a210d160f08b701c8721ba1c726c11662f877ea6b7094007e1ca9a1041945034"
[[package]]
name = "usb-device"
@@ -977,9 +987,9 @@ checksum = "77439c1b53d2303b20d9459b1ade71a83c716e3f9c34f3228c00e6f185d6c002"
[[package]]
name = "version_check"
version = "0.9.4"
version = "0.9.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f"
checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a"
[[package]]
name = "void"
@@ -998,9 +1008,9 @@ dependencies = [
[[package]]
name = "zerocopy"
version = "0.7.34"
version = "0.7.35"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ae87e3fcd617500e5d106f0380cf7b77f3c6092aae37191433159dda23cfb087"
checksum = "1b9b4fd18abc82b8136838da5d50bae7bdea537c574d8dc1a34ed098d6c166f0"
dependencies = [
"byteorder",
"zerocopy-derive",
@@ -1008,11 +1018,11 @@ dependencies = [
[[package]]
name = "zerocopy-derive"
version = "0.7.34"
version = "0.7.35"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "15e934569e47891f7d9411f1a451d947a60e000ab3bd24fbb970f000387d1b3b"
checksum = "fa4f8080344d4671fb4e831a13ad1e68092748387dfc4f55e356242fae12ce3e"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.65",
"syn 2.0.96",
]

View File

@@ -22,12 +22,11 @@ version = "2"
features = ["thumbv7-backend"]
[dependencies.rtic-monotonics]
version = "1"
version = "2"
features = ["cortex-m-systick"]
[dependencies.cobs]
git = "https://github.com/robamu/cobs.rs.git"
branch = "all_features"
version = "0.3"
default-features = false
[dependencies.stm32f3xx-hal]

View File

@@ -15,8 +15,8 @@ use rtic::app;
use heapless::{mpmc::Q8, Vec};
#[allow(unused_imports)]
use rtic_monotonics::systick::fugit::{MillisDurationU32, TimerInstantU32};
use rtic_monotonics::systick::ExtU32;
use rtic_monotonics::fugit::{MillisDurationU32, TimerInstantU32};
use rtic_monotonics::systick::prelude::*;
use satrs::seq_count::SequenceCountProviderCore;
use satrs::spacepackets::{ecss::PusPacket, ecss::WritablePusPacket};
use stm32f3xx_hal::dma::dma1;
@@ -245,8 +245,6 @@ pub fn convert_pus_tc_to_request(
mod app {
use super::*;
use core::slice::Iter;
use rtic_monotonics::systick::Systick;
use rtic_monotonics::Monotonic;
use satrs::pus::verification::{TcStateStarted, VerificationReportCreator};
use satrs::spacepackets::{ecss::tc::PusTcReader, time::cds::P_FIELD_BASE};
#[allow(unused_imports)]
@@ -259,6 +257,8 @@ mod app {
#[allow(dead_code)]
type SerialType = Serial<USART2, (PA2<AF7<PushPull>>, PA3<AF7<PushPull>>)>;
systick_monotonic!(Mono, 1000);
#[shared]
struct Shared {
blink_freq: MillisDurationU32,
@@ -279,8 +279,7 @@ mod app {
let mut rcc = cx.device.RCC.constrain();
// Initialize the systick interrupt & obtain the token to prove that we did
let systick_mono_token = rtic_monotonics::create_systick_token!();
Systick::start(cx.core.SYST, 8_000_000, systick_mono_token);
Mono::start(cx.core.SYST, 8_000_000);
let mut flash = cx.device.FLASH.constrain();
let clocks = rcc
@@ -394,7 +393,7 @@ mod app {
}
}
let current_blink_freq = cx.shared.blink_freq.lock(|current| *current);
Systick::delay(current_blink_freq).await;
Mono::delay(current_blink_freq).await;
}
}
@@ -412,15 +411,14 @@ mod app {
if is_idle {
let last_completed = cx.shared.tx_shared.lock(|shared| shared.last_completed);
if let Some(last_completed) = last_completed {
let elapsed_ms = (Systick::now() - last_completed).to_millis();
let elapsed_ms = (Mono::now() - last_completed).to_millis();
if elapsed_ms < MIN_DELAY_BETWEEN_TX_PACKETS_MS {
Systick::delay((MIN_DELAY_BETWEEN_TX_PACKETS_MS - elapsed_ms).millis())
.await;
Mono::delay((MIN_DELAY_BETWEEN_TX_PACKETS_MS - elapsed_ms).millis()).await;
}
}
} else {
// Check for completion after 1 ms
Systick::delay(1.millis()).await;
Mono::delay(1.millis()).await;
continue;
}
if let Some(vec) = TM_REQUESTS.dequeue() {
@@ -459,11 +457,11 @@ mod app {
UartTxState::Transmitting(_) => (),
});
// Check for completion after 1 ms
Systick::delay(1.millis()).await;
Mono::delay(1.millis()).await;
continue;
}
// Nothing to do, and we are idle.
Systick::delay(TX_HANDLER_FREQ_MS.millis()).await;
Mono::delay(TX_HANDLER_FREQ_MS.millis()).await;
}
}
@@ -657,7 +655,7 @@ mod app {
tx_shared.state = UartTxState::Idle(Some(TxIdle { tx, dma_channel }));
// We cache the last completed time to ensure that there is a minimum delay between consecutive
// transferred packets.
tx_shared.last_completed = Some(Systick::now());
tx_shared.last_completed = Some(Mono::now());
}
}
});

View File

@@ -1,21 +1,12 @@
# 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",
]
version = 4
[[package]]
name = "autocfg"
version = "1.3.0"
version = "1.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0c4b4d0bd25bd0b74681c0ad21497610ce1b7c91b1022cd21c80c6fbdd9476b0"
checksum = "ace50bade8e6234aa140d9a2f552bbee1db4d353f69b8217bc503490fc1a9f26"
[[package]]
name = "bare-metal"
@@ -23,7 +14,7 @@ version = "0.2.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5deb64efa5bd81e31fcd1938615a6d98c82eafcbcd787162b6f63b91d6bac5b3"
dependencies = [
"rustc_version 0.2.3",
"rustc_version",
]
[[package]]
@@ -32,6 +23,12 @@ version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f8fe8f5a8a398345e52358e18ff07cc17a568fbca5c6f73873d3a62056309603"
[[package]]
name = "base64"
version = "0.13.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8"
[[package]]
name = "bitfield"
version = "0.13.2"
@@ -64,8 +61,18 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
[[package]]
name = "cobs"
version = "0.2.3"
source = "git+https://github.com/robamu/cobs.rs.git?branch=all_features#c70a7f30fd00a7cbdb7666dec12b437977385d40"
version = "0.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0fa961b519f0b462e3a3b4a34b64d119eeaca1d59af726fe450bbba07a9fc0a1"
dependencies = [
"thiserror",
]
[[package]]
name = "const-default"
version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0b396d1f76d455557e1218ec8066ae14bba60b4b36ecd55577ba979f5db7ecaa"
[[package]]
name = "cortex-m"
@@ -82,22 +89,22 @@ dependencies = [
[[package]]
name = "cortex-m-rt"
version = "0.7.4"
version = "0.7.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2722f5b7d6ea8583cffa4d247044e280ccbb9fe501bed56552e2ba48b02d5f3d"
checksum = "801d4dec46b34c299ccf6b036717ae0fce602faa4f4fe816d9013b9a7c9f5ba6"
dependencies = [
"cortex-m-rt-macros",
]
[[package]]
name = "cortex-m-rt-macros"
version = "0.7.0"
version = "0.7.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f0f6f3e36f203cfedbc78b357fb28730aa2c6dc1ab060ee5c2405e843988d3c7"
checksum = "e37549a379a9e0e6e576fd208ee60394ccb8be963889eebba3ffe0980364f472"
dependencies = [
"proc-macro2",
"quote",
"syn 1.0.109",
"syn 2.0.96",
]
[[package]]
@@ -126,15 +133,15 @@ checksum = "19d374276b40fb8bbdee95aef7c7fa6b5316ec764510eb64b8dd0e2ed0d7e7f5"
[[package]]
name = "critical-section"
version = "1.1.2"
version = "1.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7059fff8937831a9ae6f0fe4d658ffabf58f2ca96aa9dec1c889f936f705f216"
checksum = "790eea4361631c5e7d22598ecd5723ff611904e3344ce8720784c93e3d83d40b"
[[package]]
name = "defmt"
version = "0.3.8"
version = "0.3.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a99dd22262668b887121d4672af5a64b238f026099f1a2a1b322066c9ecfe9e0"
checksum = "86f6162c53f659f65d00619fe31f14556a6e9f8752ccc4a41bd177ffcf3d6130"
dependencies = [
"bitflags",
"defmt-macros",
@@ -152,22 +159,22 @@ dependencies = [
[[package]]
name = "defmt-macros"
version = "0.3.9"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e3a9f309eff1f79b3ebdf252954d90ae440599c26c2c553fe87a2d17195f2dcb"
checksum = "9d135dd939bad62d7490b0002602d35b358dce5fd9233a709d3c1ef467d4bde6"
dependencies = [
"defmt-parser",
"proc-macro-error",
"proc-macro-error2",
"proc-macro2",
"quote",
"syn 2.0.64",
"syn 2.0.96",
]
[[package]]
name = "defmt-parser"
version = "0.3.4"
version = "0.4.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ff4a5fefe330e8d7f31b16a318f9ce81000d8e35e69b93eae154d16d2278f70f"
checksum = "3983b127f13995e68c1e29071e5d115cd96f215ccb5e6812e3728cd6f92653b3"
dependencies = [
"thiserror",
]
@@ -192,39 +199,41 @@ checksum = "984bc6eca246389726ac2826acc2488ca0fe5fcd6b8d9b48797021951d76a125"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.64",
"syn 2.0.96",
]
[[package]]
name = "delegate"
version = "0.10.0"
version = "0.13.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0ee5df75c70b95bd3aacc8e2fd098797692fb1d54121019c4de481e42f04c8a1"
checksum = "297806318ef30ad066b15792a8372858020ae3ca2e414ee6c2133b1eb9e9e945"
dependencies = [
"proc-macro2",
"quote",
"syn 1.0.109",
"syn 2.0.96",
]
[[package]]
name = "derive-new"
version = "0.6.0"
version = "0.7.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d150dea618e920167e5973d70ae6ece4385b7164e0d799fe7c122dd0a5d912ad"
checksum = "2cdc8d50f426189eef89dac62fabfa0abb27d5cc008f25bf4156a0203325becc"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.64",
"syn 2.0.96",
]
[[package]]
name = "embedded-alloc"
version = "0.5.1"
version = "0.6.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ddae17915accbac2cfbc64ea0ae6e3b330e6ea124ba108dada63646fd3c6f815"
checksum = "8f2de9133f68db0d4627ad69db767726c99ff8585272716708227008d3f1bddd"
dependencies = [
"const-default",
"critical-section",
"linked_list_allocator",
"rlsf",
]
[[package]]
@@ -300,21 +309,21 @@ dependencies = [
[[package]]
name = "futures-core"
version = "0.3.30"
version = "0.3.31"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dfc6580bb841c5a68e9ef15c77ccc837b40a7504914d52e47b8b0e9bbda25a1d"
checksum = "05f29059c0c2090612e8d742178b0580d2dc940c837851ad723096f87af6663e"
[[package]]
name = "futures-task"
version = "0.3.30"
version = "0.3.31"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "38d84fa142264698cdce1a9f9172cf383a0c82de1bddcf3092901442c4097004"
checksum = "f90f7dce0722e95104fcb095585910c0977252f286e354b5e3bd38902cd99988"
[[package]]
name = "futures-util"
version = "0.3.30"
version = "0.3.31"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3d6401deb83407ab3da39eba7e33987a73c3df0c82b4bb5813ee871c19c41d48"
checksum = "9fa08315bb612088cc391249efdc3bc77536f16c91f6cf495e6fbe85b20a4a81"
dependencies = [
"futures-core",
"futures-task",
@@ -328,15 +337,6 @@ version = "2.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1d758ba1b47b00caf47f24925c0074ecb20d6dfcffe7f6d53395c0465674841a"
[[package]]
name = "hash32"
version = "0.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b0c35f58762feb77d74ebe43bdbc3210f09be9fe6742234d573bacc26ed92b67"
dependencies = [
"byteorder",
]
[[package]]
name = "hash32"
version = "0.3.1"
@@ -348,22 +348,9 @@ dependencies = [
[[package]]
name = "hashbrown"
version = "0.14.5"
version = "0.15.2"
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 0.2.1",
"rustc_version 0.4.0",
"spin",
"stable_deref_trait",
]
checksum = "bf151400ff0baff5465007dd2f3e717f3fe502074ca563069ce3a6629d07b289"
[[package]]
name = "heapless"
@@ -372,36 +359,32 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0bfb9eb618601c89945a70e254898da93b13be0388091d42117462b265bb3fad"
dependencies = [
"defmt",
"hash32 0.3.1",
"hash32",
"stable_deref_trait",
]
[[package]]
name = "indexmap"
version = "2.2.6"
version = "2.7.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "168fb715dda47215e360912c096649d23d58bf392ac62f73919e831745e40f26"
checksum = "8c9c992b02b5b4c94ea26e32fe5bccb7aa7d9f390ab5c1221ff895bc7ea8b652"
dependencies = [
"equivalent",
"hashbrown",
]
[[package]]
name = "libc"
version = "0.2.169"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b5aba8db14291edd000dfcc4d620c7ebfb122c613afb886ca8803fa4e128a20a"
[[package]]
name = "linked_list_allocator"
version = "0.10.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9afa463f5405ee81cdb9cc2baf37e08ec7e4c8209442b5d72c04cfb2cd6e6286"
[[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 = "managed"
version = "0.8.0"
@@ -434,22 +417,22 @@ dependencies = [
[[package]]
name = "num_enum"
version = "0.7.2"
version = "0.7.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "02339744ee7253741199f897151b38e72257d13802d4ee837285cc2990a90845"
checksum = "4e613fc340b2220f734a8595782c551f1250e969d87d3be1ae0579e8d4065179"
dependencies = [
"num_enum_derive",
]
[[package]]
name = "num_enum_derive"
version = "0.7.2"
version = "0.7.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "681030a937600a36906c185595136d26abfebb4aa9c65701cefcaf8578bb982b"
checksum = "af1844ef2428cc3e1cb900be36181049ef3d3193c63e43026cfe202983b27a56"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.64",
"syn 2.0.96",
]
[[package]]
@@ -470,9 +453,9 @@ checksum = "57c0d7b74b563b49d38dae00a0c37d4d6de9b432382b2892f0574ddcae73fd0a"
[[package]]
name = "pin-project-lite"
version = "0.2.14"
version = "0.2.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bda66fc9667c18cb2758a2ac84d1167245054bcf85d5d1aaa6923f45801bdd02"
checksum = "3b3cff922bd51709b605d9ead9aa71031d81447142d828eb4a6eba76fe619f9b"
[[package]]
name = "pin-utils"
@@ -482,62 +465,72 @@ checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
[[package]]
name = "portable-atomic"
version = "1.6.0"
version = "1.10.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7170ef9988bc169ba16dd36a7fa041e5c4cbeb6a35b76d4c03daded371eae7c0"
checksum = "280dc24453071f1b63954171985a0b0d30058d287960968b9b2aca264c8d4ee6"
[[package]]
name = "proc-macro-error"
version = "1.0.4"
name = "proc-macro-error-attr2"
version = "2.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c"
checksum = "96de42df36bb9bba5542fe9f1a054b8cc87e172759a1868aa05c1f3acc89dfc5"
dependencies = [
"proc-macro-error-attr",
"proc-macro2",
"quote",
"syn 1.0.109",
"version_check",
]
[[package]]
name = "proc-macro-error-attr"
version = "1.0.4"
name = "proc-macro-error2"
version = "2.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869"
checksum = "11ec05c52be0a07b08061f7dd003e7d7092e0472bc731b4af7bb1ef876109802"
dependencies = [
"proc-macro-error-attr2",
"proc-macro2",
"quote",
"version_check",
"syn 2.0.96",
]
[[package]]
name = "proc-macro2"
version = "1.0.82"
version = "1.0.93"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8ad3d49ab951a01fbaafe34f2ec74122942fe18a3f9814c3268f1bb72042131b"
checksum = "60946a68e5f9d28b0dc1c21bb8a97ee7d018a8b322fa57838ba31cc878e22d99"
dependencies = [
"unicode-ident",
]
[[package]]
name = "quote"
version = "1.0.36"
version = "1.0.38"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0fa76aaf39101c457836aec0ce2316dbdc3ab723cdda1c6bd4e6ad4208acaca7"
checksum = "0e4dccaaaf89514f546c693ddc140f729f958c247918a13380cccc6078391acc"
dependencies = [
"proc-macro2",
]
[[package]]
name = "rtic"
version = "2.1.1"
name = "rlsf"
version = "0.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c443db16326376bdd64377da268f6616d5f804aba8ce799bac7d1f7f244e9d51"
checksum = "222fb240c3286247ecdee6fa5341e7cdad0ffdf8e7e401d9937f2d58482a20bf"
dependencies = [
"cfg-if",
"const-default",
"libc",
"svgbobdoc",
]
[[package]]
name = "rtic"
version = "2.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "401961431a1e491124cdd216a313fada2d395aa2b5bee2867c872fc8af7c1bc1"
dependencies = [
"atomic-polyfill",
"bare-metal 1.0.0",
"cortex-m",
"critical-section",
"portable-atomic",
"rtic-core",
"rtic-macros",
]
@@ -559,28 +552,27 @@ checksum = "d9369355b04d06a3780ec0f51ea2d225624db777acbc60abd8ca4832da5c1a42"
[[package]]
name = "rtic-macros"
version = "2.1.0"
version = "2.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "54053598ea24b1b74937724e366558412a1777eb2680b91ef646db540982789a"
checksum = "ac22ab522d80079b48f46ac66ded4d349e1adf81b52430d6a74faa3a7790ed80"
dependencies = [
"indexmap",
"proc-macro-error",
"proc-macro-error2",
"proc-macro2",
"quote",
"syn 2.0.64",
"syn 2.0.96",
]
[[package]]
name = "rtic-monotonics"
version = "1.5.0"
version = "2.0.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "058c2397dbd5bb4c5650a0e368c3920953e458805ff5097a0511b8147b3619d7"
checksum = "f1cb90bcfdbbacf3ca37340cdab52ec2de5611c744095ef7889e9c50c233b748"
dependencies = [
"atomic-polyfill",
"cfg-if",
"cortex-m",
"embedded-hal 1.0.0",
"fugit",
"portable-atomic",
"rtic-time",
]
@@ -595,18 +587,21 @@ dependencies = [
"embedded-hal 1.0.0",
"embedded-hal-async",
"embedded-hal-bus",
"heapless 0.8.0",
"heapless",
"portable-atomic",
"rtic-common",
]
[[package]]
name = "rtic-time"
version = "1.3.0"
version = "2.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "75b232e7aebc045cfea81cdd164bc2727a10aca9a4568d406d0a5661cdfd0f19"
checksum = "a7b1d853fa50dc125695414ce4510567a0d420221e455b1568cfa8c9aece9614"
dependencies = [
"critical-section",
"embedded-hal 1.0.0",
"embedded-hal-async",
"fugit",
"futures-util",
"rtic-common",
]
@@ -617,16 +612,7 @@ version = "0.2.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a"
dependencies = [
"semver 0.9.0",
]
[[package]]
name = "rustc_version"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366"
dependencies = [
"semver 1.0.23",
"semver",
]
[[package]]
@@ -638,20 +624,22 @@ dependencies = [
"defmt",
"delegate",
"derive-new",
"heapless 0.7.17",
"heapless",
"num-traits",
"num_enum",
"paste",
"satrs-shared",
"smallvec",
"spacepackets",
"static_cell",
"thiserror",
]
[[package]]
name = "satrs-shared"
version = "0.1.4"
version = "0.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6042477018c2d43fffccaaa5099bc299a58485139b4d31c5b276889311e474f1"
checksum = "f10b962c131d0bcb0de06fefa5d4716cbd7f836167f90229f7f38405dc573bd3"
dependencies = [
"spacepackets",
]
@@ -676,12 +664,6 @@ dependencies = [
"stm32h7xx-hal",
]
[[package]]
name = "scopeguard"
version = "1.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49"
[[package]]
name = "semver"
version = "0.9.0"
@@ -691,12 +673,6 @@ dependencies = [
"semver-parser",
]
[[package]]
name = "semver"
version = "1.0.23"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "61697e0a1c7e512e84a621326239844a24d8207b4669b41bc18b32ea5cbf988b"
[[package]]
name = "semver-parser"
version = "0.7.0"
@@ -719,39 +695,41 @@ dependencies = [
"byteorder",
"cfg-if",
"defmt",
"heapless 0.8.0",
"heapless",
"managed",
]
[[package]]
name = "spacepackets"
version = "0.11.2"
version = "0.13.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e85574d113a06312010c0ba51aadccd4ba2806231ebe9a49fc6473d0534d8696"
checksum = "591d42bfa6af2ab308e5efd8f0870e2d0eb5dd19a141bdcb7da731f5ff9cc11c"
dependencies = [
"crc",
"defmt",
"delegate",
"num-traits",
"num_enum",
"paste",
"thiserror",
"zerocopy",
]
[[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 = "static_cell"
version = "2.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d89b0684884a883431282db1e4343f34afc2ff6996fe1f4a1664519b66e14c1e"
dependencies = [
"portable-atomic",
]
[[package]]
name = "stm32h7"
version = "0.15.1"
@@ -784,6 +762,19 @@ dependencies = [
"void",
]
[[package]]
name = "svgbobdoc"
version = "0.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f2c04b93fc15d79b39c63218f15e3fdffaa4c227830686e3b7c5f41244eb3e50"
dependencies = [
"base64",
"proc-macro2",
"quote",
"syn 1.0.109",
"unicode-width",
]
[[package]]
name = "syn"
version = "1.0.109"
@@ -797,9 +788,9 @@ dependencies = [
[[package]]
name = "syn"
version = "2.0.64"
version = "2.0.96"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7ad3dee41f36859875573074334c200d1add8e4a87bb37113ebd31d926b7b11f"
checksum = "d5d0adab1ae378d7f53bdebc67a39f1f151407ef230f0ce2883572f5d8985c80"
dependencies = [
"proc-macro2",
"quote",
@@ -808,29 +799,35 @@ dependencies = [
[[package]]
name = "thiserror"
version = "1.0.61"
version = "2.0.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c546c80d6be4bc6a00c0f01730c08df82eaa7a7a61f11d656526506112cc1709"
checksum = "d452f284b73e6d76dd36758a0c8684b1d5be31f92b89d07fd5822175732206fc"
dependencies = [
"thiserror-impl",
]
[[package]]
name = "thiserror-impl"
version = "1.0.61"
version = "2.0.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "46c3384250002a6d5af4d114f2845d37b57521033f30d5c3f46c4d70e1197533"
checksum = "26afc1baea8a989337eeb52b6e72a039780ce45c3edfcc9c5b9d112feeb173c2"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.64",
"syn 2.0.96",
]
[[package]]
name = "unicode-ident"
version = "1.0.12"
version = "1.0.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b"
checksum = "a210d160f08b701c8721ba1c726c11662f877ea6b7094007e1ca9a1041945034"
[[package]]
name = "unicode-width"
version = "0.1.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7dd6e30e90baa6f72411720665d41d89b9a3d039dc45b8faea1ddd07f617f6af"
[[package]]
name = "vcell"
@@ -838,12 +835,6 @@ version = "0.1.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "77439c1b53d2303b20d9459b1ade71a83c716e3f9c34f3228c00e6f185d6c002"
[[package]]
name = "version_check"
version = "0.9.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f"
[[package]]
name = "void"
version = "1.0.2"
@@ -861,21 +852,20 @@ dependencies = [
[[package]]
name = "zerocopy"
version = "0.7.34"
version = "0.8.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ae87e3fcd617500e5d106f0380cf7b77f3c6092aae37191433159dda23cfb087"
checksum = "a367f292d93d4eab890745e75a778da40909cab4d6ff8173693812f79c4a2468"
dependencies = [
"byteorder",
"zerocopy-derive",
]
[[package]]
name = "zerocopy-derive"
version = "0.7.34"
version = "0.8.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "15e934569e47891f7d9411f1a451d947a60e000ab3bd24fbb970f000387d1b3b"
checksum = "d3931cb58c62c13adec22e38686b559c86a30565e16ad6e8510a337cedc611e1"
dependencies = [
"proc-macro2",
"quote",
"syn 2.0.64",
"syn 2.0.96",
]

View File

@@ -21,11 +21,11 @@ defmt-brtt = { version = "0.1", default-features = false, features = ["rtt"] }
panic-probe = { version = "0.3", features = ["print-defmt"] }
cortex-m-semihosting = "0.5.0"
stm32h7xx-hal = { version="0.16", features= ["stm32h743v", "ethernet"] }
embedded-alloc = "0.5"
embedded-alloc = "0.6"
rtic-sync = { version = "1", features = ["defmt-03"] }
[dependencies.smoltcp]
version = "0.11.0"
version = "0.11"
default-features = false
features = ["medium-ethernet", "proto-ipv4", "socket-raw", "socket-dhcpv4", "socket-udp", "defmt"]
@@ -34,7 +34,7 @@ version = "2"
features = ["thumbv7-backend"]
[dependencies.rtic-monotonics]
version = "1"
version = "2"
features = ["cortex-m-systick"]
[dependencies.satrs]

View File

@@ -3,8 +3,8 @@
extern crate alloc;
use rtic::app;
use rtic_monotonics::systick::Systick;
use rtic_monotonics::Monotonic;
use rtic_monotonics::fugit::TimerInstantU32;
use rtic_monotonics::systick::prelude::*;
use satrs::pool::{PoolAddr, PoolProvider, StaticHeaplessMemoryPool};
use satrs::static_subpool;
// global logger + panicking-behavior + memory layout
@@ -13,7 +13,7 @@ use smoltcp::socket::udp::UdpMetadata;
use smoltcp::socket::{dhcpv4, udp};
use core::mem::MaybeUninit;
use embedded_alloc::Heap;
use embedded_alloc::LlffHeap as Heap;
use smoltcp::iface::{Config, Interface, SocketHandle, SocketSet, SocketStorage};
use smoltcp::wire::{HardwareAddress, IpAddress, IpCidr};
use stm32h7xx_hal::ethernet;
@@ -32,6 +32,8 @@ pub type TcSourceRx = rtic_sync::channel::Receiver<'static, PoolAddr, TC_SOURCE_
#[global_allocator]
static HEAP: Heap = Heap::empty();
systick_monotonic!(Mono, 1000);
// We place the memory pool buffers inside the larger AXISRAM.
pub const SUBPOOL_SMALL_NUM_BLOCKS: u16 = 32;
pub const SUBPOOL_SMALL_BLOCK_SIZE: usize = 32;
@@ -72,7 +74,9 @@ impl Net {
let mut iface = Interface::new(
config,
&mut ethdev,
smoltcp::time::Instant::from_millis((Systick::now() - Systick::ZERO).to_millis()),
smoltcp::time::Instant::from_millis(
(Mono::now() - TimerInstantU32::<1000>::from_ticks(0)).to_millis(),
),
);
// Create sockets
let dhcp_socket = dhcpv4::Socket::new();
@@ -91,7 +95,7 @@ impl Net {
/// Polls on the ethernet interface. You should refer to the smoltcp
/// documentation for poll() to understand how to call poll efficiently
pub fn poll<'a>(&mut self, sockets: &'a mut SocketSet) -> bool {
let uptime = Systick::now() - Systick::ZERO;
let uptime = Mono::now() - TimerInstantU32::<1000>::from_ticks(0);
let timestamp = smoltcp::time::Instant::from_millis(uptime.to_millis());
self.iface.poll(timestamp, &mut self.ethdev, sockets)
@@ -203,8 +207,7 @@ mod app {
use core::ptr::addr_of_mut;
use super::*;
use rtic_monotonics::systick::fugit::MillisDurationU32;
use rtic_monotonics::systick::Systick;
use rtic_monotonics::fugit::MillisDurationU32;
use satrs::spacepackets::ecss::tc::PusTcReader;
use stm32h7xx_hal::ethernet::{EthernetMAC, PHY};
use stm32h7xx_hal::gpio::{Output, Pin};
@@ -256,12 +259,7 @@ mod app {
.freeze(pwrcfg, &cx.device.SYSCFG);
// Initialize the systick interrupt & obtain the token to prove that we did
let systick_mono_token = rtic_monotonics::create_systick_token!();
Systick::start(
cx.core.SYST,
ccdr.clocks.sys_ck().to_Hz(),
systick_mono_token,
);
Mono::start(cx.core.SYST, ccdr.clocks.sys_ck().to_Hz());
// Those are used in the smoltcp of the stm32h7xx-hal , I am not fully sure what they are
// good for.
@@ -377,24 +375,24 @@ mod app {
shared_pool
.grow(
unsafe { SUBPOOL_SMALL.assume_init_mut() },
unsafe { SUBPOOL_SMALL_SIZES.assume_init_mut() },
SUBPOOL_SMALL.get_mut().unwrap(),
SUBPOOL_SMALL_SIZES.get_mut().unwrap(),
SUBPOOL_SMALL_NUM_BLOCKS,
true,
)
.expect("growing heapless memory pool failed");
shared_pool
.grow(
unsafe { SUBPOOL_MEDIUM.assume_init_mut() },
unsafe { SUBPOOL_MEDIUM_SIZES.assume_init_mut() },
SUBPOOL_MEDIUM.get_mut().unwrap(),
SUBPOOL_MEDIUM_SIZES.get_mut().unwrap(),
SUBPOOL_MEDIUM_NUM_BLOCKS,
true,
)
.expect("growing heapless memory pool failed");
shared_pool
.grow(
unsafe { SUBPOOL_LARGE.assume_init_mut() },
unsafe { SUBPOOL_LARGE_SIZES.assume_init_mut() },
SUBPOOL_LARGE.get_mut().unwrap(),
SUBPOOL_LARGE_SIZES.get_mut().unwrap(),
SUBPOOL_LARGE_NUM_BLOCKS,
true,
)
@@ -403,7 +401,7 @@ mod app {
// Set up global allocator. Use AXISRAM for the heap.
#[link_section = ".axisram"]
static mut HEAP_MEM: [MaybeUninit<u8>; HEAP_SIZE] = [MaybeUninit::uninit(); HEAP_SIZE];
unsafe { HEAP.init(HEAP_MEM.as_ptr() as usize, HEAP_SIZE) }
unsafe { HEAP.init(&raw mut HEAP_MEM as usize, HEAP_SIZE) }
eth_link_check::spawn().expect("eth link check failed");
blinky::spawn().expect("spawning blink task failed");
@@ -435,7 +433,7 @@ mod app {
leds.led1.toggle();
leds.led2.toggle();
let current_blink_freq = cx.shared.blink_freq.lock(|current| *current);
Systick::delay(current_blink_freq).await;
Mono::delay(current_blink_freq).await;
}
}
@@ -457,7 +455,7 @@ mod app {
cx.shared.eth_link_up.lock(|link_up| *link_up = false);
defmt::info!("Ethernet link down");
}
Systick::delay(100.millis()).await;
Mono::delay(100.millis()).await;
}
}
@@ -483,7 +481,7 @@ mod app {
cx.local.udp.poll(sockets, pool);
})
});
Systick::delay(40.millis()).await;
Mono::delay(40.millis()).await;
}
}

View File

@@ -1,5 +1,6 @@
#!/usr/bin/env python3
"""Example client for the sat-rs example application"""
import logging
import sys
import time

View File

@@ -12,7 +12,7 @@ authors = [
{name = "Robin Mueller", email = "robin.mueller.m@gmail.com"},
]
dependencies = [
"tmtccmd~=8.0",
"tmtccmd~=8.1",
"pydantic~=2.7"
]

View File

@@ -0,0 +1,11 @@
from tmtccmd.config import CmdTreeNode
def create_acs_node(mode_node: CmdTreeNode, hk_node: CmdTreeNode) -> CmdTreeNode:
acs_node = CmdTreeNode("acs", "ACS Subsystem Node")
mgm_node = CmdTreeNode("mgms", "MGM devices node")
mgm_node.add_child(mode_node)
mgm_node.add_child(hk_node)
acs_node.add_child(mgm_node)
return acs_node

View File

@@ -12,7 +12,7 @@ from pytmtc.pus_tc import create_cmd_definition_tree
class SatrsConfigHook(HookBase):
def __init__(self, json_cfg_path: str):
super().__init__(json_cfg_path=json_cfg_path)
super().__init__(json_cfg_path)
def get_communication_interface(self, com_if_key: str) -> Optional[ComInterface]:
from tmtccmd.config.com import (

View File

View File

@@ -4,7 +4,7 @@ from spacepackets.ecss.pus_3_hk import Subservice
from spacepackets.ecss import PusTm
from pytmtc.common import AcsId, Apid
from pytmtc.mgms import handle_mgm_hk_report
from pytmtc.acs.mgms import handle_mgm_hk_report
_LOGGER = logging.getLogger(__name__)

View File

@@ -17,8 +17,9 @@ from tmtccmd.tmtc import (
)
from tmtccmd.pus.s11_tc_sched import create_time_tagged_cmd
from pytmtc.acs import create_acs_node
from pytmtc.common import Apid
from pytmtc.mgms import create_mgm_cmds
from pytmtc.acs.mgms import create_mgm_cmds
_LOGGER = logging.getLogger(__name__)
@@ -67,7 +68,6 @@ class TcHandler(TcHandlerBase):
def create_cmd_definition_tree() -> CmdTreeNode:
root_node = CmdTreeNode.root_node()
hk_node = CmdTreeNode("hk", "Housekeeping Node", hide_children_for_print=True)
@@ -101,15 +101,7 @@ def create_cmd_definition_tree() -> CmdTreeNode:
)
)
root_node.add_child(scheduler_node)
acs_node = CmdTreeNode("acs", "ACS Subsystem Node")
mgm_node = CmdTreeNode("mgms", "MGM devices node")
mgm_node.add_child(mode_node)
mgm_node.add_child(hk_node)
acs_node.add_child(mgm_node)
root_node.add_child(acs_node)
root_node.add_child(create_acs_node(mode_node, hk_node))
return root_node

View File

@@ -25,7 +25,6 @@ optional = true
[dependencies.satrs-shared]
version = ">=0.1.3, <=0.2"
features = ["serde"]
path = "../satrs-shared"
[dependencies.satrs-mib-codegen]
path = "codegen"

View File

@@ -29,7 +29,6 @@ trybuild = { version = "1", features = ["diff"] }
[dev-dependencies.satrs-shared]
version = ">=0.1.3, <=0.2"
path = "../../satrs-shared"
[dev-dependencies.satrs-mib]
path = ".."

View File

@@ -14,12 +14,10 @@ fern = "0.7"
strum = { version = "0.26", features = ["derive"] }
num_enum = "0.7"
humantime = "2"
tai-time = { version = "0.3", features = ["serde"] }
[dependencies.asynchronix]
version = "0.2.2"
# git = "https://github.com/asynchronics/asynchronix.git"
# branch = "main"
features = ["serde"]
[dependencies.nexosim]
version = "0.3.1"
[dependencies.satrs]
path = "../satrs"

View File

@@ -1,8 +1,8 @@
use std::{f32::consts::PI, sync::mpsc, time::Duration};
use asynchronix::{
model::{Model, Output},
time::Scheduler,
use nexosim::{
model::{Context, Model},
ports::Output,
};
use satrs::power::SwitchStateBinary;
use satrs_minisim::{
@@ -55,7 +55,7 @@ impl<ReplyProvider: MgmReplyProvider> MagnetometerModel<ReplyProvider> {
self.switch_state = switch_state;
}
pub async fn send_sensor_values(&mut self, _: (), scheduler: &Scheduler<Self>) {
pub async fn send_sensor_values(&mut self, _: (), scheduler: &mut Context<Self>) {
self.reply_sender
.send(ReplyProvider::create_mgm_reply(MgmReplyCommon {
switch_state: self.switch_state,
@@ -114,11 +114,11 @@ impl MagnetorquerModel {
pub async fn apply_torque(
&mut self,
duration_and_dipole: (Duration, MgtDipole),
scheduler: &Scheduler<Self>,
cx: &mut Context<Self>,
) {
self.torque_dipole = duration_and_dipole.1;
self.torquing = true;
if scheduler
if cx
.schedule_event(duration_and_dipole.0, Self::clear_torque, ())
.is_err()
{
@@ -138,12 +138,11 @@ impl MagnetorquerModel {
self.generate_magnetic_field(()).await;
}
pub async fn request_housekeeping_data(&mut self, _: (), scheduler: &Scheduler<Self>) {
pub async fn request_housekeeping_data(&mut self, _: (), cx: &mut Context<Self>) {
if self.switch_state != SwitchStateBinary::On {
return;
}
scheduler
.schedule_event(Duration::from_millis(15), Self::send_housekeeping_data, ())
cx.schedule_event(Duration::from_millis(15), Self::send_housekeeping_data, ())
.expect("requesting housekeeping data failed")
}
@@ -200,7 +199,7 @@ pub mod tests {
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
let sim_reply = sim_testbench.try_receive_next_reply();
assert!(sim_reply.is_some());
let sim_reply = sim_reply.unwrap();
@@ -223,21 +222,21 @@ pub mod tests {
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
let mut sim_reply_res = sim_testbench.try_receive_next_reply();
assert!(sim_reply_res.is_some());
let mut sim_reply = sim_reply_res.unwrap();
assert_eq!(sim_reply.component(), SimComponent::MgmLis3Mdl);
let first_reply = MgmLis3MdlReply::from_sim_message(&sim_reply)
.expect("failed to deserialize MGM sensor values");
sim_testbench.step_by(Duration::from_millis(50));
sim_testbench.step_until(Duration::from_millis(50)).unwrap();
request = SimRequest::new_with_epoch_time(MgmRequestLis3Mdl::RequestSensorData);
sim_testbench
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
sim_reply_res = sim_testbench.try_receive_next_reply();
assert!(sim_reply_res.is_some());
sim_reply = sim_reply_res.unwrap();
@@ -272,7 +271,7 @@ pub mod tests {
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
let sim_reply_res = sim_testbench.try_receive_next_reply();
assert!(sim_reply_res.is_none());
}
@@ -287,7 +286,7 @@ pub mod tests {
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
let sim_reply_res = sim_testbench.try_receive_next_reply();
assert!(sim_reply_res.is_some());
let sim_reply = sim_reply_res.unwrap();
@@ -308,7 +307,7 @@ pub mod tests {
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
let sim_reply_res = sim_testbench.try_receive_next_reply();
assert!(sim_reply_res.is_some());
let sim_reply = sim_reply_res.unwrap();
@@ -339,7 +338,7 @@ pub mod tests {
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step_by(Duration::from_millis(5));
sim_testbench.step_until(Duration::from_millis(5)).unwrap();
check_mgt_hk(
&mut sim_testbench,
@@ -348,7 +347,9 @@ pub mod tests {
torquing: true,
},
);
sim_testbench.step_by(Duration::from_millis(100));
sim_testbench
.step_until(Duration::from_millis(100))
.unwrap();
check_mgt_hk(
&mut sim_testbench,
MgtHkSet {

View File

@@ -1,7 +1,7 @@
use std::{sync::mpsc, time::Duration};
use asynchronix::{
simulation::{Address, Simulation},
use nexosim::{
simulation::{Address, Scheduler, Simulation},
time::{Clock, MonotonicTime, SystemClock},
};
use satrs_minisim::{
@@ -23,35 +23,52 @@ const MGM_REQ_WIRETAPPING: bool = false;
const PCDU_REQ_WIRETAPPING: bool = false;
const MGT_REQ_WIRETAPPING: bool = false;
pub struct ModelAddrWrapper {
mgm_addr: Address<MagnetometerModel<MgmLis3MdlReply>>,
pcdu_addr: Address<PcduModel>,
mgt_addr: Address<MagnetorquerModel>,
}
// The simulation controller processes requests and drives the simulation.
#[allow(dead_code)]
pub struct SimController {
pub sys_clock: SystemClock,
pub request_receiver: mpsc::Receiver<SimRequest>,
pub reply_sender: mpsc::Sender<SimReply>,
pub simulation: Simulation,
pub mgm_addr: Address<MagnetometerModel<MgmLis3MdlReply>>,
pub pcdu_addr: Address<PcduModel>,
pub mgt_addr: Address<MagnetorquerModel>,
pub scheduler: Scheduler,
pub addr_wrapper: ModelAddrWrapper,
}
impl ModelAddrWrapper {
pub fn new(
mgm_addr: Address<MagnetometerModel<MgmLis3MdlReply>>,
pcdu_addr: Address<PcduModel>,
mgt_addr: Address<MagnetorquerModel>,
) -> Self {
Self {
mgm_addr,
pcdu_addr,
mgt_addr,
}
}
}
impl SimController {
pub fn new(
sys_clock: SystemClock,
request_receiver: mpsc::Receiver<SimRequest>,
reply_sender: mpsc::Sender<SimReply>,
simulation: Simulation,
mgm_addr: Address<MagnetometerModel<MgmLis3MdlReply>>,
pcdu_addr: Address<PcduModel>,
mgt_addr: Address<MagnetorquerModel>,
scheduler: Scheduler,
addr_wrapper: ModelAddrWrapper,
) -> Self {
Self {
sys_clock,
request_receiver,
reply_sender,
simulation,
mgm_addr,
pcdu_addr,
mgt_addr,
scheduler,
addr_wrapper,
}
}
@@ -62,7 +79,7 @@ impl SimController {
// Check for UDP requests every millisecond. Shift the simulator ahead here to prevent
// replies lying in the past.
t += Duration::from_millis(udp_polling_interval_ms);
self.sys_clock.synchronize(t);
let _synch_status = self.sys_clock.synchronize(t);
self.handle_sim_requests(t_old);
self.simulation
.step_until(t)
@@ -118,11 +135,13 @@ impl SimController {
}
match mgm_request {
MgmRequestLis3Mdl::RequestSensorData => {
self.simulation.send_event(
MagnetometerModel::send_sensor_values,
(),
&self.mgm_addr,
);
self.simulation
.process_event(
MagnetometerModel::send_sensor_values,
(),
&self.addr_wrapper.mgm_addr,
)
.expect("event execution error for mgm");
}
}
Ok(())
@@ -136,14 +155,21 @@ impl SimController {
match pcdu_request {
PcduRequest::RequestSwitchInfo => {
self.simulation
.send_event(PcduModel::request_switch_info, (), &self.pcdu_addr);
.process_event(
PcduModel::request_switch_info,
(),
&self.addr_wrapper.pcdu_addr,
)
.unwrap();
}
PcduRequest::SwitchDevice { switch, state } => {
self.simulation.send_event(
PcduModel::switch_device,
(switch, state),
&self.pcdu_addr,
);
self.simulation
.process_event(
PcduModel::switch_device,
(switch, state),
&self.addr_wrapper.pcdu_addr,
)
.unwrap();
}
}
Ok(())
@@ -155,17 +181,23 @@ impl SimController {
log::info!("received MGT request: {:?}", mgt_request);
}
match mgt_request {
MgtRequest::ApplyTorque { duration, dipole } => self.simulation.send_event(
MagnetorquerModel::apply_torque,
(duration, dipole),
&self.mgt_addr,
),
MgtRequest::RequestHk => self.simulation.send_event(
MagnetorquerModel::request_housekeeping_data,
(),
&self.mgt_addr,
),
}
MgtRequest::ApplyTorque { duration, dipole } => self
.simulation
.process_event(
MagnetorquerModel::apply_torque,
(duration, dipole),
&self.addr_wrapper.mgt_addr,
)
.unwrap(),
MgtRequest::RequestHk => self
.simulation
.process_event(
MagnetorquerModel::request_housekeeping_data,
(),
&self.addr_wrapper.mgt_addr,
)
.unwrap(),
};
Ok(())
}
@@ -199,7 +231,7 @@ mod tests {
.send_request(request)
.expect("sending sim ctrl request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
let sim_reply = sim_testbench.try_receive_next_reply();
assert!(sim_reply.is_some());
let sim_reply = sim_reply.unwrap();

View File

@@ -1,8 +1,8 @@
use std::{sync::mpsc, time::Duration};
use asynchronix::{
model::{Model, Output},
time::Scheduler,
use nexosim::{
model::{Context, Model},
ports::Output,
};
use satrs::power::SwitchStateBinary;
use satrs_minisim::{
@@ -29,14 +29,13 @@ impl PcduModel {
}
}
pub async fn request_switch_info(&mut self, _: (), scheduler: &Scheduler<Self>) {
scheduler
.schedule_event(
Duration::from_millis(SWITCH_INFO_DELAY_MS),
Self::send_switch_info,
(),
)
.expect("requesting switch info failed");
pub async fn request_switch_info(&mut self, _: (), cx: &mut Context<Self>) {
cx.schedule_event(
Duration::from_millis(SWITCH_INFO_DELAY_MS),
Self::send_switch_info,
(),
)
.expect("requesting switch info failed");
}
pub fn send_switch_info(&mut self) {
@@ -92,7 +91,7 @@ pub(crate) mod tests {
.send_request(request)
.expect("sending MGM switch request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
}
#[allow(dead_code)]
@@ -113,7 +112,7 @@ pub(crate) mod tests {
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step();
sim_testbench.step().unwrap();
let sim_reply = sim_testbench.try_receive_next_reply();
assert!(sim_reply.is_some());
let sim_reply = sim_reply.unwrap();
@@ -143,12 +142,12 @@ pub(crate) mod tests {
.send_request(request)
.expect("sending MGM request failed");
sim_testbench.handle_sim_requests_time_agnostic();
sim_testbench.step_by(Duration::from_millis(1));
sim_testbench.step_until(Duration::from_millis(1)).unwrap();
let sim_reply = sim_testbench.try_receive_next_reply();
assert!(sim_reply.is_none());
// Reply takes 20ms
sim_testbench.step_by(Duration::from_millis(25));
sim_testbench.step_until(Duration::from_millis(25)).unwrap();
let sim_reply = sim_testbench.try_receive_next_reply();
assert!(sim_reply.is_some());
let sim_reply = sim_reply.unwrap();

View File

@@ -1,4 +1,4 @@
use asynchronix::time::MonotonicTime;
use nexosim::time::MonotonicTime;
use num_enum::{IntoPrimitive, TryFromPrimitive};
use serde::{de::DeserializeOwned, Deserialize, Serialize};

View File

@@ -1,8 +1,8 @@
use acs::{MagnetometerModel, MagnetorquerModel};
use asynchronix::simulation::{Mailbox, SimInit};
use asynchronix::time::{MonotonicTime, SystemClock};
use controller::SimController;
use controller::{ModelAddrWrapper, SimController};
use eps::PcduModel;
use nexosim::simulation::{Mailbox, SimInit};
use nexosim::time::{MonotonicTime, SystemClock};
use satrs_minisim::udp::SIM_CTRL_PORT;
use satrs_minisim::{SimReply, SimRequest};
use std::sync::mpsc;
@@ -63,19 +63,20 @@ fn create_sim_controller(
} else {
SimInit::new()
};
let simulation = sim_init
.add_model(mgm_model, mgm_mailbox)
.add_model(pcdu_model, pcdu_mailbox)
.add_model(mgt_model, mgt_mailbox)
.init(start_time);
let addrs = ModelAddrWrapper::new(mgm_addr, pcdu_addr, mgt_addr);
let (simulation, scheduler) = sim_init
.add_model(mgm_model, mgm_mailbox, "MGM model")
.add_model(pcdu_model, pcdu_mailbox, "PCDU model")
.add_model(mgt_model, mgt_mailbox, "MGT model")
.init(start_time)
.unwrap();
SimController::new(
sys_clock,
request_receiver,
reply_sender,
simulation,
mgm_addr,
pcdu_addr,
mgt_addr,
scheduler,
addrs,
)
}

View File

@@ -1,7 +1,10 @@
use delegate::delegate;
use std::{sync::mpsc, time::Duration};
use std::sync::mpsc;
use asynchronix::time::MonotonicTime;
use nexosim::{
simulation::ExecutionError,
time::{Deadline, MonotonicTime},
};
use satrs_minisim::{SimReply, SimRequest};
use crate::{controller::SimController, create_sim_controller, ThreadingModel};
@@ -35,8 +38,8 @@ impl SimTestbench {
pub fn handle_sim_requests(&mut self, old_timestamp: MonotonicTime);
}
to self.sim_controller.simulation {
pub fn step(&mut self);
pub fn step_by(&mut self, duration: Duration);
pub fn step(&mut self) -> Result<(), ExecutionError>;
pub fn step_until(&mut self, duration: impl Deadline) -> Result<(), ExecutionError>;
}
}

View File

@@ -1,4 +1,4 @@
use asynchronix::time::MonotonicTime;
use nexosim::time::MonotonicTime;
pub fn current_millis(time: MonotonicTime) -> u64 {
(time.as_secs() as u64 * 1000) + (time.subsec_nanos() as u64 / 1_000_000)

View File

@@ -8,6 +8,10 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
# [unreleased]
# [v0.2.1] 2024-11-15
Increased allowed spacepackets to v0.13
# [v0.2.0] 2024-11-04
Semver bump, due to added features in v0.1.4

View File

@@ -19,6 +19,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
## Added
- `StaticHeaplessMemoryPool` which can be grown with user-provided static buffers.
- Scheduling table for systems with a standard runtime
# [v0.2.1] 2024-05-19

View File

@@ -13,89 +13,36 @@ keywords = ["no-std", "space", "aerospace"]
categories = ["aerospace", "aerospace::space-protocols", "no-std", "hardware-support", "embedded"]
[dependencies]
satrs-shared = ">=0.1.3, <=0.2"
delegate = ">0.7, <=0.13"
paste = "1"
derive-new = ">=0.6, <=0.7"
smallvec = "1"
crc = "3"
num_enum = { version = ">0.5, <=0.7", default-features = false }
spacepackets = { version = "0.13", default-features = false }
cobs = { version = "0.3", default-features = false }
num-traits = { version = "0.2", default-features = false }
thiserror = { version = "2", default-features = false }
[dependencies.satrs-shared]
version = ">=0.1.3, <=0.2"
path = "../satrs-shared"
[dependencies.num_enum]
version = ">0.5, <=0.7"
default-features = false
[dependencies.spacepackets]
version = "0.13"
default-features = false
[dependencies.cobs]
git = "https://github.com/robamu/cobs.rs.git"
version = "0.2.3"
branch = "all_features"
default-features = false
[dependencies.num-traits]
version = "0.2"
default-features = false
[dependencies.dyn-clone]
version = "1"
optional = true
[dependencies.hashbrown]
version = ">=0.14, <=0.15"
optional = true
[dependencies.heapless]
version = "0.8"
optional = true
[dependencies.downcast-rs]
version = "1.2"
default-features = false
optional = true
[dependencies.bus]
version = "2.2"
optional = true
[dependencies.crossbeam-channel]
version= "0.5"
default-features = false
optional = true
[dependencies.thiserror]
version = "2"
default-features = false
[dependencies.serde]
version = "1"
default-features = false
optional = true
[dependencies.socket2]
version = "0.5.4"
features = ["all"]
optional = true
[dependencies.mio]
version = "1"
features = ["os-poll", "net"]
optional = true
[dependencies.defmt]
version = "0.3"
optional = true
hashbrown = { version = ">=0.14, <=0.15", optional = true }
static_cell = { version = "2", optional = true }
dyn-clone = { version = "1", optional = true }
heapless = { version = "0.8", optional = true }
downcast-rs = { version = "2", default-features = false, optional = true }
bus = { version = "2.2", optional = true }
crossbeam-channel = { version = "0.5", default-features = false, optional = true }
serde = { version = "1", default-features = false, optional = true }
socket2 = { version = "0.5", features = ["all"], optional = true }
mio = { version = "1", features = ["os-poll", "net"], optional = true }
defmt = { version = "0.3", optional = true }
[dev-dependencies]
serde = "1"
zerocopy = "0.8"
once_cell = "1"
serde_json = "1"
rand = "0.8"
rand = "0.9"
tempfile = "3"
[dev-dependencies.postcard]
@@ -107,7 +54,6 @@ std = [
"downcast-rs/std",
"alloc",
"bus",
"postcard/use-std",
"crossbeam-channel/std",
"serde/std",
"spacepackets/std",
@@ -125,10 +71,15 @@ alloc = [
]
serde = ["dep:serde", "spacepackets/serde", "satrs-shared/serde"]
crossbeam = ["crossbeam-channel"]
heapless = ["dep:heapless"]
heapless = ["dep:heapless", "static_cell"]
defmt = ["dep:defmt", "spacepackets/defmt"]
test_util = []
[package.metadata.docs.rs]
all-features = true
rustdoc-args = ["--generate-link-to-definition"]
[[test]]
name = "event_test"
path = "tests/pus_events.rs"
required-features = ["test_util"]

View File

@@ -15,20 +15,24 @@ pub enum OpResult {
TerminationRequested,
}
#[derive(Debug)]
pub enum ExecutionType {
Infinite,
Cycles(u32),
OneShot,
}
pub trait Executable: Send {
pub trait Executable {
type Error;
fn exec_type(&self) -> ExecutionType;
fn task_name(&self) -> &'static str;
fn periodic_op(&mut self, op_code: i32) -> Result<OpResult, Self::Error>;
}
pub trait ExecutableWithType: Executable {
fn exec_type(&self) -> ExecutionType;
}
/// This function allows executing one task which implements the [Executable] trait
///
/// # Arguments
@@ -39,7 +43,10 @@ pub trait Executable: Send {
/// * `op_code`: Operation code which is passed to the executable task
/// [operation call][Executable::periodic_op]
/// * `termination`: Optional termination handler which can cancel threads with a broadcast
pub fn exec_sched_single<T: Executable<Error = E> + Send + 'static + ?Sized, E: Send + 'static>(
pub fn exec_sched_single<
T: ExecutableWithType<Error = E> + Send + 'static + ?Sized,
E: Send + 'static,
>(
mut executable: Box<T>,
task_freq: Option<Duration>,
op_code: i32,
@@ -88,7 +95,10 @@ pub fn exec_sched_single<T: Executable<Error = E> + Send + 'static + ?Sized, E:
/// * `task_freq`: Optional frequency of task. Required for periodic and fixed cycle tasks
/// * `op_code`: Operation code which is passed to the executable task [operation call][Executable::periodic_op]
/// * `termination`: Optional termination handler which can cancel threads with a broadcast
pub fn exec_sched_multi<T: Executable<Error = E> + Send + 'static + ?Sized, E: Send + 'static>(
pub fn exec_sched_multi<
T: ExecutableWithType<Error = E> + Send + 'static + ?Sized,
E: Send + 'static,
>(
task_name: &'static str,
mut executable_vec: Vec<Box<T>>,
task_freq: Option<Duration>,
@@ -142,7 +152,10 @@ pub fn exec_sched_multi<T: Executable<Error = E> + Send + 'static + ?Sized, E: S
#[cfg(test)]
mod tests {
use super::{exec_sched_multi, exec_sched_single, Executable, ExecutionType, OpResult};
use super::{
exec_sched_multi, exec_sched_single, Executable, ExecutableWithType, ExecutionType,
OpResult,
};
use bus::Bus;
use std::boxed::Box;
use std::error::Error;
@@ -208,10 +221,6 @@ mod tests {
impl Executable for OneShotTask {
type Error = ExampleError;
fn exec_type(&self) -> ExecutionType {
ExecutionType::OneShot
}
fn task_name(&self) -> &'static str {
ONE_SHOT_TASK_NAME
}
@@ -229,15 +238,17 @@ mod tests {
}
}
impl ExecutableWithType for OneShotTask {
fn exec_type(&self) -> ExecutionType {
ExecutionType::OneShot
}
}
const CYCLE_TASK_NAME: &str = "Fixed Cycles Task";
impl Executable for FixedCyclesTask {
type Error = ExampleError;
fn exec_type(&self) -> ExecutionType {
ExecutionType::Cycles(self.cycles)
}
fn task_name(&self) -> &'static str {
CYCLE_TASK_NAME
}
@@ -255,15 +266,17 @@ mod tests {
}
}
impl ExecutableWithType for FixedCyclesTask {
fn exec_type(&self) -> ExecutionType {
ExecutionType::Cycles(self.cycles)
}
}
const PERIODIC_TASK_NAME: &str = "Periodic Task";
impl Executable for PeriodicTask {
type Error = ExampleError;
fn exec_type(&self) -> ExecutionType {
ExecutionType::Infinite
}
fn task_name(&self) -> &'static str {
PERIODIC_TASK_NAME
}
@@ -281,6 +294,12 @@ mod tests {
}
}
impl ExecutableWithType for PeriodicTask {
fn exec_type(&self) -> ExecutionType {
ExecutionType::Infinite
}
}
#[test]
fn test_simple_one_shot() {
let expected_op_code = 42;
@@ -423,7 +442,7 @@ mod tests {
});
assert_eq!(cycled_task_0.task_name(), CYCLE_TASK_NAME);
assert_eq!(one_shot_task.task_name(), ONE_SHOT_TASK_NAME);
let task_vec: Vec<Box<dyn Executable<Error = ExampleError>>> =
let task_vec: Vec<Box<dyn ExecutableWithType<Error = ExampleError> + Send>> =
vec![one_shot_task, cycled_task_0, cycled_task_1];
let jh = exec_sched_multi(
"multi-task-name",
@@ -493,7 +512,7 @@ mod tests {
});
assert_eq!(periodic_task_0.task_name(), PERIODIC_TASK_NAME);
assert_eq!(periodic_task_1.task_name(), PERIODIC_TASK_NAME);
let task_vec: Vec<Box<dyn Executable<Error = ExampleError>>> =
let task_vec: Vec<Box<dyn ExecutableWithType<Error = ExampleError> + Send>> =
vec![cycled_task, periodic_task_0, periodic_task_1];
let jh = exec_sched_multi(
"multi-task-name",

View File

@@ -36,6 +36,8 @@ pub mod pus;
pub mod queue;
pub mod request;
pub mod res_code;
#[cfg(feature = "alloc")]
pub mod scheduling;
pub mod time;
pub mod tmtc;

View File

@@ -387,18 +387,18 @@ pub mod heapless_mod {
#[macro_export]
macro_rules! static_subpool {
($pool_name: ident, $sizes_list_name: ident, $num_blocks: expr, $block_size: expr) => {
static mut $pool_name: core::mem::MaybeUninit<[u8; $num_blocks * $block_size]> =
core::mem::MaybeUninit::new([0; $num_blocks * $block_size]);
static mut $sizes_list_name: core::mem::MaybeUninit<[usize; $num_blocks]> =
core::mem::MaybeUninit::new([$crate::pool::STORE_FREE; $num_blocks]);
static $pool_name: static_cell::ConstStaticCell<[u8; $num_blocks * $block_size]> =
static_cell::ConstStaticCell::new([0; $num_blocks * $block_size]);
static $sizes_list_name: static_cell::ConstStaticCell<[usize; $num_blocks]> =
static_cell::ConstStaticCell::new([$crate::pool::STORE_FREE; $num_blocks]);
};
($pool_name: ident, $sizes_list_name: ident, $num_blocks: expr, $block_size: expr, $meta_data: meta) => {
#[$meta_data]
static mut $pool_name: core::mem::MaybeUninit<[u8; $num_blocks * $block_size]> =
core::mem::MaybeUninit::new([0; $num_blocks * $block_size]);
static $pool_name: static_cell::ConstStaticCell<[u8; $num_blocks * $block_size]> =
static_cell::ConstStaticCell::new([0; $num_blocks * $block_size]);
#[$meta_data]
static mut $sizes_list_name: core::mem::MaybeUninit<[usize; $num_blocks]> =
core::mem::MaybeUninit::new([$crate::pool::STORE_FREE; $num_blocks]);
static $sizes_list_name: static_cell::ConstStaticCell<[usize; $num_blocks]> =
static_cell::ConstStaticCell::new([$crate::pool::STORE_FREE; $num_blocks]);
};
}
@@ -435,17 +435,17 @@ pub mod heapless_mod {
///
/// let mut mem_pool: StaticHeaplessMemoryPool<2> = StaticHeaplessMemoryPool::new(true);
/// mem_pool.grow(
/// unsafe { SUBPOOL_SMALL.assume_init_mut() },
/// unsafe { SUBPOOL_SMALL_SIZES.assume_init_mut() },
/// SUBPOOL_SMALL.take(),
/// SUBPOOL_SMALL_SIZES.take(),
/// SUBPOOL_SMALL_NUM_BLOCKS,
/// false
/// );
/// ).unwrap();
/// mem_pool.grow(
/// unsafe { SUBPOOL_LARGE.assume_init_mut() },
/// unsafe { SUBPOOL_LARGE_SIZES.assume_init_mut() },
/// SUBPOOL_LARGE.take(),
/// SUBPOOL_LARGE_SIZES.take(),
/// SUBPOOL_LARGE_NUM_BLOCKS,
/// false
/// );
/// ).unwrap();
///
/// let mut read_buf: [u8; 16] = [0; 16];
/// let mut addr;
@@ -522,12 +522,14 @@ pub mod heapless_mod {
num_blocks: NumBlocks,
set_sizes_list_to_all_free: bool,
) -> Result<(), PoolIsFull> {
assert!(
(subpool_memory.len() % num_blocks as usize) == 0,
assert_eq!(
(subpool_memory.len() % num_blocks as usize),
0,
"pool slice length must be multiple of number of blocks"
);
assert!(
num_blocks as usize == sizes_list.len(),
assert_eq!(
num_blocks as usize,
sizes_list.len(),
"used block size list slice must be of same length as number of blocks"
);
let subpool_config = SubpoolConfig {
@@ -1584,21 +1586,33 @@ mod tests {
mod heapless_tests {
use super::*;
use crate::static_subpool;
use core::ptr::addr_of_mut;
use std::cell::UnsafeCell;
use std::sync::Mutex;
const SUBPOOL_1_BLOCK_SIZE: usize = 4;
const SUBPOOL_1_NUM_ELEMENTS: u16 = 4;
static mut SUBPOOL_1: [u8; SUBPOOL_1_NUM_ELEMENTS as usize * SUBPOOL_1_BLOCK_SIZE] =
[0; SUBPOOL_1_NUM_ELEMENTS as usize * SUBPOOL_1_BLOCK_SIZE];
static mut SUBPOOL_1_SIZES: [usize; SUBPOOL_1_NUM_ELEMENTS as usize] =
[STORE_FREE; SUBPOOL_1_NUM_ELEMENTS as usize];
static SUBPOOL_1: static_cell::ConstStaticCell<
[u8; SUBPOOL_1_NUM_ELEMENTS as usize * SUBPOOL_1_BLOCK_SIZE],
> = static_cell::ConstStaticCell::new(
[0; SUBPOOL_1_NUM_ELEMENTS as usize * SUBPOOL_1_BLOCK_SIZE],
);
static SUBPOOL_1_SIZES: Mutex<UnsafeCell<[usize; SUBPOOL_1_NUM_ELEMENTS as usize]>> =
Mutex::new(UnsafeCell::new(
[STORE_FREE; SUBPOOL_1_NUM_ELEMENTS as usize],
));
const SUBPOOL_2_NUM_ELEMENTS: u16 = 2;
const SUBPOOL_2_BLOCK_SIZE: usize = 8;
static mut SUBPOOL_2: [u8; SUBPOOL_2_NUM_ELEMENTS as usize * SUBPOOL_2_BLOCK_SIZE] =
[0; SUBPOOL_2_NUM_ELEMENTS as usize * SUBPOOL_2_BLOCK_SIZE];
static mut SUBPOOL_2_SIZES: [usize; SUBPOOL_2_NUM_ELEMENTS as usize] =
[STORE_FREE; SUBPOOL_2_NUM_ELEMENTS as usize];
static SUBPOOL_2: static_cell::ConstStaticCell<
[u8; SUBPOOL_2_NUM_ELEMENTS as usize * SUBPOOL_2_BLOCK_SIZE],
> = static_cell::ConstStaticCell::new(
[0; SUBPOOL_2_NUM_ELEMENTS as usize * SUBPOOL_2_BLOCK_SIZE],
);
static SUBPOOL_2_SIZES: static_cell::ConstStaticCell<
[usize; SUBPOOL_2_NUM_ELEMENTS as usize],
> = static_cell::ConstStaticCell::new([STORE_FREE; SUBPOOL_2_NUM_ELEMENTS as usize]);
const SUBPOOL_3_NUM_ELEMENTS: u16 = 1;
const SUBPOOL_3_BLOCK_SIZE: usize = 16;
@@ -1641,24 +1655,24 @@ mod tests {
StaticHeaplessMemoryPool::new(false);
assert!(heapless_pool
.grow(
unsafe { &mut *addr_of_mut!(SUBPOOL_1) },
unsafe { &mut *addr_of_mut!(SUBPOOL_1_SIZES) },
SUBPOOL_1.take(),
unsafe { &mut *SUBPOOL_1_SIZES.lock().unwrap().get() },
SUBPOOL_1_NUM_ELEMENTS,
true
)
.is_ok());
assert!(heapless_pool
.grow(
unsafe { &mut *addr_of_mut!(SUBPOOL_2) },
unsafe { &mut *addr_of_mut!(SUBPOOL_2_SIZES) },
SUBPOOL_2.take(),
SUBPOOL_2_SIZES.take(),
SUBPOOL_2_NUM_ELEMENTS,
true
)
.is_ok());
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_3.assume_init_mut() },
unsafe { SUBPOOL_3_SIZES.assume_init_mut() },
SUBPOOL_3.take(),
SUBPOOL_3_SIZES.take(),
SUBPOOL_3_NUM_ELEMENTS,
true
)
@@ -1780,16 +1794,16 @@ mod tests {
StaticHeaplessMemoryPool::new(true);
assert!(heapless_pool
.grow(
unsafe { &mut *addr_of_mut!(SUBPOOL_2) },
unsafe { &mut *addr_of_mut!(SUBPOOL_2_SIZES) },
SUBPOOL_2.take(),
SUBPOOL_2_SIZES.take(),
SUBPOOL_2_NUM_ELEMENTS,
true
)
.is_ok());
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_4.assume_init_mut() },
unsafe { SUBPOOL_4_SIZES.assume_init_mut() },
SUBPOOL_4.take(),
SUBPOOL_4_SIZES.take(),
SUBPOOL_4_NUM_ELEMENTS,
true
)
@@ -1803,16 +1817,16 @@ mod tests {
StaticHeaplessMemoryPool::new(true);
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_5.assume_init_mut() },
unsafe { SUBPOOL_5_SIZES.assume_init_mut() },
SUBPOOL_5.take(),
SUBPOOL_5_SIZES.take(),
SUBPOOL_5_NUM_ELEMENTS,
true
)
.is_ok());
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_3.assume_init_mut() },
unsafe { SUBPOOL_3_SIZES.assume_init_mut() },
SUBPOOL_3.take(),
SUBPOOL_3_SIZES.take(),
SUBPOOL_3_NUM_ELEMENTS,
true
)
@@ -1826,24 +1840,24 @@ mod tests {
StaticHeaplessMemoryPool::new(true);
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_5.assume_init_mut() },
unsafe { SUBPOOL_5_SIZES.assume_init_mut() },
SUBPOOL_5.take(),
SUBPOOL_5_SIZES.take(),
SUBPOOL_5_NUM_ELEMENTS,
true
)
.is_ok());
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_6.assume_init_mut() },
unsafe { SUBPOOL_6_SIZES.assume_init_mut() },
SUBPOOL_6.take(),
SUBPOOL_6_SIZES.take(),
SUBPOOL_6_NUM_ELEMENTS,
true
)
.is_ok());
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_3.assume_init_mut() },
unsafe { SUBPOOL_3_SIZES.assume_init_mut() },
SUBPOOL_3.take(),
SUBPOOL_3_SIZES.take(),
SUBPOOL_3_NUM_ELEMENTS,
true
)
@@ -1857,24 +1871,24 @@ mod tests {
StaticHeaplessMemoryPool::new(true);
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_5.assume_init_mut() },
unsafe { SUBPOOL_5_SIZES.assume_init_mut() },
SUBPOOL_5.take(),
SUBPOOL_5_SIZES.take(),
SUBPOOL_5_NUM_ELEMENTS,
true
)
.is_ok());
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_6.assume_init_mut() },
unsafe { SUBPOOL_6_SIZES.assume_init_mut() },
SUBPOOL_6.take(),
SUBPOOL_6_SIZES.take(),
SUBPOOL_6_NUM_ELEMENTS,
true
)
.is_ok());
assert!(heapless_pool
.grow(
unsafe { SUBPOOL_3.assume_init_mut() },
unsafe { SUBPOOL_3_SIZES.assume_init_mut() },
SUBPOOL_3.take(),
SUBPOOL_3_SIZES.take(),
SUBPOOL_3_NUM_ELEMENTS,
true
)

416
satrs/src/scheduling.rs Normal file
View File

@@ -0,0 +1,416 @@
use core::{convert::Infallible, fmt::Debug, time::Duration};
use std::time::Instant;
use thiserror::Error;
use crate::executable::Executable;
#[cfg(feature = "std")]
pub use std_mod::*;
#[derive(Debug, Default)]
pub struct SchedulingTable {
execution_frequency: Duration,
pub table: alloc::vec::Vec<u32>,
}
#[derive(Debug, Error)]
pub enum InvalidSlotError {
#[error("slot time is larger than the execution frequency")]
SlotTimeLargerThanFrequency,
#[error("slot time is smaller than previous slot")]
SmallerThanPreviousSlot {
slot_time_ms: u32,
prev_slot_time_ms: u32,
},
}
impl SchedulingTable {
pub fn new(execution_frequency: Duration) -> Self {
Self {
execution_frequency,
table: Default::default(),
}
}
pub fn add_slot(&mut self, relative_execution_time_ms: u32) -> Result<(), InvalidSlotError> {
if relative_execution_time_ms > self.execution_frequency.as_millis() as u32 {
return Err(InvalidSlotError::SlotTimeLargerThanFrequency);
}
if !self.table.is_empty() {
let prev_slot_ms = *self.table.last().unwrap();
if relative_execution_time_ms < prev_slot_ms {
return Err(InvalidSlotError::SmallerThanPreviousSlot {
slot_time_ms: relative_execution_time_ms,
prev_slot_time_ms: *self.table.last().unwrap(),
});
}
}
self.table.push(relative_execution_time_ms);
Ok(())
}
}
#[derive(Debug, Error)]
pub enum TaskWithSchedulingTableError {
#[error("scheudlig table error: {0}")]
InvalidSlot(#[from] InvalidSlotError),
#[error("task lock error")]
LockError,
#[error("task borrow error")]
BorrowError,
}
pub trait DeadlineMissedHandler {
fn deadline_missed_callback(&mut self, task_name: &'static str, op_code: i32);
}
pub trait TaskExecutor {
fn with_task<F: FnOnce(&mut dyn Executable<Error = Infallible>)>(&self, f: F);
}
#[cfg(feature = "std")]
pub mod std_mod {
use core::cell::RefCell;
use std::{
rc::Rc,
sync::{Arc, Mutex},
vec::Vec,
};
use super::*;
impl TaskExecutor for Arc<Mutex<dyn Executable<Error = Infallible> + Send>> {
fn with_task<F: FnOnce(&mut dyn Executable<Error = Infallible>)>(&self, f: F) {
let mut task = self.lock().unwrap();
f(&mut *task);
}
}
impl TaskExecutor for Rc<RefCell<dyn Executable<Error = Infallible>>> {
fn with_task<F: FnOnce(&mut dyn Executable<Error = Infallible>)>(&self, f: F) {
let mut task = self.borrow_mut();
f(&mut *task);
}
}
pub struct TaskWithOpCode<T: TaskExecutor> {
task: T,
op_code: i32,
}
pub struct TaskWithSchedulingTable<T: TaskExecutor> {
start_of_slot: Instant,
end_of_slot: Instant,
deadline_missed_ms_count: u32,
table: SchedulingTable,
tasks: Vec<TaskWithOpCode<T>>,
}
impl TaskWithSchedulingTable<Rc<RefCell<dyn Executable<Error = Infallible>>>> {
/// Add a new task to the scheduling table
///
/// The task needs to be wrapped inside [Rc] and [RefCell]. The task is not sendable and
/// needs to be created inside the target thread.
pub fn add_task(
&mut self,
relative_execution_time_ms: u32,
task: Rc<RefCell<dyn Executable<Error = Infallible>>>,
op_code: i32,
) -> Result<(), TaskWithSchedulingTableError> {
self.table.add_slot(relative_execution_time_ms)?;
self.tasks.push(TaskWithOpCode { task, op_code });
Ok(())
}
}
impl TaskWithSchedulingTable<Arc<Mutex<dyn Executable<Error = Infallible> + Send>>> {
/// Add a new task to the scheduling table
///
/// The task needs to be wrapped inside [Arc] and [Mutex], but the task can be sent to
/// a different thread.
pub fn add_task_sendable(
&mut self,
relative_execution_time_ms: u32,
task: Arc<Mutex<dyn Executable<Error = Infallible> + Send>>,
op_code: i32,
) -> Result<(), TaskWithSchedulingTableError> {
self.table.add_slot(relative_execution_time_ms)?;
self.tasks.push(TaskWithOpCode { task, op_code });
Ok(())
}
}
impl<T: TaskExecutor> TaskWithSchedulingTable<T> {
pub fn new(execution_frequency: Duration) -> Self {
Self {
start_of_slot: Instant::now(),
end_of_slot: Instant::now(),
deadline_missed_ms_count: 10,
table: SchedulingTable::new(execution_frequency),
tasks: Default::default(),
}
}
/// Can be used to set the start of the slot to the current time. This is useful if a custom
/// runner implementation is used instead of the [Self::start] method.
pub fn init_start_of_slot(&mut self) {
self.start_of_slot = Instant::now();
}
pub fn run_one_task_cycle(
&mut self,
deadline_missed_cb: &mut impl DeadlineMissedHandler,
) -> Result<(), TaskWithSchedulingTableError> {
self.end_of_slot = self.start_of_slot + self.table.execution_frequency;
for (&relative_execution_time_ms, task_with_op_code) in
self.table.table.iter().zip(self.tasks.iter_mut())
{
let scheduled_execution_time = self.start_of_slot
+ core::time::Duration::from_millis(relative_execution_time_ms as u64);
let now = Instant::now();
if now < scheduled_execution_time {
std::thread::sleep(scheduled_execution_time - now);
} else if (now - scheduled_execution_time).as_millis()
> self.deadline_missed_ms_count.into()
{
task_with_op_code.task.with_task(|task| {
deadline_missed_cb
.deadline_missed_callback(task.task_name(), task_with_op_code.op_code);
});
}
task_with_op_code.task.with_task(|task| {
// Unwrapping is okay here because we constrain the tasks to be infallible.
task.periodic_op(task_with_op_code.op_code).unwrap();
});
}
let now = Instant::now();
if now <= self.end_of_slot {
let diff = self.end_of_slot - now;
std::thread::sleep(diff);
self.start_of_slot = self.end_of_slot;
} else if now > self.end_of_slot + self.table.execution_frequency {
// We're getting strongly out of sync. Set the new start timt to now.
self.start_of_slot = now;
}
Ok(())
}
}
}
#[cfg(test)]
mod tests {
use core::{cell::RefCell, convert::Infallible, time::Duration};
use std::{
println,
rc::Rc,
sync::{
mpsc::{self, TryRecvError},
Arc, Mutex,
},
time::Instant,
};
use crate::executable::{Executable, OpResult};
use super::{DeadlineMissedHandler, TaskWithSchedulingTable};
#[derive(Debug)]
pub struct CallInfo {
time: std::time::Instant,
op_code: i32,
}
pub struct Task1 {
called_queue: mpsc::Sender<CallInfo>,
}
impl Executable for Task1 {
type Error = Infallible;
fn task_name(&self) -> &'static str {
"Task1"
}
fn periodic_op(&mut self, op_code: i32) -> Result<OpResult, Self::Error> {
self.called_queue
.send(CallInfo {
time: Instant::now(),
op_code,
})
.unwrap();
Ok(OpResult::Ok)
}
}
pub struct Task2 {
called_queue: mpsc::Sender<CallInfo>,
}
impl Executable for Task2 {
type Error = Infallible;
fn task_name(&self) -> &'static str {
"Task2"
}
fn periodic_op(&mut self, op_code: i32) -> Result<OpResult, Self::Error> {
self.called_queue
.send(CallInfo {
time: Instant::now(),
op_code,
})
.unwrap();
Ok(OpResult::Ok)
}
}
#[derive(Default)]
pub struct DeadlineMissed {
call_count: u32,
}
impl DeadlineMissedHandler for DeadlineMissed {
fn deadline_missed_callback(&mut self, task_name: &'static str, _op_code: i32) {
println!("task name {task_name} missed the deadline");
self.call_count += 1;
}
}
#[test]
pub fn basic_test() {
let (tx_t1, rx_t1) = mpsc::channel();
let (tx_t2, rx_t2) = mpsc::channel();
let t1 = Task1 {
called_queue: tx_t1,
};
let t2 = Task2 {
called_queue: tx_t2,
};
let mut deadline_missed_cb = DeadlineMissed::default();
let mut exec_task = TaskWithSchedulingTable::new(Duration::from_millis(200));
let t1_first_slot = Rc::new(RefCell::new(t1));
let t1_second_slot = t1_first_slot.clone();
let t2_first_slot = Rc::new(RefCell::new(t2));
let t2_second_slot = t2_first_slot.clone();
exec_task.add_task(0, t1_first_slot, 0).unwrap();
exec_task.add_task(50, t1_second_slot, -1).unwrap();
exec_task.add_task(100, t2_first_slot, 1).unwrap();
exec_task.add_task(150, t2_second_slot, 2).unwrap();
let now = Instant::now();
exec_task.init_start_of_slot();
exec_task
.run_one_task_cycle(&mut deadline_missed_cb)
.unwrap();
let mut call_info = rx_t1.try_recv().unwrap();
assert_eq!(call_info.op_code, 0);
let diff_call_to_start = call_info.time - now;
assert!(diff_call_to_start.as_millis() < 30);
call_info = rx_t1.try_recv().unwrap();
assert_eq!(call_info.op_code, -1);
let diff_call_to_start = call_info.time - now;
assert!(diff_call_to_start.as_millis() < 80);
assert!(diff_call_to_start.as_millis() >= 50);
matches!(rx_t1.try_recv().unwrap_err(), TryRecvError::Empty);
call_info = rx_t2.try_recv().unwrap();
assert_eq!(call_info.op_code, 1);
let diff_call_to_start = call_info.time - now;
assert!(diff_call_to_start.as_millis() < 120);
assert!(diff_call_to_start.as_millis() >= 100);
call_info = rx_t2.try_recv().unwrap();
assert_eq!(call_info.op_code, 2);
let diff_call_to_start = call_info.time - now;
assert!(diff_call_to_start.as_millis() < 180);
assert!(diff_call_to_start.as_millis() >= 150);
matches!(rx_t2.try_recv().unwrap_err(), TryRecvError::Empty);
assert_eq!(deadline_missed_cb.call_count, 0);
}
#[test]
pub fn basic_test_with_arc_mutex() {
let (tx_t1, rx_t1) = mpsc::channel();
let (tx_t2, rx_t2) = mpsc::channel();
let t1 = Task1 {
called_queue: tx_t1,
};
let t2 = Task2 {
called_queue: tx_t2,
};
let mut deadline_missed_cb = DeadlineMissed::default();
let mut exec_task = TaskWithSchedulingTable::new(Duration::from_millis(200));
let t1_first_slot = Arc::new(Mutex::new(t1));
let t1_second_slot = t1_first_slot.clone();
let t2_first_slot = Arc::new(Mutex::new(t2));
let t2_second_slot = t2_first_slot.clone();
exec_task.add_task_sendable(0, t1_first_slot, 0).unwrap();
exec_task.add_task_sendable(50, t1_second_slot, -1).unwrap();
exec_task.add_task_sendable(100, t2_first_slot, 1).unwrap();
exec_task.add_task_sendable(150, t2_second_slot, 2).unwrap();
let now = Instant::now();
exec_task.init_start_of_slot();
exec_task
.run_one_task_cycle(&mut deadline_missed_cb)
.unwrap();
let mut call_info = rx_t1.try_recv().unwrap();
assert_eq!(call_info.op_code, 0);
let diff_call_to_start = call_info.time - now;
assert!(diff_call_to_start.as_millis() < 30);
call_info = rx_t1.try_recv().unwrap();
assert_eq!(call_info.op_code, -1);
let diff_call_to_start = call_info.time - now;
assert!(diff_call_to_start.as_millis() < 80);
assert!(diff_call_to_start.as_millis() >= 50);
matches!(rx_t1.try_recv().unwrap_err(), TryRecvError::Empty);
call_info = rx_t2.try_recv().unwrap();
assert_eq!(call_info.op_code, 1);
let diff_call_to_start = call_info.time - now;
assert!(diff_call_to_start.as_millis() < 120);
assert!(diff_call_to_start.as_millis() >= 100);
call_info = rx_t2.try_recv().unwrap();
assert_eq!(call_info.op_code, 2);
let diff_call_to_start = call_info.time - now;
assert!(diff_call_to_start.as_millis() < 180);
assert!(diff_call_to_start.as_millis() >= 150);
matches!(rx_t2.try_recv().unwrap_err(), TryRecvError::Empty);
assert_eq!(deadline_missed_cb.call_count, 0);
}
#[test]
pub fn basic_test_in_thread() {
let mut deadline_missed_cb = DeadlineMissed::default();
std::thread::spawn(move || {
let (tx_t1, _rx_t1) = mpsc::channel();
let t1 = Task1 {
called_queue: tx_t1,
};
// Need to construct this in the thread, the task table in not [Send]
let mut exec_task = TaskWithSchedulingTable::new(Duration::from_millis(200));
let t1_wrapper = Rc::new(RefCell::new(t1));
exec_task.add_task(0, t1_wrapper, 0).unwrap();
exec_task
.run_one_task_cycle(&mut deadline_missed_cb)
.unwrap();
});
let mut deadline_missed_cb = DeadlineMissed::default();
let (tx_t1, _rx_t1) = mpsc::channel();
let t1 = Task1 {
called_queue: tx_t1,
};
let mut exec_task_sendable = TaskWithSchedulingTable::new(Duration::from_millis(200));
exec_task_sendable
.add_task_sendable(0, Arc::new(Mutex::new(t1)), 1)
.unwrap();
std::thread::spawn(move || {
exec_task_sendable
.run_one_task_cycle(&mut deadline_missed_cb)
.unwrap();
});
}
}

View File

@@ -17,37 +17,37 @@ impl PusTmWithCdsShortHelper {
}
#[cfg(feature = "std")]
pub fn create_pus_tm_timestamp_now<'a>(
&'a mut self,
pub fn create_pus_tm_timestamp_now<'data>(
&mut self,
service: u8,
subservice: u8,
source_data: &'a [u8],
source_data: &'data [u8],
seq_count: u16,
) -> PusTmCreator {
) -> PusTmCreator<'_, 'data> {
let time_stamp = CdsTime::now_with_u16_days().unwrap();
time_stamp.write_to_bytes(&mut self.cds_short_buf).unwrap();
self.create_pus_tm_common(service, subservice, source_data, seq_count)
}
pub fn create_pus_tm_with_stamper<'a>(
&'a mut self,
pub fn create_pus_tm_with_stamper<'data>(
&mut self,
service: u8,
subservice: u8,
source_data: &'a [u8],
source_data: &'data [u8],
stamper: &CdsTime,
seq_count: u16,
) -> PusTmCreator {
) -> PusTmCreator<'_, 'data> {
stamper.write_to_bytes(&mut self.cds_short_buf).unwrap();
self.create_pus_tm_common(service, subservice, source_data, seq_count)
}
fn create_pus_tm_common<'a>(
&'a self,
fn create_pus_tm_common<'data>(
&self,
service: u8,
subservice: u8,
source_data: &'a [u8],
source_data: &'data [u8],
seq_count: u16,
) -> PusTmCreator {
) -> PusTmCreator<'_, 'data> {
let reply_header = SpHeader::new_for_unseg_tm(self.apid, seq_count, 0);
let tc_header = PusTmSecondaryHeader::new_simple(service, subservice, &self.cds_short_buf);
PusTmCreator::new(reply_header, tc_header, source_data, true)