Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add system API endpoints for cycle cost calculation #4110

Open
wants to merge 19 commits into
base: master
Choose a base branch
from
Open
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
54 changes: 52 additions & 2 deletions docs/references/ic-interface-spec.md
Original file line number Diff line number Diff line change
Expand Up @@ -1487,8 +1487,16 @@ defaulting to `I = i32` if the canister declares no memory.
ic0.time : () -> (timestamp : i64); // *
ic0.global_timer_set : (timestamp : i64) -> i64; // I G U Ry Rt C T
ic0.performance_counter : (counter_type : i32) -> (counter : i64); // * s
ic0.is_controller: (src : I, size : I) -> ( result: i32); // * s
ic0.in_replicated_execution: () -> (result: i32); // * s
ic0.is_controller : (src : I, size : I) -> ( result : i32); // * s
ic0.in_replicated_execution : () -> (result : i32); // * s

ic0.cost_call : (method_name_size: i64, payload_size : i64, dst : I) -> (); // * s
ic0.cost_create_canister : (dst : I) -> (); // * s
ic0.cost_http_request(request_size : i64, max_res_bytes : i64, dst : I) -> (); // * s
ic0.cost_ecdsa(src : I, size : I, dst : I) -> (); // * s
ic0.cost_schnorr(src : I, size : I, dst : I) -> (); // * s
ic0.cost_vetkey(src : I, size : I, dst : I) -> (); // * s
ic0.replication_factor : (src : I, size : I) -> i32; // * s

ic0.debug_print : (src : I, size : I) -> (); // * s
ic0.trap : (src : I, size : I) -> (); // * s
Expand Down Expand Up @@ -2027,6 +2035,48 @@ When executing a query or composite query method via a query call (i.e. in non-r

This traps if `ic0.data_certificate_present()` returns `0`.

### Cycle cost calculation {#system-api-cycle-cost}

Inter-canister calls have an implicit cost, and some calls to the management canister require the caller to attach cycles to the call explicitly.
The various cost factors may change over time, so the following system calls serve to give the canister programmatic, up-to-date information about the costs.
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

These system calls return costs in Cycles, represented by 128 bits, which will be written to the caller-specified `dst` pointer.
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

- `ic0.cost_call : (method_name_size: i64, payload_size : i64, dst : I) -> () `I ∈ {i32, i64}`
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

The cost of an inter-canister call. `method_name_size` is the byte length of the method name, and `payload_size` is the length of the encoded argument to the method.
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

- `ic0.cost_create_canister : (dst : I) -> (); `I ∈ {i32, i64}`

The cost of creating a canister on the same subnet as the calling canister via [`create_canister`](#ic-create_canister). Note that canister creation via a call to the CMC can have a different cost if the target subnet has a different replication factor. In order to facilitate conversions, see `ic0.replication_factor`.
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

- `ic0.cost_http_request(request_size : i64, max_res_bytes : i64, dst : I) -> (); `I ∈ {i32, i64}`

The cost of a request via [`http_request`](#ic-http_request). `request_size` is the sum of the byte lengths of the following components of an http request:
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved
- url
- method
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved
- headers - i.e., the sum of the lengths of all keys and values
- body
- transform - i.e., the sum of the transform method name length and the length of the transform context

`max_res_bytes` is the maximum response length the caller wishes to accept.
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

- `ic0.cost_ecdsa(src : I, size : I, dst : I) -> (); `I ∈ {i32, i64}`

- `ic0.cost_schnorr(src : I, size : I, dst : I) -> (); `I ∈ {i32, i64}`

- `ic0.cost_vetkey(src : I, size : I, dst : I) -> (); `I ∈ {i32, i64}`

These system calls accept a key name via `src` + `size` for the specific signing scheme / key. See [`sign_with_ecdsa`](#ic-sign_with_ecdsa), [`sign_with_schnorr`](#ic-sign_with_schnorr) and [`vetkd_encrypted_key`](#ic-vetkd_encrypted_key) for more information.
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

These system calls trap if `src` + `size` do not decode to a valid key name.
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

- `ic0.replication_factor : (src : I, size : I) -> i32; `I ∈ {i32, i64}`

Returns the replication factor (subnet size) of the subnet identified by the `Principal` at `src` + `size`.

This system call traps if `src` + `size` do not decode to a valid `Principal` or the given `Principal` is not a subnet.
michael-weigelt marked this conversation as resolved.
Show resolved Hide resolved

### Debugging aids

In a local canister execution environment, the canister needs a way to emit textual trace messages. On the "real" network, these do not do anything.
Expand Down
Loading