aboutsummaryrefslogtreecommitdiff
path: root/book/ru/src/internals/late-resources.md
diff options
context:
space:
mode:
authorHenrik Tjäder <henrik@tjaders.com>2023-02-24 21:28:13 +0100
committerHenrik Tjäder <henrik@tjaders.com>2023-03-01 00:35:25 +0100
commit0fc86d972c0305e73252dc20d702d647eb342ee5 (patch)
treeeb01e1556958912344b890c964ff3f364aaad0d2 /book/ru/src/internals/late-resources.md
parent032316855d8b55fc572ab7fcbd1de7ba394b2fd1 (diff)
Book: Remove RTIC v1 Russian translation
Diffstat (limited to 'book/ru/src/internals/late-resources.md')
-rw-r--r--book/ru/src/internals/late-resources.md113
1 files changed, 0 insertions, 113 deletions
diff --git a/book/ru/src/internals/late-resources.md b/book/ru/src/internals/late-resources.md
deleted file mode 100644
index 146c438..0000000
--- a/book/ru/src/internals/late-resources.md
+++ /dev/null
@@ -1,113 +0,0 @@
-# Поздние ресурсы
-
-Некоторые ресурсы инициализируются во время выполнения после завершения функции `init`.
-Важно то, что ресурсы (статические переменные) полностью инициализируются
-до того, как задачи смогут запуститься, вот почему они должны быть инициализированы
-пока прерывания отключены.
-
-Ниже показан пример кода, генерируемого фреймворком для инициализации позних ресурсов.
-
-``` rust
-#[rtic::app(device = ..)]
-mod app {
- struct Resources {
- x: Thing,
- }
-
- #[init]
- fn init() -> init::LateResources {
- // ..
-
- init::LateResources {
- x: Thing::new(..),
- }
- }
-
- #[task(binds = UART0, resources = [x])]
- fn foo(c: foo::Context) {
- let x: &mut Thing = c.resources.x;
-
- x.frob();
-
- // ..
- }
-
- // ..
-}
-```
-
-Код, генерируемы фреймворком выглядит примерно так:
-
-``` rust
-fn init(c: init::Context) -> init::LateResources {
- // .. пользовательский код ..
-}
-
-fn foo(c: foo::Context) {
- // .. пользовательский код ..
-}
-
-// Public API
-pub mod init {
- pub struct LateResources {
- pub x: Thing,
- }
-
- // ..
-}
-
-pub mod foo {
- pub struct Resources<'a> {
- pub x: &'a mut Thing,
- }
-
- pub struct Context<'a> {
- pub resources: Resources<'a>,
- // ..
- }
-}
-
-/// Детали реализации
-mod app {
- // неинициализированная статическая переменная
- static mut x: MaybeUninit<Thing> = MaybeUninit::uninit();
-
- #[no_mangle]
- unsafe fn main() -> ! {
- cortex_m::interrupt::disable();
-
- // ..
-
- let late = init(..);
-
- // инициализация поздних ресурсов
- x.as_mut_ptr().write(late.x);
-
- cortex_m::interrupt::enable(); //~ compiler fence
-
- // исключения, прерывания и задачи могут вытеснить `main` в этой точке
-
- idle(..)
- }
-
- #[no_mangle]
- unsafe fn UART0() {
- foo(foo::Context {
- resources: foo::Resources {
- // `x` уже инициализирована к этому моменту
- x: &mut *x.as_mut_ptr(),
- },
- // ..
- })
- }
-}
-```
-
-Важная деталь здесь то, что `interrupt::enable` ведет себя как *барьер компиляции*, который не дает компилятору переставить запись в `X` *после*
-`interrupt::enable`. Если бы компилятор мог делать такие перестановки появились
-бы гонки данных между этой записью и любой операцией `foo`, взаимодействующей с `X`.
-
-Архитектурам с более сложным конвейером инструкций нужен барьер памяти
-(`atomic::fence`) вместо compiler fence для полной очистки операции записи
-перед включением прерываний. Архитектура ARM Cortex-M не нуждается в барьере памяти
-в одноядерном контексте.