diff --git a/docs/developer-docs/gas-cost.md b/docs/developer-docs/gas-cost.md index d31fabba0a..fd1089385c 100644 --- a/docs/developer-docs/gas-cost.md +++ b/docs/developer-docs/gas-cost.md @@ -78,3 +78,23 @@ The following table shows the calculated storage cost per GB for a 30-day month: | | | 13-node Application Subnets | 34-node Application Subnets | |----------------------|------------------------------------|-----------------------------|-----------------------------| | GB Storage Per Month | For storing a GB of data per month | $0.431 | $1.127 | + +## Resource reservation mechanism + +In order to encourage long-term usage and discourage spiky usage patterns of resources, the Internet Computer uses a *resource reservation mechanism* that was adopted by the community in [NNS proposal 12604](https://dashboard.internetcomputer.org/proposal/126094). +Every time a canister allocates new storage bytes, the system sets aside some amount of cycles from the main balance of the canister. These reserved cycles are used to cover future payments for the newly allocated bytes. The reserved cycles are not transferable and the amount of reserved cycles depends on how full the subnet is. For example, it may cover days, months, or even years of payments for the newly allocated bytes. + +The operations that allocate new bytes are: + +- Wasm instruction: `memory.grow`. +- System API calls: `ic0.stable_grow()` `ic0.stable64_grow()`. +- Increasing the `memory_allocation` in canister settings. + +These operations reserve some amount of cycles by moving them from the main balance of the canister to the reserved cycles balance. +The amount of reserved cycles depends on how many bytes are allocated and on the current subnet usage: + +- If subnet usage is below `450GiB`, then the amount of reserved cycles per allocated byte is `0`. +- If subnet usage is above `450GiB`, then the amount of reserved cycles per allocated byte grows linearly depending on the subnet usage from `0` to `10` years worth of storage payments at the subnet capacity (which is currently `750GiB`). + +A controller of a canister can disable resource reservation by setting the `reserved_cycles_limit=0` in canister settings. +Such opted-out canisters would not be able to allocate if the subnet usage is above `450GiB` though. \ No newline at end of file diff --git a/docs/tutorials/developer-journey/level-1/1.6-managing-canisters.md b/docs/tutorials/developer-journey/level-1/1.6-managing-canisters.md index a0ce2b9d09..a6e9d915be 100644 --- a/docs/tutorials/developer-journey/level-1/1.6-managing-canisters.md +++ b/docs/tutorials/developer-journey/level-1/1.6-managing-canisters.md @@ -157,6 +157,8 @@ Compute allocation: 0 Freezing threshold: 2_592_000 Memory Size: Nat(2363181) Balance: 3_100_000_000_000 Cycles +Reserved: 0 Cycles +Reserved Cycles Limit: 5_000_000_000_000 Cycles Module hash: 0xf8680eb74022a1079012b7e9c644d1156580002a6126305791811533d3fd6f17 ``` @@ -196,6 +198,8 @@ Compute allocation: 0 Freezing threshold: 2_592_000 Memory Size: Nat(2363181) Balance: 3_100_000_000_000 Cycles +Reserved: 0 Cycles +Reserved Cycles Limit: 5_000_000_000_000 Cycles Module hash: 0xf8680eb74022a1079012b7e9c644d1156580002a6126305791811533d3fd6f17 ``` @@ -220,7 +224,7 @@ To check a canister's cycles balance, you must be the controller of the canister dfx canister status 5o6tz-saaaa-aaaaa-qaacq-cai --network ic ``` -The output will resemble the following, where the value `Balance` refers to the cycles balance: +The output will resemble the following, where the value `Balance` refers to the main cycles balance and `Reserved` refers to the reserved cycles balance: ``` Canister status call result for 5o6tz-saaaa-aaaaa-qaacq-cai. @@ -231,6 +235,8 @@ Compute allocation: 0 Freezing threshold: 2_592_000 Memory Size: Nat(2363181) Balance: 3_100_000_000_000 Cycles +Reserved: 0 Cycles +Reserved Cycles Limit: 5_000_000_000_000 Cycles Module hash: 0xf8680eb74022a1079012b7e9c644d1156580002a6126305791811533d3fd6f17 ``` @@ -249,6 +255,40 @@ There are a few ways to top up a canister: This tutorial will cover the first two workflows. For more information on using a third-party service for cycles management, please see [here](../../../developer-docs/setup/cycles/cycles_management_services). + +## Setting the reserved cycles limit + +When a canister allocates storage bytes, the system may reserve some amount of cycles by moving them from the main cycles balance of the canister to the reserved cycles balance. +These reserved cycles are used for future storage payments as explained [here](../../../developer-docs/gas-cost#resource-reservation-mechanism). + +You can control the maximum amount of reserved cycles by setting the reserved cycles limit: + +```sh +dfx canister update-settings 5o6tz-saaaa-aaaaa-qaacq-cai --reserved-cycles-limit 42 --network ic +dfx canister status 5o6tz-saaaa-aaaaa-qaacq-cai --network ic +``` + +The first command sets the reserved cycles limit to `42` and the second command queries the canister status and shows the following output: + +``` +Canister status call result for 5o6tz-saaaa-aaaaa-qaacq-cai. +... +Reserved: 0 Cycles +Reserved Cycles Limit: 42 Cycles +... + +``` + +Once the reserved cycles balances reaches the reserved cycles limit, the system is going to fail all operations that require cycle reservation. +The error message might look like this: + +``` +Canister cannot grow memory by 65536 bytes due to its reserved cycles limit. The current limit (42) would be exceeded by 1000. +``` + +Such errors can be fixed by increasing the reserved cycles limit. + + ### Using ICP If you currently have a balance of ICP tokens within your dfx ledger account ID, you can use the `dfx ledger top-up` command to automatically convert that ICP into cycles and deposit it into the specified canister, for example: