core::arch::wasm32::memory_size
function will give you the memory size in 64KiB pages.
Heap size is a bit more involved, I don’t think there is an API that gives you that directly.
You can get the size of currently allocated objects by defining a custom global allocator that keeps track of allocations, std::alloc::System
docs provide an example.
If you serialize/deserialize the whole state on upgrade, this can actually make things worse: Motoko canister memory size increased after upgrade - #6 by roman-kashitsyn
In Rust, Candid encoding for serde_bytes::ByteBuf
is much more efficient compared to Vec<u8>
.
In case of Vec<u8>
, the encoder treats the data as a generic array, encoding each byte as a separate value, one at a time. Same inefficiency affects on the decoding side.
In case of ByteBuf
, the encoder records the blob size and then memcopies the contents into the output buffer. This is much more efficient (I observed 3x-10x reduction in cycle consumption for large byte arrays). Note that this is not just Candid issue, the same is true for any serde
backend.
I assume that Motoko implementation has similar peculiarities when it comes to Blob
vs [Nat8]
, but I’m not 100% sure.