canic_core/ops/runtime/
mod.rs1pub mod cycles;
2pub mod log;
3pub mod metrics;
4
5use crate::{
6 VERSION,
7 cdk::{
8 api::{canister_self, trap},
9 println,
10 },
11 ids::{CanisterRole, SubnetRole},
12 log::Topic,
13 ops::{
14 service::TimerService,
15 storage::{
16 CanisterInitPayload,
17 directory::{AppDirectoryOps, SubnetDirectoryOps},
18 env::EnvOps,
19 memory::MemoryRegistryOps,
20 topology::{SubnetCanisterRegistryOps, SubnetIdentity},
21 },
22 },
23};
24use canic_memory::runtime::init_eager_tls;
25
26fn init_memory_or_trap(phase: &str) {
27 if let Err(err) = MemoryRegistryOps::init_memory() {
28 println!("[canic] FATAL: memory init failed during {phase}: {err}");
29 let msg = format!("canic init failed during {phase}: memory init failed: {err}");
30 trap(&msg);
31 }
32}
33
34pub fn root_init(identity: SubnetIdentity) {
37 println!("");
41 println!("");
42 println!("");
43 crate::log!(
44 Topic::Init,
45 Info,
46 "🔧 --------------------- 'canic v{VERSION} -----------------------",
47 );
48 crate::log!(Topic::Init, Info, "🏁 init: root ({identity:?})");
49
50 init_eager_tls();
52 init_memory_or_trap("root_init");
53
54 let self_pid = canister_self();
56 EnvOps::set_canister_role(CanisterRole::ROOT);
57 EnvOps::set_root_pid(self_pid);
58
59 match identity {
60 SubnetIdentity::Prime => {
61 EnvOps::set_prime_root_pid(self_pid);
62 EnvOps::set_subnet_role(SubnetRole::PRIME);
63 EnvOps::set_subnet_pid(self_pid);
64 }
65 SubnetIdentity::Standard(params) => {
66 EnvOps::set_prime_root_pid(params.prime_root_pid);
67 EnvOps::set_subnet_role(params.subnet_type);
68 EnvOps::set_subnet_pid(self_pid);
69 }
70 SubnetIdentity::Manual(subnet_pid) => {
71 EnvOps::set_prime_root_pid(self_pid);
72 EnvOps::set_subnet_role(SubnetRole::PRIME);
73 EnvOps::set_subnet_pid(subnet_pid);
74 }
75 }
76
77 SubnetCanisterRegistryOps::register_root(self_pid);
78
79 if let Err(err) = TimerService::start_all_root() {
81 crate::log!(Topic::Init, Warn, "timer startup failed (root): {err}");
82 }
83}
84
85pub fn root_post_upgrade() {
87 crate::log!(Topic::Init, Info, "🏁 post_upgrade: root");
89 init_eager_tls();
90 init_memory_or_trap("root_post_upgrade");
91
92 if let Err(err) = TimerService::start_all_root() {
96 crate::log!(Topic::Init, Warn, "timer startup failed (root): {err}");
97 }
98}
99
100pub fn nonroot_init(canister_type: CanisterRole, payload: CanisterInitPayload) {
102 crate::log!(Topic::Init, Info, "🏁 init: {}", canister_type);
104 init_eager_tls();
105 init_memory_or_trap("nonroot_init");
106
107 EnvOps::import(payload.env);
109 AppDirectoryOps::import(payload.app_directory);
110 SubnetDirectoryOps::import(payload.subnet_directory);
111
112 if let Err(err) = TimerService::start_all() {
114 crate::log!(Topic::Init, Warn, "timer startup failed (nonroot): {err}");
115 }
116}
117
118pub fn nonroot_post_upgrade(canister_type: CanisterRole) {
120 crate::log!(Topic::Init, Info, "🏁 post_upgrade: {}", canister_type);
122 init_eager_tls();
123 init_memory_or_trap("nonroot_post_upgrade");
124
125 if let Err(err) = TimerService::start_all() {
129 crate::log!(Topic::Init, Warn, "timer startup failed (nonroot): {err}");
130 }
131}